Showing posts with label AdGroupCriterionService. Show all posts
Showing posts with label AdGroupCriterionService. Show all posts

Concurrency Management in the AdWords API

Wednesday, March 30, 2011


Has a call from your application ever returned a CONCURRENT_MODIFICATION error but you can’t figure out why? Let’s look at concurrency management in the API to understand what might have happened.

The AdWords API uses an optimistic concurrency control mechanism.  When the server begins to process a request, it checkpoints the current state of the relevant account, then executes the business logic and validation rules in the request.  Before committing the requested change, the server again checkpoints the account. If the “before and after” checks don’t match, the server returns a concurrency error to ensure that the request doesn’t introduce data inconsistency.

A concurrency issue occurs when two different applications or two different instances or threads of the same application attempt to change a single piece of data at the same time. Let’s say that request1 and request2 both want to operate on the same original version of some data. If request1 changes the data first and is committed, request2 becomes invalid, because it’s trying to operate on data that is now out-of-date.

A concurrency issue doesn’t occur only when your application tries to modify an entity that’s changed during processing. A problem can also occur if the entity that your request modifies has a dependency on another entity that’s been changed.  For example, an ad group entity references a campaign. If your request modifies an ad group and the referenced campaign is modified while your request is executing, you’ll get an error.   

In an exception to this general rule, we’ve recently introduced the ability to make concurrent changes to some services, such as AdGroupCriterionService and AdGroupAdService. However, the principle still applies at the field level: field-level changes are exclusive to one request at a time.

In the past, you might have gotten a CONCURRENT_MODIFICATION error even when using a single-threaded application to modify one account at a time. The problem was likely due to background processing, such as approvals, which also modified the account’s entities. We’ve made some changes that should reduce the likelihood of these errors occurring

To summarize, when you get a concurrency error, consider whether the application has done one of the following:
  • Run multiple threads that attempted to modify the same entity
  • Modified an entity on which another entity is dependent 
As always, if you have more questions, feel free to post them to AdWords API Forum.

Posted by Dan H. and Nina Silk, AdWords API Team

Discover v201008: Product ads and criteria

Tuesday, February 01, 2011


We’ve recently released additional product advertising options in Google AdWords, and have exposed features in AdWords API v201008 to enable you to leverage these new ad formats. Product extensions enhance your existing text ads with relevant production information, while product listing ads expose your entire product catalog with minimal setup and maintenance. You can read further about the differences between these ad formats here.

In this post we’ll discuss how product ads can be created using the API. Note: both features require that you first link your Google Merchant Center account to your AdWords account. This is done through the Google Merchant Center web interface using these instructions.

Product extensions

Like other extensions, product extensions are represented as CampaignAdExtensions using the type ProductExtension. The CampaignAdExtensionService can be used to retrieve or delete product extensions, but at this time they can only be created through the AdWords web interface. Once they have been created they will be automatically applied to all text ads in the campaign, and utilize existing keyword targeting.

Product listing ads

The API type ProductAd corresponds to a product listing ad, and can be manipulated using the AdGroupAdService. Unlike other ad types, a majority of the information displayed in the ad is not stored in the AdWords system but is pulled from the Google Merchant Center when the ad is served. For this reason the ad is very simple, introducing only an optional promotionLine field. Additionally, the fields url and displayUrl aren’t supported for product listing ads, as these values are populated based on the product that is being shown.

The Product criterion (known as a “product target” in the web interface) is what allows you to control which products are eligible to be shown with a product listing ad and what the bid should be for those products. This criterion contains conditional rules used to filter your product catalog, limited to the following product attributes: product_type, brand, adwords_grouping, condition, and adwords_labels. It’s worth noting that a single Product criterion usually corresponds to multiple different products in the catalog.

Let’s take the example of a merchant that wants to advertise their line of store-made premium chocolates for Valentine’s day. Using the PHP client library they would first add the product listing ad to the ad group, with a promotional message for the holiday.

// Create product listing ad.
$productAd = new ProductAd();
$productAd->promotionLine = 'Order some sweets for your sweet!';

// Create ad group ad.
$adGroupAd = new AdGroupAd();
$adGroupAd->adGroupId = $adGroupId;
$adGroupAd->ad = $productAd;

// Create operation.
$operation = new AdGroupAdOperation();
$operation->operand = $adGroupAd;
$operation->operator = 'ADD';
$operations = array($operation);

// Add ad.
$result = $adGroupAdService->mutate($operations);


They would then add a product criterion to the ad group, filtering for products that are chocolates in their premium brand.

