Apps are usually connected via webhooks - one App sends an HTTP request to another App, informing about some event or requesting some action to be performed.
To inform your App about events originated from Saleor, you need to expose a webhook handler, which Saleor will call with POST request.
The App SDK provides a utility that abstracts connection details and auth, allowing developers to focus on business logic.
Depending on the type of the webhook, you can choose one of the classes:
-`SaleorAsyncWebhook`
-`SaleorSyncWebhook`
## Common configuration
Both `SaleorSyncWebhook` and `SaleorAsyncWebhook` contain similar API with little differences.
### Constructing Webhook instance
In Next.js pages create a page, e.g. `pages/api/webhooks/order-created.ts`. We recommend to keep webhook type in file name, which will be resolved by Next.js to route path.
```typescript
import { SaleorAsyncWebhook } from "@saleor/app-sdk/handlers/next";
Webhooks are created in Saleor when the App is installed. Saleor uses [AppManifest](https://docs.saleor.io/docs/3.x/developer/extending/apps/manifest) to get information about webhooks to create.
`SaleorSyncWebhook`&`SaleorAsyncWebhook` utility can generate this manifest:
```typescript
// pages/api/manifest
import { createManifestHandler } from "@saleor/app-sdk/handlers/next";
import { orderCreatedWebhook } from "./order-created.ts";
Now, try to read your manifest, in default Next.js config it will be `GET localhost:3000/api/manifest`. You should see webhook configuration as part of manifest response.
### Creating webhook domain logic
Now, let's create a handler that will process webhook data. Let's back to handler file `pages/api/webhooks/order-created.ts`.
```typescript
type OrderPayload = {
id: string;
};
export const orderCreatedWebhook = new SaleorAsyncWebhook<OrderPayload>({
// ... your configuration
});
/**
* Handler has to be a default export so the Next.js will be able to use it
Sync webhooks need to return response to Saleor, so operation can be completed. To achieve that, `SaleorAsyncWebhook` injects additional context field `buildResponse`.
It infers even from constructor and provides typed factory:
```typescript
const webhook = new SaleorAsyncWebhook({ event: "ORDER_CALCULATE_TAXES" /* ... rest of config */ });
Subscription query can be specified using plain string or as `ASTNode` object created by `gql` tag.
If your project does not use any code generation for GraphQL operations, use the string. In case you are using [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), which we highly recommend, you should pass a subscription as GraphQL ASTNode:
```typescript
/**
* Subscription query, you can define it in the `.ts` file. If you write operations in separate `.graphql` files, codegen will also export them in the generated file.