Google Ads API is returning to beta status. Please read our blog post for more details.

结算设置

结算设置是 Google Ads 帐号与付款帐号之间的一种帐号级关联,可以有效地确定由谁支付该结算设置的帐号预算产生的费用。每个付款帐号会对应一份帐单。

关于付款帐号

每个 BillingSetup 都会标识一个付款帐号,该帐号会针对自己的帐号预算产生的费用开具帐单。此付款帐号与最终负责支付费用的付款资料相关联。

结算设置包含一个 payments_account 字段和一组 payments_account_info 字段,用于标识正在使用的付款帐号,这些字段包括:

如果付款帐号符合合并结算的条件,您就可以设置多个 Google Ads 帐号的结算设置,让其使用同一个基础付款帐号,从而将这些帐号分组到同一帐单。

创建新的结算设置

您既可以将新的结算设置关联到现有的付款帐号,也可以在创建新的结算设置时创建新的付款帐号。

要使用现有的付款帐号注册,请将 payments_account 设置为有效付款帐号的资源 ID(但不应设置 payments_account_info)。

您可以使用 PaymentsAccountService.ListPaymentsAccounts 方法列出已登录用户的可用付款帐号。

要使用新的付款帐号注册,请在 payments_account_info 中设置以下字段(但不应设置 payments_account):

  • payments_account_name
  • payments_profile_id

请注意,在随后获取结算设置时,系统会填充 payments_accountpayments_account_info

下面的示例演示了如何通过现有的付款资料 ID 创建新的结算设置。如上所述,此操作还将创建一个名为“My New Payments Account”的新付款帐号。

BillingSetup bsetup = BillingSetup.newBuilder()
    .setPaymentsAccountInfo(PaymentsAccountInfo.newBuilder()
        .setPaymentsAccountName(StringValue.of("My New Payments Account"))
        .setPaymentsProfileId(StringValue.of("1234-5678-9012"))
        .build())
    .setStartTimeType(TimeType.NOW)
    .build();

BillingSetupOperation op = BillingSetupOperation.newBuilder().setCreate(bsetup).build();

try (BillingSetupServiceClient billingSetupServiceClient = googleAdsClient
    .getBillingSetupServiceClient()) {

  MutateBillingSetupResponse response =
      billingSetupServiceClient.mutateBillingSetup(Long.toString(customerId), op);
}

如果这是首个添加到 Google Ads 帐号的结算设置,则可以有效地为客户完成注册,以便通过引用的付款资料进行结算。

结算设置状态

新的 BillingSetup 实例需要经过批准才能生效,在生效之前它们将处于 PENDING 状态。BillingSetup 可能处于如下状态之一。

状态 说明
PENDING 待批准。
APPROVED_HELD 已获批准,但对应的第一项预算尚未获得批准。这仅适用于针对按月帐单结算配置的结算设置。
APPROVED 设置已获批准。
CANCELLED 在获得批准之前,用户取消了设置。

检索帐号的结算设置

与 Google Ads API 中的大多数其他实体一样,BillingSetup 的获取方式是查询 GoogleAdsService.Search,查询时使用的是指定应返回哪些字段的 Google Ads 查询语言。

Java

