Skip to content

Commit b6deb10

Browse files
Merge pull request #6833 from topcoder-platform/TCA-768_member-profile-tca-certs
TCA-768 member profile with TCA certs
2 parents a7c3e22 + 6ca9882 commit b6deb10

File tree

16 files changed

+297
-36
lines changed

16 files changed

+297
-36
lines changed

.circleci/config.yml

+2-2
Original file line numberDiff line numberDiff line change
@@ -349,14 +349,14 @@ workflows:
349349
filters:
350350
branches:
351351
only:
352-
- sprig-lib
352+
- free
353353
# This is alternate dev env for parallel testing
354354
- "build-test":
355355
context : org-global
356356
filters:
357357
branches:
358358
only:
359-
- PROD-3199
359+
- TCA-768_member-profile-tca-certs
360360
# This is alternate dev env for parallel testing
361361
- "build-qa":
362362
context : org-global

__tests__/shared/components/ProfilePage/__snapshots__/index.jsx.snap

+2
Original file line numberDiff line numberDiff line change
@@ -715,6 +715,7 @@ exports[`renders a full Profile correctly 1`] = `
715715
}
716716
}
717717
tcAcademyCertifications={Array []}
718+
tcAcademyCourses={Array []}
718719
/>
719720
`;
720721

@@ -866,5 +867,6 @@ exports[`renders an empty Profile correctly 1`] = `
866867
}
867868
}
868869
tcAcademyCertifications={Array []}
870+
tcAcademyCourses={Array []}
869871
/>
870872
`;
Loading

src/shared/components/ProfilePage/ProfileModal/index.jsx

