# Channel, domain and keys

> Creating a channel, verifying the domain, and creating the site key and the server key.

Source: /en/integrate/channels-and-keys/

Before connecting the site, three things are prepared in the panel: a **channel**, a verified **domain** and the channel's **keys**. All of these steps are carried out in order with the **Set up a channel** wizard on the **Setup › Channels** screen.

:::note[Permission]
Only users with the **Administrator** role can work with channels, domains and keys (the "Can manage users and channels" permission). Other roles only see status information on the **Integration** screen. Every creation and cancellation is recorded in the **Activity history**.
:::

## Channel

A channel is a point of sale where reviews are collected and shown, for example your Turkish website, your mobile app, your site in another country or a site on another domain where you sell under another name. All of a brand's channels are managed in the same panel. Each channel has three properties:

| Field | Description |
|---|---|
| Name | The name shown in the panel, for example "Turkish website" |
| Market | The country rules the channel is subject to. The proof of purchase requirement, the time allowed to write a review and the permitted sort orders are set by the market rules: Sayproof's market rule is the baseline, and within its limits your brand can publish its own rule version for a market or a channel. **The market cannot be changed once the channel has been created.** |
| Language | The default language of invitation emails and the review form (`tr` or `en`) |

The channel code is generated automatically from the channel name and identifies the channel in the API (for example `channel=web`). Reviews from channels in the same market are shown together and counted in a single average; reviews from different markets are never mixed. This also applies to channels that sell under another name: if two of your brand's sites are in the same market, the same product's reviews appear on both sites.

### Editing a channel

