-
Notifications
You must be signed in to change notification settings - Fork 26
Add a more complex example #24
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
base: master
Are you sure you want to change the base?
Changes from all commits
eaed1bd
ecafd07
a7b92c7
7710a46
a342c2a
d4bebe8
a614736
cdf65d8
fd92641
c881694
fde93d7
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,172 @@ | ||
package main | ||
|
||
import ( | ||
"net/http" | ||
|
||
"github.com/functionalfoundry/graphqlws" | ||
"github.com/graphql-go/graphql" | ||
"github.com/graphql-go/handler" | ||
|
||
log "github.com/sirupsen/logrus" | ||
) | ||
|
||
type document struct { | ||
Title string `json:"title"` | ||
Content string `json:"content"` | ||
} | ||
|
||
var documents = []document{ | ||
{Title: "My diary", Content: "Today I had fun with graphqlws"}, | ||
{Title: "Todo", Content: "Add a complete example"}, | ||
} | ||
|
||
var schema graphql.Schema | ||
var subscriptionManager graphqlws.SubscriptionManager | ||
|
||
func main() { | ||
log.SetLevel(log.InfoLevel) | ||
log.Info("Starting example server on :8085") | ||
|
||
var documentType = graphql.NewObject( | ||
graphql.ObjectConfig{ | ||
Name: "Document", | ||
Fields: graphql.Fields{ | ||
"title": &graphql.Field{ | ||
Type: graphql.String, | ||
}, | ||
"content": &graphql.Field{ | ||
Type: graphql.String, | ||
}, | ||
}, | ||
}, | ||
) | ||
|
||
var queryType = graphql.NewObject( | ||
graphql.ObjectConfig{ | ||
Name: "Query", | ||
Fields: graphql.Fields{ | ||
"document": &graphql.Field{ | ||
Type: documentType, | ||
Args: graphql.FieldConfigArgument{ | ||
"id": &graphql.ArgumentConfig{ | ||
Type: graphql.Int, | ||
}, | ||
}, | ||
Resolve: func(p graphql.ResolveParams) (interface{}, error) { | ||
id := p.Args["id"].(int) | ||
return documents[id], nil | ||
}, | ||
}, | ||
}, | ||
}, | ||
) | ||
|
||
var mutationType = graphql.NewObject( | ||
graphql.ObjectConfig{ | ||
Name: "Mutation", | ||
Fields: graphql.Fields{ | ||
"updateDocument": &graphql.Field{ | ||
Type: documentType, | ||
Args: graphql.FieldConfigArgument{ | ||
"id": &graphql.ArgumentConfig{ | ||
Type: graphql.NewNonNull(graphql.Int), | ||
}, | ||
"title": &graphql.ArgumentConfig{ | ||
Type: graphql.NewNonNull(graphql.String), | ||
}, | ||
"content": &graphql.ArgumentConfig{ | ||
Type: graphql.NewNonNull(graphql.String), | ||
}, | ||
}, | ||
Resolve: func(p graphql.ResolveParams) (interface{}, error) { | ||
id := p.Args["id"].(int) | ||
documents[id].Title = p.Args["title"].(string) | ||
documents[id].Content = p.Args["content"].(string) | ||
|
||
for _, subs := range subscriptionManager.Subscriptions() { | ||
for _, sub := range subs { | ||
// JSON interface is float64 | ||
var subID int = int(sub.Variables["id"].(float64)) | ||
|
||
if id == subID { | ||
params := graphql.Params{ | ||
Schema: schema, | ||
RequestString: sub.Query, | ||
VariableValues: sub.Variables, | ||
OperationName: sub.OperationName, | ||
} | ||
result := graphql.Do(params) | ||
|
||
data := graphqlws.DataMessagePayload{ | ||
Data: result.Data, | ||
Errors: graphqlws.ErrorsFromGraphQLErrors( | ||
result.Errors, | ||
), | ||
} | ||
|
||
sub.SendData(&data) | ||
} | ||
} | ||
} | ||
|
||
return documents[id], nil | ||
}, | ||
}, | ||
}, | ||
}, | ||
) | ||
|
||
var subscriptionType = graphql.NewObject( | ||
graphql.ObjectConfig{ | ||
Name: "Subscription", | ||
Fields: graphql.Fields{ | ||
"documentUpdates": &graphql.Field{ | ||
Type: documentType, | ||
Args: graphql.FieldConfigArgument{ | ||
"id": &graphql.ArgumentConfig{ | ||
Type: graphql.Int, | ||
}, | ||
}, | ||
Resolve: func(p graphql.ResolveParams) (interface{}, error) { | ||
id := p.Args["id"].(int) | ||
return documents[id], nil | ||
}, | ||
}, | ||
}, | ||
}, | ||
) | ||
|
||
schemaConfig := graphql.SchemaConfig{ | ||
Query: queryType, | ||
Mutation: mutationType, | ||
Subscription: subscriptionType, | ||
} | ||
|
||
var err error | ||
schema, err = graphql.NewSchema(schemaConfig) | ||
if err != nil { | ||
log.WithField("err", err).Panic("GraphQL schema is invalid") | ||
} | ||
|
||
subscriptionManager = graphqlws.NewSubscriptionManager(&schema) | ||
websocketHandler := graphqlws.NewHandler(graphqlws.HandlerConfig{ | ||
SubscriptionManager: subscriptionManager, | ||
Authenticate: func(token string) (interface{}, error) { | ||
return "Default user", nil | ||
}, | ||
}) | ||
|
||
graphqlHandler := handler.New(&handler.Config{ | ||
Schema: &schema, | ||
Pretty: true, | ||
GraphiQL: true, | ||
Endpoint: "http://localhost:8085", | ||
SubscriptionsEndpoint: "ws://localhost:8085/subscriptions", | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. In There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You will also need this PR https://github.com/graphql-go/handler/pull/33/files |
||
}) | ||
|
||
http.Handle("/", graphqlHandler) | ||
http.Handle("/subscriptions", websocketHandler) | ||
if err := http.ListenAndServe(":8085", nil); err != nil { | ||
log.WithField("err", err).Error("Failed to start server") | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
schema
is only needed inmain()
, so I'd remove thevar schema graphql.Schema
further towards the top and just do the following here:That way you also don't have to declare
err
as avar
before using it.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
schema
is also used in the mutation resolverThere was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, you're right, sorry. Ignore this comment then. :)