# Connect Reverse ETL Source to Google Ads Remarketing Lists


This guide takes you through the steps to connect a [Reverse ETL source]({{< ref "sources/reverse-etl/" >}}) to your Google Ads Remarketing Lists destination.

{{< info >}}
RudderStack uses the [Data Manager API](https://developers.google.com/data-manager/api) to manage Customer Match for this integration.
{{< /info >}}

## Prerequisites: Account permissions

To use this integration, your Google Ads account must have [Standard or Admin permissions](#what-are-the-account-permissions-required-for-the-google-ads-remarketing-lists-integration). Otherwise, the API calls to Google Ads will fail.

## Setup 

1. Set up and configure your Reverse ETL source.
2. In the **Overview** tab of the source page, click **Add destination** > **Create new destination**. You can also select an already-configured destination here.
3. From the list of destinations, select **Google Ads Remarketing Lists** and click **Continue**.
4. Specify a unique name to identify this destination in RudderStack.
5. In the **Event delivery account** section, click **Select** to choose an existing Google Ads account from the list, then skip to **Step 7**. To add a new account, click **Add account** and select any of the [account types](#account-types):

| Account type | Description | 
| :----| :-----|
| OAuth (Google Ads API) | If you choose this account type, RudderStack asks for the `adwords` OAuth scope during authentication | 
| OAuth (Data Manager API) (**Recommended**)<br/> <span style="color: #4D4DFF;font-size:12px;">Beta</span> | If you choose this account type, RudderStack asks for the `dataManager` OAuth scope during authentication |

6. After selecting the account type, specify the following settings:

| Setting | <div style="width: 350px;">Description</div> |
| :----| :-----|
| Account Name | Specify a unique account name |
| Connect account | Click **Connect account**, sign in with Google, and give RudderStack the required permissions to access your Google Ads account. |

7. After successful authentication, RudderStack automatically populates the **Customer ID** associated with your Google Ads account — select the relevant ID from the dropdown.
8. Turn on the **Subaccount** setting if you are using a [Google Ads subaccount](https://support.google.com/campaignmanager/answer/2829448?hl=en#zippy=%2Cwhat-are-subaccounts).
9. If **Subaccount** is toggled on, enter the **Login Customer ID** of the parent (manager) account associated with the subaccount. See the [FAQ](#when-do-i-need-to-provide-a-login-customer-id) for guidance on when this field is required.
10. Click **Continue** to configure the [mapping settings](#mapping-settings).

### OAuth (Data Manager API) account type

{{< stability level="beta" >}}

The **OAuth (Data Manager API)** account type uses the [Data Manager API](https://developers.google.com/data-manager/api). Creating this account grants RudderStack the `datamanager` scope on your Google account, which is used to manage your audience data.

#### Migrate from OAuth (Google Ads API) account type

If an existing destination uses the **OAuth (Google Ads API)** account type for authentication, follow these steps to migrate to **OAuth (Data Manager API)**:

1. Go to the **Configuration** tab of the destination and click **Switch account**.

{{< figure src="images/audiences/destinations/garl/switch-account.webp" alt="Switch account" >}}

2. Click **Add account** and select **OAuth (Data Manager API)** as the account type.
3. Specify the **Account name** and click **Connect account** to sign in with Google and give RudderStack the required permissions.
4. After successful authentication, RudderStack automatically populates the **Customer ID** associated with your Google Ads account — select the relevant ID from the dropdown.
5. Configure **Subaccount** and **Login Customer ID** as required and save the changes.

## Mapping settings 

This section lists the settings to correctly map data from your Reverse ETL source to the Google Ads Remarketing Lists destination.

### Select user list

In this section, you can create a new user list or use an existing one.

- **Create new list**: Use this option to create a new list in Google Ads. You can specify the name and description of the new list.
- **Use existing list**: Use this option if you have an existing list in Google Ads. RudderStack automatically populates this field with the relevant lists based on your specified [connection settings](#setup).

### Sync mode

RudderStack supports only [Mirror mode]({{< ref "data-pipelines/reverse-etl/developer-guides/sync-modes.md#mirror-mode" >}}) for this integration.

### Select list type

If you select the **Create new list** option, you need to select the [type of list](https://developers.google.com/google-ads/api/reference/rpc/v23/CustomerMatchUploadKeyTypeEnum.CustomerMatchUploadKeyType) where you want to sync the data. RudderStack provides three options: 

| List type | Description |
| :---| :-----|
| CONTACT_INFO | You can send email, phone number, and address information in this list |
| CRM_ID | You can send internal customer IDs in this list |
| MOBILE_ADVERTISING_ID | You can send mobile advertising IDs (IDFA/GAID) in this list <br /><br />**Note**: If selected, specify the **App ID** of the mobile app the data was collected from. <br /><br /><ul><li>For iOS, it is the 9-digit number at the end of the App Store URL, for example, `123456789`.</li><li>For Android, it's the package name, for example, `com.sampleapp.samplename`.</li></ul> |

### Map identifiers

In this section, you can map your warehouse columns to specific Google Ads fields that represent your audience's identity.

{{< info >}}
The fields available for mapping depend on the [list type](#select-list-type) you select.
{{< /info >}}

{{< image src="images/audiences/destinations/garl/map-identifiers.webp" >}}

### Advanced settings

| Setting | <div style="width: 350px;">Description</div> |
| :----| :-----|
| Automatically hash PII data | When set to **Yes**, RudderStack hash-encodes sensitive user data like email, phone, first name, and last name in the SHA-256 format. <br /><br />See [Data hashing](#data-hashing) section for more information. |
| Specify user consent | Specify the consent type for the  uploaded users for using their data in Google Ads. RudderStack provides four options for this setting:<br /><br /><ul><li>**Unspecified**</li><li> **Unknown**</li><li>**Granted**</li><li>**Denied**</li></ul>Note that if you do not set this field, RudderStack sets it to  **Unspecified**, by default. |
| Specify ad personalization consent | Specify consent for uploaded users for personalizing ads. RudderStack provides four options for this setting:<br /><br /><ul><li>**Unspecified**</li><li> **Unknown**</li><li>**Granted**</li><li>**Denied**</li></ul>Note that if you do not set this field, RudderStack sets it to **Unspecified** by default. |

## Sync settings

{{< customreadfile "/includes/retl/schedule-syncs.md" >}}

#### Sync observability settings

{{< customreadfile "/includes/retl/sync-observability-settings.md" >}}

## Data normalization

By default, RudderStack automatically cleans and standardizes the data as prescribed by Google Ads.

After normalization, RudderStack validates each field before sending it to Google Ads: 

- If a field is determined to be invalid, RudderStack **does not** send it to Google Ads.
- If all fields in a row are invalid, then the entire row is rejected and marked as failed

{{< info >}}
RudderStack first normalizes the data and then validates it, skipping any invalid rows. Then, it [hashes the data](#data-hashing) before sending it to Google Ads.
{{< /info >}}

## Data hashing

The [Automatically hash PII data](#advanced-settings) setting lets you hash your user data before sending it to Google Ads. This setting is enabled by default.

- Configure the setting to **Yes** if your incoming data is not pre-hashed
- Configure this setting to **No** if your data is already hashed

{{< warning >}}
Incorrect configuration of the **Automatically hash PII data** setting will result in failures.

- If the **Automatically hash PII data** setting is configured to **Yes** and your data is pre-hashed, the event will fail.
- If the **Automatically hash PII data** setting is configured to **No** and your data is not pre-hashed, the event will fail.
{{< /warning >}}

RudderStack rejects such events with a clear error message, for example:

```text
Hashing is disabled but the value for field EMAIL appears to be unhashed. Either enable hashing or send pre-hashed data.
```

You will also see errors in the **Events** tab for cases that were previously marked as successful, but were effectively resulting in no matches, helping you quickly identify and fix any data quality or configuration issues.

## FAQ

#### Why can't I add a Reverse ETL source from the destination page?

The Reverse ETL feature supports only source-driven pipeline configuration. It means that you must configure a Reverse ETL source in RudderStack and then connect it to a new or existing destination. Note that this destination should not be connected to any other source.

See [Reverse ETL FAQ]({{< ref "data-pipelines/reverse-etl/developer-guides/faq.md" >}}) for more information.

#### What are the account permissions required for the Google Ads Remarketing Lists integration?

Make sure the customer account used for OAuth verification adheres to Google's [Customer Match policy](https://support.google.com/google-ads/answer/6299717) and has **Standard** or higher (**Administrative**) access level permissions. 

For more information on the access level permissions, refer to this [Google Ads support page](https://support.google.com/google-ads/answer/9978556?visit_id=637611563637058259-4176462731&rd=1).

Follow these steps to set the access level:

1. Sign in to your Google Ads account and go to **TOOLS AND SETTINGS** > **Access and security**:

{{< image src="images/event-stream-destinations/gads-access-security.webp" alt="Access and Security option in Google Ads dashboard" >}}

2. Enter the email address of the account. From the list of permissions, select **Standard** or **Administrative**. Then, click **SEND INVITATION**:

{{< image src="images/event-stream-destinations/gads-specify-access-level.webp" alt="Specifying access levels" >}}

The account will have the required access-level permissions once the user accepts the invitation.

#### How do I create a Google Ads customer list?

1. Open your Google Ads account.
2. Go to **Tools and settings**.
3. Under **Shared Library**, go to **Audience Manager**.
4. Click the + button and select **Customer list**.
5. Under **Segment name**, assign a name to the list.
6. From the dropdown, select the list type of data to upload.
7. Upload the CSV containing the user data. You can also download the template and upload the data.
8. Click **UPLOAD AND CREATE**.

#### When do I need to provide a Login Customer ID?

You need to provide the Manager Account ID (**Login Customer ID** setting in the dashboard) only when:

- The Manager Account ID is a manager of the Customer ID
- The Google account you authenticated with does not have direct user access to the Customer ID.

You can leave the **Login Customer ID** field empty if the authenticated Google account has direct access to the Customer ID.

See [About manager accounts](https://support.google.com/google-ads/answer/7459399) for more information.

#### How do I know which Customer ID and Login Customer ID combination applies to my setup?

| Setup | Customer ID | Login Customer ID |
| :--- | :--- | :--- |
| Standalone account, direct OAuth access | The account itself | Leave empty |
| Standalone account, OAuth access via a manager | The account itself | The manager |

#### Why am I getting the `USER_PERMISSION_DENIED`, `INVALID_CUSTOMER_ID`, or `CUSTOMER_NOT_ACCEPTED_CUSTOMER_DATA_TERMS` errors?

These errors usually mean the **Customer ID** or Manager Account ID (**Login Customer ID** setting in the dashboard) is misconfigured or you are hitting the API rate limits.

| Error | Notes |
| :----| :----|
| `USER_PERMISSION_DENIED` | The authenticated Google account doesn't have permission to act on the **Customer ID** or you're trying to modify a customer list created by a different account (only the owning account can edit a list).<br /><br /> Verify the **Login Customer ID** is correct, and that this manager is linked to the **Customer ID** in Google Ads. |
| `INVALID_CUSTOMER_ID` | Either the **Customer ID** is wrong, or the **Login Customer ID** isn't authorized to access it. |
| `RESOURCE_EXHAUSTED` | Too many requests are sent in a short period — this is a quota/rate limit issue rather than a configuration error. Batch your operations and review Google's [API limits and quotas](https://developers.google.com/google-ads/api/docs/best-practices/quotas). |

For other Customer Match-specific errors, see Google's [Customer Match Troubleshooting Guide](https://developers.google.com/google-ads/api/docs/remarketing/audience-segments/customer-match/troubleshoot).

#### Why am I getting a 400 Bad Request error message while setting up the Google Ads Remarketing Lists destination?

If you get a 400 Bad Request error while configuring the destination, make sure your customer account is allowlisted and configured to have **Standard** or **Administrative** access levels in Google Ads. 

See the above [FAQ](#what-are-the-account-permissions-required-for-the-google-ads-remarketing-lists-integration) for steps on setting the access level permissions for the account.
