Skip to content
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

major(core): remove default exchanges #3033

Merged
merged 12 commits into from
Mar 16, 2023
18 changes: 18 additions & 0 deletions .changeset/calm-buckets-scream.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
---
'@urql/core': major
---

Remove `defaultExchanges` from `@urql/core` and make `exchanges` a required property on `Client` construction.
In doing so we make the `urql` package more tree-shakeable as the three default exchanges are in no code paths
meaning they can be removed if not used.

A migration would look as follows if you are currently creating a client without exchanges

```js
import { createClient, cacheExchange, fetchExchange } from '@urql/core'

const client = createClient({
url: '',
exchanges: [cacheExchange, fetchExchange]
});
```
6 changes: 6 additions & 0 deletions .changeset/honest-apples-join.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
'@urql/preact': major
'urql': major
---

Remove the default `Client` from `Context`. Previously, `urql` kept a legacy default client in its context, with default exchanges and calling an API at `/graphql`. This has now been removed and you will have to create your own `Client` if you were relying on this behaviour.
1 change: 0 additions & 1 deletion docs/advanced/authoring-exchanges.md
Original file line number Diff line number Diff line change
Expand Up @@ -283,7 +283,6 @@ The default order of exchanges is:
```js
import { dedupExchange, cacheExchange, fetchExchange } from 'urql';

// Also exported as `defaultExchanges`:
[dedupExchange, cacheExchange, fetchExchange];
```

Expand Down
18 changes: 12 additions & 6 deletions docs/advanced/subscriptions.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,14 @@ APIs and ability to handle GraphQL subscriptions.
To add support for subscriptions we need to add the `subscriptionExchange` to our `Client`.

```js
import { Client, defaultExchanges, subscriptionExchange } from 'urql';
import { Client, dedupExchange, cacheExchange, fetchExchange, subscriptionExchange } from 'urql';

const client = new Client({
url: 'http://localhost:3000/graphql',
exchanges: [
...defaultExchanges,
dedupExchange,
cacheExchange,
fetchExchange,
subscriptionExchange({
forwardSubscription,
}),
Expand All @@ -45,7 +47,7 @@ object with a `.subscribe()` method accepting an observer.
For backends supporting `graphql-ws`, we recommend using the [graphql-ws](https://github.com/enisdenjo/graphql-ws) client.

```js
import { createClient, defaultExchanges, subscriptionExchange } from 'urql';
import { createClient, dedupExchange, cacheExchange, fetchExchange, subscriptionExchange } from 'urql';
import { createClient as createWSClient } from 'graphql-ws';