On the **Channels** screen, the **Edit** button on the channel card opens the **Edit the channel** form. In the form you can change the **Name**, **Language** and **Page the invitation link opens** fields; turning the channel off or back on is done not in the form but with the **Turn the channel off** and **Turn the channel on** buttons on the channel card ([Turning a channel off and removing it](#turning-a-channel-off-and-removing-it)). As in the wizard, **Language** is picked from a list (**Türkçe** or **English**). The market cannot be changed. Changes are saved with the **Save changes** button and recorded in the **Activity history**.

Three fields in the same form decide under which name, from which address and with which support page this channel appears in the emails sent to customers:

- **Name shown to customers:** Shown as the brand name in this channel's invitation emails, rejection notices and unsubscribe page.
- **Sender email address:** This channel's invitation emails are sent from this address. The address's domain must be verified on the **Sender domains** card; an address on an unverified domain is not saved (`sender_domain_unverified`).
- **Support page address:** The support link in this channel's invitation emails opens this page (`https`).

Where a field is left empty, the brand name and the sender address and support page from the **Invitation sending › Sending** step are used. Unsubscribing, however, applies to the whole brand: a customer who chooses to stop invitations from one channel's email receives no invitations from any channel of the brand.

The **Privacy notice link** field takes the address of your privacy notice on the processing of personal data (`https`; the address does not have to be on a verified domain). When it is set, a **Privacy notice on the processing of personal data** link is shown on this channel's site under the review, question and answer forms and the review form on the order page, and in the footer of the invitation email; the link opens in a new tab. This field has no brand-wide counterpart: if it is left empty, no link is shown. An address that does not start with `https` is not saved (`privacy_url_not_https`).

The design and layout of the default component on this channel's site are not chosen in this form but on the **Setup › Store appearance** screen: [Store appearance](/en/features/setup-screens.md#store-appearance).

### Turning a channel off and removing it

A channel is turned off with the **Turn the channel off** button on its card on the **Channels** screen; the button first shows the consequences below and asks for confirmation. The card of a channel that is off has a **Turn the channel on** button. While a channel is off:

- The script answers every request made with this channel's site key with `channel_inactive`; reviews are not shown or written on the site. SSR and signed-in customer requests made with a server key for this channel return `unknown_channel`.
- Order submissions with the channel code are refused with `invalid / channel_unknown`. The channel's order connection does not read; **Read now** returns `409 channel_inactive`.
- No new invitations are built for the channel's orders. A pending invitation stops with the reason "Channel off", and no reminder goes to an invitation already sent.
- Rejection notices keep going out. Written reviews and past records do not change.

When the channel is turned back on, the order connection continues where it left off, and invitations are built for orders whose writing period is still open and that have not been invited yet.

A channel with no reviews, orders or order connection is deleted with the **Remove channel** button in the **Edit the channel** form. Its site keys, view counts and any publishing method set for this channel are deleted with it; the action is recorded in the **Activity history** and cannot be undone. A channel with reviews, orders or an order connection cannot be removed (`409 channel_in_use`); because reviews and orders are records that must be kept, such channels are turned off instead.

### Channel allowance

By default each brand can have up to 3 open channels; this number is the **Channel allowance**. Channels that are off do not count towards it.

- An administrator adds channels with the **Set up a channel** wizard until the allowance is full.
- When the allowance is full, the **Set up a channel** button is replaced by **Request another channel**. The button sends a request, with an optional note, to the Sayproof team; only one open request can exist at a time (`409 channel_request_open`). When the Sayproof team accepts the request, your channel allowance is raised. The request and its outcome are recorded in the **Activity history**.
- Turning a channel off frees a slot. Turning a channel that is off back on needs a free slot. While the allowance is full, no new channel can be created and no channel that is off can be turned back on (`409 channel_quota`).

## Domain verification

Reviews only appear on pages of verified domains. So even if someone copies your site key, they cannot show your reviews on their own site.

1. Add the domain in the **Domain check** step of the wizard or on the **Domains** card on the **Channels › Domains** tab, for example `www.yourbrand.com`.
2. For every domain waiting for verification, the panel shows the **Verification method** choice under the heading "How to verify `<domain>`": **File on your site** or **DNS record**. Both methods use the same verification text; choose whichever is easier for you.
3. With **File on your site**, the panel shows the **File address** and the **Text inside the file**, each with a copy button. Your developer puts a small text file on your site that opens at this address and contains only this text:

   ```text
   https://www.yourbrand.com/.well-known/sayproof-domain-verification
   ```

4. With **DNS record**, the panel shows the **Record type** (`TXT`), **Name** and **Value** rows; **Name** and **Value** come with copy buttons. A `TXT` record with this name and the verification text as its value is added in your domain's DNS settings (in the panel of the company you bought the domain from, or a service such as Cloudflare). The name is the domain with `_sayproof-verification` in front of it:

   ```text
   _sayproof-verification.www.yourbrand.com
   ```

   Some DNS panels add the domain to the end of the name themselves; there, enter only the part before your domain (`_sayproof-verification.www`). Use this method on hosted platforms where you can't put a file on your site, such as Shopify or Wix.
5. Once the file or the record is in place, press **Verify**. Sayproof reads the file first and, if there is no file or its content doesn't match, looks at the DNS record; if either matches the verification text, the domain is verified.

Verification rules:

- The address must be served over `https` and return a `200` response. Redirects are not followed; the file must be located at this exact address.
- Each domain is verified separately: `yourbrand.com` and `www.yourbrand.com` are two different domains. Add every address on which reviews will be shown.
- A domain belongs to the brand, not to a channel. A verified domain is valid for all your channels.
- For domains that resolve to a private network address the file is not read; these domains can only be verified with a DNS record.
- The DNS record's value must consist of the verification text only; other `TXT` records with the same name may exist. A new DNS record can take from a few minutes to a few hours to appear; if the record wasn't found, press **Verify** again after a while.
- If verification fails, the panel says why: "the file on your site does not have the expected content" if the file's content differs, "neither the verification file nor the DNS record was found" if neither was found, "the DNS record was found but its value is not the expected one" if the record exists with another value, and "the domain's DNS server could not be reached; try again shortly" if there is no file and the domain's DNS server could not be reached.

Reviews do not appear on a page of an unverified domain: the request is turned away and recorded on the **Connection log** screen with the result "Site not verified".

### The page the invitation link opens

In the same step, you enter the page that opens when the customer clicks the link in the invitation email, for example `https://www.yourbrand.com/write-a-review`. The rules:

- The page must be on one of your verified domains and start with `https`.
- The page must contain a review container. Sayproof adds the token to the part of the link after the `#` sign (`https://www.yourbrand.com/write-a-review#review_token=…`); when the script detects this value, it opens the review form automatically and removes the value from the address bar. The `?review_token=…` form of older invitations is also read. On a page without a container (for example the home page), the link does not open the form.
- If no page is set, the link opens the product's page address from the catalogue (see [Products](/en/features/products.md)). If neither exists, no invitation is sent and the reason "No invitation landing page set" is recorded.

You can use a product page, or a separate "write a review" page that contains a container.

### Removing a domain

On the **Domains** card on the **Channels › Domains** tab, the **Remove** button on each row deletes the domain, verified or waiting for verification, after you confirm. Reviews are no longer shown on the pages of a removed domain. If a channel's **Page the invitation link opens** address is on this domain, the domain cannot be removed (`409 domain_in_use`; the detail lists those channels' codes); change the channel's address first. It also cannot be removed while a channel's method statement address is on it (`409 domain_in_statement`; the detail lists the channel code and language); change the address in **Market rules › Method statement** first. The removal is recorded in the **Activity history**.

## Sender domains

For invitation emails to leave from your brand's address (for example `reviews@yourbrand.com`), the address's domain is verified on the **Sender domains** card on the **Channels › Domains** tab. The sender address is entered in the **Sender email address** field in the **Invitation sending › Sending route** step, and a channel's own address in the field of the same name in the **Edit the channel** form ([Editing a channel](#editing-a-channel)); an address on an unverified domain cannot be saved in these fields (`sender_domain_unverified`).

The **Add a sender domain** button opens a three-step wizard:

1. **Domain:** The part after the `@` sign in the address emails are sent from, for example `yourbrand.com`.
2. **DNS records:** The four `TXT` records to add in your domain's DNS settings are listed. The values are shown in the wizard and can be copied; if a record's value is shown empty ("Your email sending provider gives this value"), get that value from your email sending provider.
3. **Check:** The **Check the records** button looks for the records on your domain and shows "Found" or "Not found" for each record.

| Record | Type | Name | Value looked for |
|---|---|---|---|
| Ownership record (Sayproof) | `TXT` | `_sayproof.yourbrand.com` | The `sayproof-verification=…` value shown in the wizard. The value is specific to your brand and the domain; it shows that the domain belongs to you. |
| Sending permission (SPF) | `TXT` | `yourbrand.com` | A record starting with `v=spf1`; if the wizard shows an `include:` value, the record must contain it too |
| Signing key (DKIM) | `TXT` | `<selector>._domainkey.yourbrand.com`; the selector is shown in the wizard | A record containing the public key (`p=`) |
| Domain policy (DMARC) | `TXT` | `_dmarc.yourbrand.com` | A record starting with `v=DMARC1`; the wizard suggests `v=DMARC1; p=none` |

The domain is verified when all four records are found. A new DNS record can take a few minutes to a few hours to spread; if a record is not found, open the domain from the list again after a while and check again. If the domain's DNS server cannot be reached, or it returns a temporary error, the records are not counted as "Not found"; the answer is `502 sender_domain_check_failed / dns_unreachable` and the check can be run again later.

A verified domain's row shows when it was first verified; as long as the records stay in place, checking again does not change that time. The **Go to Invitation sending › Sending route** button on the row opens the **Invitation sending** screen.

A domain used by the sender address on the **Invitation sending** screen or by any channel's sender address cannot be removed (`409 sender_domain_refused / sender_domain_in_use`); change the sender address first.

## Keys

Two keys are enough for a channel:

| Value | Secret? | Where it is kept | Purpose |
|---|---|---|---|
| **Site key** | No | In the page's code, in the browser | Allows the script to fetch reviews and open the review form. Only works on verified domains. |
| **Server key** | Yes | Only on your store's server | Allows orders and deliveries to be sent to Sayproof, reviews to be prepared on the server together with the page (SSR), and the status of a signed-in customer to be queried. |

Both are created on the **Channels › Keys** tab and in the **Keys** step of the channel setup wizard ("The two keys your site and your server will use"). For teams that want to sign their orders, there is also an optional [signing password](#signing-password).

### Site key

The site key belongs to a channel, and there is no harm in it appearing in the page source. On its own it does not allow a review to be written; writing a review requires an order check or an invitation link.

A site key is created in the channel's setup wizard or with the **New site key** button on the **Site keys** card on the **Channels › Keys** tab; if you have more than one channel, choose the **Channel** on the card first. All of a channel's site keys in use keep working until they are cancelled. The setup screens (the channel wizard, **Integration** and the setup guide shared with a developer) show the channel's newest key.

### Server key

The server key is used for [sending orders and deliveries](/en/integrate/orders.md), for [SSR](/en/integrate/server-rendering.md) and for the [signed-in customer](/en/integrate/signed-in-customers.md) feature; one key is enough for all of them. The server key belongs to the brand, not to a channel: the same key can be used for all your channels, and the channel code in the request decides which channel it is for. It is created on the **Server keys** card by entering a **Key name** and pressing **Create a server key**. A server key created in the panel automatically carries the "Send orders" (`orders`) and "Prepare pages on the server" (`ssr`) permissions; no permission is chosen in the panel. The key cannot call the Admin API.

- The full key is shown **once**, at the moment it is created. Sayproof does not store the key; if you lose it, you need to create a new one.
- The key is sent in the `Authorization: Bearer …` header and must **never** reach the browser. It must not be written to an environment variable that is exposed to the browser (such as `NEXT_PUBLIC_…`).
- With this key, the signed-in customer query can be made for any email address: whether the address bought a product and whether it wrote a review can be learned. Protect the key like a password and keep it on the server only; if you suspect it has been exposed, cancel it immediately. For details, see [Keys and access](/en/security/keys.md).

### Signing password

This is optional. Orders are sent with the server key; teams that also want to sign their requests with a password open the collapsed **Advanced: signing passwords** section at the bottom of the **Channels › Keys** tab, enter a **Password name** on the **Signing passwords** card and press **Create a password**.

The signing password has two parts: the **password ID** (sent in the `X-Sayproof-Secret` header of every request) and the **password itself** (only used to calculate the signature and never sent in a request). The password is only shown once, at the moment it is created. The card that opens after creation shows the **Secret ID** and the **Secret** together. The ID is not secret; it also stays visible, with a copy button, in the **Secret ID** column of the **Signing passwords** table. The name in the **Name** column is only there to help you recognise the password; the header carries the ID, not the name. For how it is used, see [Sending orders and deliveries › Signature](/en/integrate/orders.md#signature).

The same table also lists two special-purpose passwords. These passwords cannot sign order transfers; they are only used for their own purpose:

- **Notification address password:** If your own system sends invitations, it signs the notices Sayproof sends to your system. See [Sending invitations with your own system](/en/integrate/own-sending.md).
- **Email delivery events password:** Used by your email service to report delivery and open events to Sayproof. See [Email delivery events](/en/integrate/email-events.md).

## Replacing a key

A cancelled key or password is closed permanently and cannot be restored; any system using it stops working immediately. To replace one without an interruption:

1. Create the new key or password (give the password a new name). For a site key, use the **New site key** button on the **Site keys** card.
2. Switch your system to the new value (for a site key, update the code on your site to use the new key) and confirm that it works from the **Connection log** screen or the **Recent requests** list on the **Integration › Order transfer** tab.
3. Cancel the old key or password.

If you suspect that a value has leaked, cancel it immediately and create a new one.

## Test

The last step of the wizard shows the latest request from your site for this channel and the number of orders transferred to this channel (**Orders received**). After adding the code, open a product page and press **Check again**. The same information is later shown in the "Seen on your site?" section on the **Integration › Showing reviews** tab once the channel is chosen.