// Create product conditions.
$productTypeCondition = new ProductCondition('Chocolate',
new ProductConditionOperand('product_type'));
$brandCondition = new ProductCondition('Acme Premium',
new ProductConditionOperand('brand'));

// Create product criterion.
$product = new Product();
$product->conditions = array($productTypeCondition, $brandCondition);

// Create biddable ad group criterion.
$adGroupCriterion = new BiddableAdGroupCriterion();
$adGroupCriterion->adGroupId = $adGroupId;
$adGroupCriterion->criterion = $product;

// Create operation.
$operation = new AdGroupCriterionOperation();
$operation->operand = $adGroupCriterion;
$operation->operator = 'ADD';
$operations = array($operation);

// Add ad group criteria.
$result = $adGroupCriterionService->mutate($operations);


Using only this single ad and criterion all of their premium chocolates are ready to be advertised.

Additional information on how you can set up your campaigns to use product listing ads is available here. If you have any question about how to use product ad features in the API you can reach us on the forum.

Best,
- Eric Koleda, AdWords API Team

Discover v201008: Partial Failure for AdGroupCriterionService

Tuesday, December 07, 2010


With v201008 of the AdWords API we have introduced a new beta feature for AdGroupCriterionService: Partial Failure. Typically all requests to the AdWords API are atomic, so each of them either fails or succeeds in full. While this can be helpful to maintain consistency, we’ve heard from you that, in some cases, you would prefer that some operations fail while other changes are applied.

AdGroupCriterionService requests often contain many Criteria to add or update. Having an error in just one of them will force you to resend the whole set of objects again. We’ve introduced Partial Failure to enable you to get back a list of failed and successful operations and retry the failed ones only.

To utilize the new feature you’ll need to set this extra SOAP header:
partialFailure = true

Here’s an example from the Java client library:
// usual initialization code
AdWordsUser user = new AdWordsUser();
// Enable partial failure
user.setUsePartialFailure(true);
// Get the AdGroupCriterionService
AdGroupCriterionServiceInterface adGroupCriterionService =
  user.getService(AdWordsService.V201008.ADGROUP_CRITERION_SERVICE);
// Set up operations and operands here
List<AdGroupCriterionOperation> operations = new ArrayList<AdGroupCriterionOperation>();
// [...]

// Execute operations (add ad group criteria)
AdGroupCriterionReturnValue result =
  adGroupCriterionService.mutate(operations.toArray(
      new AdGroupCriterionOperation[] {}));

Now processing succeeded results:
// Display results
if ((result != null) && (result.getValue() != null)) {
  // A result is returned for every operation requested
  for (AdGroupCriterion adGroupCriterionResult : result.getValue()) {
    // Successful operation result will contain a non-null Criterion
    if (adGroupCriterionResult.getCriterion() != null) {
      System.out.printf("Ad group criterion with ad group id '%d', and " +
          "criterion id '%d', and keyword '%s' was added.\n",
          adGroupCriterionResult.getAdGroupId(),
          adGroupCriterionResult.getCriterion().getId(),
          ((Keyword) adGroupCriterionResult.getCriterion()).getText());
    }
  }
} else {
  System.out.println("No ad group criteria were added.");
}

Here is how to handle the failed operations:
// Is there any Partial Failure errors in the results?
if ((result != null) && (result.getPartialFailureErrors() != null)) {
  // Retrieving ApiError object for each of failures
  for (ApiError apiError : result.getPartialFailureErrors()) {
    // The order of the fields might be different to the order of operations in the
    // request, so we are getting the corresponding operation index from the fieldPath.
    Matcher matcher = operationIndexPattern.matcher(apiError.getFieldPath());
    if (matcher.matches()) {
      int operationIndex = Integer.parseInt(matcher.group(1));
      AdGroupCriterion adGroupCriterion =
          operations.get(operationIndex).getOperand();
      System.out.printf("Ad group criterion with ad group id '%d' and " +
          "keyword '%s' triggered a failure for the following reason: '%s'.\n",
          adGroupCriterion.getAdGroupId(),
          ((Keyword) adGroupCriterion.getCriterion()).getText(),
          apiError.getErrorString());
    } else {
      System.out.printf(
          "A failure for the following reason: '%s' has occurred.\n",
          apiError.getErrorString());
    }
  }
}


Partial Failure is fully supported in our client libraries. If you have any questions please post them on the AdWords API forum. This topic is also covered in a video presentation.

-- Danial Klimkin, AdWords API Team.