New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
GraphQL Mutations #9406
Comments
I am stuck too at trying to use mutation from GatsbyJS version 2. I was excited to get AWS Appsync and Gatsby querying data. This is the next missing puzzle. |
@tommy-dev This is my current workaround if you are interested: const GraphQLClient = require("graphql-request").GraphQLClient;
async mutate(mutationField: string) {
const client = new GraphQLClient(process.env.API_URL, {
headers: {
"x-api-key": process.env.API_KEY
}
});
return await client.request(
`
mutation Mutation($mutationField: String!){
applyMutation(mutationField: $mutationField) {
MutationId
}
}`,
{
mutationField: "abcde"
}
);
}
|
Thanks @juankaram I managed to get mutation to work with AppSync and Dynamodb using Apollo Client. I am pretty new to the graphql world, so a bit curious why you did not go forward with Apollo Client? Example code below for those interested
|
GraphQL only runs at build time and isn't supposed to do Mutations. You can use Apollo Client though, e.g. like the Gatsby store: |
Hello. I succeeded in mutation execution with AppSync with the following code. ( using Typescript ) // client.ts
import AWSAppSyncClient, { AUTH_TYPE } from 'aws-appsync'
import AppSyncConfig from './aws-exports'
const appSyncClientOptions = {
url: AppSyncConfig.graphqlEndpoint,
region: AppSyncConfig.region,
auth: {
type: AUTH_TYPE.API_KEY,
apiKey: AppSyncConfig.apiKey,
// jwtToken: async () => token, // Required when you use Cognito UserPools OR OpenID Connect. token object is obtained previously
},
}
export default new AWSAppSyncClient(appSyncClientOptions) // page/form.tsx
import * as React from 'react'
import Layout from '../components/layout'
import { CreateBlogMutationVariables, CreateBlogMutation } from '../API'
import client from '../client'
import { createBlog } from '../graphql/mutations'
import gql from 'graphql-tag'
interface formProps {
}
interface formState {
headline: string,
content: string,
date: string,
}
class Form extends React.Component< formProps , formState> {
constructor(props:formProps){
super(props)
this.state = {
headline: "",
content: "",
date: this.getDateString()
}
}
getDateString = () => {
const nowDate = new Date()
const dateString = `${nowDate.getFullYear()}-${nowDate.getMonth()+1}-${nowDate.getDate()}`
return dateString
}
handleSubmit = (event: React.FormEvent<HTMLFormElement>) => {
event.preventDefault()
this.asyncTask()
return
}
handleChange = (event: React.ChangeEvent<HTMLInputElement | HTMLTextAreaElement>) => {
const inputId = event.currentTarget.id
const updateState = {
headline: inputId === "headline" ? event.currentTarget.value : this.state.headline,
content: inputId === "content" ? event.currentTarget.value : this.state.content,
}
this.setState(
Object.assign(
this.state,
updateState
)
)
}
async asyncTask(): Promise<void> {
console.log("mutation start")
try {
const response = await client.mutate<CreateBlogMutation, CreateBlogMutationVariables>({
mutation: gql( createBlog ),
variables: {
input: this.state
}
})
} catch (err) {
console.error(err);
} finally {
console.log("mutation end")
}
return
}
render() {
return <Layout>
<form onSubmit={this.handleSubmit} action="/">
<div className="form__headline">
<label htmlFor="headline">title</label>
<input type="text" id="headline" onChange={this.handleChange} />
</div>
<div className="form__content">
<label htmlFor="content">content</label>
<textarea id="content" rows={3} cols={20} style={{resize:"none"}} onChange={this.handleChange} />
</div>
<input type="submit" value="submit"/>
</form>
</Layout>
}
}
export default Form I referred to this site → https://aws-amplify.github.io/docs/js/api#run-a-mutation |
The code I posted works fine in the development environment... Building static HTML for pages/Path/To/Working/Dir/public/render-page.js:9192
var store = disableOffline ? null : store_1.createStore(function () { return _this; }, function () { resolveClient(_this); }, dataIdFromObject, storage, callback);
^
TypeError: resolveClient is not a function
at /Users/Tucker/Desktop/gatsby-site/public/render-page.js:9192:110
at persistCallback (/Users/Tucker/Desktop/gatsby-site/public/render-page.js:12194:13)
at complete (/Users/Tucker/Desktop/gatsby-site/public/render-page.js:51176:19)
at /Users/Tucker/Desktop/gatsby-site/public/render-page.js:51168:11
at complete (/Users/Tucker/Desktop/gatsby-site/public/render-page.js:51035:5)
at /Users/Tucker/Desktop/gatsby-site/public/render-page.js:51009:29
at Immediate.<anonymous> (/Users/Tucker/Desktop/gatsby-site/public/render-page.js:50906:19)
at runCallback (timers.js:697:11)
at tryOnImmediate (timers.js:667:5)
at processImmediate (timers.js:649:5)
at process.topLevelDomainCallback (domain.js:121:23)
error Building static HTML for pages failed
See our docs page on debugging HTML builds for help https://gatsby.app/debug-html
77 | if (typeof window === 'undefined')
78 | library = 'node-fetch';
> 79 | throw new Error("\nfetch is not found globally and no fetcher passed, to fix pass a fetch for\nyour environment like https://www.npmjs.com/package/" + library + ".\n\nFor example:\nimport fetch from '" + library + "';\nimport { createHttpLink } from 'apollo-link-http';\n\nconst link = createHttpLink({ uri: '/graphql', fetch: fetch });");
| ^
80 | }
81 | };
82 | export var createSignalIfSupported = function () {
WebpackError:
- index.js:79 checkFetcher
[lib]/[apollo-link-http-common]/lib/index.js:79:1
- httpLink.js:43 Module.createHttpLink
[lib]/[apollo-link-http]/lib/httpLink.js:43:17
- client.js:125 Object../node_modules/aws-appsync/lib/client.js.exports.createAppSyncLink
[lib]/[aws-appsync]/lib/client.js:125:1
- client.js:184 new AWSAppSyncClient
[lib]/[aws-appsync]/lib/client.js:184:1
- client.ts:19 Module../src/client.ts
lib/src/client.ts:19:16
- bootstrap:19 __webpack_require__
lib/webpack/bootstrap:19:1
- bootstrap:19 __webpack_require__
lib/webpack/bootstrap:19:1
- bootstrap:19 __webpack_require__
lib/webpack/bootstrap:19:1
- sync-requires.js:9 Object../.cache/sync-requires.js
lib/.cache/sync-requires.js:9:55
- bootstrap:19 __webpack_require__
lib/webpack/bootstrap:19:1
- static-entry.js:9 Module../.cache/static-entry.js
lib/.cache/static-entry.js:9:22
- bootstrap:19 __webpack_require__
lib/webpack/bootstrap:19:1
- bootstrap:83
lib/webpack/bootstrap:83:1 I don’t know this error solution at gatsby ... |
@jlengstorf gave a great talk on this exact topic https://m.youtube.com/watch?v=wNUg1jpj9T0&feature=youtu.be Also Dustin's talk https://github.com/DSchau/beyond-static-fitc |
Wow!! fantastic!! I used // client.ts
import AppSyncConfig from './aws-exports'
import ApolloClient from 'apollo-client'
import { createHttpLink } from 'apollo-link-http'
import { setContext } from 'apollo-link-context'
import 'isomorphic-fetch' // Comment out this line results in an error ...
import { InMemoryCache } from 'apollo-cache-inmemory';
const httpLink = createHttpLink({
uri: AppSyncConfig.graphqlEndpoint,
})
const authLink = setContext( (_, { headers } ) => {
return {
headers: {
...headers,
"x-api-key": AppSyncConfig.apiKey
}
}
})
export const client = new ApolloClient({
link: authLink.concat(httpLink),
cache: new InMemoryCache(),
}); // gatsby-ssr.js and gatsby-browser.js
import React from 'react';
import { ApolloProvider } from 'react-apollo';
import { client } from './src/client';
export const wrapRootElement = ({ element }) => (
<ApolloProvider client={client}>
{element}
</ApolloProvider>
); import * as React from 'react'
import Layout from '../components/layout'
import { CreateBlogMutationVariables, CreateBlogMutation } from '../API'
import { createBlog } from '../graphql/mutations'
import gql from 'graphql-tag'
import { Mutation } from 'react-apollo';
interface formProps {
}
interface formState {
headline: string,
content: string,
date: string,
}
class BlogMutation extends Mutation<CreateBlogMutation, CreateBlogMutationVariables> {}
class Form extends React.Component< formProps , formState> {
constructor(props:formProps){
super(props)
this.state = {
headline: "",
content: "",
date: this.getDateString()
}
}
getDateString = () => {
const nowDate = new Date()
const dateString = `${nowDate.getFullYear()}-${nowDate.getMonth()+1}-${nowDate.getDate()}`
return dateString
}
handleSubmit = (event: React.FormEvent<HTMLFormElement>) => {
event.preventDefault()
return
}
handleChange = (event: React.ChangeEvent<HTMLInputElement | HTMLTextAreaElement>) => {
const inputId = event.currentTarget.id
const updateState = {
headline: inputId === "headline" ? event.currentTarget.value : this.state.headline,
content: inputId === "content" ? event.currentTarget.value : this.state.content,
}
this.setState(
Object.assign(
this.state,
updateState
)
)
}
render() {
return <Layout>
<BlogMutation mutation={ gql(createBlog) }>
{( addBlog, { loading, error }) => (
<form
onSubmit={ e => {
this.handleSubmit(e)
addBlog({variables: {input: this.state }})
}}
action="/">
<div className="form__headline">
<label htmlFor="headline">title</label>
<input type="text" id="headline" onChange={this.handleChange} />
</div>
<div className="form__content">
<label htmlFor="content">content</label>
<textarea id="content" rows={3} cols={20} style={{resize:"none"}} onChange={this.handleChange} />
</div>
<input type="submit" value="submit"/>
{loading && <p>loading...</p>}
{error && <p>Erorr: {error.message}</p>}
</form>
)}
</BlogMutation>
</Layout>
}
}
export default Form |
@KyleAMathews Thank you !! |
I cant find any mutation delete,update, subscription example for gatsby-source-firebase-firestore. I can query a post document with five elements . Id, Name, description, date, town. But I have still problem with mutation. |
Summary
Is it possible to run graphql mutations using the Gatsby graphql wrapper?
Relevant information
I did a little reading of the source code and didn't found any pieces that indicate that this is possible, besides going the apollo client route. If is not possible is totally fine, i just want to make sure before i commit to add the apollo client, etc. Also, adding support will be something you would welcome in a pull request? It seems really valuable to be able to send data back to the server in certain cases, and Gatsby does a phenomenal job simplifying this operations.
Just with the objective of understanding more the line that lead me to think that there is no support is:
gatsby/packages/gatsby-source-graphql/src/gatsby-node.js
Line 92 in 27dc8f3
Thank you for your hard work on supporting Gatsby and all the developers that depend on it!
The text was updated successfully, but these errors were encountered: