Skip to content

Commit 3800505

Browse files
committed
Merge branch 'develop' into feature/filter-update
# Conflicts: # package-lock.json # src/shared/components/challenge-listing/Filters/ChallengeFilters.jsx # src/shared/containers/challenge-listing/Listing/index.jsx
2 parents f612696 + fcf4c59 commit 3800505

File tree

40 files changed

+342
-89
lines changed

40 files changed

+342
-89
lines changed

.circleci/config.yml

+5-3
Original file line numberDiff line numberDiff line change
@@ -230,21 +230,21 @@ workflows:
230230
filters:
231231
branches:
232232
only:
233-
- develop
233+
- free
234234
# This is alternate dev env for parallel testing
235235
- "build-test":
236236
context : org-global
237237
filters:
238238
branches:
239239
only:
240-
- free
240+
- gig-apply-fixes
241241
# This is alternate dev env for parallel testing
242242
- "build-qa":
243243
context : org-global
244244
filters:
245245
branches:
246246
only:
247-
- free
247+
- seo-fix
248248
# This is beta env for production soft releases
249249
- "build-prod-beta":
250250
context : org-global
@@ -260,6 +260,7 @@ workflows:
260260
branches:
261261
only:
262262
- develop
263+
- listing-search
263264
# Production builds are exectuted
264265
# when PR is merged to the master
265266
# Don't change anything in this configuration
@@ -279,3 +280,4 @@ workflows:
279280
branches:
280281
ignore:
281282
- develop
283+

config/default.js

