Skip to content
This repository has been archived by the owner on Jul 11, 2023. It is now read-only.

Commit

Permalink
Merge pull request #155 from wbprice/limit-questions-to-survey
Browse files Browse the repository at this point in the history
User flow, limit questions to survey
  • Loading branch information
ttavenner authored Jul 18, 2017
2 parents 7f63fda + 38d9288 commit 2cac116
Show file tree
Hide file tree
Showing 13 changed files with 128 additions and 66 deletions.
9 changes: 9 additions & 0 deletions api/controllers/ViewController.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,15 @@ module.exports = class ViewController extends Controller {
});
}

surveyList(request, reply) {
getLayout(request, 'client', function(error, html) {
if (error) {
// handle error
}
reply(html);
});
}

category(request, reply) {
getLayout(request, 'client', function(error, html) {
if (error) {
Expand Down
51 changes: 25 additions & 26 deletions config/dev-fixtures/question-fixtures.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,39 +15,38 @@ const questions = [
},
{
text: 'What do you think about clouds',
CategoryId: 4
CategoryId: 1
}
];

module.exports = {

load: (app) => {
return app.orm.Question.count({})
.then(count => {
if (count > 0) {
return [];
}
else {
// For all surveys, create three questions.
return app.orm.Survey.findAll({where: {}})
.then(surveys => {
surveys.map((survey, index) => {
return Promise.all(
questions.map(question => {
return app.orm.Question.create(
Object.assign({}, question, {SurveyId: survey.toJSON().id})
);
})
);
});
})
// Create Questions
.then(questions => {
app.log.info('Questions created.');
return questions;
.then(count => {
if (count > 0) {
return [];
}
else {
// For all surveys, create three questions.
return app.orm.Survey.findAll({where: {}})
.then(surveys => {
surveys.map((survey, index) => {
return Promise.all(
questions.map(question => {
return app.orm.Question.create(
Object.assign({}, question, {SurveyId: survey.toJSON().id})
);
})
);
});
})
// Create Questions
.then(questions => {
app.log.info('Questions created.');
return questions;
});
}
});
}
});
}

};
14 changes: 12 additions & 2 deletions config/routes.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,13 +21,23 @@ module.exports = [
{
method: 'GET',
path: '/survey',
handler: 'ViewController.survey'
handler: 'ViewController.surveyList'
},
{
method: 'GET',
path: '/survey/{id}',
handler: 'ViewController.category'
},
{
method: 'GET',
path: '/category',
path: '/survey/{id}/category',
handler: 'ViewController.category'
},
{
method: 'GET',
path: '/survey/{id}/questions',
handler: 'ViewController.survey'
},
{
method: 'GET',
path: '/admin/{view*}',
Expand Down
21 changes: 15 additions & 6 deletions frontend/js/components/atoms/Card.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,12 +7,20 @@ class Card extends Component {
}

render() {
const cardStyle = {};

if (this.props.onClick) {
cardStyle.cursor = 'pointer';
}

return (
<section
className={`card ${this.props.className}`}
style={this.props.style}>
{this.props.children}
</section>
<section
style={cardStyle}
className={`card ${this.props.className}`}
style={this.props.style}
onClick={this.props.onClick}>
{this.props.children}
</section>
);
}

Expand All @@ -21,7 +29,8 @@ class Card extends Component {
Card.propTypes = {
style: PropTypes.object,
children: PropTypes.any,
className: PropTypes.string
className: PropTypes.string,
onClick: PropTypes.func
};

export default Card;
52 changes: 33 additions & 19 deletions frontend/js/components/ecosystems/CategoryList.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import update from 'immutability-helper';

import CategoryListItem from './../organisms/CategoryListItem';
import { CategoryListItemNameStatic } from './../organisms/CategoryListItemName';
import { gotoRoute } from './../../redux/actions/router-actions';

class CategoryList extends Component {

Expand Down Expand Up @@ -52,31 +53,44 @@ class CategoryList extends Component {
}));
}

back() {
gotoRoute('/');
}

next() {
gotoRoute(`/survey/${this.props.surveyId}/questions`);
}

render() {
return (
<div className="category-list">
<Preview generator={this.generatePreview.bind(this)} />
{
this.state.categories.map((categoryItem, index) => {
return (
<CategoryListItem
key={categoryItem.id}
index={index}
id={categoryItem.id}
name={categoryItem.name}
icon={categoryItem.icon}
moveCard={this.moveCard} />
);
})
}
<div>
<p>Sort these categories in order of importance to you.</p>
<div className="category-list">
<Preview generator={this.generatePreview.bind(this)} />
{
this.state.categories.map((categoryItem, index) => {
return (
<CategoryListItem
key={categoryItem.id}
index={index}
id={categoryItem.id}
name={categoryItem.name}
icon={categoryItem.icon}
moveCard={this.moveCard} />
);
})
}
</div>
<button onClick={this.next.bind(this)}>OK</button>
</div>
);
}}


}
}

CategoryList.propTypes = {
categories: PropTypes.array
categories: PropTypes.array,
surveyId: PropTypes.string,
dispatch: PropTypes.func
};

export default DragDropContext(MultiBackend(HTML5toTouch))(CategoryList);
7 changes: 5 additions & 2 deletions frontend/js/components/environments/Category.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,10 @@ class Category extends Component {

render() {
const categories = this.props.category.categories;

return (
<CategoryList
surveyId={this.props.router.params.id}
dispatch={this.props.dispatch}
categories={categories.sort((catA, catB) => {
return catA.rank - catB.rank;
})} />
Expand All @@ -37,7 +38,9 @@ Category.propTypes = {
ui: PropTypes.object,
login: PropTypes.object,
survey: PropTypes.object,
dispatch: PropTypes.func
dispatch: PropTypes.func,
params: PropTypes.object,
router: PropTypes.object
};

export default connect(
Expand Down
7 changes: 4 additions & 3 deletions frontend/js/components/environments/Survey.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ class Survey extends Component {
}

componentDidMount() {
this.props.dispatch(fetchSurveyQuestions());
this.props.dispatch(fetchSurveyQuestions(this.props.params.id));
}

gotoPrevQuestion() {
Expand All @@ -33,7 +33,7 @@ class Survey extends Component {

gotoNextQuestion() {
if (this.props.survey.questionIndex >= this.props.survey.questions.length - 1) {
return gotoRoute('/results');
return gotoRoute('/results/publicPhraseOne');
}
return this.props.dispatch(gotoNextQuestion());
}
Expand Down Expand Up @@ -62,7 +62,8 @@ class Survey extends Component {

Survey.propTypes = {
dispatch: PropTypes.func,
survey: PropTypes.object
survey: PropTypes.object,
params: PropTypes.object
};

module.exports = connect(
Expand Down
20 changes: 16 additions & 4 deletions frontend/js/components/environments/SurveySelector.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import React, { Component } from 'react';
import PropTypes from 'prop-types';
import { gotoRoute } from './../../redux/actions/router-actions';

import { connect } from 'react-redux';

Expand All @@ -12,19 +13,30 @@ class SurveySelector extends Component {
super(props);
}

onClickSurveyCard(id) {
gotoRoute(`survey/${id}`);
}

render() {
return (
<section>
<Card>
<pre>Survey Selector</pre>
</Card>
{this.props.pickSurvey.surveys.map((survey, index) => {
return (
<Card
key={index}
onClick={this.onClickSurveyCard.bind(this, survey.id)}>
<h2>{survey.name}</h2>
<button>Take it!</button>
</Card>
);
})}
</section>
);
}
}

SurveySelector.propTypes = {
surveys: PropTypes.array
pickSurvey: PropTypes.object
};

export default connect(
Expand Down
2 changes: 1 addition & 1 deletion frontend/js/components/organisms/AppLogo.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ class AppLogo extends Component {
<IconButton
onClick={this.props.onClick}
icon="menu" />
<a href="#">
<a href="/">
<img alt="OKCandidate" src="/dist/images/okcandidate-logo.svg" />
</a>
</section>
Expand Down
2 changes: 2 additions & 0 deletions frontend/js/redux/actions/pick-survey-actions.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import fetch from 'isomorphic-fetch';
import checkStatus from './../utils/checkStatus';
import { gotoRoute } from './../actions/router-actions';

export const FETCH_SURVEYS_BY_LOCATION_REQUEST = 'FETCH_SURVEYS_BY_LOCATION_REQUEST';
export const FETCH_SURVEYS_BY_LOCATION_SUCCESS = 'FETCH_SURVEYS_BY_LOCATION_SUCCESS';
Expand Down Expand Up @@ -33,6 +34,7 @@ export function fetchSurveysByLocation(coordinates) {
.then(response => response.json())
.then(response => {
dispatch(fetchSurveysByLocationSuccess(response));
gotoRoute('/survey');
})
.catch(error => dispatch(fetchSurveysByLocationFailure(error)));
};
Expand Down
7 changes: 4 additions & 3 deletions frontend/js/redux/actions/survey-actions.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import fetch from 'isomorphic-fetch';
import checkStatus from './../utils/checkStatus';
import uniqBy from 'lodash.uniqby';

export const FETCH_SURVEY_QUESTIONS_REQUEST = 'FETCH_SURVEY_QUESTIONS_REQUEST';
export const FETCH_SURVEY_QUESTIONS_SUCCESS = 'FETCH_SURVEY_QUESTIONS_SUCCESS';
Expand All @@ -25,14 +26,14 @@ export function fetchSurveyQuestionsFailure(error) {
};
}

export function fetchSurveyQuestions() {
export function fetchSurveyQuestions(id) {
return function(dispatch) {
dispatch(fetchSurveyQuestionsRequest());
return fetch('/api/v1/question')
return fetch(`/api/v1/question?SurveyId=${id}`)
.then(checkStatus)
.then(response => response.json())
.then(response => {
dispatch(fetchSurveyQuestionsSuccess(response));
dispatch(fetchSurveyQuestionsSuccess(uniqBy(response, 'id')));
})
.catch(error => dispatch(fetchSurveyQuestionsFailure(error)));
};
Expand Down
1 change: 1 addition & 0 deletions frontend/js/routes.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ module.exports = (
<Route path="/" component={Frame}>
<IndexRoute component={Home} />
<Route path="survey" component={SurveySelector} />
<Route path="survey/:id" component={Category} />
<Route path="survey/:id/category" component={Category} />
<Route path="survey/:id/questions" component={Survey} />
<Route path="results/:passPhrase" component={Results} />
Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@
"immutability-helper": "^2.2.2",
"inert": "^4.2.0",
"isomorphic-fetch": "^2.2.1",
"lodash.uniqby": "^4.7.0",
"pg": "^6.1.0",
"prop-types": "^15.5.10",
"react": "^15.3.2",
Expand Down

0 comments on commit 2cac116

Please sign in to comment.