Fix job saving on form submit

This commit is contained in:
Berkeley Martinez
2016-03-01 20:31:43 -08:00
parent 5dab7fddbc
commit 15c9417911
5 changed files with 42 additions and 18 deletions

View File

@ -1,4 +1,4 @@
import { helpers } from 'rx'; import { CompositeDisposable, helpers } from 'rx';
import React, { PropTypes } from 'react'; import React, { PropTypes } from 'react';
import { reduxForm } from 'redux-form'; import { reduxForm } from 'redux-form';
// import debug from 'debug'; // import debug from 'debug';
@ -70,14 +70,17 @@ const fieldValidators = {
locale: makeRequired(isAscii), locale: makeRequired(isAscii),
description: makeRequired(helpers.identity), description: makeRequired(helpers.identity),
email: makeRequired(isEmail), email: makeRequired(isEmail),
url: isValidURL, url: makeRequired(isValidURL),
logo: isValidURL, logo: makeOptional(isValidURL),
company: makeRequired(isAscii), company: makeRequired(isAscii),
howToApply: makeRequired(isAscii) howToApply: makeRequired(isAscii)
}; };
function makeOptional(validator) {
return val => val ? validator(val) : true;
}
function makeRequired(validator) { function makeRequired(validator) {
return (val) => !!val && validator(val); return (val) => val ? validator(val) : false;
} }
function validateForm(values) { function validateForm(values) {
@ -86,7 +89,7 @@ function validateForm(values) {
if (fieldValidators[field](values[field])) { if (fieldValidators[field](values[field])) {
return null; return null;
} }
return { [field]: fieldValidators[field](values[field]) }; return { [field]: !fieldValidators[field](values[field]) };
}) })
.filter(Boolean) .filter(Boolean)
.reduce((errors, error) => ({ ...errors, ...error }), {}); .reduce((errors, error) => ({ ...errors, ...error }), {});
@ -103,17 +106,32 @@ function getBsStyle(field) {
} }
export class NewJob extends React.Component { export class NewJob extends React.Component {
constructor(...args) {
super(...args);
this._subscriptions = new CompositeDisposable();
}
static displayName = 'NewJob'; static displayName = 'NewJob';
static propTypes = { static propTypes = {
fields: PropTypes.object, fields: PropTypes.object,
handleSubmit: PropTypes.func handleSubmit: PropTypes.func,
saveJob: PropTypes.func
}; };
componentDidMount() { componentDidMount() {
// this.prop.getSavedForm(); // this.prop.getSavedForm();
} }
componentWillUnmount() {
this._subscriptions.dispose();
}
handleSubmit(job) {
const subscription = this.props.saveJob(job).subscribe();
this._subscriptions.add(subscription);
}
handleCertClick(name) { handleCertClick(name) {
const { fields } = this.props; const { fields } = this.props;
Object.keys(certTypes).forEach(certType => { Object.keys(certTypes).forEach(certType => {
@ -372,6 +390,6 @@ export default reduxForm(
}, },
null, null,
{ {
onSubmit: saveJob saveJob
} }
)(NewJob); )(NewJob);

View File

@ -4,5 +4,6 @@ export types from './types';
import fetchJobsSaga from './fetch-jobs-saga'; import fetchJobsSaga from './fetch-jobs-saga';
import saveJobSaga from './save-job-saga'; import saveJobSaga from './save-job-saga';
export formNormalizer from './jobs-form-normalizer';
export const sagas = [ fetchJobsSaga, saveJobSaga ]; export const sagas = [ fetchJobsSaga, saveJobSaga ];

View File

@ -8,7 +8,11 @@ const normalizeOptions = {
stripWWW: false stripWWW: false
}; };
function formatUrl(url, shouldKeepTrailingSlash = true) { function ifDefinedNormalize(normalizer) {
return value => value ? normalizer(value) : value;
}
function formatUrl(url) {
if ( if (
typeof url === 'string' && typeof url === 'string' &&
url.length > 4 && url.length > 4 &&
@ -16,7 +20,7 @@ function formatUrl(url, shouldKeepTrailingSlash = true) {
) { ) {
// prevent trailing / from being stripped during typing // prevent trailing / from being stripped during typing
let lastChar = ''; let lastChar = '';
if (shouldKeepTrailingSlash && url.substring(url.length - 1) === '/') { if (url.substring(url.length - 1) === '/') {
lastChar = '/'; lastChar = '/';
} }
return normalizeUrl(url, normalizeOptions) + lastChar; return normalizeUrl(url, normalizeOptions) + lastChar;
@ -26,13 +30,13 @@ function formatUrl(url, shouldKeepTrailingSlash = true) {
export default { export default {
NewJob: { NewJob: {
position: inHTMLData, position: ifDefinedNormalize(inHTMLData),
locale: inHTMLData, locale: ifDefinedNormalize(inHTMLData),
description: inHTMLData, description: ifDefinedNormalize(inHTMLData),
email: inHTMLData, email: ifDefinedNormalize(inHTMLData),
url: value => formatUrl(uriInSingleQuotedAttr(value)), url: ifDefinedNormalize(value => formatUrl(uriInSingleQuotedAttr(value))),
logo: value => formatUrl(uriInSingleQuotedAttr(value)), logo: ifDefinedNormalize(value => formatUrl(uriInSingleQuotedAttr(value))),
company: inHTMLData, company: ifDefinedNormalize(inHTMLData),
howToApply: inHTMLData howToApply: ifDefinedNormalize(inHTMLData)
} }
}; };

View File

@ -4,6 +4,7 @@ const types = [
'findJob', 'findJob',
'saveJob', 'saveJob',
'saveJobCompleted',
'saveForm', 'saveForm',
'clearForm', 'clearForm',

View File

@ -32,7 +32,7 @@ export default stampit({
}); });
}, },
createService$({ service: resource, params, body, config }) { createService$({ service: resource, params, body, config }) {
return Observable.create(function(observer) { return Observable.create(observer => {
this.services.create( this.services.create(
resource, resource,
params, params,