

翻訳は機械翻訳により提供されています。提供された翻訳内容と英語版の間で齟齬、不一致または矛盾がある場合、英語版が優先します。

# でのリアルタイムデータアプリケーションのサブスクリプションの使用 AWS AppSync
<a name="aws-appsync-real-time-data"></a>

**重要**  
2025 年 3 月 13 日以降、 AWS AppSync Events を使用して WebSockets を搭載したリアルタイム PubSub API を構築できます。詳細については、「*AWS AppSync Events デベロッパーガイド*」の「[WebSocket 経由でイベントを公開する](https://docs.aws.amazon.com/appsync/latest/eventapi/publish-websocket.html)」を参照してください。

AWS AppSync では、サブスクリプションを利用して、ライブアプリケーションの更新、プッシュ通知などを実装できます。クライアントが GraphQL サブスクリプションオペレーションを呼び出すと、 AWS AppSync によって安全な WebSocket 接続が自動的に確立され、維持されます。その後、アプリケーションはデータソースからサブスクライバーにデータをリアルタイムで配信でき、 AWS AppSync はアプリケーションの接続とスケーリング要件を継続的に管理します。以下のセクションでは、 AWS AppSync のサブスクリプションの仕組みを示します。

## GraphQL スキーマサブスクリプションディレクティブ
<a name="graphql-schema-subscription-directives"></a>

 AWS AppSync のサブスクリプションは、ミューテーションへの応答として呼び出されます。つまり、ミューテーションに GraphQL スキーマディレクティブを指定することで、 AWS AppSync のデータソースをリアルタイムで作成できます。

 AWS Amplify クライアントライブラリは、サブスクリプション接続管理を自動的に処理します。ライブラリは純粋な WebSockets をクライアントとサービス間のネットワークプロトコルとして使用します。

**注記**  
サブスクリプションへの接続時に認可を制御するには、 AWS Identity and Access Management (IAM) AWS Lambda、、Amazon Cognito ID プール、または Amazon Cognito ユーザープールを使用して、フィールドレベルの認可を行うことができます。サブスクリプションのきめ細かなアクセスコントロールの場合、リゾルバーをサブスクリプションフィールドにアタッチし、発信者と AWS AppSync データソースの ID を使用してロジックを実行できます。詳細については、「[GraphQL API を保護するための認可と認証の設定](security-authz.md)」を参照してください。

サブスクリプションはミューテーションからトリガーされ、ミューテーション選択セットが受信者に送信されます。

次の例では、GraphQL サブスクリプションの操作方法を示します。データソースを指定しません。これは、データソースが 、Amazon DynamoDB、または Amazon OpenSearch Service のいずれかであるからです。

サブスクリプションを開始するには、次のようにスキーマにサブスクリプションのエントリポイントを追加します。

```
schema {
    query: Query
    mutation: Mutation
    subscription: Subscription
}
```

ブログ投稿サイトを持っており、新しいブログにサブスクライブし、既存のブログに変わるものとします。これを行うには、スキーマに次の `Subscription` 定義を追加します。

```
type Subscription {
    addedPost: Post
    updatedPost: Post
    deletedPost: Post
}
```

さらに、次のミューテーションがあるとします。

```
type Mutation {
    addPost(id: ID! author: String! title: String content: String url: String): Post!
    updatePost(id: ID! author: String! title: String content: String url: String ups: Int! downs: Int! expectedVersion: Int!): Post!
    deletePost(id: ID!): Post!
}
```

通知を受け取る各サブスクリプションに `@aws_subscribe(mutations: ["mutation_field_1", "mutation_field_2"])` ディレクティブを追加することで、これらのフィールドをリアルタイム対応にできます。手順は以下のとおりです。

```
type Subscription {
    addedPost: Post
    @aws_subscribe(mutations: ["addPost"])
    updatedPost: Post
    @aws_subscribe(mutations: ["updatePost"])
    deletedPost: Post
    @aws_subscribe(mutations: ["deletePost"])
}
```

`@aws_subscribe(mutations: ["",..,""])` は、ミューテーション入力の配列を受け取るため、サブスクリプションを開始する複数のミューテーションを指定できます。クライアントからサブスクライブする場合、GraphQL クエリは次のようになります。

```
subscription NewPostSub {
    addedPost {
        __typename
        version
        title
        content
        author
        url
    }
}
```

このサブスクリプションクエリは、クライアント接続とツールに必要です。

ピュアな WebSocket クライアントを使用する場合、各クライアントが独自の選択セットを定義できるため、選択セットのフィルタリングはクライアントごとに行われます。この場合、サブスクリプション選択セットは、ミューテーション選択セットのサブセットである必要があります。例えば、サブスクリプションが `addedPost{author title}` ミューテーションにリンクされていると、`addPost(...){id author title url version}` 投稿の作成者とタイトルのみを受け取ります。他のフィールドは受け取りません。ただし、ミューテーションの選択セットに作成者が欠けていた場合、サブスクライバーは作成者フィールドに対して `null` 値を取得します (または、スキーマ内で作成者フィールドが required/not-null と定義されている場合はエラー)。

ピュアな WebSockets を使用する場合は、サブスクリプション選択セットが不可欠です。サブスクリプションでフィールドが明示的に定義されていない場合、 AWS AppSync は フィールドを返しません。

前の例では、サブスクリプションに引数はありませんでした。次のようなスキーマがあるとします。

```
type Subscription {
    updatedPost(id:ID! author:String): Post
    @aws_subscribe(mutations: ["updatePost"])
}
```

この場合、クライアントでサブスクリプションが次のように定義されます。

```
subscription UpdatedPostSub {
    updatedPost(id:"XYZ", author:"ABC") {
        title
        content
    }
}
```

スキーマの `subscription` フィールドの戻り値の型は、対応する mutation フィールドの戻り値の型に一致する必要があります。前の例では、これが `addPost` と `addedPost` の両方が `Post` タイプとして返され、表示されます。

クライアントでサブスクリプションをセットアップするには、「[Amplify クライアントを使用したクライアントアプリケーションの構築](building-a-client-app.md)」を参照してください。

## サブスクリプション引数の使用
<a name="using-subscription-arguments"></a>

GraphQL サブスクリプションを使用する上で重要なのは、引数をいつ、どのように使うかを理解することです。微妙な変更を加えることで、発生したミューテーションをクライアントに通知する方法とタイミングを変更できます。そのためには、クイックスタートの章にある「Todos」を作成するサンプルスキーマを参照してください。このサンプルスキーマでは、以下のミューテーションが定義されます。

```
type Mutation {
    createTodo(input: CreateTodoInput!): Todo
    updateTodo(input: UpdateTodoInput!): Todo
    deleteTodo(input: DeleteTodoInput!): Todo
}
```

デフォルトのサンプルでは、クライアントは引数なしで `onUpdateTodo` `subscription` を使うことで、任意の `Todo` への更新を購読できます。

```
subscription OnUpdateTodo {
  onUpdateTodo {
    description
    id
    name
    when
  }
}
```

引数を使用して `subscription` をフィルタリングできます。例えば、特定の `ID` を含む `todo` が更新された場合に `subscription` のみをトリガーするには、`ID` 値を指定します。

```
subscription OnUpdateTodo {
  onUpdateTodo(id: "{{a-todo-id}}") {
    description
    id
    name
    when
  }
}
```

複数の引数を渡すこともできます。例えば、次の `subscription` は、特定の場所と時間に `Todo` 更新があった場合に通知を受ける方法を示しています。

```
subscription todosAtHome {
  onUpdateTodo(when: "tomorrow", where: "at home") {
    description
    id
    name
    when
    where
  }
}
```

引数はすべてオプションであることに注意してください。`subscription` で引数を指定しない場合、アプリケーションで発生するすべての `Todo` 更新を購読することになります。ただし、`subscription` のフィールド定義を更新して `ID` 引数を必須にすることはできます。これにより、すべての `todo` の代わりに、特定の `todo` への応答が強制されます。

```
onUpdateTodo(
  id: ID!,
  name: String,
  when: String,
  where: String,
  description: String
): Todo
```

### 引数値 null には意味があります。
<a name="argument-null-value-has-meaning"></a>

 AWS AppSync でサブスクリプションクエリを作成する場合、`null`引数の値は引数を完全に省略するのとは異なる方法で結果をフィルタリングします。

todo を作成できる todos API サンプルに戻りましょう。クイックスタートの章にあるサンプルスキーマを参照してください。

スキーマを変更して、所有者が誰であるかを記述する新しい `owner` フィールドを `Todo` タイプに追加してみましょう。`owner` フィールドは必須ではなく、`UpdateTodoInput` に設定することしかできません。スキーマの次の簡略版を参照してください。

```
type Todo {
  id: ID!
  name: String!
  when: String!
  where: String!
  description: String!
  owner: String
}

input CreateTodoInput {
  name: String!
  when: String!
  where: String!
  description: String!
}

input UpdateTodoInput {
  id: ID!
  name: String
  when: String
  where: String
  description: String
  owner: String
}

type Subscription {
    onUpdateTodo(
        id: ID,
        name: String,
        when: String,
        where: String,
        description: String
    ): Todo @aws_subscribe(mutations: ["updateTodo"])
}
```

次のサブスクリプションはすべての `Todo` 更新を返します。

```
subscription MySubscription {
  onUpdateTodo {
    description
    id
    name
    when
    where
  }
}
```

前のサブスクリプションを変更してフィールド引数 `owner: null` を追加すると、別の質問をすることになります。これで、所有者が指定されていないすべての `Todo` 更新について通知を受けることができるように、このサブスクリプションによってクライアントが登録されるようになりました。

```
subscription MySubscription {
  onUpdateTodo(owner: null) {
    description
    id
    name
    when
    where
  }
}
```

**注記**  
**2022 年 1 月 1 日現在、MQTT over WebSockets は API の GraphQL サブスクリプションのプロトコルとして利用できなくなりました。 AWS AppSync APIs Pure WebSockets は、 でサポートされている唯一のプロトコルです AWS AppSync。**  
2019 年 11 月以降にリリースされた AWS AppSync SDK または Amplify ライブラリに基づくクライアントは、デフォルトで純粋な WebSocketsを自動的に使用します。クライアントを最新バージョンにアップグレードすると、 AWS AppSyncクライアントは純粋な WebSockets エンジンを使用できます。  
純粋な WebSockets には、より大きなペイロードサイズ (240KB)、幅広いクライアントオプション、改善された CloudWatch メトリックスが付属しています。純粋な WebSocket クライアントを使用する方法の詳細については、「[ AWS AppSync でのリアルタイム WebSocket クライアントの構築](real-time-websocket-client.md)」を参照してください。