Skip to content

Commit

Permalink
More minor doc fixes
Browse files Browse the repository at this point in the history
  • Loading branch information
cfilby committed Oct 16, 2019
1 parent 7abf0ac commit 9f4df68
Show file tree
Hide file tree
Showing 4 changed files with 62 additions and 48 deletions.
33 changes: 19 additions & 14 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@

[gqlgen](https://github.com/99designs/gqlgen) is a Go library for building GraphQL servers without any fuss. gqlgen is:

- **Schema first** — Define your API using the GraphQL [Schema Definition Language](http://graphql.org/learn/schema/).
- **Type safe** — You should never see `map[string]interface{}` here.
- **Codegen** — Let us generate the boring bits, so you can build your app quickly.
- **Schema first** — Define your API using the GraphQL [Schema Definition Language](http://graphql.org/learn/schema/).
- **Type safe** — You should never see `map[string]interface{}` here.
- **Codegen** — Let us generate the boring bits, so you can build your app quickly.

[Feature Comparison](https://gqlgen.com/feature-comparison/)

Expand All @@ -29,20 +29,22 @@ Read our [Contribution Guidelines](https://github.com/99designs/gqlgen/blob/mast
### How do I prevent fetching child objects that might not be used?

When you have nested or recursive schema like this:

```graphql
type User {
id: ID!
name: String!
friends: [User!]!
id: ID!
name: String!
friends: [User!]!
}
```

You need to tell gqlgen that we should only fetch friends if the user requested it. There are two ways to do this.

1. Write the model yourself and leave off friends.

```go
type User struct {
Id int
ID int
Name string
}
```
Expand All @@ -66,6 +68,7 @@ models:
```
After doing either of the above and running generate we will need to provide a resolver for friends:
```go
func (r *userResolver) Friends(ctx context.Context, obj *User) ([]*User, error) {
// select * from user where friendid = obj.ID
Expand All @@ -76,23 +79,25 @@ func (r *userResolver) Friends(ctx context.Context, obj *User) ([]*User, error)
### IDs are strings but I like ints, why cant I have ints?

You can by remapping it in config:

```yaml
models:
ID: # The GraphQL type ID is backed by
model:
- github.com/99designs/gqlgen/graphql.IntID # An go integer
- github.com/99designs/gqlgen/graphql.ID # or a go string
- github.com/99designs/gqlgen/graphql.IntID # An go integer
- github.com/99designs/gqlgen/graphql.ID # or a go string
```
This means gqlgen will be able to automatically bind to strings or ints for models you have written yourself, but the
first model in this list is used as the default type and it will always be used when:
- generating models based on schema
- as arguments in resolvers
- generating models based on schema
- as arguments in resolvers
There isnt any way around this, gqlgen has no way to know what you want in a given context.
## Other Resources
- [Christopher Biscardi @ Gophercon UK 2018](https://youtu.be/FdURVezcdcw)
- [Introducing gqlgen: a GraphQL Server Generator for Go](https://99designs.com.au/blog/engineering/gqlgen-a-graphql-server-generator-for-go/)
- [Dive into GraphQL by Iván Corrales Solera](https://medium.com/@ivan.corrales.solera/dive-into-graphql-9bfedf22e1a)
- [Christopher Biscardi @ Gophercon UK 2018](https://youtu.be/FdURVezcdcw)
- [Introducing gqlgen: a GraphQL Server Generator for Go](https://99designs.com.au/blog/engineering/gqlgen-a-graphql-server-generator-for-go/)
- [Dive into GraphQL by Iván Corrales Solera](https://medium.com/@ivan.corrales.solera/dive-into-graphql-9bfedf22e1a)
37 changes: 22 additions & 15 deletions docs/content/reference/file-upload.md
Original file line number Diff line number Diff line change
@@ -1,29 +1,32 @@
---
title: 'File Upload'
title: "File Upload"
description: How to upload files.
linkTitle: File Upload
menu: { main: { parent: 'reference' } }
menu: { main: { parent: "reference" } }
---

Graphql server has an already built-in Upload scalar to upload files using a multipart request. \
It implements the following spec https://github.com/jaydenseric/graphql-multipart-request-spec,
that defines an interoperable multipart form field structure for GraphQL requests, used by
various file upload client implementations.
It implements the following spec https://github.com/jaydenseric/graphql-multipart-request-spec,
that defines an interoperable multipart form field structure for GraphQL requests, used by
various file upload client implementations.

To use it you need to add the Upload scalar in your schema, and it will automatically add the
marshalling behaviour to Go types.

# Configuration

There are two specific options that can be configured for uploading files:

- uploadMaxSize \
This option specifies the maximum number of bytes used to parse a request body as multipart/form-data.
This option specifies the maximum number of bytes used to parse a request body as multipart/form-data.
- uploadMaxMemory \
This option specifies the maximum number of bytes used to parse a request body as
multipart/form-data in memory, with the remainder stored on disk in temporary files.
This option specifies the maximum number of bytes used to parse a request body as
multipart/form-data in memory, with the remainder stored on disk in temporary files.

# Examples

## Single file upload

For this use case, the schema could look like this.

```graphql
Expand All @@ -41,7 +44,8 @@ type Mutation {
}
```

cURL can be used the make a query as follows:
cURL can be used the make a query as follows:

```
curl localhost:4000/graphql \
-F operations='{ "query": "mutation ($file: Upload!) { singleUpload(file: $file) { id } }", "variables": { "file": null } }' \
Expand All @@ -50,7 +54,8 @@ curl localhost:4000/graphql \
```
That invokes the following operation:
```
```graphql
{
query: `
mutation($file: Upload!) {
Expand All @@ -66,8 +71,9 @@ That invokes the following operation:
```

## Multiple file upload

For this use case, the schema could look like this.

```graphql
"The `Upload` scalar type represents a multipart file upload."
scalar Upload
Expand Down Expand Up @@ -97,9 +103,9 @@ type Mutation {

```

cURL can be used the make a query as follows:
cURL can be used the make a query as follows:

```
```bash
curl localhost:4000/query \
-F operations='{ "query": "mutation($req: [UploadFile!]!) { multipleUpload(req: $req) { id, name, content } }", "variables": { "req": [ { "id": 1, "file": null }, { "id": 2, "file": null } ] } }' \
-F map='{ "0": ["variables.req.0.file"], "1": ["variables.req.1.file"] }' \
Expand All @@ -108,7 +114,8 @@ curl localhost:4000/query \
```

That invokes the following operation:
```

```graphql
{
query: `
mutation($req: [UploadFile!]!)
Expand All @@ -129,7 +136,7 @@ That invokes the following operation:
id: 2,
File, // c.txt
}
]
]
}
}
```
Expand Down
23 changes: 11 additions & 12 deletions docs/content/reference/plugins.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,14 @@
linkTitle: Plugins
title: How to write plugins for gqlgen
description: Use plugins to customize code generation and integrate with other libraries
menu: { main: { parent: 'reference' } }
menu: { main: { parent: "reference" } }
---

Plugins provide a way to hook into the gqlgen code generation lifecycle. In order to use anything other than the
default plugins you will need to create your own entrypoint:


## Using a plugin

```go
// +build ignore

Expand All @@ -36,7 +36,7 @@ func main() {
}


err = api.Generate(cfg,
err = api.Generate(cfg,
api.AddPlugin(yourplugin.New()), // This is the magic line
)
if err != nil {
Expand All @@ -45,18 +45,17 @@ func main() {
}
}

```
```

## Writing a plugin

There are currently only two hooks:
- MutateConfig: Allows a plugin to mutate the config before codegen starts. This allows plugins to add
custom directives, define types, and implement resolvers. see
[modelgen](https://github.com/99designs/gqlgen/tree/master/plugin/modelgen) for an example
- GenerateCode: Allows a plugin to generate a new output file, see
[stubgen](https://github.com/99designs/gqlgen/tree/master/plugin/stubgen) for an example

Take a look at [plugin.go](https://github.com/99designs/gqlgen/blob/master/plugin/plugin.go) for the full list of
available hooks. These are likely to change with each release.

- MutateConfig: Allows a plugin to mutate the config before codegen starts. This allows plugins to add
custom directives, define types, and implement resolvers. see
[modelgen](https://github.com/99designs/gqlgen/tree/master/plugin/modelgen) for an example
- GenerateCode: Allows a plugin to generate a new output file, see
[stubgen](https://github.com/99designs/gqlgen/tree/master/plugin/stubgen) for an example

Take a look at [plugin.go](https://github.com/99designs/gqlgen/blob/master/plugin/plugin.go) for the full list of
available hooks. These are likely to change with each release.
17 changes: 10 additions & 7 deletions docs/content/reference/scalars.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,12 @@
linkTitle: Scalars
title: Mapping GraphQL scalar types to Go types
description: Mapping GraphQL scalar types to Go types
menu: { main: { parent: 'reference' } }
menu: { main: { parent: "reference" } }
---

## Built-in helpers

gqlgen ships with three built-in helpers for common custom scalar use-cases, `Time`, `Any`, `Upload` and `Map`. Adding any of these to a schema will automatically add the marshalling behaviour to Go types.
gqlgen ships with three built-in helpers for common custom scalar use-cases, `Time`, `Any`, `Upload` and `Map`. Adding any of these to a schema will automatically add the marshalling behaviour to Go types.

### Time

Expand All @@ -32,13 +32,15 @@ scalar Upload
```

Maps a `Upload` GraphQL scalar to a `graphql.Upload` struct, defined as follows:
```

```go
type Upload struct {
File io.Reader
Filename string
Size int64
}
```

### Any

```graphql
Expand All @@ -47,7 +49,7 @@ scalar Any

Maps an arbitrary GraphQL value to a `interface{}` Go type.

## Custom scalars with user defined types
## Custom scalars with user defined types

For user defined types you can implement the graphql.Marshaler and graphql.Unmarshaler interfaces and they will be called.

Expand Down Expand Up @@ -88,13 +90,13 @@ func (y YesNo) MarshalGQL(w io.Writer) {
```

and then in .gqlgen.yml point to the name without the Marshal|Unmarshal in front:

```yaml
models:
YesNo:
model: github.com/me/mypkg.YesNo
```
## Custom scalars with third party types
Sometimes you cant add methods to a type because its in another repo, part of the standard
Expand Down Expand Up @@ -136,11 +138,12 @@ func UnmarshalMyCustomBooleanScalar(v interface{}) (bool, error) {
}
```

and then in .gqlgen.yml point to the name without the Marshal|Unmarshal in front:
Then in .gqlgen.yml point to the name without the Marshal|Unmarshal in front:

```yaml
models:
MyCustomBooleanScalar:
model: github.com/me/mypkg.MyCustomBooleanScalar
```
see the [example/scalars](https://github.com/99designs/gqlgen/tree/master/example/scalars) package for more examples.
See the [example/scalars](https://github.com/99designs/gqlgen/tree/master/example/scalars) package for more examples.

0 comments on commit 9f4df68

Please sign in to comment.