const wsClient = createWSClient({
Expand All @@ -55,7 +57,9 @@ const wsClient = createWSClient({
const client = createClient({
url: '/graphql',
exchanges: [
...defaultExchanges,
dedupExchange,
cacheExchange,
fetchExchange,
subscriptionExchange({
forwardSubscription: (operation) => ({
subscribe: (sink) => ({
Expand Down Expand Up @@ -84,15 +88,17 @@ package](https://github.com/apollographql/subscriptions-transport-ws) can be use
> The `subscriptions-transport-ws` package isn't actively maintained. If your API supports the new protocol or you can swap the package out, consider using [`graphql-ws`](#setting-up-graphql-ws) instead.

```js
import { Client, defaultExchanges, subscriptionExchange } from 'urql';
import { Client, dedupExchange, cacheExchange, fetchExchange, subscriptionExchange } from 'urql';
import { SubscriptionClient } from 'subscriptions-transport-ws';

const subscriptionClient = new SubscriptionClient('ws://localhost/graphql', { reconnect: true });

const client = new Client({
url: '/graphql',
exchanges: [
...defaultExchanges,
dedupExchange,
cacheExchange,
fetchExchange,
subscriptionExchange({
forwardSubscription: (operation) => subscriptionClient.request(operation)
}),
Expand Down
11 changes: 1 addition & 10 deletions docs/api/core.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ It accepts several options on creation.

| Input | Type | Description |
| ----------------- | ------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `exchanges` | `Exchange[]` | An array of `Exchange`s that the client should use instead of the list of `defaultExchanges` |
| `exchanges` | `Exchange[]` | An array of `Exchange`s that the client should use |
| `url` | `string` | The GraphQL API URL as used by `fetchExchange` |
| `fetchOptions` | `RequestInit \| () => RequestInit` | Additional `fetchOptions` that `fetch` in `fetchExchange` should use to make a request |
| `fetch` | `typeof fetch` | An alternative implementation of `fetch` that will be used by the `fetchExchange` instead of `window.fetch` |
Expand Down Expand Up @@ -523,15 +523,6 @@ this problem.

It's used by the [`Client`](#client) when the `maskTypename` option is enabled.

### defaultExchanges

This is an array of the default `Exchange`s that the `Client` uses when the `exchanges` option isn't
passed.

```js
const defaultExchanges = [dedupExchange, cacheExchange, fetchExchange];
```

### composeExchanges

This utility accepts an array of `Exchange`s and composes them into a single one.
Expand Down
3 changes: 2 additions & 1 deletion docs/architecture.md
Original file line number Diff line number Diff line change
Expand Up @@ -45,11 +45,12 @@ Whenever we decide to send a request to our API we start by using `urql`'s
extra information on how the GraphQL requests are executed.

```js
import { Client } from '@urql/core';
import { Client, dedupExchange, cacheExchange, fetchExchange } from '@urql/core';

new Client({
url: 'http://localhost:3000/graphql',
requestPolicy: 'cache-first',
exchanges: [dedupExchange, cacheExchange, fetchExchange]
});
```

Expand Down
12 changes: 5 additions & 7 deletions docs/basics/core.md
Original file line number Diff line number Diff line change
Expand Up @@ -134,10 +134,11 @@ The `@urql/core` package exports a function called `createClient` which we can u
create the GraphQL client. This central `Client` manages all of our GraphQL requests and results.

```js
import { createClient } from '@urql/core';
import { createClient, dedupExchange, cacheExchange, fetchExchange } from '@urql/core';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});
```

Expand All @@ -153,6 +154,7 @@ GraphQL API.
```js
const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
fetchOptions: () => {
const token = getToken();
return {
Expand All @@ -168,17 +170,13 @@ As we've seen above, the most important option for the `Client` is `url`, since
without it. However, another important option on the `Client` is the `exchanges` option.

This option passes a list of exchanges to the `Client`, which tell it how to execute our requests
and how to cache data in a certain order. By default, this will be populated with the list of
`defaultExchanges`.
and how to cache data in a certain order.

```js
import { createClient, defaultExchanges } from '@urql/core';
import { createClient, dedupExchange, cacheExchange, fetchExchange } from '@urql/core';

const client = createClient({
url: 'http://localhost:3000/graphql',
// the default:
exchanges: defaultExchanges,
// the same as:
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});
```
Expand Down
8 changes: 6 additions & 2 deletions docs/basics/react-preact.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,10 +41,11 @@ The `urql` and `@urql/preact` packages export a method called `createClient` whi
create the GraphQL client. This central `Client` manages all of our GraphQL requests and results.

```js
import { createClient } from 'urql';
import { createClient, dedupExchange, cacheExchange, fetchExchange } from 'urql';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});
```

Expand All @@ -60,6 +61,7 @@ GraphQL API.
```js
const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
fetchOptions: () => {
const token = getToken();
return {
Expand All @@ -76,10 +78,11 @@ To make use of the `Client` in React & Preact we will have to provide it via the
the `Provider` export.

```jsx
import { createClient, Provider } from 'urql';
import { createClient, Provider, dedupExchange, cacheExchange, fetchExchange } from 'urql';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});

const App = () => (
Expand Down Expand Up @@ -245,6 +248,7 @@ import { createClient } from 'urql';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
// every operation will by default use cache-and-network rather
// than cache-first now:
requestPolicy: 'cache-and-network',
Expand Down
8 changes: 6 additions & 2 deletions docs/basics/svelte.md
Original file line number Diff line number Diff line change
Expand Up @@ -48,10 +48,11 @@ The `@urql/svelte` package exports a method called `createClient` which we can u
the GraphQL client. This central `Client` manages all of our GraphQL requests and results.

```js
import { createClient } from '@urql/svelte';
import { createClient, dedupExchange, cacheExchange, fetchExchange } from '@urql/svelte';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});
```

Expand All @@ -67,6 +68,7 @@ GraphQL API.
```js
const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
fetchOptions: () => {
const token = getToken();
return {
Expand All @@ -85,10 +87,11 @@ components. This will share one `Client` with the rest of our app, if we for ins

```html
<script>
import { createClient, setContextClient } from '@urql/svelte';
import { createClient, setContextClient, dedupExchange, cacheExchange, fetchExchange } from '@urql/svelte';
const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});
setContextClient(client);
Expand Down Expand Up @@ -292,6 +295,7 @@ import { createClient } from '@urql/svelte';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
// every operation will by default use cache-and-network rather
// than cache-first now:
requestPolicy: 'cache-and-network',
Expand Down
10 changes: 7 additions & 3 deletions docs/basics/vue.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,10 +37,11 @@ The `@urql/vue` package exports a method called `createClient` which we can use
the GraphQL client. This central `Client` manages all of our GraphQL requests and results.

```js
import { createClient } from '@urql/vue';
import { createClient, dedupExchange, cacheExchange, fetchExchange } from '@urql/vue';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});
```

Expand All @@ -56,6 +57,7 @@ GraphQL API.
```js
const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
fetchOptions: () => {
const token = getToken();
return {
Expand All @@ -77,10 +79,11 @@ your parent components and accepts either a `Client` directly or just the option

```html
<script>
import { createClient, provideClient } from '@urql/vue';
import { createClient, provideClient, dedupExchange, cacheExchange, fetchExchange } from '@urql/vue';
const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
});
provideClient(client);
Expand Down Expand Up @@ -361,10 +364,11 @@ provides metadata apart from the usual `query` and `variables` we may pass. This
we may also change the `Client`'s default `requestPolicy` by passing it there.

```js
import { createClient } from '@urql/vue';
import { createClient, dedupExchange, cacheExchange, fetchExchange } from '@urql/vue';

const client = createClient({
url: 'http://localhost:3000/graphql',
exchanges: [dedupExchange, cacheExchange, fetchExchange],
// every operation will by default use cache-and-network rather
// than cache-first now:
requestPolicy: 'cache-and-network',
Expand Down
5 changes: 4 additions & 1 deletion exchanges/auth/src/authExchange.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,10 @@ const makeExchangeArgs = () => {
tap(op => operations.push(op)),
map(result)
),
client: new Client({ url: '/api' }),
client: new Client({
url: '/api',
exchanges: [],
}),
} as any,
};
};
Expand Down
5 changes: 4 additions & 1 deletion exchanges/context/src/context.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,10 @@ const queryOneData = {
const dispatchDebug = vi.fn();
let client, op, ops$, next;
beforeEach(() => {
client = createClient({ url: 'http://0.0.0.0' });
client = createClient({
url: 'http://0.0.0.0',
exchanges: [],
});
op = client.createRequestOperation('query', {
key: 1,
query: queryOne,
Expand Down
6 changes: 4 additions & 2 deletions exchanges/graphcache/src/ast/schemaPredicates.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,10 @@ import { minifyIntrospectionQuery } from '@urql/introspection';
const mocked = (x: any): any => x;

describe('SchemaPredicates', () => {
// eslint-disable-next-line
const schema = buildClientSchema(minifyIntrospectionQuery(require('../test-utils/simple_schema.json')));
const schema = buildClientSchema(
// eslint-disable-next-line
minifyIntrospectionQuery(require('../test-utils/simple_schema.json'))
);

const frag = (value: string): InlineFragmentNode => ({
kind: Kind.INLINE_FRAGMENT,
Expand Down
Loading