Skip to content

Commit

Permalink
Merge pull request #5914 from topcoder-platform/develop
Browse files Browse the repository at this point in the history
Release v1.14.6
  • Loading branch information
luizrrodrigues authored Dec 8, 2021
2 parents 1580cba + 23e89c5 commit 6a0bacb
Show file tree
Hide file tree
Showing 27 changed files with 508 additions and 49 deletions.
6 changes: 3 additions & 3 deletions .circleci/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -357,22 +357,22 @@ workflows:
filters:
branches:
only:
- free
- thrive-rss
# This is beta env for production soft releases
- "build-prod-beta":
context : org-global
filters:
branches:
only:
- free
- mm-leaderboard-theme
# This is stage env for production QA releases
- "build-prod-staging":
context : org-global
filters: &filters-staging
branches:
only:
- develop
- feature/recommended-challenges-update
- ast-timeline-fix
# Production builds are exectuted
# when PR is merged to the master
# Don't change anything in this configuration
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -294,7 +294,6 @@ export class ChallengeDetailPageHelper {
'Started',
'Registration',
'Submission',
'Review',
'Winners',
];
for (let i = 0; i < childDivs.length; i++) {
Expand Down
1 change: 1 addition & 0 deletions config/default.js
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,7 @@ module.exports = {
HOME: '/home',
BLOG: 'https://www.topcoder-dev.com/blog',
BLOG_FEED: 'https://www.topcoder.com/blog/feed/',
THRIVE_FEED: 'https://topcoder-dev.com/api/feeds/thrive',
COMMUNITY: 'https://community.topcoder-dev.com',
FORUMS: 'https://apps.topcoder-dev.com/forums',
FORUMS_VANILLA: 'https://vanilla.topcoder-dev.com',
Expand Down
1 change: 1 addition & 0 deletions config/production.js
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ module.exports = {
CS: 'https://cs.topcoder.com',
},
EMAIL_VERIFY_URL: 'http://www.topcoder.com/settings/account/changeEmail',
THRIVE_FEED: 'https://topcoder.com/api/feeds/thrive',
},
/* Filestack configuration for uploading Submissions
* These are for the production back end */
Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,7 @@
"redux-promise": "^0.6.0",
"request-ip": "^2.0.2",
"require-context": "^1.1.0",
"rss": "^1.2.2",
"rss-parser": "^3.12.0",
"serialize-javascript": "^2.1.1",
"serve-favicon": "^2.5.0",
Expand Down
2 changes: 2 additions & 0 deletions src/server/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ import mmLeaderboardRouter from './routes/mmLeaderboard';
import growsurfRouter from './routes/growsurf';
import gSheetsRouter from './routes/gSheet';
import blogRouter from './routes/blog';
import feedsRouter from './routes/feeds';

/* Dome API for topcoder communities */
import tcCommunitiesDemoApi from './tc-communities';
Expand Down Expand Up @@ -143,6 +144,7 @@ async function onExpressJsSetup(server) {
server.use('/api/growsurf', growsurfRouter);
server.use('/api/gsheets', gSheetsRouter);
server.use('/api/blog', blogRouter);
server.use('/api/feeds', feedsRouter);

// serve demo api
server.use(
Expand Down
62 changes: 62 additions & 0 deletions src/server/routes/feeds.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
/**
* The routes that expose assets and content from Contentful CMS to the CDN.
*/

import express from 'express';
import RSS from 'rss';
import ReactDOMServer from 'react-dom/server';
import md from 'utils/markdown';
import {
getService,
} from '../services/contentful';

const cors = require('cors');

const routes = express.Router();

// Enables CORS on those routes according config above
// ToDo configure CORS for set of our trusted domains
routes.use(cors());
routes.options('*', cors());

routes.get('/thrive', async (req, res, next) => {
try {
const data = await getService('EDU', 'master', true).queryEntries({
content_type: 'article',
limit: 20,
order: '-sys.createdAt',
include: 2,
});
const feed = new RSS({
title: 'Topcoder Thrive',
description: 'Tutorials And Workshops That Matter | Thrive | Topcoder',
feed_url: 'https://topcoder.com/api/feeds/thrive',
site_url: 'https://topcoder.com/thrive',
image_url: 'https://www.topcoder.com/wp-content/uploads/2020/05/cropped-TC-Icon-32x32.png',
docs: 'https://www.topcoder.com/thrive/tracks?track=Topcoder',
webMaster: '<[email protected]> Kiril Kartunov',
copyright: '2021 - today, Topcoder',
language: 'en',
categories: ['Competitive Programming', 'Data Science', 'Design', 'Development', 'QA', 'Gig work', 'Topcoder'],
ttl: '60',
});
if (data && data.total) {
data.items.forEach((entry) => {
feed.item({
title: entry.fields.title,
description: ReactDOMServer.renderToString(md(entry.fields.content)),
url: `https://topcoder.com/thrive/articles/${entry.fields.slug || encodeURIComponent(entry.fields.title)}?utm_source=community&utm_campaign=thrive-feed&utm_medium=promotion`,
date: entry.fields.creationDate,
categories: entry.fields.tags,
author: entry.fields.contentAuthor[0].fields.name,
});
});
}
res.set('Content-Type', 'application/rss+xml');
res.send(feed.xml({ indent: true }));
} catch (e) {
next(e);
}
});

export default routes;
16 changes: 14 additions & 2 deletions src/shared/actions/mmLeaderboard.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import { redux } from 'topcoder-react-utils';
import { redux, config } from 'topcoder-react-utils';
import Service from 'services/mmLeaderboard';
import _ from 'lodash';


/**
* Fetch init
*/
Expand Down Expand Up @@ -34,11 +35,22 @@ async function getMMLeaderboardDone(id) {
score: scores && scores.length ? scores[0].score : '...',
});
});
data = _.orderBy(data, [d => (Number(d.score) ? Number(d.score) : 0)], ['desc']).map((r, i) => ({
data = _.orderBy(data, [d => (Number(d.score) ? Number(d.score) : 0), d => new Date(d.updated) - new Date()], ['desc']).map((r, i) => ({
...r,
rank: i + 1,
score: r.score % 1 ? Number(r.score).toFixed(5) : r.score,
}));
// Fetch member photos and rating for top 10
const results = await Promise.all(
_.take(data, 10).map(d => fetch(`${config.API.V5}/members/${d.createdBy}`)),
);
const memberData = await Promise.all(results.map(r => r.json()));
// merge with data
// eslint-disable-next-line array-callback-return
memberData.map((member, indx) => {
data[indx].photoUrl = member.photoURL;
data[indx].rating = member.maxRating && member.maxRating.rating;
});
}
return {
id,
Expand Down
10 changes: 7 additions & 3 deletions src/shared/components/InputSelect/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,7 @@ export default class InputSelect extends Component {
let i = 0;
let node = e.target;
const REG = new RegExp(_id);
while (node && i < 5) {
while (node && i < 20) {
if (REG.test(node.className)) {
return true;
}
Expand All @@ -131,6 +131,7 @@ export default class InputSelect extends Component {
placeholder,
labelKey,
options,
onKeyPress,
} = this.props;

const {
Expand All @@ -139,9 +140,10 @@ export default class InputSelect extends Component {
filterVal,
} = this.state;

const escapeRegExp = stringToGoIntoTheRegex => stringToGoIntoTheRegex.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&'); /* eslint-disable-line no-useless-escape */
let fiterList = options;
if (filterVal) {
const REG = new RegExp(filterVal, 'i');
const REG = new RegExp(escapeRegExp(filterVal), 'i');
fiterList = filter(options, o => REG.test(o[labelKey]));
}
const list = map(fiterList, o => (
Expand Down Expand Up @@ -171,7 +173,7 @@ export default class InputSelect extends Component {
<div styleName="modal">
<div styleName="modal-input-container">

<input type="text" onChange={this.onFilterChange} placeholder="Search" />
<input type="text" onChange={this.onFilterChange} placeholder="Search" onKeyPress={onKeyPress} />
</div>
<div styleName="modal-list-container" onScroll={this.onLoadMore}>
{list}
Expand All @@ -195,6 +197,7 @@ InputSelect.defaultProps = {
isLoading: false,
onChange: () => {},
onLoadMore: () => {},
onKeyPress: () => {},
};

InputSelect.propTypes = {
Expand All @@ -205,6 +208,7 @@ InputSelect.propTypes = {
placeholder: PT.string,
onChange: PT.func,
onLoadMore: PT.func,
onKeyPress: PT.func,
hasMore: PT.bool,
isLoading: PT.bool,
disabled: PT.bool,
Expand Down
Loading

0 comments on commit 6a0bacb

Please sign in to comment.