Skip to content

Commit e96be88

Browse files
committed
docs(readme): enhance readme
1 parent f1dc331 commit e96be88

File tree

1 file changed

+115
-12
lines changed

1 file changed

+115
-12
lines changed

README.md

Lines changed: 115 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -17,22 +17,26 @@
1717
npm install fraql graphql graphql-tools graphql-tag
1818
```
1919

20-
FraQL brings component isolation and automocking into your application. You can now build data aware components.
20+
FraQL solves several things:
21+
22+
* ☀️ Isolation: fragments don't rely on name anymore
23+
* ✨ Mocking: generate data & props from fragments
24+
* 🤯 Collocation: put GraphQL in your components
2125

2226
## Example
2327

2428
```js
2529
import gql from 'fraql'
2630

27-
// Create fragment without naming it
31+
// Create fragment without naming it.
2832
const fragment = gql`
2933
fragment _ on Article {
3034
title
3135
description
3236
}
3337
`
3438

35-
// Just use it in your query!
39+
// Just use it in your queries!
3640
const query = gql`
3741
query Articles {
3842
articles {
@@ -45,9 +49,11 @@ const query = gql`
4549

4650
## Motivation
4751

48-
Puting data next to your component is a good practice. It is built-in [Relay](https://facebook.github.io/relay/) and Lee Byron explains the advantages into [his talk about the IDEA architecture](https://www.youtube.com/watch?v=oTcDmnAXZ4E).
52+
Putting data next to your component is a good practice. It is built-in [Relay](https://facebook.github.io/relay/) and Lee Byron explains the advantages into [his talk about the IDEA architecture](https://www.youtube.com/watch?v=oTcDmnAXZ4E).
53+
54+
I tried to do it by myself, but relying on fragment names is not an easy task. FraQL solves this issue by bringing isolation, fragments do not rely on their names.
4955

50-
If you use Apollo or other GraphQL client, it is not an easy task. The goal of FraQL is to make it simple and easy to do in all your applications (React, VueJS...). Since GraphQL is statically typed, FraQL can also generate mock from fragments!
56+
The second problem solved by FraQL is the mocking. Generating a set of data for complex components is a pain. FraQL solves it by generating data right from your fragments!
5157

5258
## Usage with React
5359

@@ -57,7 +63,7 @@ FraQL exports a default tag function that is a drop-in replacement for `graphql-
5763

5864
FraQL is not a framework, but it is recommended create a static property `fragments` on your components that contains a map of properties. For each one, you can specify the associated fragment.
5965

60-
You may have noticed that the fragment use "\_" as name. FraQL transforms your fragment into an inline fragment, the name is just dropped, using "\_" is just a convention.
66+
You may have noticed that the fragment uses "\_" as name. FraQL transforms your fragment into an inline fragment, the name is just dropped, using "\_" is just a convention.
6167

6268
```js
6369
import React from 'react'
@@ -70,6 +76,7 @@ const ArticleCard = ({ article }) => (
7076
</div>
7177
)
7278

79+
// Create a map of fragments and reference them on a static property "fragments"
7380
ArticleCard.fragments = {
7481
article: gql`
7582
fragment _ on Article {
@@ -84,16 +91,17 @@ export default ArticleCard
8491

8592
### Use fragments into your queries
8693

87-
Using a fragment into a query is natural, the only thing to do it to reference it in your query.
94+
With FraQL, using a fragment into a query is natural, the only thing to do it to reference it at the place you want to use it.
8895

89-
You can choose to import `gql` either from `fraql` or from `graphql-tag` since the magic of FraQL happens only when you use it on fragments. Using `fraql` on a query has exactly the same effect as using `graphql-tag`.
96+
Importing `gql` from `fraql` is not require for building query. In this case this is just a pass-throught to `graphql-tag`. The magic behind FraQL only happens when you use it on a fragment.
9097

9198
```js
9299
import React from 'react'
93100
import gql from 'fraql'
94101
import { Query } from 'apollo-client'
95102
import ArticleCard from './ArticleCard'
96103

104+
// Build your query by using your fragment.
97105
const ARTICLES = gql`
98106
query Articles {
99107
articles {
@@ -119,11 +127,13 @@ const ArticleList = ({ articles }) => (
119127
export default ArticleList
120128
```
121129

130+
**[See an example of FraQL + React & Apollo](https://github.com/smooth-code/fraql/tree/master/examples/react)**
131+
122132
## Mocking
123133

124-
It is common to use a tool like [StoryBook](https://github.com/storybooks/storybook) to develop your components in an isolated environment. But it is always complicated to know what data are required by the component.
134+
Tools like [StoryBook](https://github.com/storybooks/storybook) permits you to develop your components into an isolated environment. But you still have to generate a set of data for displaying your components. Maintaining this set of data is a pain.
125135

126-
FraQL solves this by generating your props directly from the fragments.
136+
If all your components have fragments, you get mocking for free!
127137

128138
#### 1. Generate introspection
129139

@@ -132,7 +142,7 @@ Mocking data from a fragment requires to know all schema types. You have to gene
132142
FraQL exposes a method `introspectSchema` to simplify this operation. The only thing you have to do is creating a script that dump your introspection result into a JSON file.
133143

134144
```js
135-
// buildIntrospectionResult.js
145+
// Example of script that generate an introspection result into "schema.json"
136146
const { writeFileSync } = require('fs')
137147
const { introspectSchema } = require('fraql/server')
138148
const schema = require('./myGraphQLSchema') // Your schema defined server-side
@@ -159,6 +169,8 @@ export default createMockerFromIntrospection(introspectionData)
159169

160170
You can now mock fragments using `mockFragment` or `mockFragments` methods.
161171

172+
**Single fragment**
173+
162174
```js
163175
import gql from 'fraql'
164176
import mocker from './mocker'
@@ -183,9 +195,73 @@ const data = mocker.mockFragment(fragment)
183195
// }
184196
```
185197

198+
**Multiple fragments (components)**
199+
200+
```js
201+
import React from 'react'
202+
import gql from 'fraql'
203+
import mocker from './mocker'
204+
import ArticleCard from './ArticleCard'
205+
206+
// Generate all props directly from fragments
207+
const props = mocker.mockFragments(ArticleCard.fragments)
208+
209+
// Create a component using props
210+
const articleCard = <ArticleCard {...props} />
211+
```
212+
213+
**[See an example of mock usage into StoryBook](https://github.com/smooth-code/fraql/tree/master/examples/react)**
214+
186215
## Recipes
187216

188-
### Convert a GraphQL fragment into a FraQL fragment
217+
### Compose fragments
218+
219+
One of the principle of React is component composition. It is recommended to do the same with your GraphQL fragments. FraQL makes it easy:
220+
221+
```js
222+
// ArticleTitle.js
223+
import React from 'react'
224+
import gql from 'fraql'
225+
226+
const ArticleTitle = ({ article }) => <h2>{article.title}</h2>
227+
228+
ArticleTitle.fragments = {
229+
article: gql`
230+
fragment _ on Article {
231+
title
232+
}
233+
`,
234+
}
235+
236+
export default ArticleTitle
237+
```
238+
239+
```js
240+
// ArticleCard.js
241+
import React from 'react'
242+
import gql from 'fraql'
243+
import ArticleTitle from './ArticleTitle'
244+
245+
const ArticleCard = ({ article }) => (
246+
<div>
247+
<ArticleTitle article={article} />
248+
<div>{article.text}</div>
249+
</div>
250+
)
251+
252+
ArticleCard.fragments = {
253+
article: gql`
254+
fragment _ on Article {
255+
${ArticleTitle.fragments.article}
256+
text
257+
}
258+
`,
259+
}
260+
261+
export default ArticleCard
262+
```
263+
264+
### Use without `gql`
189265

190266
FraQL offers a drop-in replacement for `graphql-tag` but sometimes you don't want to use `gql` to define your fragments. As mentioned in [graphql-tag documentation](https://github.com/apollographql/graphql-tag) there is a lot of other ways to do it (using Babel, Webpack, etc..).
191267

@@ -207,6 +283,33 @@ const query = gql`
207283
`
208284
```
209285

286+
### Mix named and inline fragments
287+
288+
Sometimes you may want to have the best of the two world, use a name fragment in one query and a inline fragment in another.
289+
290+
For this specific use-case FraQL exposes the original document:
291+
292+
```js
293+
import gql from 'fraql'
294+
295+
const fragment = gql`
296+
fragment BaseArticleInfos on Article {
297+
title
298+
text
299+
}
300+
`
301+
302+
const query = gql`
303+
query Articles {
304+
articles {
305+
...BaseArticleInfos
306+
}
307+
}
308+
309+
${fragment.originalDocument}
310+
`
311+
```
312+
210313
### Use custom mocks
211314

212315
Mocking feature of FraQL is build on top of [grapql-tools](https://www.apollographql.com/docs/graphql-tools/), it means you can [customize all mocks](https://www.apollographql.com/docs/graphql-tools/mocking.html#Customizing-mocks).

0 commit comments

Comments
 (0)