Issue submitting data from a form with Meteor / Apollo / React!

Hi all,

I’m having issues with a form submission. I’ve looked at both Learn Apollo and the Apollo docs themselves so I think I’m doing this right (well, mostly) but it just won’t work for me! Here’s my component:

import React from 'react';
import Helmet from 'react-helmet';
import { Editor, EditorState, RichUtils } from 'draft-js';
import { graphql } from 'react-apollo';
import gql from 'graphql-tag';

export default class CreateAd extends React.Component {

  constructor( props ) {
    super( props );
    this.state = {
      editorState: EditorState.createEmpty(),
      titleState: ''
    };
    this.onChange = ( editorState ) => this.setState( { editorState } );
    this.handleTitleChange = this.handleTitleChange.bind( this );
  }

  slugify() {
    const title = this.state.titleState;
    return title.toString().toLowerCase()
      .replace(/\s+/g, '-')
      .replace(/[^\w\-]+/g, '')
      .replace(/\-\-+/g, '-')
      .replace(/^-+/, '')
      .replace(/-+$/, '');
  }

  handleTitleChange( event ) {
    this.setState({ titleState: event.target.value });
  }

  formAction( event ) {
    // prevent normal form submission
    event.preventDefault();
    this.props.mutate({ variables: {
      type: 'corporation',
      title: this.state.titleState,
      slug: 'test-slug',
      image: 'https://imageserver.eveonline.com/Corporation/98437545_128.png',
      content: 'Some test content!',
      owner: Meteor.userId()
    } }).then(() => {
      alert( "Successfully submitted!" )
    }).catch( ( error ) => {
      console.log( error );
    });
  }

  render() {
    return (
      <div className="create-ad">

      <div className="cont">
        <h1 className="ttu fw300 f2 lh-title tc">Create Advert</h1>
          <div className="fl w-third pa2">
          </div>
          <div className="fl w-two-thirds pa2">
            <div className="form-container">
              <form onSubmit={ this.formAction.bind( this ) } className="advert-form">
                <div className="input-area">
                  <label htmlFor="adtitle">Advert Title:</label>
                  <input value={ this.state.titleState } onChange={ this.handleTitleChange } type="text" id="adtitle" className="form-input" name="adtitle" placeholder="Eg: Top PVP corporation looking for new pilots" />
                </div>
                <Editor editorState={ this.state.editorState } onChange={ this.onChange } />
                <button type="submit" className="ttu fw300 btn btn-submit">Submit</button>
              </form>
            </div>
          </div>
        </div>
      </div>
    )
  }
}

CreateAd.propTypes = {
  mutate: React.PropTypes.func.isRequired,
};

const submitAdvert = gql`
  mutation createAdvert ( $type: String!, $title: String!, $slug: String!, $image: String!, $content: String!, $owner: String! ) {
    createAdvert( type: $type, title: $title, slug: $slug, image: $image, content: $content, owner: $owner ) {
      type
      title
      slug
      image
      content
      owner
    }
  }
`;

const NewAdvertData = graphql( submitAdvert )( CreateAd );

The issue is with props. The page renders fine with no errors in the console, but when I click submit I get the following error:

Warning: Failed prop type: The prop `mutate` is marked as required in `CreateAd`, but its value is `undefined`.
    in CreateAd (created by RouterContext)
    in RouterContext (created by Router)
    in Router
    in ApolloProvider

I’m not sure whether this is a bug or some error with my code. Here is a basic example on dev.apollodata that I assume works. My own submission isn’t that different!

Any help would be appreciated :slight_smile:

Cheers.

[EDIT] Got rid of some unnecessary code.
[Further EDIT] Renamed post to be more clear about the issue.

You’re exporting the wrong component, you should export the one at the bottom of the file returned from graphql.

As if it was that easy… I’m such a numpty!

Thanks a lot @sashko :thumbsup:

1 Like

No problem! Have fun!

1 Like