fix(api, client): update Gatsby, webpack & related things (#41452)
Co-authored-by: Oliver Eyton-Williams <ojeytonwilliams@gmail.com>
This commit is contained in:
committed by
GitHub
parent
92dfb3065c
commit
ad9b1f89d8
@ -33,6 +33,7 @@
|
||||
"import/no-duplicates": 2,
|
||||
"import/no-unresolved": [2, { "commonjs": true }],
|
||||
"import/unambiguous": 2,
|
||||
"import/no-anonymous-default-export": 2,
|
||||
"jsx-quotes": [2, "prefer-single"],
|
||||
"jsx-a11y/accessible-emoji": "error",
|
||||
"jsx-a11y/alt-text": "error",
|
||||
|
@ -14,7 +14,7 @@ export function ensureLowerCaseEmail(profile) {
|
||||
: '';
|
||||
}
|
||||
|
||||
export default function (UserIdent) {
|
||||
export default function initializeUserIdent(UserIdent) {
|
||||
UserIdent.on('dataSourceAttached', () => {
|
||||
UserIdent.findOne$ = observeMethod(UserIdent, 'findOne');
|
||||
});
|
||||
|
@ -1,6 +1,6 @@
|
||||
import { Observable } from 'rx';
|
||||
|
||||
export default function (Block) {
|
||||
export default function initializeBlock(Block) {
|
||||
Block.on('dataSourceAttached', () => {
|
||||
Block.findOne$ = Observable.fromNodeCallback(Block.findOne, Block);
|
||||
Block.findById$ = Observable.fromNodeCallback(Block.findById, Block);
|
||||
|
@ -152,7 +152,7 @@ function populateRequiredFields(user) {
|
||||
return;
|
||||
}
|
||||
|
||||
export default function (User) {
|
||||
export default function initializeUser(User) {
|
||||
// set salt factor for passwords
|
||||
User.settings.saltWorkFactor = 5;
|
||||
// set user.rand to random number
|
||||
|
@ -1,6 +1,6 @@
|
||||
import csurf from 'csurf';
|
||||
|
||||
export default function () {
|
||||
export default function getCsurf() {
|
||||
const protection = csurf({
|
||||
cookie: {
|
||||
domain: process.env.COOKIE_DOMAIN || 'localhost',
|
||||
|
@ -1,7 +1,7 @@
|
||||
import qs from 'query-string';
|
||||
|
||||
// add rx methods to express
|
||||
export default function () {
|
||||
export default function getExpressExtensions() {
|
||||
return function expressExtensions(req, res, next) {
|
||||
res.redirectWithFlash = uri => {
|
||||
const flash = req.flash();
|
||||
|
@ -48,8 +48,11 @@ export function isAllowedPath(path, pathsAllowedREs = _pathsAllowedREs) {
|
||||
return pathsAllowedREs.some(re => re.test(path));
|
||||
}
|
||||
|
||||
export default ({ jwtSecret = _jwtSecret, getUserById = _getUserById } = {}) =>
|
||||
function requestAuthorisation(req, res, next) {
|
||||
export default function getRequestAuthorisation({
|
||||
jwtSecret = _jwtSecret,
|
||||
getUserById = _getUserById
|
||||
} = {}) {
|
||||
return function requestAuthorisation(req, res, next) {
|
||||
const { origin } = getRedirectParams(req);
|
||||
const { path } = req;
|
||||
if (!isAllowedPath(path)) {
|
||||
@ -102,3 +105,4 @@ export default ({ jwtSecret = _jwtSecret, getUserById = _getUserById } = {}) =>
|
||||
}
|
||||
return Promise.resolve(next());
|
||||
};
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
import { Observable } from 'rx';
|
||||
|
||||
export default function (AuthToken) {
|
||||
export default function initializeAuthToken(AuthToken) {
|
||||
AuthToken.on('dataSourceAttached', () => {
|
||||
AuthToken.findOne$ = Observable.fromNodeCallback(
|
||||
AuthToken.findOne.bind(AuthToken)
|
||||
|
@ -7,7 +7,7 @@ import InMemoryCache from '../utils/in-memory-cache';
|
||||
const log = debug('fcc:boot:donate');
|
||||
const fiveMinutes = 1000 * 60 * 5;
|
||||
|
||||
export default function (Donation) {
|
||||
export default function initializeDonation(Donation) {
|
||||
let activeDonationUpdateInterval = null;
|
||||
const activeDonationCountCacheTTL = fiveMinutes;
|
||||
const activeDonationCountCache = InMemoryCache(0, reportError);
|
||||
|
@ -9,7 +9,7 @@ const failureRedirect = `${homeLocation}/signin`;
|
||||
|
||||
// TODO: can we remove passport-mock-strategy entirely in prod? That would let
|
||||
// us make passport-mock-strategy a dev dep, as it should be.
|
||||
export default {
|
||||
const passportProviders = {
|
||||
devlogin: {
|
||||
authScheme: 'mock',
|
||||
provider: 'dev',
|
||||
@ -45,3 +45,5 @@ export default {
|
||||
failureFlash: true
|
||||
}
|
||||
};
|
||||
|
||||
export default passportProviders;
|
||||
|
@ -1,19 +0,0 @@
|
||||
export default {
|
||||
bg9997c9c79feddfaeb9bdef: '56bbb991ad1ed5201cd392ca',
|
||||
bg9995c9c69feddfaeb9bdef: '56bbb991ad1ed5201cd392cb',
|
||||
bg9994c9c69feddfaeb9bdef: '56bbb991ad1ed5201cd392cc',
|
||||
bg9996c9c69feddfaeb9bdef: '56bbb991ad1ed5201cd392cd',
|
||||
bg9997c9c69feddfaeb9bdef: '56bbb991ad1ed5201cd392ce',
|
||||
bg9997c9c89feddfaeb9bdef: '56bbb991ad1ed5201cd392cf',
|
||||
bg9998c9c99feddfaeb9bdef: '56bbb991ad1ed5201cd392d0',
|
||||
bg9999c9c99feddfaeb9bdef: '56bbb991ad1ed5201cd392d1',
|
||||
bg9999c9c99feedfaeb9bdef: '56bbb991ad1ed5201cd392d2',
|
||||
bg9999c9c99fdddfaeb9bdef: '56bbb991ad1ed5201cd392d3',
|
||||
bb000000000000000000001: '56bbb991ad1ed5201cd392d4',
|
||||
bc000000000000000000001: '56bbb991ad1ed5201cd392d5',
|
||||
bb000000000000000000002: '56bbb991ad1ed5201cd392d6',
|
||||
bb000000000000000000003: '56bbb991ad1ed5201cd392d7',
|
||||
bb000000000000000000004: '56bbb991ad1ed5201cd392d8',
|
||||
bb000000000000000000005: '56bbb991ad1ed5201cd392d9',
|
||||
bb000000000000000000006: '56bbb991ad1ed5201cd392da'
|
||||
};
|
@ -1,17 +1,13 @@
|
||||
const path = require('path');
|
||||
|
||||
const {
|
||||
clientLocale,
|
||||
curriculumLocale,
|
||||
homeLocation
|
||||
} = require('../config/env.json');
|
||||
|
||||
const envData = require('../config/env.json');
|
||||
const {
|
||||
buildChallenges,
|
||||
replaceChallengeNode,
|
||||
localeChallengesRootDir
|
||||
} = require('./utils/buildChallenges');
|
||||
|
||||
const { clientLocale, curriculumLocale, homeLocation } = envData;
|
||||
|
||||
const curriculumIntroRoot = path.resolve(__dirname, './src/pages');
|
||||
const pathPrefix =
|
||||
clientLocale === 'english' || clientLocale === 'chinese'
|
||||
@ -84,20 +80,20 @@ module.exports = {
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
resolve: `gatsby-plugin-advanced-sitemap`,
|
||||
options: {
|
||||
exclude: [
|
||||
`/dev-404-page`,
|
||||
`/404`,
|
||||
`/404.html`,
|
||||
`/offline-plugin-app-shell-fallback`,
|
||||
`/learn`,
|
||||
/(\/)learn(\/)\S*/
|
||||
],
|
||||
addUncaughtPages: true
|
||||
}
|
||||
},
|
||||
// {
|
||||
// resolve: `gatsby-plugin-advanced-sitemap`,
|
||||
// options: {
|
||||
// exclude: [
|
||||
// `/dev-404-page`,
|
||||
// `/404`,
|
||||
// `/404.html`,
|
||||
// `/offline-plugin-app-shell-fallback`,
|
||||
// `/learn`,
|
||||
// /(\/)learn(\/)\S*/
|
||||
// ],
|
||||
// addUncaughtPages: true
|
||||
// }
|
||||
// },
|
||||
{
|
||||
resolve: 'gatsby-plugin-manifest',
|
||||
options: {
|
||||
|
@ -1,4 +1,5 @@
|
||||
const env = require('../config/env');
|
||||
const webpack = require('webpack');
|
||||
|
||||
const { createFilePath } = require('gatsby-source-filesystem');
|
||||
const uniq = require('lodash/uniq');
|
||||
@ -184,6 +185,13 @@ exports.onCreateWebpackConfig = ({ stage, plugins, actions }) => {
|
||||
process.env.HOME_PATH || 'http://localhost:3000'
|
||||
),
|
||||
STRIPE_PUBLIC_KEY: JSON.stringify(process.env.STRIPE_PUBLIC_KEY || '')
|
||||
}),
|
||||
// We add the shims of the node globals to the global scope
|
||||
new webpack.ProvidePlugin({
|
||||
Buffer: ['buffer', 'Buffer']
|
||||
}),
|
||||
new webpack.ProvidePlugin({
|
||||
process: 'process/browser'
|
||||
})
|
||||
];
|
||||
// The monaco editor relies on some browser only globals so should not be
|
||||
@ -193,8 +201,17 @@ exports.onCreateWebpackConfig = ({ stage, plugins, actions }) => {
|
||||
newPlugins.push(new MonacoWebpackPlugin());
|
||||
}
|
||||
actions.setWebpackConfig({
|
||||
node: {
|
||||
fs: 'empty'
|
||||
resolve: {
|
||||
fallback: {
|
||||
fs: false,
|
||||
path: false,
|
||||
assert: require.resolve('assert'),
|
||||
crypto: require.resolve('crypto-browserify'),
|
||||
util: false,
|
||||
buffer: require.resolve('buffer'),
|
||||
stream: require.resolve('stream-browserify'),
|
||||
process: require.resolve('process/browser')
|
||||
}
|
||||
},
|
||||
plugins: newPlugins
|
||||
});
|
||||
|
@ -1,9 +1,11 @@
|
||||
import i18n from 'i18next';
|
||||
import { initReactI18next } from 'react-i18next';
|
||||
|
||||
const { clientLocale } = require('../../config/env.json');
|
||||
const envData = require('../../config/env.json');
|
||||
const { i18nextCodes } = require('../../config/i18n/all-langs');
|
||||
|
||||
const { clientLocale } = envData;
|
||||
|
||||
const i18nextCode = i18nextCodes[clientLocale];
|
||||
|
||||
i18n.use(initReactI18next).init({
|
||||
|
43790
client/package-lock.json
generated
43790
client/package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@ -21,33 +21,37 @@
|
||||
"@reach/router": "^1.3.4",
|
||||
"@stripe/react-stripe-js": "^1.4.0",
|
||||
"algoliasearch": "^3.35.1",
|
||||
"assert": "^2.0.0",
|
||||
"axios": "^0.21.1",
|
||||
"babel-plugin-prismjs": "^2.0.1",
|
||||
"bezier-easing": "^2.1.0",
|
||||
"browser-cookies": "^1.2.0",
|
||||
"buffer": "^6.0.3",
|
||||
"chai": "^4.3.3",
|
||||
"crypto-browserify": "^3.12.0",
|
||||
"csrf": "^3.1.0",
|
||||
"date-fns": "^2.19.0",
|
||||
"enzyme": "^3.10.0",
|
||||
"enzyme-adapter-react-16": "^1.15.6",
|
||||
"final-form": "^4.20.2",
|
||||
"gatsby": "^2.32.9",
|
||||
"gatsby-cli": "^2.19.1",
|
||||
"gatsby": "^3.1.2",
|
||||
"gatsby-cli": "^3.0.0",
|
||||
"gatsby-plugin-advanced-sitemap": "^1.6.0",
|
||||
"gatsby-plugin-create-client-paths": "^2.10.0",
|
||||
"gatsby-plugin-manifest": "^2.12.1",
|
||||
"gatsby-plugin-postcss": "^2.3.13",
|
||||
"gatsby-plugin-react-helmet": "^3.10.0",
|
||||
"gatsby-plugin-create-client-paths": "^3.0.0",
|
||||
"gatsby-plugin-manifest": "^3.0.0",
|
||||
"gatsby-plugin-postcss": "^4.0.0",
|
||||
"gatsby-plugin-react-helmet": "^4.0.0",
|
||||
"gatsby-plugin-remove-serviceworker": "^1.0.0",
|
||||
"gatsby-remark-prismjs": "^3.13.0",
|
||||
"gatsby-source-filesystem": "^2.11.1",
|
||||
"gatsby-transformer-remark": "^2.16.1",
|
||||
"gatsby-remark-prismjs": "^4.0.0",
|
||||
"gatsby-source-filesystem": "^3.0.0",
|
||||
"gatsby-transformer-remark": "^3.0.0",
|
||||
"i18next": "^19.9.1",
|
||||
"jquery": "^3.6.0",
|
||||
"lodash": "^4.17.21",
|
||||
"monaco-editor": "^0.22.3",
|
||||
"nanoid": "^3.1.20",
|
||||
"prismjs": "^1.23.0",
|
||||
"process": "^0.11.10",
|
||||
"query-string": "^6.14.1",
|
||||
"react": "^16.14.0",
|
||||
"react-dom": "^16.14.0",
|
||||
@ -77,6 +81,7 @@
|
||||
"sanitize-html": "^2.3.2",
|
||||
"sass.js": "^0.11.0",
|
||||
"store": "^2.0.12",
|
||||
"stream-browserify": "^3.0.0",
|
||||
"typescript": "^4.2.3",
|
||||
"validator": "^13.5.2"
|
||||
},
|
||||
@ -87,8 +92,8 @@
|
||||
"scripts": {
|
||||
"prebuild": "echo 'Client workers building...' && npm run build:workers && echo 'Client workers ready.' && node ../tools/scripts/build/ensure-env.js",
|
||||
"build": "node --max_old_space_size=7168 node_modules/gatsby-cli build --prefix-paths",
|
||||
"build:workers": "node --max_old_space_size=7168 node_modules/webpack-cli --env.production --config ./webpack-workers.js && echo",
|
||||
"build:workers:debug": "node --max_old_space_size=7168 node_modules/webpack-cli --env.production --config ./webpack-workers.js --progress",
|
||||
"build:workers": "node --max_old_space_size=7168 node_modules/webpack-cli/bin/cli --env production --config ./webpack-workers.js && echo",
|
||||
"build:workers:debug": "node --max_old_space_size=7168 node_modules/webpack-cli/bin/cli --env production --config ./webpack-workers.js --progress",
|
||||
"clean": "gatsby clean",
|
||||
"predevelop": "npm run prebuild",
|
||||
"develop": "gatsby develop --inspect=9230",
|
||||
@ -115,8 +120,8 @@
|
||||
"monaco-editor-webpack-plugin": "^3.0.0",
|
||||
"react-test-renderer": "^16.14.0",
|
||||
"redux-saga-test-plan": "^4.0.1",
|
||||
"webpack": "^4.46.0",
|
||||
"webpack-cli": "^3.3.12"
|
||||
"webpack": "^5.25.1",
|
||||
"webpack-cli": "^4.5.0"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
|
@ -1,3 +1,5 @@
|
||||
export default {
|
||||
const analytics = {
|
||||
event: () => {}
|
||||
};
|
||||
|
||||
export default analytics;
|
||||
|
@ -1,4 +1,4 @@
|
||||
export default [
|
||||
const mockChallengeNodes = [
|
||||
{
|
||||
fields: {
|
||||
slug: '/super-block-one/block-a/challenge-one',
|
||||
@ -133,3 +133,5 @@ export default [
|
||||
dashedName: 'challenge-two'
|
||||
}
|
||||
];
|
||||
|
||||
export default mockChallengeNodes;
|
||||
|
@ -1 +0,0 @@
|
||||
export default ['a', 'c', 'g'];
|
@ -4,7 +4,9 @@ const React = require('react');
|
||||
|
||||
const gatsby = jest.requireActual('gatsby');
|
||||
|
||||
const { clientLocale } = require('../../../config/env.json');
|
||||
const envData = require('../../../config/env.json');
|
||||
|
||||
const { clientLocale } = envData;
|
||||
|
||||
module.exports = {
|
||||
...gatsby,
|
||||
|
@ -1,29 +0,0 @@
|
||||
export default [
|
||||
{
|
||||
fields: {
|
||||
slug: '/super-block-one/block-a'
|
||||
},
|
||||
frontmatter: {
|
||||
block: 'Block A',
|
||||
title: 'Introduction to Block A'
|
||||
}
|
||||
},
|
||||
{
|
||||
fields: {
|
||||
slug: '/super-block-one/block-b'
|
||||
},
|
||||
frontmatter: {
|
||||
block: 'Block B',
|
||||
title: 'Introduction to Block B'
|
||||
}
|
||||
},
|
||||
{
|
||||
fields: {
|
||||
slug: '/super-block-one/block-c'
|
||||
},
|
||||
frontmatter: {
|
||||
block: 'Block C',
|
||||
title: 'Introduction to Block C'
|
||||
}
|
||||
}
|
||||
];
|
@ -28,12 +28,14 @@ import { createFlashMessage } from '../components/Flash/redux';
|
||||
import standardErrorMessage from '../utils/standardErrorMessage';
|
||||
import reallyWeirdErrorMessage from '../utils/reallyWeirdErrorMessage';
|
||||
import { langCodes } from '../../../config/i18n/all-langs';
|
||||
import { clientLocale } from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
|
||||
import RedirectHome from '../components/RedirectHome';
|
||||
import { Loader, Spacer } from '../components/helpers';
|
||||
import { isEmpty } from 'lodash';
|
||||
|
||||
const { clientLocale } = envData;
|
||||
|
||||
const localeCode = langCodes[clientLocale];
|
||||
|
||||
const propTypes = {
|
||||
|
@ -5,7 +5,7 @@ import { createSelector } from 'reselect';
|
||||
import { Grid, Button } from '@freecodecamp/react-bootstrap';
|
||||
import Helmet from 'react-helmet';
|
||||
|
||||
import { apiLocation } from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
import {
|
||||
signInLoadingSelector,
|
||||
userSelector,
|
||||
@ -27,6 +27,8 @@ import Certification from '../components/settings/Certification';
|
||||
import DangerZone from '../components/settings/DangerZone';
|
||||
import { User } from '../redux/propTypes';
|
||||
|
||||
const { apiLocation } = envData;
|
||||
|
||||
const propTypes = {
|
||||
createFlashMessage: PropTypes.func.isRequired,
|
||||
isSignedIn: PropTypes.bool.isRequired,
|
||||
|
@ -1,10 +1,12 @@
|
||||
/* global jest, expect */
|
||||
import React from 'react';
|
||||
import ShallowRenderer from 'react-test-renderer/shallow';
|
||||
import { apiLocation } from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
|
||||
import { ShowSettings } from './ShowSettings';
|
||||
|
||||
const { apiLocation } = envData;
|
||||
|
||||
describe('<ShowSettings />', () => {
|
||||
it('renders to the DOM when user is logged in', () => {
|
||||
const shallow = new ShallowRenderer();
|
||||
|
@ -4,11 +4,11 @@ import { Grid, Panel, Button } from '@freecodecamp/react-bootstrap';
|
||||
import Helmet from 'react-helmet';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
import env from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
import FullWidthRow from '../components/helpers/FullWidthRow';
|
||||
import { Spacer } from '../components/helpers';
|
||||
|
||||
const { apiLocation } = env;
|
||||
const { apiLocation } = envData;
|
||||
|
||||
function ShowUnsubscribed({ unsubscribeId }) {
|
||||
const { t } = useTranslation();
|
||||
|
@ -24,7 +24,7 @@ import {
|
||||
donationUrls,
|
||||
modalDefaultDonation
|
||||
} from '../../../../config/donation-settings';
|
||||
import { stripePublicKey, deploymentEnv } from '../../../../config/env.json';
|
||||
import envData from '../../../../config/env.json';
|
||||
import { stripeScriptLoader } from '../../utils/scriptLoaders';
|
||||
import Spacer from '../helpers/Spacer';
|
||||
import PaypalButton from './PaypalButton';
|
||||
@ -44,6 +44,8 @@ import {
|
||||
|
||||
import './Donation.css';
|
||||
|
||||
const { stripePublicKey, deploymentEnv } = envData;
|
||||
|
||||
const numToCommas = num =>
|
||||
num.toString().replace(/(\d)(?=(\d{3})+(?!\d))/g, '$1,');
|
||||
|
||||
|
@ -7,13 +7,14 @@ import { createSelector } from 'reselect';
|
||||
import PayPalButtonScriptLoader from './PayPalButtonScriptLoader';
|
||||
import { withTranslation } from 'react-i18next';
|
||||
|
||||
import { paypalClientId, deploymentEnv } from '../../../../config/env.json';
|
||||
import envData from '../../../../config/env.json';
|
||||
import {
|
||||
paypalConfigurator,
|
||||
paypalConfigTypes
|
||||
} from '../../../../config/donation-settings';
|
||||
import { signInLoadingSelector, userSelector } from '../../redux';
|
||||
|
||||
const { paypalClientId, deploymentEnv } = envData;
|
||||
export class PaypalButton extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
|
@ -6,7 +6,9 @@ import { UniversalNav } from './components/UniversalNav';
|
||||
import { NavLinks } from './components/NavLinks';
|
||||
import AuthOrProfile from './components/AuthOrProfile';
|
||||
|
||||
import { apiLocation, clientLocale } from '../../../../config/env.json';
|
||||
import envData from '../../../../config/env.json';
|
||||
|
||||
const { apiLocation, clientLocale } = envData;
|
||||
|
||||
describe('<UniversalNav />', () => {
|
||||
const UniversalNavProps = {
|
||||
|
@ -6,10 +6,12 @@ import { Button } from '@freecodecamp/react-bootstrap';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
import { isSignedInSelector } from '../../../redux';
|
||||
import { apiLocation, homeLocation } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
import './login.css';
|
||||
|
||||
const { apiLocation, homeLocation } = envData;
|
||||
|
||||
const mapStateToProps = createSelector(isSignedInSelector, isSignedIn => ({
|
||||
isSignedIn
|
||||
}));
|
||||
|
@ -12,14 +12,12 @@ import {
|
||||
} from '@fortawesome/free-solid-svg-icons';
|
||||
import { Link } from '../../helpers';
|
||||
import { updateUserFlag } from '../../../redux/settings';
|
||||
import {
|
||||
clientLocale,
|
||||
radioLocation,
|
||||
apiLocation
|
||||
} from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
import createLanguageRedirect from '../../createLanguageRedirect';
|
||||
import createExternalRedirect from '../../createExternalRedirects';
|
||||
|
||||
const { clientLocale, radioLocation, apiLocation } = envData;
|
||||
|
||||
const {
|
||||
availableLangs,
|
||||
i18nextCodes,
|
||||
|
@ -1,10 +1,11 @@
|
||||
import React from 'react';
|
||||
import { Link, Spacer } from '../../helpers';
|
||||
import { forumLocation } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
import { Trans, useTranslation } from 'react-i18next';
|
||||
|
||||
import '../intro.css';
|
||||
|
||||
const { forumLocation } = envData;
|
||||
function IntroDescription() {
|
||||
const { t } = useTranslation();
|
||||
|
||||
|
@ -8,7 +8,9 @@ import { Link, Spacer } from '../helpers';
|
||||
import LinkButton from '../../assets/icons/LinkButton';
|
||||
import './map.css';
|
||||
import { isAuditedCert } from '../../../../utils/is-audited';
|
||||
import { curriculumLocale } from '../../../../config/env.json';
|
||||
import envData from '../../../../config/env.json';
|
||||
|
||||
const { curriculumLocale } = envData;
|
||||
|
||||
const propTypes = {
|
||||
currentSuperBlock: PropTypes.string,
|
||||
|
@ -1,4 +1,6 @@
|
||||
import { forumLocation } from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
|
||||
const { forumLocation } = envData;
|
||||
|
||||
const createExternalRedirect = (page, { clientLocale }) => {
|
||||
const isNotEnglish = clientLocale !== 'english';
|
||||
|
@ -1,7 +1,9 @@
|
||||
import React from 'react';
|
||||
import PropTypes from 'prop-types';
|
||||
|
||||
import { apiLocation } from '../../../../config/env.json';
|
||||
import envData from '../../../../config/env.json';
|
||||
|
||||
const { apiLocation } = envData;
|
||||
|
||||
const currentChallengeApi = '/challenges/current-challenge';
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
export default `
|
||||
const styles = `
|
||||
|
||||
.sprite-container {
|
||||
height: 100%;
|
||||
@ -71,3 +71,5 @@ export default `
|
||||
animation-direction: normal;
|
||||
}
|
||||
`;
|
||||
|
||||
export default styles;
|
||||
|
@ -2,7 +2,7 @@
|
||||
import React from 'react';
|
||||
import ShallowRenderer from 'react-test-renderer/shallow';
|
||||
|
||||
import { IndexPage } from '../../pages';
|
||||
import IndexPage from '../../pages';
|
||||
import mockChallengeNodes from '../../__mocks__/challenge-nodes';
|
||||
|
||||
describe('<Landing />', () => {
|
||||
|
@ -11,7 +11,9 @@ import HeatMap from './components/HeatMap';
|
||||
import Certifications from './components/Certifications';
|
||||
import Portfolio from './components/Portfolio';
|
||||
import Timeline from './components/TimeLine';
|
||||
import { apiLocation } from '../../../../config/env.json';
|
||||
import envData from '../../../../config/env.json';
|
||||
|
||||
const { apiLocation } = envData;
|
||||
|
||||
const propTypes = {
|
||||
isSessionUser: PropTypes.bool,
|
||||
|
@ -16,8 +16,9 @@ import Link from '../../helpers/Link';
|
||||
import './camper.css';
|
||||
|
||||
import { langCodes } from '../../../../../config/i18n/all-langs';
|
||||
import { clientLocale } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
const { clientLocale } = envData;
|
||||
const localeCode = langCodes[clientLocale];
|
||||
|
||||
const propTypes = {
|
||||
|
@ -16,7 +16,9 @@ import '@freecodecamp/react-calendar-heatmap/dist/styles.css';
|
||||
import './heatmap.css';
|
||||
|
||||
import { langCodes } from '../../../../../config/i18n/all-langs';
|
||||
import { clientLocale } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
const { clientLocale } = envData;
|
||||
|
||||
const localeCode = langCodes[clientLocale];
|
||||
|
||||
|
@ -25,7 +25,9 @@ import { maybeUrlRE } from '../../../utils';
|
||||
import CertificationIcon from '../../../assets/icons/CertificationIcon';
|
||||
|
||||
import { langCodes } from '../../../../../config/i18n/all-langs';
|
||||
import { clientLocale } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
const { clientLocale } = envData;
|
||||
|
||||
const localeCode = langCodes[clientLocale];
|
||||
|
||||
|
@ -15,10 +15,12 @@ import {
|
||||
toggleSearchDropdown,
|
||||
updateSearchQuery
|
||||
} from './redux';
|
||||
import { algoliaAppId, algoliaAPIKey } from '../../../../config/env.json';
|
||||
import envData from '../../../../config/env.json';
|
||||
|
||||
import { createSelector } from 'reselect';
|
||||
|
||||
const { algoliaAppId, algoliaAPIKey } = envData;
|
||||
|
||||
const DEBOUNCE_TIME = 100;
|
||||
|
||||
// If a key is missing, searches will fail, but the client will still render.
|
||||
|
@ -3,6 +3,8 @@ import React from 'react';
|
||||
import { Router } from '@reach/router';
|
||||
import { navigate, withPrefix } from 'gatsby';
|
||||
|
||||
import toLearnPath from '../utils/to-learn-path';
|
||||
|
||||
const Redirect = props => {
|
||||
if (typeof window !== 'undefined') {
|
||||
navigate(toLearnPath(props));
|
||||
@ -21,12 +23,4 @@ const Challenges = () => (
|
||||
|
||||
Challenges.displayName = 'Challenges';
|
||||
|
||||
export function toLearnPath({ superBlock, block, challenge }) {
|
||||
let path = withPrefix('/learn');
|
||||
if (superBlock) path += `/${superBlock}`;
|
||||
if (block) path += `/${block}`;
|
||||
if (challenge) path += `/${challenge}`;
|
||||
return path;
|
||||
}
|
||||
|
||||
export default Challenges;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* global expect */
|
||||
import { toLearnPath } from './challenges';
|
||||
import toLearnPath from '../utils/to-learn-path';
|
||||
import { withPrefix } from 'gatsby';
|
||||
|
||||
describe('toLearnPath', () => {
|
||||
|
@ -42,7 +42,7 @@ const mapDispatchToProps = dispatch =>
|
||||
dispatch
|
||||
);
|
||||
|
||||
export class DonatePage extends Component {
|
||||
class DonatePage extends Component {
|
||||
constructor(...props) {
|
||||
super(...props);
|
||||
this.state = {
|
||||
|
@ -4,7 +4,7 @@ import PropTypes from 'prop-types';
|
||||
import Landing from '../components/landing';
|
||||
import { AllChallengeNode } from '../redux/propTypes';
|
||||
|
||||
export const IndexPage = () => {
|
||||
const IndexPage = () => {
|
||||
return <Landing />;
|
||||
};
|
||||
|
||||
|
@ -47,7 +47,7 @@ const propTypes = {
|
||||
})
|
||||
};
|
||||
|
||||
export const LearnPage = ({
|
||||
const LearnPage = ({
|
||||
isSignedIn,
|
||||
fetchState: { pending, complete },
|
||||
user: { name = '', completedChallengeCount = 0 },
|
||||
|
@ -9,7 +9,9 @@ import rootReducer from './rootReducer';
|
||||
import rootSaga from './rootSaga';
|
||||
import { isBrowser } from '../../utils';
|
||||
|
||||
import { environment } from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
|
||||
const { environment } = envData;
|
||||
|
||||
const clientSide = isBrowser();
|
||||
|
||||
|
@ -22,4 +22,6 @@ function* errorHandlerSaga({ payload: error }) {
|
||||
yield put(createFlashMessage(reportedErrorMessage));
|
||||
}
|
||||
|
||||
export default [takeEvery(errorActionSelector, errorHandlerSaga)];
|
||||
const errorSagas = [takeEvery(errorActionSelector, errorHandlerSaga)];
|
||||
|
||||
export default errorSagas;
|
||||
|
@ -4,7 +4,9 @@ import PropTypes from 'prop-types';
|
||||
import { first } from 'lodash';
|
||||
import EditorTabs from './EditorTabs';
|
||||
import ActionRow from './ActionRow';
|
||||
import { showUpcomingChanges } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
const { showUpcomingChanges } = envData;
|
||||
|
||||
const propTypes = {
|
||||
challengeFiles: PropTypes.object,
|
||||
|
@ -8,9 +8,11 @@ import { createStructuredSelector } from 'reselect';
|
||||
import { currentTabSelector, moveToTab } from '../redux';
|
||||
import { bindActionCreators } from 'redux';
|
||||
import EditorTabs from './EditorTabs';
|
||||
import { showUpcomingChanges } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
import i18next from 'i18next';
|
||||
|
||||
const { showUpcomingChanges } = envData;
|
||||
|
||||
const mapStateToProps = createStructuredSelector({
|
||||
currentTab: currentTabSelector
|
||||
});
|
||||
|
@ -7,10 +7,12 @@ import { Trans, withTranslation } from 'react-i18next';
|
||||
|
||||
import { createQuestion, closeModal, isHelpModalOpenSelector } from '../redux';
|
||||
import { executeGA } from '../../../redux';
|
||||
import { forumLocation } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
import './help-modal.css';
|
||||
|
||||
const { forumLocation } = envData;
|
||||
|
||||
const mapStateToProps = state => ({ isOpen: isHelpModalOpenSelector(state) });
|
||||
const mapDispatchToProps = dispatch =>
|
||||
bindActionCreators(
|
||||
|
@ -82,7 +82,7 @@ const mapDispatchToActions = {
|
||||
updateSolutionFormValues
|
||||
};
|
||||
|
||||
export class BackEnd extends Component {
|
||||
class BackEnd extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state = {};
|
||||
|
@ -62,7 +62,7 @@ const propTypes = {
|
||||
updateSolutionFormValues: PropTypes.func.isRequired
|
||||
};
|
||||
|
||||
export class Project extends Component {
|
||||
class Project extends Component {
|
||||
constructor() {
|
||||
super();
|
||||
this.handleSubmit = this.handleSubmit.bind(this);
|
||||
|
@ -17,7 +17,9 @@ import createWorker from '../utils/worker-executor';
|
||||
|
||||
// the config files are created during the build, but not before linting
|
||||
// eslint-disable-next-line import/no-unresolved
|
||||
import { filename as sassCompile } from '../../../../../config/client/sass-compile';
|
||||
import sassData from '../../../../../config/client/sass-compile.json';
|
||||
|
||||
const { filename: sassCompile } = sassData;
|
||||
|
||||
const protectTimeout = 100;
|
||||
const testProtectTimeout = 1500;
|
||||
|
@ -8,7 +8,9 @@ import {
|
||||
projectFormValuesSelector
|
||||
} from '../redux';
|
||||
import { tap, mapTo } from 'rxjs/operators';
|
||||
import { forumLocation } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
const { forumLocation } = envData;
|
||||
|
||||
function filesToMarkdown(files = {}) {
|
||||
const moreThenOneFile = Object.keys(files).length > 1;
|
||||
|
@ -10,9 +10,12 @@ import {
|
||||
|
||||
// the config files are created during the build, but not before linting
|
||||
// eslint-disable-next-line import/no-unresolved
|
||||
import { filename as runner } from '../../../../../config/client/frame-runner';
|
||||
import frameRunnerData from '../../../../../config/client/frame-runner.json';
|
||||
// eslint-disable-next-line import/no-unresolved
|
||||
import { filename as testEvaluator } from '../../../../../config/client/test-evaluator';
|
||||
import testEvaluatorData from '../../../../../config/client/test-evaluator.json';
|
||||
|
||||
const { filename: runner } = frameRunnerData;
|
||||
const { filename: testEvaluator } = testEvaluatorData;
|
||||
|
||||
const frameRunner = [
|
||||
{
|
||||
|
@ -1,4 +1,6 @@
|
||||
import { forumLocation } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
const { forumLocation } = envData;
|
||||
|
||||
export function getGuideUrl({ forumTopicId, title = '' }) {
|
||||
title = encodeURIComponent(title);
|
||||
|
@ -1,6 +1,8 @@
|
||||
/* global expect */
|
||||
|
||||
import { forumLocation } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
|
||||
const { forumLocation } = envData;
|
||||
|
||||
const { getGuideUrl } = require('./');
|
||||
|
||||
|
@ -68,7 +68,7 @@ const propTypes = {
|
||||
};
|
||||
|
||||
// Component
|
||||
export class Project extends Component {
|
||||
class Project extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state = {
|
||||
|
@ -71,7 +71,7 @@ const mapDispatchToProps = dispatch =>
|
||||
dispatch
|
||||
);
|
||||
|
||||
export class SuperBlockIntroductionPage extends Component {
|
||||
class SuperBlockIntroductionPage extends Component {
|
||||
componentDidMount() {
|
||||
this.initializeExpandedState();
|
||||
|
||||
|
@ -13,9 +13,11 @@ import Caret from '../../../assets/icons/Caret';
|
||||
import GreenPass from '../../../assets/icons/GreenPass';
|
||||
import GreenNotCompleted from '../../../assets/icons/GreenNotCompleted';
|
||||
import { isAuditedCert } from '../../../../../utils/is-audited';
|
||||
import { curriculumLocale } from '../../../../../config/env.json';
|
||||
import envData from '../../../../../config/env.json';
|
||||
import { Link } from '../../../components/helpers/';
|
||||
|
||||
const { curriculumLocale } = envData;
|
||||
|
||||
const mapStateToProps = (state, ownProps) => {
|
||||
const expandedSelector = makeExpandedBlockSelector(ownProps.blockDashedName);
|
||||
|
||||
|
@ -1,8 +1,10 @@
|
||||
import { apiLocation } from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
import axios from 'axios';
|
||||
import Tokens from 'csrf';
|
||||
import cookies from 'browser-cookies';
|
||||
|
||||
const { apiLocation } = envData;
|
||||
|
||||
const base = apiLocation;
|
||||
const tokens = new Tokens();
|
||||
|
||||
|
@ -1,4 +1,6 @@
|
||||
import { clientLocale } from '../../../config/env.json';
|
||||
import envData from '../../../config/env.json';
|
||||
|
||||
const { clientLocale } = envData;
|
||||
|
||||
const algoliaIndices = {
|
||||
english: {
|
||||
|
@ -27,9 +27,11 @@ const removeWhiteSpace = (str = '') => {
|
||||
return str.replace(/\s/g, '');
|
||||
};
|
||||
|
||||
export default {
|
||||
const curriculumHelpers = {
|
||||
removeHtmlComments,
|
||||
removeCssComments,
|
||||
removeJSComments,
|
||||
removeWhiteSpace
|
||||
};
|
||||
|
||||
export default curriculumHelpers;
|
||||
|
@ -1,4 +1,6 @@
|
||||
export default {
|
||||
const reallyWeirdErrorMessage = {
|
||||
type: 'danger',
|
||||
message: 'flash.really-weird'
|
||||
};
|
||||
|
||||
export default reallyWeirdErrorMessage;
|
||||
|
@ -1,4 +1,6 @@
|
||||
export default {
|
||||
const reportedErrorMessage = {
|
||||
type: 'danger',
|
||||
message: 'flash.not-right'
|
||||
};
|
||||
|
||||
export default reportedErrorMessage;
|
||||
|
@ -1,4 +1,6 @@
|
||||
export default {
|
||||
const standardErrorMessage = {
|
||||
type: 'danger',
|
||||
message: 'flash.went-wrong'
|
||||
};
|
||||
|
||||
export default standardErrorMessage;
|
||||
|
9
client/src/utils/to-learn-path.js
Normal file
9
client/src/utils/to-learn-path.js
Normal file
@ -0,0 +1,9 @@
|
||||
import { withPrefix } from 'gatsby';
|
||||
|
||||
export default function toLearnPath({ superBlock, block, challenge }) {
|
||||
let path = withPrefix('/learn');
|
||||
if (superBlock) path += `/${superBlock}`;
|
||||
if (block) path += `/${block}`;
|
||||
if (challenge) path += `/${challenge}`;
|
||||
return path;
|
||||
}
|
@ -6,7 +6,9 @@ const {
|
||||
challengesDir,
|
||||
getChallengesDirForLang
|
||||
} = require('../../curriculum/getChallenges');
|
||||
const { curriculumLocale } = require('../../config/env.json');
|
||||
const envData = require('../../config/env.json');
|
||||
|
||||
const { curriculumLocale } = envData;
|
||||
|
||||
exports.localeChallengesRootDir = getChallengesDirForLang(curriculumLocale);
|
||||
|
||||
|
@ -1,4 +1,5 @@
|
||||
const path = require('path');
|
||||
const webpack = require('webpack');
|
||||
const CopyWebpackPlugin = require('copy-webpack-plugin');
|
||||
const { writeFileSync } = require('fs');
|
||||
|
||||
@ -60,7 +61,21 @@ module.exports = (env = {}) => {
|
||||
plugins: [
|
||||
new CopyWebpackPlugin([
|
||||
{ from: 'node_modules/sass.js/dist/sass.sync.js' }
|
||||
])
|
||||
]
|
||||
]),
|
||||
new webpack.ProvidePlugin({
|
||||
process: 'process/browser'
|
||||
}),
|
||||
new webpack.ProvidePlugin({
|
||||
Buffer: ['buffer', 'Buffer']
|
||||
})
|
||||
],
|
||||
resolve: {
|
||||
fallback: {
|
||||
buffer: require.resolve('buffer'),
|
||||
util: false,
|
||||
stream: false,
|
||||
process: require.resolve('process/browser')
|
||||
}
|
||||
}
|
||||
};
|
||||
};
|
||||
|
@ -61,7 +61,8 @@ const TRANSLATABLE_COMMENTS = getTranslatableComments(
|
||||
|
||||
// the config files are created during the build, but not before linting
|
||||
// eslint-disable-next-line import/no-unresolved
|
||||
const testEvaluator = require('../../config/client/test-evaluator').filename;
|
||||
const testEvaluator = require('../../config/client/test-evaluator.json')
|
||||
.filename;
|
||||
const { inspect } = require('util');
|
||||
|
||||
const commentExtractors = {
|
||||
|
Reference in New Issue
Block a user