Merge branch 'master' into refactor
Conflicts: app.js controllers/api.js controllers/challenges.js gulpfile.js
This commit is contained in:
34
app.js
34
app.js
@ -1,19 +1,19 @@
|
|||||||
require('newrelic');
|
require('newrelic');
|
||||||
|
require('dotenv').load();
|
||||||
/**
|
/**
|
||||||
* Module dependencies.
|
* Module dependencies.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
var express = require('express'),
|
var express = require('express'),
|
||||||
debug = require('debug')('freecc:server'),
|
debug = require('debug')('freecc:server'),
|
||||||
cookieParser = require('cookie-parser'),
|
cookieParser = require('cookie-parser'),
|
||||||
compress = require('compression'),
|
compress = require('compression'),
|
||||||
session = require('express-session'),
|
session = require('express-session'),
|
||||||
bodyParser = require('body-parser'),
|
|
||||||
logger = require('morgan'),
|
logger = require('morgan'),
|
||||||
errorHandler = require('errorhandler'),
|
errorHandler = require('errorhandler'),
|
||||||
methodOverride = require('method-override'),
|
methodOverride = require('method-override'),
|
||||||
bodyParser = require('body-parser'),
|
bodyParser = require('body-parser'),
|
||||||
helmet = require('helmet'),
|
helmet = require('helmet'),
|
||||||
|
|
||||||
_ = require('lodash'),
|
_ = require('lodash'),
|
||||||
MongoStore = require('connect-mongo')(session),
|
MongoStore = require('connect-mongo')(session),
|
||||||
flash = require('express-flash'),
|
flash = require('express-flash'),
|
||||||
@ -99,15 +99,19 @@ app.use(helmet.xframe());
|
|||||||
var trusted = [
|
var trusted = [
|
||||||
'"self"',
|
'"self"',
|
||||||
'*.freecodecamp.com',
|
'*.freecodecamp.com',
|
||||||
'*.google-analytics.com',
|
|
||||||
'*.googleapis.com',
|
|
||||||
'*.gstatic.com',
|
'*.gstatic.com',
|
||||||
'*.doubleclick.net',
|
"*.google-analytics.com",
|
||||||
'*.twitter.com',
|
"*.googleapis.com",
|
||||||
|
"*.google.com",
|
||||||
|
"*.gstatic.com",
|
||||||
|
"*.doubleclick.net",
|
||||||
|
"*.twitter.com",
|
||||||
'*.twimg.com',
|
'*.twimg.com',
|
||||||
'*.githubusercontent.com',
|
"*.githubusercontent.com",
|
||||||
'"unsafe-eval"',
|
"'unsafe-eval'",
|
||||||
'"unsafe-inline"'
|
"'unsafe-inline'",
|
||||||
|
"*.rafflecopter.com",
|
||||||
|
"localhost:3001"
|
||||||
];
|
];
|
||||||
//TODO(Berks): conditionally add localhost domains to csp;
|
//TODO(Berks): conditionally add localhost domains to csp;
|
||||||
/*var connectSrc;
|
/*var connectSrc;
|
||||||
@ -123,14 +127,12 @@ debug(trusted);
|
|||||||
app.use(helmet.contentSecurityPolicy({
|
app.use(helmet.contentSecurityPolicy({
|
||||||
defaultSrc: trusted,
|
defaultSrc: trusted,
|
||||||
scriptSrc: ['*.optimizely.com'].concat(trusted),
|
scriptSrc: ['*.optimizely.com'].concat(trusted),
|
||||||
'connect-src': ['ws://localhost:3001/', 'http://localhost:3001/'],
|
'connect-src': ['ws://*.rafflecopter.com', 'wss://*.rafflecopter.com','https://*.rafflecopter.com', 'ws://www.freecodecamp.com', 'ws://localhost:3001/', 'http://localhost:3001', 'http://www.freecodecamp.com'],
|
||||||
styleSrc: trusted,
|
styleSrc: trusted,
|
||||||
imgSrc: ['*.evernote.com', '*.amazonaws.com', 'data:'].concat(trusted),
|
imgSrc: ['*.evernote.com', '*.amazonaws.com', "data:", '*.licdn.com', '*.gravatar.com', '*.youtube.com'].concat(trusted),
|
||||||
fontSrc: ['"self"', '*.googleapis.com'].concat(trusted),
|
fontSrc: ["'self", '*.googleapis.com'].concat(trusted),
|
||||||
mediaSrc: ['*.amazonaws.com', '*.twitter.com'],
|
mediaSrc: ['*.amazonaws.com', '*.twitter.com'],
|
||||||
frameSrc: ['*.gitter.im', '*.vimeo.com', '*.twitter.com'],
|
frameSrc: ['*.gitter.im', '*.vimeo.com', '*.twitter.com', '*.rafflecopter.com'],
|
||||||
// sandbox: ['allow-forms', 'allow-scripts'],
|
|
||||||
// reportUri: '/report-violation',
|
|
||||||
reportOnly: false, // set to true if you only want to report errors
|
reportOnly: false, // set to true if you only want to report errors
|
||||||
setAllHeaders: false, // set to true if you want to set all headers
|
setAllHeaders: false, // set to true if you want to set all headers
|
||||||
safari5: false // set to true if you want to force buggy CSP in Safari 5
|
safari5: false // set to true if you want to force buggy CSP in Safari 5
|
||||||
@ -208,10 +210,8 @@ app.post(
|
|||||||
|
|
||||||
app.get(
|
app.get(
|
||||||
'/challenges/:challengeNumber',
|
'/challenges/:challengeNumber',
|
||||||
passportConf.isAuthenticated,
|
|
||||||
challengesController.returnChallenge
|
challengesController.returnChallenge
|
||||||
);
|
);
|
||||||
|
|
||||||
app.all('/account', passportConf.isAuthenticated);
|
app.all('/account', passportConf.isAuthenticated);
|
||||||
app.get('/account', userController.getAccount);
|
app.get('/account', userController.getAccount);
|
||||||
app.post('/account/profile', userController.postUpdateProfile);
|
app.post('/account/profile', userController.postUpdateProfile);
|
||||||
|
137
controllers/api.js
Normal file
137
controllers/api.js
Normal file
@ -0,0 +1,137 @@
|
|||||||
|
var secrets = require('../config/secrets');
|
||||||
|
var User = require('../models/User');
|
||||||
|
var querystring = require('querystring');
|
||||||
|
var validator = require('validator');
|
||||||
|
var async = require('async');
|
||||||
|
var cheerio = require('cheerio');
|
||||||
|
var request = require('request');
|
||||||
|
var graph = require('fbgraph');
|
||||||
|
var Github = require('github-api');
|
||||||
|
var Twit = require('twit');
|
||||||
|
var Linkedin = require('node-linkedin')(secrets.linkedin.clientID, secrets.linkedin.clientSecret, secrets.linkedin.callbackURL);
|
||||||
|
var Y = require('yui/yql');
|
||||||
|
var _ = require('lodash');
|
||||||
|
|
||||||
|
/**
|
||||||
|
* GET /api
|
||||||
|
* List of API examples.
|
||||||
|
*/
|
||||||
|
|
||||||
|
exports.getApi = function(req, res) {
|
||||||
|
res.render('api/index', {
|
||||||
|
title: 'API Examples'
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* GET /api/facebook
|
||||||
|
* Facebook API example.
|
||||||
|
*/
|
||||||
|
|
||||||
|
exports.getFacebook = function(req, res, next) {
|
||||||
|
var token = _.find(req.user.tokens, { kind: 'facebook' });
|
||||||
|
graph.setAccessToken(token.accessToken);
|
||||||
|
async.parallel({
|
||||||
|
getMe: function(done) {
|
||||||
|
graph.get(req.user.facebook, function(err, me) {
|
||||||
|
done(err, me);
|
||||||
|
});
|
||||||
|
},
|
||||||
|
getMyFriends: function(done) {
|
||||||
|
graph.get(req.user.facebook + '/friends', function(err, friends) {
|
||||||
|
done(err, friends.data);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
},
|
||||||
|
function(err, results) {
|
||||||
|
if (err) return next(err);
|
||||||
|
res.render('api/facebook', {
|
||||||
|
title: 'Facebook API',
|
||||||
|
me: results.getMe,
|
||||||
|
friends: results.getMyFriends
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* GET /api/github
|
||||||
|
* GitHub API Example.
|
||||||
|
*/
|
||||||
|
|
||||||
|
exports.getGithub = function(req, res, next) {
|
||||||
|
var token = _.find(req.user.tokens, { kind: 'github' });
|
||||||
|
var github = new Github({ token: token.accessToken });
|
||||||
|
var repo = github.getRepo('sahat', 'requirejs-library');
|
||||||
|
repo.show(function(err, repo) {
|
||||||
|
if (err) return next(err);
|
||||||
|
res.render('api/github', {
|
||||||
|
title: 'GitHub API',
|
||||||
|
repo: repo
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* GET /api/twitter
|
||||||
|
* Twiter API example.
|
||||||
|
*/
|
||||||
|
|
||||||
|
exports.getTwitter = function(req, res, next) {
|
||||||
|
var token = _.find(req.user.tokens, { kind: 'twitter' });
|
||||||
|
var T = new Twit({
|
||||||
|
consumer_key: secrets.twitter.consumerKey,
|
||||||
|
consumer_secret: secrets.twitter.consumerSecret,
|
||||||
|
access_token: token.accessToken,
|
||||||
|
access_token_secret: token.tokenSecret
|
||||||
|
});
|
||||||
|
T.get('search/tweets', { q: 'nodejs since:2013-01-01', geocode: '40.71448,-74.00598,5mi', count: 10 }, function(err, reply) {
|
||||||
|
if (err) return next(err);
|
||||||
|
res.render('api/twitter', {
|
||||||
|
title: 'Twitter API',
|
||||||
|
tweets: reply.statuses
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* POST /api/twitter
|
||||||
|
* Post a tweet.
|
||||||
|
*/
|
||||||
|
|
||||||
|
exports.postTwitter = function(req, res, next) {
|
||||||
|
req.assert('tweet', 'Tweet cannot be empty.').notEmpty();
|
||||||
|
var errors = req.validationErrors();
|
||||||
|
if (errors) {
|
||||||
|
req.flash('errors', errors);
|
||||||
|
return res.redirect('/api/twitter');
|
||||||
|
}
|
||||||
|
var token = _.find(req.user.tokens, { kind: 'twitter' });
|
||||||
|
var T = new Twit({
|
||||||
|
consumer_key: secrets.twitter.consumerKey,
|
||||||
|
consumer_secret: secrets.twitter.consumerSecret,
|
||||||
|
access_token: token.accessToken,
|
||||||
|
access_token_secret: token.tokenSecret
|
||||||
|
});
|
||||||
|
T.post('statuses/update', { status: req.body.tweet }, function(err, data, response) {
|
||||||
|
if (err) return next(err);
|
||||||
|
req.flash('success', { msg: 'Tweet has been posted.'});
|
||||||
|
res.redirect('/api/twitter');
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* GET /api/linkedin
|
||||||
|
* LinkedIn API example.
|
||||||
|
*/
|
||||||
|
|
||||||
|
exports.getLinkedin = function(req, res, next) {
|
||||||
|
var token = _.find(req.user.tokens, { kind: 'linkedin' });
|
||||||
|
var linkedin = Linkedin.init(token.accessToken);
|
||||||
|
linkedin.people.me(function(err, $in) {
|
||||||
|
if (err) return next(err);
|
||||||
|
res.render('api/linkedin', {
|
||||||
|
title: 'LinkedIn API',
|
||||||
|
profile: $in
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
@ -8,23 +8,48 @@ var _ = require('lodash'),
|
|||||||
|
|
||||||
exports.returnChallenge = function(req, res, next) {
|
exports.returnChallenge = function(req, res, next) {
|
||||||
var challengeNumber = parseInt(req.params.challengeNumber) || 0;
|
var challengeNumber = parseInt(req.params.challengeNumber) || 0;
|
||||||
|
var verbs = [
|
||||||
if (challengeNumber > 59) {
|
'ACED',
|
||||||
challengeNumber = 0;
|
'NAILED',
|
||||||
}
|
'ROCKED',
|
||||||
|
'SCORCHED',
|
||||||
Challenge.findOne({ challengeNumber: challengeNumber }, function(err, c) {
|
'DEVASTATED',
|
||||||
|
'OWNED',
|
||||||
|
'CRUSHED',
|
||||||
|
'CONQUERED',
|
||||||
|
'KILLED',
|
||||||
|
'SHREDDED',
|
||||||
|
'ANNIHILATED',
|
||||||
|
'NUKED'
|
||||||
|
];
|
||||||
|
var phrases = [
|
||||||
|
"Shout it from on top of a mountain",
|
||||||
|
"Tell everyone and their dogs",
|
||||||
|
"Show them. Show them all!",
|
||||||
|
"Inspire your friends",
|
||||||
|
"Tell the world of your greatness",
|
||||||
|
"Look accomplished on social media",
|
||||||
|
"Share news of your grand endeavor",
|
||||||
|
"Establish your alibi for the past two hours",
|
||||||
|
"Prove to mom that computers aren't just for games"
|
||||||
|
];
|
||||||
|
if (challengeNumber > 59) { challengeNumber = 0; }
|
||||||
|
Challenge.find({}, function (err, c) {
|
||||||
if (err) {
|
if (err) {
|
||||||
debug('Challenge err: ', err);
|
debug('Challenge err: ', err);
|
||||||
return next(err);
|
next(err);
|
||||||
}
|
}
|
||||||
res.render('challenges/show', {
|
res.render('challenges/show', {
|
||||||
title: 'Challenge: ' + c.name,
|
title: 'Challenge: ' + c[challengeNumber].name,
|
||||||
name: c.name,
|
name: c[challengeNumber].name,
|
||||||
video: c.video,
|
video: c[challengeNumber].video,
|
||||||
time: c.time,
|
time: c[challengeNumber].time,
|
||||||
steps: c.steps,
|
steps: c[challengeNumber].steps,
|
||||||
cc: req.user.challengesHash
|
number: challengeNumber,
|
||||||
|
cc: req.user ? req.user.challengesHash : undefined,
|
||||||
|
verb: verbs[Math.floor(Math.random() * verbs.length)],
|
||||||
|
phrase: phrases[Math.floor(Math.random() * phrases.length)],
|
||||||
|
challenges: c
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
@ -6,6 +6,7 @@ var passport = require('passport');
|
|||||||
var User = require('../models/User');
|
var User = require('../models/User');
|
||||||
var secrets = require('../config/secrets');
|
var secrets = require('../config/secrets');
|
||||||
var moment = require('moment');
|
var moment = require('moment');
|
||||||
|
var Challenge = require('./../models/Challenge');
|
||||||
|
|
||||||
//TODO(Berks): Refactor to use module.exports = {} pattern.
|
//TODO(Berks): Refactor to use module.exports = {} pattern.
|
||||||
/**
|
/**
|
||||||
@ -133,11 +134,18 @@ exports.postEmailSignup = function(req, res, next) {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
exports.getAccount = function(req, res) {
|
exports.getAccount = function(req, res) {
|
||||||
|
Challenge.find({}, function (err, c) {
|
||||||
|
if (err) {
|
||||||
|
console.error('Challenge err: ', err);
|
||||||
|
next(err);
|
||||||
|
}
|
||||||
res.render('account/profile', {
|
res.render('account/profile', {
|
||||||
title: 'Manage your Free Code Camp Account',
|
title: 'Manage your Free Code Camp Account',
|
||||||
cc: req.user.challengesHash,
|
cc: c,
|
||||||
|
ch: req.user.challengesHash,
|
||||||
moment: moment
|
moment: moment
|
||||||
});
|
});
|
||||||
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -36,7 +36,7 @@
|
|||||||
{
|
{
|
||||||
"name": "Join our Forum",
|
"name": "Join our Forum",
|
||||||
"time": 5,
|
"time": 5,
|
||||||
"video": "114578442",
|
"video": "115275066",
|
||||||
"challengeNumber": 2,
|
"challengeNumber": 2,
|
||||||
"steps": [
|
"steps": [
|
||||||
"Go to Free Code Camp's forum: <a href='http://forum.freecodecamp.com' target='_blank'>http://forum.freecodecamp.com</a>.",
|
"Go to Free Code Camp's forum: <a href='http://forum.freecodecamp.com' target='_blank'>http://forum.freecodecamp.com</a>.",
|
||||||
@ -46,7 +46,7 @@
|
|||||||
"Click on the \"Introduce yourself here\" discussion.",
|
"Click on the \"Introduce yourself here\" discussion.",
|
||||||
"Here you can read through other Free Code Camp community members' self introductions.",
|
"Here you can read through other Free Code Camp community members' self introductions.",
|
||||||
"Go ahead and type a brief self introduction of your own.",
|
"Go ahead and type a brief self introduction of your own.",
|
||||||
"Click on the \"Categories\" drop-down menu. You should see a category called \"Local Chapters\". Click that. If your city isn't already on the list, you can create a topic for it. Otherwise, you can also introduce yourself to the other Code Campers from your city.",
|
"Click on the \"Categories\" drop-down menu. You should see a category called \"Local Chapters\". Click that. If your city isn't already on the list, create a topic for it. Otherwise, introduce yourself to the other Code Campers from your city.",
|
||||||
"Come back here daily to ask questions, engage in discussions, and share links to helpful coding tools."
|
"Come back here daily to ask questions, engage in discussions, and share links to helpful coding tools."
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
@ -192,8 +192,8 @@
|
|||||||
]
|
]
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"name": "Customize Bootstrap with Bootswatch",
|
"name": "Customize Bootstrap",
|
||||||
"time": 10,
|
"time": 15,
|
||||||
"video": "110752741",
|
"video": "110752741",
|
||||||
"challengeNumber": 16,
|
"challengeNumber": 16,
|
||||||
"steps": [
|
"steps": [
|
||||||
|
@ -40,246 +40,12 @@ block content
|
|||||||
tr
|
tr
|
||||||
th Challenge
|
th Challenge
|
||||||
th Date Finished
|
th Date Finished
|
||||||
if cc[0] > 0
|
for challenge in cc
|
||||||
|
if ch[challenge.challengeNumber] > 0
|
||||||
tr
|
tr
|
||||||
td Learn how Free Code Camp Works
|
td= cc[challenge.challengeNumber].name
|
||||||
td=moment(cc[0], 'X').format("MMM DD, YYYY")
|
td= moment(ch[challenge.challengeNumber], 'X').format("MMM DD, YYYY")
|
||||||
if cc[1] > 0
|
|
||||||
tr
|
|
||||||
td Join Our Chat Room
|
|
||||||
td=moment(cc[1], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[2] > 0
|
|
||||||
tr
|
|
||||||
td Subscribe to Our Subreddit
|
|
||||||
td=moment(cc[2], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[3] > 0
|
|
||||||
tr
|
|
||||||
td Build a Personal Website
|
|
||||||
td=moment(cc[3], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[4] > 0
|
|
||||||
tr
|
|
||||||
td Build a Responsive Blog Theme
|
|
||||||
td=moment(cc[4], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[5] > 0
|
|
||||||
tr
|
|
||||||
td Build a Small Business Website
|
|
||||||
td=moment(cc[5], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[6] > 0
|
|
||||||
tr
|
|
||||||
td Tweak HTML and CSS in CodePen
|
|
||||||
td=moment(cc[6], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[7] > 0
|
|
||||||
tr
|
|
||||||
td Build a CSS Robot
|
|
||||||
td=moment(cc[7], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[8] > 0
|
|
||||||
tr
|
|
||||||
td Get Started with jQuery
|
|
||||||
td=moment(cc[8], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[9] > 0
|
|
||||||
tr
|
|
||||||
td Traverse the DOM
|
|
||||||
td=moment(cc[9], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[10] > 0
|
|
||||||
tr
|
|
||||||
td Work with the DOM
|
|
||||||
td=moment(cc[10], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[11] > 0
|
|
||||||
tr
|
|
||||||
td Listen for DOM Events
|
|
||||||
td=moment(cc[11], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[12] > 0
|
|
||||||
tr
|
|
||||||
td Use jQuery for Styling
|
|
||||||
td=moment(cc[12], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[13] > 0
|
|
||||||
tr
|
|
||||||
td Build a MadLibs Game
|
|
||||||
td=moment(cc[13], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[14] > 0
|
|
||||||
tr
|
|
||||||
td Discover Chrome's DevTools
|
|
||||||
td=moment(cc[14], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[15] > 0
|
|
||||||
tr
|
|
||||||
td Tackle jQuery Exercises
|
|
||||||
td=moment(cc[15], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[16] > 0
|
|
||||||
tr
|
|
||||||
td Customize Bootstrap
|
|
||||||
td=moment(cc[16], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[17] > 0
|
|
||||||
tr
|
|
||||||
td Inject Animation into CSS
|
|
||||||
td=moment(cc[17], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[18] > 0
|
|
||||||
tr
|
|
||||||
td Learn Basic Computer Science
|
|
||||||
td=moment(cc[18], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[19] > 0
|
|
||||||
tr
|
|
||||||
td Learn Loops
|
|
||||||
td=moment(cc[19], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[20] > 0
|
|
||||||
tr
|
|
||||||
td Learn Computer Hardware
|
|
||||||
td=moment(cc[20], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[21] > 0
|
|
||||||
tr
|
|
||||||
td Learn Computer Networking
|
|
||||||
td=moment(cc[21], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[22] > 0
|
|
||||||
tr
|
|
||||||
td Learn Boolean Logic
|
|
||||||
td=moment(cc[22], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[23] > 0
|
|
||||||
tr
|
|
||||||
td Learn Computer Security
|
|
||||||
td=moment(cc[23], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[24] > 0
|
|
||||||
tr
|
|
||||||
td Build an Adventure Game
|
|
||||||
td=moment(cc[24], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[25] > 0
|
|
||||||
tr
|
|
||||||
td Build Rock Paper Scissors
|
|
||||||
td=moment(cc[25], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[26] > 0
|
|
||||||
tr
|
|
||||||
td Learn JavaScript For Loops
|
|
||||||
td=moment(cc[26], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[27] > 0
|
|
||||||
tr
|
|
||||||
td Learn JavaScript While Loops
|
|
||||||
td=moment(cc[27], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[28] > 0
|
|
||||||
tr
|
|
||||||
td Learn Control Flow
|
|
||||||
td=moment(cc[28], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[29] > 0
|
|
||||||
tr
|
|
||||||
td Build a Contact List
|
|
||||||
td=moment(cc[29], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[30] > 0
|
|
||||||
tr
|
|
||||||
td Build an Address Book
|
|
||||||
td=moment(cc[30], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[31] > 0
|
|
||||||
tr
|
|
||||||
td Build a Cash Register
|
|
||||||
td=moment(cc[31], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[32] > 0
|
|
||||||
tr
|
|
||||||
td Get Help the Hacker Way
|
|
||||||
td=moment(cc[32], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[33] > 0
|
|
||||||
tr
|
|
||||||
td Learn Regular Expressions
|
|
||||||
td=moment(cc[33], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[34] > 0
|
|
||||||
tr
|
|
||||||
td Pair Program on CoderByte
|
|
||||||
td=moment(cc[34], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[35] > 0
|
|
||||||
tr
|
|
||||||
td Learn Relational Database Theory
|
|
||||||
td=moment(cc[35], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[36] > 0
|
|
||||||
tr
|
|
||||||
td Pair Program to Query SQL pt 1
|
|
||||||
td=moment(cc[36], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[37] > 0
|
|
||||||
tr
|
|
||||||
td Pair Program to Query SQL pt 2
|
|
||||||
td=moment(cc[37], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[38] > 0
|
|
||||||
tr
|
|
||||||
td Pair Program to modify SQL pt 1
|
|
||||||
td=moment(cc[38], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[39] > 0
|
|
||||||
tr
|
|
||||||
td Pair Program to modify SQL pt 2
|
|
||||||
td=moment(cc[39], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[40] > 0
|
|
||||||
tr
|
|
||||||
td Learn JSON
|
|
||||||
td=moment(cc[40], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[41] > 0
|
|
||||||
tr
|
|
||||||
td Manage Source Code with Git
|
|
||||||
td=moment(cc[41], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[42] > 0
|
|
||||||
tr
|
|
||||||
td Get Started with Node.js
|
|
||||||
td=moment(cc[42], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[43] > 0
|
|
||||||
tr
|
|
||||||
td Try Node.js Events
|
|
||||||
td=moment(cc[43], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[44] > 0
|
|
||||||
tr
|
|
||||||
td Try Node.js Streams
|
|
||||||
td=moment(cc[44], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[45] > 0
|
|
||||||
tr
|
|
||||||
td Learn how Node.js Modules Work
|
|
||||||
td=moment(cc[45], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[46] > 0
|
|
||||||
tr
|
|
||||||
td Start an Express.js Server
|
|
||||||
td=moment(cc[46], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[47] > 0
|
|
||||||
tr
|
|
||||||
td Use Socket.io
|
|
||||||
td=moment(cc[47], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[48] > 0
|
|
||||||
tr
|
|
||||||
td Use Redis to Persist Data
|
|
||||||
td=moment(cc[48], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[49] > 0
|
|
||||||
tr
|
|
||||||
td Dive Deeper into Express.js
|
|
||||||
td=moment(cc[49], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[50] > 0
|
|
||||||
tr
|
|
||||||
td Set up Express.js Middleware
|
|
||||||
td=moment(cc[50], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[51] > 0
|
|
||||||
tr
|
|
||||||
td Take Advantage of Parameters
|
|
||||||
td=moment(cc[51], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[52] > 0
|
|
||||||
tr
|
|
||||||
td Add the Body Parser
|
|
||||||
td=moment(cc[52], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[53] > 0
|
|
||||||
tr
|
|
||||||
td Configure Routes in Express.js
|
|
||||||
td=moment(cc[53], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[54] > 0
|
|
||||||
tr
|
|
||||||
td Try MongoDB
|
|
||||||
td=moment(cc[54], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[55] > 0
|
|
||||||
tr
|
|
||||||
td Get Started with Angular.js
|
|
||||||
td=moment(cc[55], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[56] > 0
|
|
||||||
tr
|
|
||||||
td Apply Angular.js Directives
|
|
||||||
td=moment(cc[56], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[57] > 0
|
|
||||||
tr
|
|
||||||
td Power Forms with Angular.js
|
|
||||||
td=moment(cc[57], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[58] > 0
|
|
||||||
tr
|
|
||||||
td Customize Angular.js Directives
|
|
||||||
td=moment(cc[58], 'X').format("MMM DD, YYYY")
|
|
||||||
if cc[59] > 0
|
|
||||||
tr
|
|
||||||
td Create Angular.js Services
|
|
||||||
td=moment(cc[59], 'X').format("MMM DD, YYYY")
|
|
||||||
h3 Danger Zone
|
h3 Danger Zone
|
||||||
button.btn.btn-danger.confirm-deletion
|
button.btn.btn-danger.confirm-deletion
|
||||||
span.ion-trash-b
|
span.ion-trash-b
|
||||||
|
@ -15,7 +15,7 @@ block content
|
|||||||
.btn.btn-primary.btn-big.btn-block.completed-challenge I've completed this challenge
|
.btn.btn-primary.btn-big.btn-block.completed-challenge I've completed this challenge
|
||||||
.ten-pixel-break
|
.ten-pixel-break
|
||||||
.btn.btn-success.btn-large.btn-block.skip-challenge I want to skip this challenge for now
|
.btn.btn-success.btn-large.btn-block.skip-challenge I want to skip this challenge for now
|
||||||
- if (cc[2] > 0)
|
- if (cc && cc[2] > 0)
|
||||||
.panel-footer.text-center
|
.panel-footer.text-center
|
||||||
span Need a break? Check out our:
|
span Need a break? Check out our:
|
||||||
a(href="https://gitter.im/FreeCodeCamp/FreeCodeCamp", target="_blank") Chat Room
|
a(href="https://gitter.im/FreeCodeCamp/FreeCodeCamp", target="_blank") Chat Room
|
||||||
@ -34,6 +34,11 @@ block content
|
|||||||
.animated.zoomInUp.delay-1
|
.animated.zoomInUp.delay-1
|
||||||
span.landing-icon.ion-checkmark-circled.text-primary
|
span.landing-icon.ion-checkmark-circled.text-primary
|
||||||
a.animated.fadeIn.delay-2.btn.btn-lg.btn-primary.btn-block.next-button(name='_csrf', value=_csrf, aria-hidden='true') Take me to my next challenge
|
a.animated.fadeIn.delay-2.btn.btn-lg.btn-primary.btn-block.next-button(name='_csrf', value=_csrf, aria-hidden='true') Take me to my next challenge
|
||||||
|
if (cc && cc[2] > 0)
|
||||||
|
a.animated.fadeIn.delay-2.btn-twitter.btn.btn-lg.btn-info.btn-block(href="https://twitter.com/intent/tweet?text=I%20just%20#{verb}%20Free%20Code%20Camp%20Challenge%20%23#{number}:%20#{name}&url=http%3A%2F%2Ffreecodecamp.com/challenges/#{number}&hashtags=learntocode, javascript")
|
||||||
|
i.fa.fa-twitter
|
||||||
|
= phrase
|
||||||
|
|
||||||
#skip-dialog.modal
|
#skip-dialog.modal
|
||||||
.modal-dialog.animated.zoomIn.fast-animation
|
.modal-dialog.animated.zoomIn.fast-animation
|
||||||
.modal-content
|
.modal-content
|
||||||
|
@ -2,185 +2,9 @@
|
|||||||
.panel-heading Challenges
|
.panel-heading Challenges
|
||||||
.panel-body
|
.panel-body
|
||||||
ol(start='0')
|
ol(start='0')
|
||||||
|
for challenge in challenges
|
||||||
li
|
li
|
||||||
a(href="/challenges/0", class="#{ cc[0] > 0 ? 'strikethrough' : '' }") Learn how Free Code Camp Works
|
a(href="/challenges/#{challenge.challengeNumber}", class="#{ (cc && cc[challenge.challengeNumber] > 0) ? 'strikethrough' : '' }") #{challenge.name}
|
||||||
| (2 minutes)
|
| (#{challenge.time} mins)
|
||||||
li
|
|
||||||
a(href="/challenges/1", class="#{ cc[1] > 0 ? 'strikethrough' : '' }") Join Our Chat Room
|
|
||||||
| (5 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/2", class="#{ cc[2] > 0 ? 'strikethrough' : '' }") Subscribe to Our Subreddit
|
|
||||||
| (5 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/3", class="#{ cc[3] > 0 ? 'strikethrough' : '' }") Build a Personal Website
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/4", class="#{ cc[4] > 0 ? 'strikethrough' : '' }") Build a Responsive Blog Theme
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/5", class="#{ cc[5] > 0 ? 'strikethrough' : '' }") Build a Small Business Website
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/6", class="#{ cc[6] > 0 ? 'strikethrough' : '' }") Tweak HTML and CSS in CodePen
|
|
||||||
| (10 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/7", class="#{ cc[7] > 0 ? 'strikethrough' : '' }") Build a CSS Robot
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/8", class="#{ cc[8] > 0 ? 'strikethrough' : '' }") Get Started with jQuery
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/9", class="#{ cc[9] > 0 ? 'strikethrough' : '' }") Traverse the DOM
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/10", class="#{ cc[10] > 0 ? 'strikethrough' : '' }") Work with the DOM
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/11", class="#{ cc[11] > 0 ? 'strikethrough' : '' }") Listen for DOM Events
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/12", class="#{ cc[12] > 0 ? 'strikethrough' : '' }") Use jQuery for Styling
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/13", class="#{ cc[13] > 0 ? 'strikethrough' : '' }") Build a MadLibs Game
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/14", class="#{ cc[14] > 0 ? 'strikethrough' : '' }") Discover Chrome's DevTools
|
|
||||||
| (90 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/15", class="#{ cc[15] > 0 ? 'strikethrough' : '' }") Tackle jQuery Exercises
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/16", class="#{ cc[16] > 0 ? 'strikethrough' : '' }") Customize Bootstrap
|
|
||||||
| (10 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/17", class="#{ cc[17] > 0 ? 'strikethrough' : '' }") Inject Animation into CSS
|
|
||||||
| (15 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/18", class="#{ cc[18] > 0 ? 'strikethrough' : '' }") Learn Basic Computer Science
|
|
||||||
| (120 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/19", class="#{ cc[19] > 0 ? 'strikethrough' : '' }") Learn Loops
|
|
||||||
| (120 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/20", class="#{ cc[20] > 0 ? 'strikethrough' : '' }") Learn Computer Hardware
|
|
||||||
| (120 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/21", class="#{ cc[21] > 0 ? 'strikethrough' : '' }") Learn Computer Networking
|
|
||||||
| (120 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/22", class="#{ cc[22] > 0 ? 'strikethrough' : '' }") Learn Boolean Logic
|
|
||||||
| (120 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/23", class="#{ cc[23] > 0 ? 'strikethrough' : '' }") Learn Computer Security
|
|
||||||
| (120 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/24", class="#{ cc[24] > 0 ? 'strikethrough' : '' }") Build an Adventure Game
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/25", class="#{ cc[25] > 0 ? 'strikethrough' : '' }") Build Rock Paper Scissors
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/26", class="#{ cc[26] > 0 ? 'strikethrough' : '' }") Learn JavaScript For Loops
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/27", class="#{ cc[27] > 0 ? 'strikethrough' : '' }") Learn JavaScript While Loops
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/28", class="#{ cc[28] > 0 ? 'strikethrough' : '' }") Learn Control Flow
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/29", class="#{ cc[29] > 0 ? 'strikethrough' : '' }") Build a Contact List
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/30", class="#{ cc[30] > 0 ? 'strikethrough' : '' }") Build an Address Book
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/31", class="#{ cc[31] > 0 ? 'strikethrough' : '' }") Build a Cash Register
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/32", class="#{ cc[32] > 0 ? 'strikethrough' : '' }") Get Help the Hacker Way
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/33", class="#{ cc[33] > 0 ? 'strikethrough' : '' }") Learn Regular Expressions
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/34", class="#{ cc[34] > 0 ? 'strikethrough' : '' }") Pair Program on CoderByte
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/35", class="#{ cc[35] > 0 ? 'strikethrough' : '' }") Learn Relational Database Theory
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/36", class="#{ cc[36] > 0 ? 'strikethrough' : '' }") Pair Program to Query SQL pt 1
|
|
||||||
| (90 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/37", class="#{ cc[37] > 0 ? 'strikethrough' : '' }") Pair Program to Query SQL pt 2
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/38", class="#{ cc[38] > 0 ? 'strikethrough' : '' }") Pair Program to modify SQL pt 1
|
|
||||||
| (90 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/39", class="#{ cc[39] > 0 ? 'strikethrough' : '' }") Pair Program to modify SQL pt 2
|
|
||||||
| (60 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/40", class="#{ cc[40] > 0 ? 'strikethrough' : '' }") Learn JSON
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/41", class="#{ cc[41] > 0 ? 'strikethrough' : '' }") Manage Source Code with Git
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/42", class="#{ cc[42] > 0 ? 'strikethrough' : '' }") Get Started with Node.js
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/43", class="#{ cc[43] > 0 ? 'strikethrough' : '' }") Try Node.js Events
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/44", class="#{ cc[44] > 0 ? 'strikethrough' : '' }") Try Node.js Streams
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/45", class="#{ cc[45] > 0 ? 'strikethrough' : '' }") Learn how Node.js Modules Work
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/46", class="#{ cc[46] > 0 ? 'strikethrough' : '' }") Start an Express.js Server
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/47", class="#{ cc[47] > 0 ? 'strikethrough' : '' }") Use Socket.io
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/48", class="#{ cc[48] > 0 ? 'strikethrough' : '' }") Use Redis to Persist Data
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/49", class="#{ cc[49] > 0 ? 'strikethrough' : '' }") Dive Deeper into Express.js
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/50", class="#{ cc[50] > 0 ? 'strikethrough' : '' }") Set up Express.js Middleware
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/51", class="#{ cc[51] > 0 ? 'strikethrough' : '' }") Take Advantage of Parameters
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/52", class="#{ cc[52] > 0 ? 'strikethrough' : '' }") Add the Body Parser
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/53", class="#{ cc[53] > 0 ? 'strikethrough' : '' }") Configure Routes in Express.js
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/54", class="#{ cc[54] > 0 ? 'strikethrough' : '' }") Try MongoDB
|
|
||||||
| (30 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/55", class="#{ cc[55] > 0 ? 'strikethrough' : '' }") Get Started with Angular.js
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/56", class="#{ cc[56] > 0 ? 'strikethrough' : '' }") Apply Angular.js Directives
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/57", class="#{ cc[57] > 0 ? 'strikethrough' : '' }") Power Forms with Angular.js
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/58", class="#{ cc[58] > 0 ? 'strikethrough' : '' }") Customize Angular.js Directives
|
|
||||||
| (45 minutes)
|
|
||||||
li
|
|
||||||
a(href="/challenges/59", class="#{ cc[59] > 0 ? 'strikethrough' : '' }") Create Angular.js Services
|
|
||||||
| (45 minutes)
|
|
||||||
|
|
||||||
a.btn.btn-primary(href="/done-with-first-100-hours", class="#{ cc[59] > 0 ? '' : 'disabled' }") I've finished all Free Code Camp challenges and all the Easy and Medium CoderByte Challenges
|
a.btn.btn-primary(href="/done-with-first-100-hours", class="#{ ((cc && cc[59] === 0) || (!cc)) ? 'disabled' : '' }") I've finished all Free Code Camp challenges and all the Easy and Medium CoderByte Challenges
|
@ -27,26 +27,26 @@
|
|||||||
a(href='/')
|
a(href='/')
|
||||||
span.ion-map
|
span.ion-map
|
||||||
| My Challenges
|
| My Challenges
|
||||||
- if (cc[1] > 0)
|
- if (cc && cc[1] < 1)
|
||||||
li.hamburger
|
|
||||||
a(href='https://gitter.im/FreeCodeCamp/FreeCodeCamp', target='_blank')
|
|
||||||
span.ion-coffee
|
|
||||||
| Chat Room
|
|
||||||
- else
|
|
||||||
li.hamburger.disabled
|
li.hamburger.disabled
|
||||||
a(href='https://gitter.im/FreeCodeCamp/FreeCodeCamp', target='_blank')
|
a(href='https://gitter.im/FreeCodeCamp/FreeCodeCamp', target='_blank')
|
||||||
span.ion-coffee
|
span.ion-coffee
|
||||||
| Chat Room (do Challenge 1 first)
|
| Chat Room (do Challenge 1 first)
|
||||||
- if (cc[2] > 0)
|
|
||||||
li.hamburger
|
|
||||||
a(href='http://forum.freecodecamp.com/', target='_blank')
|
|
||||||
span.ion-planet
|
|
||||||
| Forum
|
|
||||||
- else
|
- else
|
||||||
|
li.hamburger
|
||||||
|
a(href='https://gitter.im/FreeCodeCamp/FreeCodeCamp', target='_blank')
|
||||||
|
span.ion-coffee
|
||||||
|
| Chat Room
|
||||||
|
- if (cc && cc[2] < 1)
|
||||||
li.hamburger.disabled
|
li.hamburger.disabled
|
||||||
a(href='http://forum.freecodecamp.com/', target='_blank')
|
a(href='http://forum.freecodecamp.com/', target='_blank')
|
||||||
span.ion-planet
|
span.ion-planet
|
||||||
| Forum (do Challenge 2 first)
|
| Forum (do Challenge 2 first)
|
||||||
|
- else
|
||||||
|
li.hamburger
|
||||||
|
a(href='http://forum.freecodecamp.com/', target='_blank')
|
||||||
|
span.ion-planet
|
||||||
|
| Forum
|
||||||
li.hamburger
|
li.hamburger
|
||||||
a(href='/account')
|
a(href='/account')
|
||||||
span.ion-person
|
span.ion-person
|
||||||
|
Reference in New Issue
Block a user