private void runExample(GoogleAdsClient googleAdsClient, long customerId) {
  // Defines a GAQL query to retrieve all billing setup information.
  String searchQuery = "SELECT billing_setup.id, "
      + "  billing_setup.status, "
      + "  billing_setup.payments_account, "
      + "  billing_setup.payments_account_info.payments_account_id, "
      + "  billing_setup.payments_account_info.payments_account_name, "
      + "  billing_setup.payments_account_info.payments_profile_id, "
      + "  billing_setup.payments_account_info.payments_profile_name, "
      + "  billing_setup.payments_account_info.secondary_payments_profile_id "
      + "FROM billing_setup";

  // Creates a request that will retrieve all billing setups using pages of the specified
  // page size.
  SearchGoogleAdsRequest request = SearchGoogleAdsRequest.newBuilder()
      .setCustomerId(String.valueOf(customerId)).setPageSize(PAGE_SIZE).setQuery(
          searchQuery).build();

  try (GoogleAdsServiceClient googleAdsServiceClient = googleAdsClient.getLatestVersion()
      .createGoogleAdsServiceClient()) {
    // Issues the search request.
    SearchPagedResponse response = googleAdsServiceClient.search(request);

    // Iterates over all rows in all pages and prints the requested field values for the billing
    // setup in each row.
    for (GoogleAdsRow googleAdsRow : response.iterateAll()) {
      BillingSetup billingSetup = googleAdsRow.getBillingSetup();
      System.out.printf(
          "Billing setup with ID '%d', "
              + "status '%s', "
              + "payments_account '%s', "
              + "payments_account_id '%s', "
              + "payments_account_name '%s', "
              + "payments_profile_id '%s', "
              + "payments_profile_name '%s', "
              + "secondary_payments_profile_id '%s'.%n",
          billingSetup.getId().getValue(),
          billingSetup.getStatus(),
          billingSetup.getPaymentsAccount().getValue(),
          billingSetup.getPaymentsAccountInfo().getPaymentsAccountId().getValue(),
          billingSetup.getPaymentsAccountInfo().getPaymentsAccountName().getValue(),
          billingSetup.getPaymentsAccountInfo().getPaymentsProfileId().getValue(),
          billingSetup.getPaymentsAccountInfo().getPaymentsProfileName().getValue(),
          billingSetup.getPaymentsAccountInfo().getSecondaryPaymentsProfileId().getValue());
    }
  }
}

C#

public void Run(GoogleAdsClient client, long customerId)

PHP

public static function main()

Python

def main(client, customer_id, page_size):
    ga_service = client.get_service('GoogleAdsService', version='v1')

    query = (
        'SELECT billing_setup.id, billing_setup.status, '
        'billing_setup.payments_account, '
        'billing_setup.payments_account_info.payments_account_id, '
        'billing_setup.payments_account_info.payments_account_name, '
        'billing_setup.payments_account_info.payments_profile_id, '
        'billing_setup.payments_account_info.payments_profile_name, '
        'billing_setup.payments_account_info.secondary_payments_profile_id '
        'FROM billing_setup')

    results = ga_service.search(customer_id, query=query, page_size=page_size)

    try:
        # Use the enum type to determine the enum name from the value.
        billing_setup_status_enum = (
            client.get_type('BillingSetupStatusEnum', version='v1')
                .BillingSetupStatus)

        print('Found the following billing setup results:')
        for row in results:
            billing_setup = row.billing_setup
            payments_account_info = billing_setup.payments_account_info
            print('Billing setup with ID "%s", status "%s", '
                  'payments_account "%s", payments_account_id "%s", '
                  'payments_account_name "%s", payments_profile_id "%s", '
                  'payments_profile_name "%s", '
                  'secondary_payments_profile_id "%s".'
                  % (billing_setup.id.value,
                     billing_setup_status_enum.Name(billing_setup.status),
                     billing_setup.payments_account.value,
                     payments_account_info.payments_account_id.value,
                     payments_account_info.payments_account_name.value,
                     payments_account_info.payments_profile_id.value,
                     payments_account_info.payments_profile_name.value,
                     payments_account_info.secondary_payments_profile_id.value))
    except google.ads.google_ads.errors.GoogleAdsException as ex:
        print('Request with ID "%s" failed with status "%s" and includes the '
              'following errors:' % (ex.request_id, ex.error.code().name))
        for error in ex.failure.errors:
            print('\tError with message "%s".' % error.message)
            if error.location:
                for field_path_element in error.location.field_path_elements:
                    print('\t\tOn field: %s' % field_path_element.field_name)
        sys.exit(1)

Ruby