+1-1
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ const ProfileModal = ({
2525
<h2 styleName="title">
2626
{title}
2727
</h2>
28-
<div styleName="icon" role="presentation" onClick={onCancel}>
28+
<div className="close-icon" styleName="icon" role="presentation" onClick={onCancel}>
2929
<IconClose />
3030
</div>
3131
</div>

src/shared/components/ProfilePage/ProfileModal/styles.scss

+2
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,8 @@
3030
justify-content: space-between;
3131
align-items: center;
3232
padding-bottom: 24px;
33+
z-index: 1;
34+
position: relative;
3335

3436
.title {
3537
@include barlow-medium;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
import React from 'react';
2+
import PT from 'prop-types';
3+
4+
import 'assets/images/profile/tca-certificates/tca-certifications-badges-sprite.png';
5+
import './styles.scss';
6+
7+
const CertificationBadge = ({ type: badgeType, level, size }) => (
8+
<div
9+
className={`badge-${badgeType}--${level}`.toLowerCase()}
10+
styleName={`tca-badge-wrap size-${size}`}
11+
/>
12+
);
13+
14+
CertificationBadge.defaultProps = {
15+
size: 'md',
16+
};
17+
18+
CertificationBadge.propTypes = {
19+
size: PT.oneOf(['md']),
20+
level: PT.oneOf(['Beginner', 'Intermediate', 'Expert', 'All Levels']).isRequired,
21+
type: PT.oneOf(['DATASCIENCE', 'DESIGN', 'DEV', 'DATABASE', 'INTERVIEW', 'QA', 'SECURITY']).isRequired,
22+
};
23+
24+
25+
export default CertificationBadge;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,95 @@
1+
.tca-badge-wrap {
2+
background-repeat: no-repeat;
3+
background-position: 0 0;
4+
background-size: 300px 283.6363px;
5+
background-image: url('../../../../../assets/images/profile/tca-certificates/tca-certifications-badges-sprite.png');
6+
7+
&.size-md {
8+
width: 48px;
9+
height: 48px;
10+
}
11+
12+
&:global(.badge-interview--beginner) {
13+
background-position: -6px -6px;
14+
}
15+
16+
&:global(.badge-interview--intermediate) {
17+
background-position: -66px -6px;
18+
}
19+
20+
&:global(.badge-interview--expert) {
21+
background-position: -6px -63px;
22+
}
23+
24+
&:global(.badge-datascience--beginner) {
25+
background-position: -126px -6px;
26+
}
27+
28+
&:global(.badge-datascience--intermediate) {
29+
background-position: -66px -63px;
30+
}
31+
32+
&:global(.badge-datascience--expert) {
33+
background-position: -6px -119px;
34+
}
35+
36+
&:global(.badge-database--beginner) {
37+
background-position: -126px -63px;
38+
}
39+
40+
&:global(.badge-database--intermediate) {
41+
background-position: -126px -119px;
42+
}
43+
44+
&:global(.badge-database--expert) {
45+
background-position: -66px -119px;
46+
}
47+
48+
&:global(.badge-design--beginner) {
49+
background-position: -186px -6px;
50+
}
51+
52+
&:global(.badge-design--intermediate) {
53+
background-position: -186px -63px;
54+
}
55+
56+
&:global(.badge-design--expert) {
57+
background-position: -186px -119px;
58+
}
59+
60+
&:global(.badge-dev--beginner) {
61+
background-position: -6px -176px;
62+
}
63+
64+
&:global(.badge-dev--intermediate) {
65+
background-position: -66px -176px;
66+
}
67+
68+
&:global(.badge-dev--expert) {
69+
background-position: -126px -176px;
70+
}
71+
72+
&:global(.badge-qa--beginner) {
73+
background-position: -186px -176px;
74+
}
75+
76+
&:global(.badge-qa--intermediate) {
77+
background-position: -246px -6px;
78+
}
79+
80+
&:global(.badge-qa--expert) {
81+
background-position: -246px -63px;
82+
}
83+
84+
&:global(.badge-security--beginner) {
85+
background-position: -246px -119px;
86+
}
87+
88+
&:global(.badge-security--intermediate) {
89+
background-position: -246px -176px;
90+
}
91+
92+
&:global(.badge-security--expert) {
93+
background-position: -6px -233px;
94+
}
95+
}

src/shared/components/ProfilePage/TcaCertificates/List/index.jsx

+12-9
Original file line numberDiff line numberDiff line change
@@ -2,36 +2,38 @@ import React from 'react';
22
import PT from 'prop-types';
33

44
import './styles.scss';
5-
import CourseBadge from '../CourseBadge';
65

76
const preventDefault = ev => ev.stopPropagation();
87

98
const List = ({
109
certificates,
1110
onClick,
11+
renderIcon,
1212
}) => (
1313
<div styleName="list">
1414
{certificates.map(certificate => (
1515
<div
1616
styleName="list-item"
1717
key={certificate.id}
1818
onClick={() => onClick(certificate)}
19-
onKeyPress={() => onClick(certificate)}
19+
onKeyDown={() => onClick(certificate)}
2020
role="button"
2121
tabIndex={-1}
2222
>
2323
<div styleName="list-item_badge">
24-
<CourseBadge type={certificate.certificationTrackType || 'DEV'} />
24+
{renderIcon(certificate)}
2525
</div>
2626
<div>
2727
<div styleName="list-item_title">
28-
{certificate.certificationTitle}
29-
</div>
30-
<div styleName="list-item_sub">
31-
<a href={`//${certificate.providerUrl}`} target="blank" rel="noopener" onClick={preventDefault}>
32-
by {certificate.provider}
33-
</a>
28+
{certificate.certificationTitle || certificate.topcoderCertification.title}
3429
</div>
30+
{certificate.resourceProvider && (
31+
<div styleName="list-item_sub">
32+
<a href={`//${certificate.resourceProvider.url}`} target="blank" rel="noopener" onClick={preventDefault}>
33+
by {certificate.resourceProvider.name}
34+
</a>
35+
</div>
36+
)}
3537
</div>
3638
</div>
3739
))}
@@ -41,6 +43,7 @@ const List = ({
4143
List.propTypes = {
4244
certificates: PT.arrayOf(PT.shape()).isRequired,
4345
onClick: PT.func.isRequired,
46+
renderIcon: PT.element.isRequired,
4447
};
4548

4649
export default List;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
import React from 'react';
2+
import PT from 'prop-types';
3+
import { noop } from 'lodash/noop';
4+
import { config } from 'topcoder-react-utils';
5+
6+
import ProfileModal from '../../ProfileModal';
7+
import styles from './styles.scss';
8+
9+
const tcAcademyPath = `${config.PLATFORMUI_SITE_URL}${config.TC_ACADEMY_BASE_PATH}`;
10+
11+
const TcaCertificationCertificateModal = ({
12+
certificate,
13+
onCancel,
14+
}) => (
15+
<ProfileModal
16+
title=""
17+
onCancel={onCancel}
18+
containerClassName={styles['tca-modal']}
19+
>
20+
<iframe
21+
styleName="iframe"
22+
src={`${tcAcademyPath}/${certificate.completionUuid}?view-style=modal`}
23+
title={certificate.certificationTitle}
24+
/>
25+
</ProfileModal>
26+
);
27+
28+
TcaCertificationCertificateModal.defaultProps = {
29+
onCancel: noop,
30+
};
31+
32+
TcaCertificationCertificateModal.propTypes = {
33+
certificate: PT.shape().isRequired,
34+
onCancel: PT.func,
35+
};
36+
37+
export default TcaCertificationCertificateModal;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
@import "~styles/mixins";
2+
3+
.tca-modal {
4+
display: flex;
5+
flex-direction: column;
6+
min-height: auto;
7+
padding: 36px;
8+
width: 980px;
9+
max-width: 96vw;
10+
background: transparent;
11+
12+
:global(.close-icon) {
13+
color: #fff;
14+
15+
svg > path {
16+
fill: currentColor;
17+
}
18+
}
19+
20+
@include xs-to-sm {
21+
display: flex;
22+
flex-direction: column;
23+
max-width: none;
24+
width: 100%;
25+
}
26+
}
27+
28+
.iframe {
29+
display: block;
30+
height: 788px;
31+
max-height: 100%;
32+
width: calc(100% + 37px + 37px);
33+
margin: -102px -37px -36px;
34+
35+
@include xs-to-sm {
36+
height: auto;
37+
flex: 1;
38+
}
39+
}

src/shared/components/ProfilePage/TcaCertificates/TcaCertificateModal/index.jsx renamed to src/shared/components/ProfilePage/TcaCertificates/TcaCourseCertificateModal/index.jsx

+4-4
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import styles from './styles.scss';
88

99
const tcAcademyPath = `${config.PLATFORMUI_SITE_URL}${config.TC_ACADEMY_BASE_PATH}`;
1010

11-
const TcaCertificateModal = ({
11+
const TcaCourseCertificateModal = ({
1212
certificate,
1313
onCancel,
1414
memberHandle,
@@ -32,14 +32,14 @@ const TcaCertificateModal = ({
3232
</ProfileModal>
3333
);
3434

35-
TcaCertificateModal.defaultProps = {
35+
TcaCourseCertificateModal.defaultProps = {
3636
onCancel: noop,
3737
};
3838

39-
TcaCertificateModal.propTypes = {
39+
TcaCourseCertificateModal.propTypes = {
4040
certificate: PT.shape().isRequired,
4141
onCancel: PT.func,
4242
memberHandle: PT.string.isRequired,
4343
};
4444

45-
export default TcaCertificateModal;
45+
export default TcaCourseCertificateModal;

src/shared/components/ProfilePage/TcaCertificates/TcaCertificateModal/styles.scss renamed to src/shared/components/ProfilePage/TcaCertificates/TcaCourseCertificateModal/styles.scss

+1-1
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@
1818

1919
.iframe {
2020
display: block;
21-
height: 600px;
21+
height: 760px;
2222
width: 100%;
2323

2424
@include xs-to-sm {

0 commit comments

Comments
 (0)