Skip to content

Commit

Permalink
use underscored props
Browse files Browse the repository at this point in the history
  • Loading branch information
JoviDeCroock committed Jul 19, 2023
1 parent 0c45c9a commit 7148e5f
Show file tree
Hide file tree
Showing 8 changed files with 56 additions and 15 deletions.
31 changes: 30 additions & 1 deletion docs/graphcache/local-directives.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,33 @@
---
title: Local Directives
order: 2
order: 3
---

# Local Directives

Graphcache supports adding directives to GraphQL Documents, when we prefix a
directive with an underscore (`_`) it will be stripped from the document and stored
on the `_directives` property on the AST-node.

> Ensure you prefix directives with `_` if you only want to alter local behavior.
By default graphcache will add two directives `@_optional` and `@_required` which
allow you to mark fields as being optional or mandatory.

If you want to add directives yourself you can do so by performing

```js
cacheExchange({
directives: {
// If you now add `@_pagination` to your document we will execute this
pagination: () => {},
},
});
```

The function signature of a directive is the same as the one of a [Resolver](./local-directives.md). In
case you need to access the arguments you have passed to a directive you can do so by checking `info.directiveArguments`.

### Reading on

[On the next page we'll learn about "Cache Updates".](./cache-updates.md)
2 changes: 1 addition & 1 deletion docs/graphcache/local-resolvers.md
Original file line number Diff line number Diff line change
Expand Up @@ -565,4 +565,4 @@ cannot be stiched together.

### Reading on

[On the next page we'll learn about "Cache Updates".](./cache-updates.md)
[On the next page we'll learn about "Cache Directives".](./local-directives.md)
4 changes: 2 additions & 2 deletions exchanges/graphcache/src/cacheExchange.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -691,7 +691,7 @@ describe('directives', () => {
todos {
id
text
completed @optional
completed @_optional
}
}
`;
Expand Down Expand Up @@ -763,7 +763,7 @@ describe('directives', () => {
todos {
id
text
completed @required
completed @_required
}
}
`;
Expand Down
1 change: 0 additions & 1 deletion exchanges/graphcache/src/cacheExchange.ts
Original file line number Diff line number Diff line change
Expand Up @@ -237,7 +237,6 @@ export const cacheExchange =
operations.set(operation.key, operation);
updateDependencies(operation, result.dependencies);

// TODO: remove directives before sending it on
return {
outcome: cacheOutcome,
operation,
Expand Down
2 changes: 1 addition & 1 deletion exchanges/graphcache/src/extras/relayPagination.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1542,7 +1542,7 @@ describe('as directive', () => {
const Pagination = gql`
query ($cursor: String) {
__typename
items(first: 1, after: $cursor) @relayPagination {
items(first: 1, after: $cursor) @_relayPagination {
__typename
edges {
__typename
Expand Down
2 changes: 1 addition & 1 deletion exchanges/graphcache/src/extras/simplePagination.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -443,7 +443,7 @@ describe('as directive', () => {
const Pagination = gql`
query ($skip: Number, $limit: Number) {
__typename
persons(skip: $skip, limit: $limit) @simplePagination {
persons(skip: $skip, limit: $limit) @_simplePagination {
__typename
id
name
Expand Down
9 changes: 3 additions & 6 deletions exchanges/graphcache/src/operations/query.ts
Original file line number Diff line number Diff line change
Expand Up @@ -356,8 +356,8 @@ const readSelection = (
let node: FormattedNode<FieldNode> | void;
const output = InMemoryData.makeData(input);
while ((node = iterate()) !== undefined) {
const fieldDirectives = node.directives?.map(x => x.name.value);
const storeDirective = fieldDirectives?.find(x => store.directives[x]);
const fieldDirectives = Object.keys(node._directives || {}).map(x => x);
const storeDirective = fieldDirectives.find(x => store.directives[x]);

// Derive the needed data from our node.
const fieldName = getName(node);
Expand Down Expand Up @@ -415,9 +415,7 @@ const readSelection = (
}

if (storeDirective) {
const fieldDirective = node.directives!.find(
x => x.name.value === storeDirective
)!;
const fieldDirective = node._directives![storeDirective];
const directiveArguments =
getFieldArguments(fieldDirective, ctx.variables) || {};
dataFieldValue = store.directives[storeDirective]!(
Expand Down Expand Up @@ -448,7 +446,6 @@ const readSelection = (
if (
store.schema &&
dataFieldValue === null &&
// TODO: how would we inform this that we are indeed dealing with a nullable field
!isFieldNullable(store.schema, typename, fieldName)
) {
// Special case for when null is not a valid value for the
Expand Down
20 changes: 18 additions & 2 deletions exchanges/graphcache/src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -555,7 +555,14 @@ export type CacheExchangeOpts = {
* @see {@link https://urql.dev/goto/docs/graphcache/local-resolvers} for the full resolvers docs.
*/
resolvers?: ResolverConfig;
// TODO: docs
/** Configures directives which can perform custom logic on fields.
*
* @remarks
* `directives` is a map of a directive-name to a function which will be executed
* when graphcache encounters this directive.
*
* @see {@link https://urql.dev/goto/docs/graphcache/local-directives} for the full directives docs.
*/
directives?: DirectivesConfig;
/** Configures optimistic updates to react to mutations instantly before an API response.
*
Expand Down Expand Up @@ -678,6 +685,16 @@ export type Resolver<
): Result;
}['bivarianceHack'];

/** Cache Directive, which may resolve or replace data during cache reads.
*
* @param parent - The GraphQL object that is currently being constructed from cache data.
* @param args - This field’s arguments.
* @param cache - {@link Cache} interface.
* @param info - {@link ResolveInfo} interface.
* @returns a {@link ResolverResult}, which is an updated value, partial entity, or entity key
*
* @see {@link https://urql.dev/goto/docs/graphcache/local-directives} for the full directives docs.
*/
export type Directive<
ParentData = DataFields,
Args = Variables,
Expand Down Expand Up @@ -708,7 +725,6 @@ export type ResolverConfig = {
} | void;
};

// TODO: docs
export type DirectivesConfig = {
[directiveName: string]: Directive;
};
Expand Down

0 comments on commit 7148e5f

Please sign in to comment.