def get_billing_setup(customer_id)
  # GoogleAdsClient will read a config file from
  # ENV['HOME']/google_ads_config.rb when called without parameters
  client = Google::Ads::GoogleAds::GoogleAdsClient.new

  ga_service = client.service(:GoogleAds)

  search_query = <<~QUERY
    SELECT billing_setup.id,
      billing_setup.status,
      billing_setup.payments_account,
      billing_setup.payments_account_info.payments_account_id,
      billing_setup.payments_account_info.payments_account_name,
      billing_setup.payments_account_info.payments_profile_id,
      billing_setup.payments_account_info.payments_profile_name,
      billing_setup.payments_account_info.secondary_payments_profile_id
    FROM billing_setup
  QUERY

  response = ga_service.search(
    customer_id,
    search_query,
    page_size: PAGE_SIZE
  )

  response.each do |row|
    billing_setup = row.billing_setup
    payments_account_info = billing_setup.payments_account_info

    puts sprintf('Billing setup with ID "%s", status "%s",'\
        ' payments_account "%s", payments_account_id "%s",'\
        ' payments_account_name "%s", payments_profile_id "%s",'\
        ' payments_profile_name "%s", secondary_payments_profile_id "%s"',
        billing_setup.id,
        billing_setup.status,
        billing_setup.payments_account,
        payments_account_info.payments_account_id,
        payments_account_info.payments_account_name,
        payments_account_info.payments_profile_id,
        payments_account_info.payments_profile_name,
        payments_account_info.secondary_payments_profile_id
    )
  end
end

获得 BillingSetup 的引用后,您就可以按帐号预算文中所述使用它创建 AccountBudgetProposal

取消待处理的结算设置

使用 remove 操作可以取消尚未生效的 BillingSetup。只有当结算设置处于 PENDING 状态,或者处于 APPROVED 状态并且要在将来某个时间开始时,您才可以取消它们。

Java

private void runExample(GoogleAdsClient googleAdsClient, long customerId, long billingSetupId) {
  // Formats the customerId and billingSetupId into a resource name.
  String billingSetupResourceName = ResourceNames.billingSetup(customerId, billingSetupId);

  // Constructs an operation that will remove the billing setup.
  BillingSetupOperation operation = BillingSetupOperation.newBuilder()
      .setRemove(billingSetupResourceName)
      .build();

  try (BillingSetupServiceClient billingSetupServiceClient = googleAdsClient.getLatestVersion()
      .createBillingSetupServiceClient()) {
    // Sends the operation in a mutate request.
    MutateBillingSetupResponse response = billingSetupServiceClient
        .mutateBillingSetup(String.valueOf(customerId), operation);

    System.out.printf("Removed billing setup with resource name '%s'.%n",
        response.getResult().getResourceName());
  }
}

C#

public void Run(GoogleAdsClient client, long customerId, long billingSetupId)

PHP

public static function main()

Python

def main(client, customer_id, billing_setup_id):
    billing_setup_service = client.get_service('BillingSetupService',
                                               version='v1')

    # Create billing setup operation.
    billing_setup_operation = client.get_type('BillingSetupOperation',
                                              version='v1')
    billing_setup_operation.remove = billing_setup_service.billing_setup_path(
        customer_id, billing_setup_id)

    # Remove the billing setup.
    try:
        billing_setup_response = billing_setup_service.mutate_billing_setup(
            customer_id, billing_setup_operation)
    except google.ads.google_ads.errors.GoogleAdsException as ex:
        print('Request with ID "%s" failed with status "%s" and includes the '
              'following errors:' % (ex.request_id, ex.error.code().name))
        for error in ex.failure.errors:
            print('\tError with message "%s".' % error.message)
            if error.location:
                for field_path_element in error.location.field_path_elements:
                    print('\t\tOn field: %s' % field_path_element.field_name)
        sys.exit(1)

    print('Removed billing setup %s.'
          % billing_setup_response.results[0].resource_name)

Ruby

def remove_billing_setup(customer_id, billing_setup_id)
  # GoogleAdsClient will read a config file from
  # ENV['HOME']/google_ads_config.rb when called without parameters
  client = Google::Ads::GoogleAds::GoogleAdsClient.new

  billing_setup_service = client.service(:BillingSetup)

  resource =  client.path.billing_setup(customer_id, billing_setup_id)

  response = billing_setup_service.mutate_billing_setups(customer_id,
      [{remove: resource}])

  puts sprintf("Removed billing_setup %s", response.results.first.resource_name)
end