+1
Original file line numberDiff line numberDiff line change
@@ -112,6 +112,7 @@ module.exports = {
112112
COMMUNITY: 'https://community.topcoder-dev.com',
113113
FORUMS: 'https://apps.topcoder-dev.com/forums',
114114
HELP: 'https://www.topcoder.com/thrive/tracks?track=Topcoder&tax=Help%20Articles',
115+
SUBMISSION_REVIEW: 'https://submission-review.topcoder-dev.com',
115116

116117
THRIVE: 'https://www.topcoder.com/thrive',
117118

config/production.js

+1
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ module.exports = {
3232
COMMUNITY: 'https://community.topcoder.com',
3333
FORUMS: 'https://apps.topcoder.com/forums',
3434
HELP: 'https://www.topcoder.com/thrive/tracks?track=Topcoder&tax=Help%20Articles',
35+
SUBMISSION_REVIEW: 'https://submission-review.topcoder.com',
3536
MEMBER: 'https://member.topcoder.com',
3637
ONLINE_REVIEW: 'https://software.topcoder.com',
3738
PAYMENT_TOOL: 'https://payment.topcoder.com',

package.json

+2-2
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@
3737
},
3838
"dependencies": {
3939
"@hapi/joi": "^16.1.4",
40-
"@topcoder-platform/tc-auth-lib": "topcoder-platform/tc-auth-lib#1.0.1",
40+
"@topcoder-platform/tc-auth-lib": "topcoder-platform/tc-auth-lib#1.0.3",
4141
"aos": "^2.3.4",
4242
"atob": "^2.1.1",
4343
"babel-register": "^6.26.0",
@@ -143,7 +143,7 @@
143143
"supertest": "^3.1.0",
144144
"tc-core-library-js": "github:appirio-tech/tc-core-library-js#v2.6.3",
145145
"tc-ui": "^1.0.12",
146-
"topcoder-react-lib": "1.1.2",
146+
"topcoder-react-lib": "1.1.3",
147147
"topcoder-react-ui-kit": "2.0.1",
148148
"topcoder-react-utils": "0.7.8",
149149
"turndown": "^4.0.2",

src/shared/components/Contentful/Route.jsx

+1-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ import _ from 'lodash';
77
import ContentfulLoader from 'containers/ContentfulLoader';
88
import Error404 from 'components/Error404';
99
import LoadingIndicator from 'components/LoadingIndicator';
10-
import { MetaTags } from 'topcoder-react-utils';
10+
import MetaTags from 'components/MetaTags';
1111
import PT from 'prop-types';
1212
import React from 'react';
1313
import { Route, Switch } from 'react-router-dom';

src/shared/components/Contentful/Viewport/index.jsx

+1-1
Original file line numberDiff line numberDiff line change
@@ -113,7 +113,7 @@ function ViewportContentLoader(props) {
113113
let animation = {};
114114
if (animationOnScroll) {
115115
contentIds.pop();
116-
animation = { ...data.entries.items[animationOnScroll.sys.id].fields };
116+
animation = { ...animationOnScroll.fields };
117117
// Animations only on client side
118118
if (isomorphy.isClientSide()) {
119119
AOS.init();

src/shared/components/GUIKit/DropdownTerms/index.jsx

+8-14
Original file line numberDiff line numberDiff line change
@@ -33,22 +33,12 @@ function DropdownTerms({
3333
let inputField;
3434
useEffect(() => {
3535
const selectInput = containerRef.current.getElementsByClassName('Select-input');
36-
const selectMenuOuter = containerRef.current.getElementsByClassName('Select-menu-outer');
3736
if (selectInput && selectInput.length) {
38-
const selectControl = containerRef.current.getElementsByClassName(
39-
'Select-control',
40-
);
41-
const height1 = selectMenuOuter && selectMenuOuter.length
42-
? selectMenuOuter[0].offsetHeight
43-
: 0;
44-
const height2 = selectControl && selectControl.length
45-
? selectControl[0].offsetHeight
46-
: 0;
47-
selectInput[0].style.top = focused ? `${height1 + height2 - 1}px` : '0';
4837
inputField = selectInput[0].getElementsByTagName('input');
4938
inputField[0].placeholder = focused ? addNewOptionPlaceholder : '';
5039
inputField[0].style.border = 'none';
5140
inputField[0].style.boxShadow = 'none';
41+
selectInput[0].style.borderTop = 'none';
5242
}
5343
}, [focused, selectedOption]);
5444

@@ -145,9 +135,13 @@ function DropdownTerms({
145135
backspaceRemoves={false}
146136
multi
147137
promptTextCreator={() => null}
148-
filterOptions={() => _.filter(
149-
internalTerms, t => !_.find(selectedOption, { label: t.label }),
150-
).map(o => ({ value: o.label, label: o.label }))}
138+
filterOptions={(option, inputValue) => _.filter(
139+
internalTerms,
140+
t => (inputValue && inputValue.length >= 2
141+
? t.label.toLowerCase().includes(inputValue.toLowerCase())
142+
&& !_.find(selectedOption, { label: t.label })
143+
: !_.find(selectedOption, { label: t.label })),
144+
)}
151145
/>
152146
<img width="15" height="9" styleName="iconDropdown" src={iconDown} alt="dropdown-arrow-icon" />
153147
</div>

src/shared/components/HallOfFamePage/HoF.jsx

+16
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import React from 'react';
77
import PT from 'prop-types';
88
import ContentfulLoader from 'containers/ContentfulLoader';
99
import { PrimaryButton, Button } from 'topcoder-react-ui-kit';
10+
import ContentBlock from 'components/Contentful/ContentBlock';
1011

1112
import Error404 from 'components/Error404';
1213

@@ -239,6 +240,21 @@ const HallOfFamePage = ({ eventId, hallOfFame }) => {
239240
</div>
240241
)
241242
}
243+
{
244+
data.fields.spiritAwardWinners && (
245+
<div styleName="spirit-awards">
246+
<h3>Spirit Award</h3>
247+
<div styleName="spirit-awards-wrap">
248+
{
249+
_.map(
250+
data.fields.spiritAwardWinners,
251+
sA => <ContentBlock id={sA.sys.id} />,
252+
)
253+
}
254+
</div>
255+
</div>
256+
)
257+
}
242258
{
243259
tripWinnersBoard.data.length > 0 && (
244260
<div styleName="trip-winners">

src/shared/components/HallOfFamePage/styles.scss

+20
Original file line numberDiff line numberDiff line change
@@ -372,3 +372,23 @@
372372
background-color: #5cc900;
373373
}
374374
}
375+
376+
.spirit-awards {
377+
margin-top: 50px;
378+
display: flex;
379+
flex-direction: column;
380+
align-items: center;
381+
382+
h3 {
383+
margin-bottom: 20px;
384+
}
385+
386+
.spirit-awards-wrap {
387+
display: flex;
388+
justify-content: center;
389+
390+
a {
391+
font-size: 16px;
392+
}
393+
}
394+
}

src/shared/components/MMatchLeaderboard/index.jsx

+2-1
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,8 @@ export default class MMLeaderboard extends Component {
7070
// Use Lodash to sort array
7171
data = _.orderBy(
7272
data,
73-
[d => String(d[sortParam.field]).toLowerCase()], [sortParam.order],
73+
[d => Number(d[sortParam.field]) || String(d[sortParam.field]).toLowerCase()],
74+
[sortParam.order],
7475
);
7576
}
7677

src/shared/components/MetaTags.jsx

+82
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
/**
2+
* Auxiliary wrapper around React Helmet that helps to generate meta tags for
3+
* generic use cases.
4+
*
5+
* NOTE: This component relies on `domain` path of Redux store to hold
6+
* the current app domain, which will serve as the base path for the bundled
7+
* images.
8+
*/
9+
10+
import PT from 'prop-types';
11+
import React from 'react';
12+
import { connect } from 'react-redux';
13+
import { Helmet } from 'react-helmet';
14+
15+
function MetaTags({
16+
description,
17+
domain,
18+
image,
19+
siteName,
20+
socialDescription,
21+
socialTitle,
22+
title,
23+
url,
24+
}) {
25+
const img = `${domain}${image}`;
26+
const socTitle = socialTitle || title;
27+
const socDesc = socialDescription || description;
28+
return (
29+
<Helmet>
30+
{/* General tags. */}
31+
<title>
32+
{title}
33+
</title>
34+
<meta name="description" content={description} />
35+
36+
{/* Twitter cards. */}
37+
<meta name="twitter:card" content="summary_large_image" />
38+
<meta name="twitter:title" content={socTitle} />
39+
<meta name="twitter:description" content={socDesc} />
40+
{ image ? <meta name="twitter:image" content={img} /> : null }
41+
{
42+
siteName ? (
43+
<meta name="twitter:site" content={`@${siteName}`} />
44+
) : null
45+
}
46+
47+
{/* Open Graph data. */}
48+
<meta property="og:title" content={socTitle} />
49+
{ image ? <meta property="og:image" content={img} /> : null }
50+
{ image ? <meta property="og:image:alt" content={socTitle} /> : null }
51+
<meta property="og:description" content={socDesc} />
52+
{
53+
siteName ? (<meta property="og:sitename" content={siteName} />) : null
54+
}
55+
{ url ? (<meta property="og:url" content={url} />) : null }
56+
</Helmet>
57+
);
58+
}
59+
60+
MetaTags.defaultProps = {
61+
image: null,
62+
siteName: null,
63+
socialDescription: null,
64+
socialTitle: null,
65+
url: null,
66+
};
67+
68+
MetaTags.propTypes = {
69+
description: PT.string.isRequired,
70+
domain: PT.string.isRequired,
71+
image: PT.string,
72+
siteName: PT.string,
73+
socialDescription: PT.string,
74+
socialTitle: PT.string,
75+
title: PT.string.isRequired,
76+
url: PT.string,
77+
};
78+
79+
/* TODO: It is not good to depend on the domain written into redux state here,
80+
* better pass it via the renderer context at the server side, and get it from
81+
* the location at the frontend side, or something similar? */
82+
export default connect(state => ({ domain: state.domain }))(MetaTags);

src/shared/components/Settings/index.jsx

+1-1
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
*/
44
import React from 'react';
55
import PT from 'prop-types';
6-
import { MetaTags } from 'topcoder-react-utils';
6+
import MetaTags from 'components/MetaTags';
77

88
import { TABS } from 'actions/page/settings';
99

src/shared/components/challenge-detail/Header/TabSelector/index.jsx

+13
Original file line numberDiff line numberDiff line change
@@ -160,6 +160,18 @@ export default function ChallengeViewSelector(props) {
160160
</a>
161161
) : null
162162
}
163+
{
164+
(hasRegistered && mySubmissions.length > 0) && (
165+
<a
166+
href={`${config.URL.SUBMISSION_REVIEW}/challenges/${challenge.legacyId}`}
167+
styleName="challenge-selector-common challenge-unselected-view"
168+
target="_blank"
169+
rel="oopener noreferrer"
170+
>
171+
SUBMISSION REVIEW
172+
</a>
173+
)
174+
}
163175
{
164176
numWinners ? (
165177
<a
@@ -225,6 +237,7 @@ ChallengeViewSelector.defaultProps = {
225237
ChallengeViewSelector.propTypes = {
226238
isLoggedIn: PT.bool,
227239
challenge: PT.shape({
240+
legacyId: PT.string,
228241
legacy: PT.shape({
229242
forumId: PT.number,
230243
}),

src/shared/components/challenge-detail/Header/index.jsx

+2-1
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,8 @@ export default function ChallengeHeader(props) {
8181
const sortedAllPhases = _.cloneDeep(allPhases)
8282
.sort((a, b) => moment(phaseEndDate(a)).diff(phaseEndDate(b)));
8383

84-
const { prizes } = prizeSets && prizeSets.length ? prizeSets[0] : [];
84+
const placementPrizes = _.find(prizeSets, { type: 'placement' });
85+
const { prizes } = placementPrizes || [];
8586

8687
const checkpointPrizes = _.find(prizeSets, { type: 'checkpoint' });
8788
let numberOfCheckpointsPrizes = 0;

src/shared/components/challenge-listing/Filters/FiltersPanel/index.jsx

+1-1
Original file line numberDiff line numberDiff line change
@@ -553,7 +553,7 @@ export default function FiltersPanel({
553553
DS: true,
554554
QA: true,
555555
},
556-
name: '',
556+
search: '',
557557
tags: [],
558558
types: ['CH', 'F2F', 'TSK'],
559559
groups: [],

src/shared/containers/Dashboard/index.jsx

+4-2
Original file line numberDiff line numberDiff line change
@@ -70,8 +70,10 @@ export class DashboardPageContainer extends React.Component {
7070

7171
if (challengeFilter) switchChallengeFilter('');
7272

73-
const user = decodeToken(tokenV3);
74-
getMemberResources(user.userId, tokenV3);
73+
if (this.authCheck(tokenV3)) {
74+
const user = decodeToken(tokenV3);
75+
getMemberResources(user.userId, tokenV3);
76+
}
7577
}
7678

7779
componentWillReceiveProps(nextProps) {

src/shared/containers/EDU/Home.jsx

+8-8
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
*/
44
import React from 'react';
55
import { config } from 'topcoder-react-utils';
6-
import { Helmet } from 'react-helmet';
6+
import MetaTags from 'components/MetaTags';
77
import Viewport from 'components/Contentful/Viewport';
88
import SearchBar from 'components/Contentful/SearchBar/SearchBar';
99
import { getService } from 'services/contentful';
@@ -44,15 +44,15 @@ export default class EDUHome extends React.Component {
4444

4545
render() {
4646
const { taxonomy } = this.state;
47+
const title = 'Topcoder Thrive | Topcoder Community | Topcoder';
48+
const description = 'Thrive is our vault of content that we have been gathering over the years. It is full of tutorials and workshops that matter. Grow with us!';
49+
4750
return (
4851
<div className={homeTheme.container}>
49-
<Helmet>
50-
<title>THRIVE - Grow with us. Tutorials and workshops that matter.</title>
51-
<meta name="title" property="og:title" content="THRIVE - Grow with us. Tutorials and workshops that matter." />
52-
<meta name="description" property="og:description" content="THRIVE - Grow with us. Tutorials and workshops that matter." />
53-
<meta name="description" property="description" content="THRIVE - Grow with us. Tutorials and workshops that matter." />
54-
<meta name="twitter:description" content="THRIVE - Grow with us. Tutorials and workshops that matter." />
55-
</Helmet>
52+
<MetaTags
53+
description={description}
54+
title={title}
55+
/>
5656
{/* Banner */}
5757
<div className={homeTheme.bannerContainer}>
5858
<div className={homeTheme.bannerImage} />

0 commit comments

Comments
 (0)