useMutationって何やってんの？ 型から追うuseMutationの挙動・オプション・引数

# 概要
`useMutation`って何やってんのか気になったから調査
まずは何を返すかを知りたかったため、型だけ追ってみる
（なぜかって、いろんなファイルやリポジトリ追うから、中身と型どっちも追うと疲れちゃうから）

# 結論

- 返り値：以下2つの要素の配列を返却
    - `Promise<FetchResult<TData>>`を返却する関数 = graphql通信する関数
    - `MutationResult<TData>` = `data`とか`loading`とかapolloあるあるな値
- 引数
    - クエリ
        - ここは調べてないですが、チュートリアルとかでクエリを入れている引数だったのでこのように記述。追うのが複雑そうだったのとクエリ以上の情報が得られそうでなかったため調査割愛
    - `refetchQueries`や`fetchPolicy`など`<Mutation>`とかに使えるオプション


# 調査
https://github.com/apollographql/apollo-client/blob/c2698e5fdbd109a4765ce269d345b20cfccc0ec9/src/react/hooks/useMutation.ts

```src/react/hooks/useMutation.ts
export function useMutation<TData = any, TVariables = OperationVariables>(
  mutation: DocumentNode,
  options?: MutationHookOptions<TData, TVariables>
): MutationTuple<TData, TVariables> {
  ...
  return mutationData.execute(result);
}
```

わかったこと

- 返り値（結局何ができるの？）
    - `useMutation`はなんやかんややって`MutationTuple<TData, TVariables>`型の値を返す
        - →`MutationTuple`って何や
- 引数（どんな柔軟性があるの？）
    - `DocumentNode`ってクエリを受け取れる（なんの不思議もない）
    - `MutationHookOptions`というオプションを受け取れる
        - →`MutationHookOptions`って何や

## 返り値
### 返り値の型`MutationTuple`
https://github.com/apollographql/apollo-client/blob/c2698e5fdbd109a4765ce269d345b20cfccc0ec9/src/react/types/types.ts#L214

```src/react/types/types.ts
export type MutationTuple<TData, TVariables> = [
  (
    options?: MutationFunctionOptions<TData, TVariables>
  ) => Promise<FetchResult<TData>>,
  MutationResult<TData>
];
```

気になること

- `FetchResult<TData>`
- `MutationResult<TData>`

## `FetchResult`
https://github.com/apollographql/apollo-client/blob/c2698e5fdbd109a4765ce269d345b20cfccc0ec9/src/react/types/types.ts#L5

```src/react/types/types.ts
import { FetchResult } from '../../link/core/types';
```

https://github.com/apollographql/apollo-client/blob/c2698e5fdbd109a4765ce269d345b20cfccc0ec9/src/link/core/types.ts#L24

```src/link/core/types.ts
export interface FetchResult<
  TData = { [key: string]: any },
  C = Record<string, any>,
  E = Record<string, any>
> extends ExecutionResult {
  data?: TData | null;
  extensions?: E;
  context?: C;
};
```

### `ExecutionResult`
https://github.com/graphql/graphql-js/blob/master/src/execution/execute.js#L114

```src/execution/execute.js
export type ExecutionResult = {|
  errors?: $ReadOnlyArray<GraphQLError>,
  data?: ObjMap<mixed> | null,
  extensions?: ObjMap<mixed>,
|};
```

データやエラーの詰め場所。それも`FetchResult`でオーバーライドしてるやつばっかだから、調査はここで終わり

## `MutationResult`
https://github.com/apollographql/apollo-client/blob/c2698e5fdbd109a4765ce269d345b20cfccc0ec9/src/react/types/types.ts#L187

```src/react/types/types.ts
export interface MutationResult<TData = any> {
  data?: TData | null;
  error?: ApolloError;
  loading: boolean;
  called: boolean;
  client?: ApolloClient<object>;
}

```

よく使う`data`とか`loading`ってここに書いてあったんだ！

## 引数
### 引数で指定できるオプション`MutationHookOptions
`https://github.com/apollographql/apollo-client/blob/c2698e5fdbd109a4765ce269d345b20cfccc0ec9/src/react/types/types.ts#L202

``` src/react/types/types.ts
export interface MutationHookOptions<
  TData = any,
  TVariables = OperationVariables
> extends BaseMutationOptions<TData, TVariables> {
  mutation?: DocumentNode;
}
```

気になること

- `BaseMutationOptions`
- `DocumentNode`

### `BaseMutationOptions`
https://github.com/apollographql/apollo-client/blob/c2698e5fdbd109a4765ce269d345b20cfccc0ec9/src/react/types/types.ts#L155

```src/react/types/types.ts
export interface BaseMutationOptions<
  TData = any,
  TVariables = OperationVariables
> {
  variables?: TVariables;
  optimisticResponse?: TData | ((vars: TVariables) => TData);
  refetchQueries?: Array<string | PureQueryOptions> | RefetchQueriesFunction;
  awaitRefetchQueries?: boolean;
  errorPolicy?: ErrorPolicy;
  update?: MutationUpdaterFn<TData>;
  client?: ApolloClient<object>;
  notifyOnNetworkStatusChange?: boolean;
  context?: Context;
  onCompleted?: (data: TData) => void;
  onError?: (error: ApolloError) => void;
  fetchPolicy?: Extract<WatchQueryFetchPolicy, 'no-cache'>;
  ignoreResults?: boolean;
}
```


### `DocumentNode`

```src/react/types/types.ts
import { DocumentNode } from 'graphql';
```

DocumentNodeを追ってみる
↓
https://github.com/graphql/graphql-js/blob/master/src/index.js
↓
https://github.com/graphql/graphql-js/blob/master/src/language/ast.js#L248

```src/language/ast.js
export type DocumentNode = {|
  +kind: 'Document',
  +loc?: Location,
  +definitions: $ReadOnlyArray<DefinitionNode>,
|};
```