Campaign Management Samples

The code samples below provide examples for managing campaigns using the AdWords API. Client Library.

Add a campaign group and sets a performance target for that group

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.ApiException;
import com.google.api.ads.adwords.axis.v201708.cm.Campaign;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignGroup;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignGroupOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignGroupPerformanceTarget;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignGroupPerformanceTargetOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignGroupPerformanceTargetServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignGroupServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignReturnValue;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.EfficiencyTargetType;
import com.google.api.ads.adwords.axis.v201708.cm.Money;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.axis.v201708.cm.PerformanceTarget;
import com.google.api.ads.adwords.axis.v201708.cm.SpendTargetType;
import com.google.api.ads.adwords.axis.v201708.cm.VolumeGoalType;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;
import java.rmi.RemoteException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import org.joda.time.DateTime;

/**
 * This code example adds a campaign group and sets a performance target for that group. To get
 * campaigns, run GetCampaigns.java. To download reports, run DownloadCriteriaReportWithAwql.java.
 */
public class AddCampaignGroupsAndPerformanceTargets {

  private static class AddCampaignGroupsAndPerformanceTargetsParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.CAMPAIGN_ID, required = true)
    private List<Long> campaignIds;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential =
        new OfflineCredentials.Builder()
            .forApi(Api.ADWORDS)
            .fromFile()
            .build()
            .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session =
        new AdWordsSession.Builder().fromFile().withOAuth2Credential(oAuth2Credential).build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    AddCampaignGroupsAndPerformanceTargetsParams params =
        new AddCampaignGroupsAndPerformanceTargetsParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.campaignIds = Arrays.asList(
          Long.valueOf("INSERT_CAMPAIGN_ID_HERE"),
          Long.valueOf("INSERT_CAMPAIGN_ID_HERE"));
    }

    runExample(adWordsServices, session, params.campaignIds);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, List<Long> campaignIds)
      throws ApiException, RemoteException {
    CampaignGroup campaignGroup = createCampaignGroup(adWordsServices, session);
    addCampaignsToGroup(adWordsServices, session, campaignGroup, campaignIds);
    createPerformanceTarget(adWordsServices, session, campaignGroup);
  }

  /** Creates a campaign group. */
  private static CampaignGroup createCampaignGroup(
      AdWordsServicesInterface adWordsServices, AdWordsSession session)
      throws ApiException, RemoteException {
    // Get the CampaignGroupService.
    CampaignGroupServiceInterface campaignGroupService =
        adWordsServices.get(session, CampaignGroupServiceInterface.class);

    // Create the campaign group.
    CampaignGroup campaignGroup = new CampaignGroup();
    campaignGroup.setName("Mars campaign group #" + System.currentTimeMillis());

    // Create the operation.
    CampaignGroupOperation operation = new CampaignGroupOperation();
    operation.setOperand(campaignGroup);
    operation.setOperator(Operator.ADD);

    CampaignGroup newCampaignGroup =
        campaignGroupService.mutate(new CampaignGroupOperation[] {operation}).getValue(0);
    System.out.printf(
        "Campaign group with ID %d and name '%s' was created.%n",
        newCampaignGroup.getId(), newCampaignGroup.getName());

    return newCampaignGroup;
  }

  /** Adds multiple campaigns to a campaign group. */
  private static void addCampaignsToGroup(
      AdWordsServicesInterface adWordsServices,
      AdWordsSession session,
      CampaignGroup campaignGroup,
      List<Long> campaignIds)
      throws ApiException, RemoteException {
    // Get the CampaignService.
    CampaignServiceInterface campaignService =
        adWordsServices.get(session, CampaignServiceInterface.class);

    List<CampaignOperation> operations = new ArrayList<>();
    for (Long campaignId : campaignIds) {
      Campaign campaign = new Campaign();
      campaign.setId(campaignId);
      campaign.setCampaignGroupId(campaignGroup.getId());

      CampaignOperation operation = new CampaignOperation();
      operation.setOperand(campaign);
      operation.setOperator(Operator.SET);
      operations.add(operation);
    }

    CampaignReturnValue returnValue =
        campaignService.mutate(operations.toArray(new CampaignOperation[operations.size()]));
    System.out.printf(
        "The following campaign IDs were added to the campaign group with ID %d:%n",
        campaignGroup.getId());
    for (Campaign campaign : returnValue.getValue()) {
      System.out.printf("\t%d%n", campaign.getId());
    }
  }

  /** Creates a performance target for the campaign group. */
  private static void createPerformanceTarget(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, CampaignGroup campaignGroup)
      throws ApiException, RemoteException {
    // Get the CampaignGroupPerformanceTargetService.
    CampaignGroupPerformanceTargetServiceInterface campaignGroupPerformanceTargetService =
        adWordsServices.get(session, CampaignGroupPerformanceTargetServiceInterface.class);

    // Create the performance target.
    CampaignGroupPerformanceTarget campaignGroupPerformanceTarget =
        new CampaignGroupPerformanceTarget();
    campaignGroupPerformanceTarget.setCampaignGroupId(campaignGroup.getId());

    PerformanceTarget performanceTarget = new PerformanceTarget();
    // Keep the CPC for the campaigns < $3.
    performanceTarget.setEfficiencyTargetType(EfficiencyTargetType.CPC_LESS_THAN_OR_EQUAL_TO);
    performanceTarget.setEfficiencyTargetValue(3000000d);

    // Keep the maximum spend under $50.
    performanceTarget.setSpendTargetType(SpendTargetType.MAXIMUM);
    Money maxSpend = new Money();
    maxSpend.setMicroAmount(500000000L);
    performanceTarget.setSpendTarget(maxSpend);

    // Aim for at least 3000 clicks.
    performanceTarget.setVolumeTargetValue(3000L);
    performanceTarget.setVolumeGoalType(VolumeGoalType.MAXIMIZE_CLICKS);

    // Start the performance target today, and run it for the next 90 days.
    DateTime startDate = DateTime.now();
    DateTime endDate = DateTime.now().plusDays(90);

    performanceTarget.setStartDate(startDate.toString("yyyyMMdd"));
    performanceTarget.setEndDate(endDate.toString("yyyyMMdd"));

    campaignGroupPerformanceTarget.setPerformanceTarget(performanceTarget);

    // Create the operation.
    CampaignGroupPerformanceTargetOperation operation =
        new CampaignGroupPerformanceTargetOperation();
    operation.setOperand(campaignGroupPerformanceTarget);
    operation.setOperator(Operator.ADD);

    CampaignGroupPerformanceTarget newCampaignGroupPerformanceTarget =
        campaignGroupPerformanceTargetService
            .mutate(new CampaignGroupPerformanceTargetOperation[] {operation})
            .getValue(0);

    // Display the results.
    System.out.printf(
        "Campaign group performance target with ID %d was added for campaign group ID %d.%n",
        newCampaignGroupPerformanceTarget.getId(),
        newCampaignGroupPerformanceTarget.getCampaignGroupId());
  }
}

Add a label to multiple campaigns

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignLabel;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignLabelOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
 * This example adds a label to multiple campaigns.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class AddCampaignLabels {

  private static class AddCampaignLabelsParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.CAMPAIGN_ID, required = true)
    private List<Long> campaignIds = new ArrayList<>();

    @Parameter(names = ArgumentNames.LABEL_ID, required = true)
    private Long labelId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    AddCampaignLabelsParams params = new AddCampaignLabelsParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.campaignIds = Arrays.asList(
          Long.valueOf("INSERT_CAMPAIGN_ID_HERE"),
          Long.valueOf("INSERT_CAMPAIGN_ID_HERE"));
      params.labelId = Long.parseLong("INSERT_LABEL_ID_HERE");
    }

    runExample(adWordsServices, session, params.campaignIds, params.labelId);
  }

  public static void runExample(AdWordsServicesInterface adWordsServices, AdWordsSession session,
      List<Long> campaignIds, Long labelId) throws Exception {
    // Get the CampaignService.
    CampaignServiceInterface campaignService =
        adWordsServices.get(session, CampaignServiceInterface.class);

    // Create label operations.
    List<CampaignLabelOperation> operations = new ArrayList<>(
        campaignIds.size());
    for (Long campaignId : campaignIds) {
      CampaignLabel campaignLabel = new CampaignLabel();
      campaignLabel.setCampaignId(campaignId);
      campaignLabel.setLabelId(labelId);
      
      CampaignLabelOperation operation = new CampaignLabelOperation();
      operation.setOperand(campaignLabel);
      operation.setOperator(Operator.ADD);
      
      operations.add(operation);
    }

    // Display campaign labels.
    for (CampaignLabel campaignLabelResult : campaignService.mutateLabel(
        operations.toArray(new CampaignLabelOperation[operations.size()])).getValue()) {
      System.out.printf("Campaign label for campaign ID %d and label ID %d was added.%n",
          campaignLabelResult.getCampaignId(), campaignLabelResult.getLabelId());
    }
  }
}

Add complete campaigns using batch jobs

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.utils.v201708.SelectorBuilder;
import com.google.api.ads.adwords.axis.utils.v201708.batchjob.BatchJobHelper;
import com.google.api.ads.adwords.axis.utils.v201708.batchjob.BatchJobMutateResponse;
import com.google.api.ads.adwords.axis.utils.v201708.batchjob.MutateResult;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroup;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAd;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdOperation;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupCriterionOperation;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupOperation;
import com.google.api.ads.adwords.axis.v201708.cm.AdvertisingChannelType;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJob;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobOperation;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobProcessingError;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobStatus;
import com.google.api.ads.adwords.axis.v201708.cm.BiddableAdGroupCriterion;
import com.google.api.ads.adwords.axis.v201708.cm.BiddingStrategyConfiguration;
import com.google.api.ads.adwords.axis.v201708.cm.BiddingStrategyType;
import com.google.api.ads.adwords.axis.v201708.cm.Bids;
import com.google.api.ads.adwords.axis.v201708.cm.Budget;
import com.google.api.ads.adwords.axis.v201708.cm.BudgetBudgetDeliveryMethod;
import com.google.api.ads.adwords.axis.v201708.cm.BudgetOperation;
import com.google.api.ads.adwords.axis.v201708.cm.Campaign;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterionOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignStatus;
import com.google.api.ads.adwords.axis.v201708.cm.CpcBid;
import com.google.api.ads.adwords.axis.v201708.cm.ExpandedTextAd;
import com.google.api.ads.adwords.axis.v201708.cm.Keyword;
import com.google.api.ads.adwords.axis.v201708.cm.KeywordMatchType;
import com.google.api.ads.adwords.axis.v201708.cm.ManualCpcBiddingScheme;
import com.google.api.ads.adwords.axis.v201708.cm.Money;
import com.google.api.ads.adwords.axis.v201708.cm.NegativeCampaignCriterion;
import com.google.api.ads.adwords.axis.v201708.cm.Operation;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.axis.v201708.cm.Selector;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.selectorfields.v201708.cm.BatchJobField;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.client.auth.oauth2.Credential;
import com.google.common.collect.AbstractSequentialIterator;
import com.google.common.collect.Sets;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.UUID;
import java.util.concurrent.TimeoutException;

/**
 * This code sample illustrates how to use BatchJobService to create a complete
 * campaign, including ad groups and keywords.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class AddCompleteCampaignsUsingBatchJob {
  private static final long NUMBER_OF_CAMPAIGNS_TO_ADD = 2;
  private static final long NUMBER_OF_ADGROUPS_TO_ADD = 2;
  private static final long NUMBER_OF_KEYWORDS_TO_ADD = 5;
  private static final int MAX_POLL_ATTEMPTS = 5;
  private static final Set<BatchJobStatus> PENDING_STATUSES =
      Sets.newHashSet(
          BatchJobStatus.ACTIVE, BatchJobStatus.AWAITING_FILE, BatchJobStatus.CANCELING);

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential =
        new OfflineCredentials.Builder()
            .forApi(Api.ADWORDS)
            .fromFile()
            .build()
            .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session =
        new AdWordsSession.Builder().fromFile().withOAuth2Credential(oAuth2Credential).build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    runExample(adWordsServices, session);
  }

  public static void runExample(AdWordsServicesInterface adWordsServices, AdWordsSession session)
      throws Exception {
    // Get the MutateJobService.
    BatchJobServiceInterface batchJobService =
        adWordsServices.get(session, BatchJobServiceInterface.class);

    // Create a BatchJob.
    BatchJobOperation addOp = new BatchJobOperation();
    addOp.setOperator(Operator.ADD);
    addOp.setOperand(new BatchJob());

    BatchJob batchJob = batchJobService.mutate(new BatchJobOperation[] {addOp}).getValue(0);

    // Get the upload URL from the new job.
    String uploadUrl = batchJob.getUploadUrl().getUrl();

    System.out.printf("Created BatchJob with ID %d, status '%s' and upload URL %s.%n",
        batchJob.getId(), batchJob.getStatus(), uploadUrl);

    // Create a temporary ID generator that will produce a sequence of descending negative numbers.
    Iterator<Long> tempIdGenerator =
        new AbstractSequentialIterator<Long>(-1L) {
          @Override
          protected Long computeNext(Long previous) {
            return Long.MIN_VALUE == previous.longValue() ? null : previous - 1;
          }
        };

    // Use a random UUID name prefix to avoid name collisions.
    String namePrefix = UUID.randomUUID().toString();

    // Create the mutate request that will be sent to the upload URL.
    List<Operation> operations = new ArrayList<>();

    // Create and add an operation to create a new budget.
    BudgetOperation budgetOperation = buildBudgetOperation(tempIdGenerator, namePrefix);
    operations.add(budgetOperation);

    // Create and add operations to create new campaigns.
    List<CampaignOperation> campaignOperations =
        buildCampaignOperations(tempIdGenerator, namePrefix, budgetOperation);
    operations.addAll(campaignOperations);

    // Create and add operations to create new negative keyword criteria for each campaign.
    operations.addAll(buildCampaignCriterionOperations(campaignOperations));

    // Create and add operations to create new ad groups.
    List<AdGroupOperation> adGroupOperations =
        new ArrayList<>(buildAdGroupOperations(tempIdGenerator, namePrefix, campaignOperations));
    operations.addAll(adGroupOperations);

    // Create and add operations to create new ad group criteria (keywords).
    operations.addAll(buildAdGroupCriterionOperations(adGroupOperations));

    // Create and add operations to create new ad group ads (text ads).
    operations.addAll(buildAdGroupAdOperations(adGroupOperations));

    // Use a BatchJobHelper to upload all operations.
    BatchJobHelper batchJobHelper = adWordsServices.getUtility(session, BatchJobHelper.class);

    batchJobHelper.uploadBatchJobOperations(operations, uploadUrl);
    System.out.printf("Uploaded %d operations for batch job with ID %d.%n",
        operations.size(), batchJob.getId());

    // Poll for completion of the batch job using an exponential back off.
    int pollAttempts = 0;
    boolean isPending = true;
    Selector selector =
        new SelectorBuilder()
            .fields(BatchJobField.Id, BatchJobField.Status, BatchJobField.DownloadUrl,
                BatchJobField.ProcessingErrors, BatchJobField.ProgressStats)
            .equalsId(batchJob.getId())
            .build();
    do {
      long sleepSeconds = (long) Math.scalb(30, pollAttempts);
      System.out.printf("Sleeping %d seconds...%n", sleepSeconds);
      Thread.sleep(sleepSeconds * 1000);

      batchJob = batchJobService.get(selector).getEntries(0);
      System.out.printf(
          "Batch job ID %d has status '%s'.%n", batchJob.getId(), batchJob.getStatus());

      pollAttempts++;
      isPending = PENDING_STATUSES.contains(batchJob.getStatus());
    } while (isPending && pollAttempts < MAX_POLL_ATTEMPTS);

    if (isPending) {
      throw new TimeoutException(
          "Job is still in pending state after polling " + MAX_POLL_ATTEMPTS + " times.");
    }

    if (batchJob.getProcessingErrors() != null) {
      int i = 0;
      for (BatchJobProcessingError processingError : batchJob.getProcessingErrors()) {
        System.out.printf(
            "  Processing error [%d]: errorType=%s, trigger=%s, errorString=%s, fieldPath=%s"
            + ", reason=%s%n",
            i++, processingError.getApiErrorType(), processingError.getTrigger(),
            processingError.getErrorString(), processingError.getFieldPath(),
            processingError.getReason());
      }
    } else {
      System.out.println("No processing errors found.");
    }

    if (batchJob.getDownloadUrl() != null && batchJob.getDownloadUrl().getUrl() != null) {
      BatchJobMutateResponse mutateResponse =
          batchJobHelper.downloadBatchJobMutateResponse(batchJob.getDownloadUrl().getUrl());
      System.out.printf("Downloaded results from %s:%n", batchJob.getDownloadUrl().getUrl());
      for (MutateResult mutateResult : mutateResponse.getMutateResults()) {
        String outcome = mutateResult.getErrorList() == null ? "SUCCESS" : "FAILURE";
        System.out.printf("  Operation [%d] - %s%n", mutateResult.getIndex(), outcome);
      }
    } else {
      System.out.println("No results available for download.");
    }
  }

  private static List<AdGroupAdOperation> buildAdGroupAdOperations(
      List<AdGroupOperation> adGroupOperations) {
    List<AdGroupAdOperation> operations = new ArrayList<>();
    for (AdGroupOperation adGroupOperation : adGroupOperations) {
      long adGroupId = adGroupOperation.getOperand().getId();
      AdGroupAd adGroupAd = new AdGroupAd();
      adGroupAd.setAdGroupId(adGroupId);

      ExpandedTextAd textAd = new ExpandedTextAd();
      textAd.setHeadlinePart1("Luxury Cruise to Mars");
      textAd.setHeadlinePart2("Visit the Red Planet in style.");
      textAd.setDescription("Low-gravity fun for everyone!");
      textAd.setFinalUrls(new String[] {"http://www.example.com/1"});

      adGroupAd.setAd(textAd);

      AdGroupAdOperation operation = new AdGroupAdOperation();
      operation.setOperator(Operator.ADD);
      operation.setOperand(adGroupAd);

      operations.add(operation);
    }
    return operations;
  }

  private static List<AdGroupCriterionOperation> buildAdGroupCriterionOperations(
      List<AdGroupOperation> adGroupOperations) {
    List<AdGroupCriterionOperation> adGroupCriteriaOperations = new ArrayList<>();

    // Create AdGroupCriterionOperations to add keywords.
    for (AdGroupOperation adGroupOperation : adGroupOperations) {
      long newAdGroupId = adGroupOperation.getOperand().getId();
      for (int i = 0; i < NUMBER_OF_KEYWORDS_TO_ADD; i++) {
        // Create Keyword.
        String text = String.format("mars%d", i);

        // Make 50% of keywords invalid to demonstrate error handling.
        if (i % 2 == 0) {
          text = text + "!!!";
        }
        Keyword keyword = new Keyword();
        keyword.setText(text);
        keyword.setMatchType(KeywordMatchType.BROAD);

        // Create BiddableAdGroupCriterion.
        BiddableAdGroupCriterion biddableAdGroupCriterion = new BiddableAdGroupCriterion();
        biddableAdGroupCriterion.setAdGroupId(newAdGroupId);
        biddableAdGroupCriterion.setCriterion(keyword);

        // Create AdGroupCriterionOperation.
        AdGroupCriterionOperation operation = new AdGroupCriterionOperation();
        operation.setOperand(biddableAdGroupCriterion);
        operation.setOperator(Operator.ADD);

        // Add to list.
        adGroupCriteriaOperations.add(operation);
      }
    }
    return adGroupCriteriaOperations;
  }

  private static List<AdGroupOperation> buildAdGroupOperations(Iterator<Long> tempIdGenerator,
      String namePrefix, Iterable<CampaignOperation> campaignOperations) {
    List<AdGroupOperation> operations = new ArrayList<>();
    for (CampaignOperation campaignOperation : campaignOperations) {
      for (int i = 0; i < NUMBER_OF_ADGROUPS_TO_ADD; i++) {
        AdGroup adGroup = new AdGroup();
        adGroup.setCampaignId(campaignOperation.getOperand().getId());
        adGroup.setId(tempIdGenerator.next());
        adGroup.setName(String.format("Batch Ad Group %s.%s", namePrefix, i));

        BiddingStrategyConfiguration biddingStrategyConfiguration =
            new BiddingStrategyConfiguration();
        CpcBid bid = new CpcBid();
        bid.setBid(new Money(null, 10000000L));
        biddingStrategyConfiguration.setBids(new Bids[] {bid});

        adGroup.setBiddingStrategyConfiguration(biddingStrategyConfiguration);

        AdGroupOperation operation = new AdGroupOperation();
        operation.setOperand(adGroup);
        operation.setOperator(Operator.ADD);

        operations.add(operation);
      }
    }
    return operations;
  }

  private static List<CampaignCriterionOperation> buildCampaignCriterionOperations(
      List<CampaignOperation> campaignOperations) {

    List<CampaignCriterionOperation> operations = new ArrayList<>();
    for (CampaignOperation campaignOperation : campaignOperations) {
      Keyword keyword = new Keyword();
      keyword.setMatchType(KeywordMatchType.BROAD);
      keyword.setText("venus");

      NegativeCampaignCriterion negativeCriterion = new NegativeCampaignCriterion();
      negativeCriterion.setCampaignId(campaignOperation.getOperand().getId());
      negativeCriterion.setCriterion(keyword);

      CampaignCriterionOperation operation = new CampaignCriterionOperation();
      operation.setOperand(negativeCriterion);
      operation.setOperator(Operator.ADD);

      operations.add(operation);
    }

    return operations;
  }

  private static List<CampaignOperation> buildCampaignOperations(
      Iterator<Long> tempIdGenerator, String namePrefix, BudgetOperation budgetOperation) {
    long budgetId = budgetOperation.getOperand().getBudgetId();

    List<CampaignOperation> operations = new ArrayList<>();
    for (int i = 0; i < NUMBER_OF_CAMPAIGNS_TO_ADD; i++) {
      Campaign campaign = new Campaign();
      campaign.setName(String.format("Batch Campaign %s.%s", namePrefix, i));

      // Recommendation: Set the campaign to PAUSED when creating it to prevent
      // the ads from immediately serving. Set to ENABLED once you've added
      // targeting and the ads are ready to serve.
      campaign.setStatus(CampaignStatus.PAUSED);

      campaign.setId(tempIdGenerator.next());
      campaign.setAdvertisingChannelType(AdvertisingChannelType.SEARCH);
      Budget budget = new Budget();
      budget.setBudgetId(budgetId);
      campaign.setBudget(budget);
      BiddingStrategyConfiguration biddingStrategyConfiguration =
          new BiddingStrategyConfiguration();
      biddingStrategyConfiguration.setBiddingStrategyType(BiddingStrategyType.MANUAL_CPC);

      // You can optionally provide a bidding scheme in place of the type.
      ManualCpcBiddingScheme cpcBiddingScheme = new ManualCpcBiddingScheme();
      cpcBiddingScheme.setEnhancedCpcEnabled(false);
      biddingStrategyConfiguration.setBiddingScheme(cpcBiddingScheme);

      campaign.setBiddingStrategyConfiguration(biddingStrategyConfiguration);

      CampaignOperation operation = new CampaignOperation();
      operation.setOperand(campaign);
      operation.setOperator(Operator.ADD);
      operations.add(operation);
    }
    return operations;
  }

  private static BudgetOperation buildBudgetOperation(Iterator<Long> tempIdGenerator,
      String namePrefix) {
    Budget budget = new Budget();
    budget.setBudgetId(tempIdGenerator.next());
    budget.setName(String.format("Interplanetary Cruise %s", namePrefix));
    Money budgetAmount = new Money();
    budgetAmount.setMicroAmount(50000000L);
    budget.setAmount(budgetAmount);
    budget.setDeliveryMethod(BudgetBudgetDeliveryMethod.STANDARD);

    BudgetOperation budgetOperation = new BudgetOperation();
    budgetOperation.setOperand(budget);
    budgetOperation.setOperator(Operator.ADD);
    return budgetOperation;
  }
}

Add a draft

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterion;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterionOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterionServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.Draft;
import com.google.api.ads.adwords.axis.v201708.cm.DraftOperation;
import com.google.api.ads.adwords.axis.v201708.cm.DraftServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.Language;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example illustrates how to create a draft and access its associated draft campaign.
 *
 * <p>See the Campaign Drafts and Experiments guide for more information:
 * https://developers.google.com/adwords/api/docs/guides/campaign-drafts-experiments
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class AddDraft {

  private static class AddDraftParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.BASE_CAMPAIGN_ID, required = true)
    private Long baseCampaignId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    AddDraftParams params = new AddDraftParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.baseCampaignId = Long.parseLong("INSERT_BASE_CAMPAIGN_ID_HERE");
    }

    runExample(adWordsServices, session, params.baseCampaignId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, long baseCampaignId)
      throws Exception {

    // Get the DraftService.
    DraftServiceInterface draftService = adWordsServices.get(session, DraftServiceInterface.class);
    Draft draft = new Draft();
    draft.setBaseCampaignId(baseCampaignId);
    draft.setDraftName("Test Draft #" + System.currentTimeMillis());

    DraftOperation draftOperation = new DraftOperation();
    draftOperation.setOperator(Operator.ADD);
    draftOperation.setOperand(draft);

    draft = draftService.mutate(new DraftOperation[] {draftOperation}).getValue(0);

    System.out.printf(
        "Draft with ID %d and base campaign ID %d and draft campaign ID %d created.%n",
        draft.getDraftId(), draft.getBaseCampaignId(), draft.getDraftCampaignId());

    // Once the draft is created, you can modify the draft campaign as if it
    // were a real campaign. For example, you may add criteria, adjust bids,
    // or even include additional ads. Adding a criterion is shown here.
    CampaignCriterionServiceInterface campaignCriterionService =
        adWordsServices.get(session, CampaignCriterionServiceInterface.class);

    Language language = new Language();
    language.setId(1003L); // Spanish

    // Make sure to use the draftCampaignId when modifying the virtual draft campaign.
    CampaignCriterion campaignCriterion = new CampaignCriterion();
    campaignCriterion.setCampaignId(draft.getDraftCampaignId());
    campaignCriterion.setCriterion(language);

    CampaignCriterionOperation criterionOperation = new CampaignCriterionOperation();
    criterionOperation.setOperator(Operator.ADD);
    criterionOperation.setOperand(campaignCriterion);

    campaignCriterion =
        campaignCriterionService
            .mutate(new CampaignCriterionOperation[] {criterionOperation})
            .getValue(0);

    System.out.printf(
        "Draft updated to include criteria in draft campaign ID %d.%n", draft.getDraftCampaignId());
  }
}

Add keywords using an incremental batch job

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.utils.v201708.SelectorBuilder;
import com.google.api.ads.adwords.axis.utils.v201708.batchjob.BatchJobHelper;
import com.google.api.ads.adwords.axis.utils.v201708.batchjob.BatchJobMutateResponse;
import com.google.api.ads.adwords.axis.utils.v201708.batchjob.MutateResult;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupCriterionOperation;
import com.google.api.ads.adwords.axis.v201708.cm.ApiException;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJob;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobError;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobErrorReason;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobOperation;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobProcessingError;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.BatchJobStatus;
import com.google.api.ads.adwords.axis.v201708.cm.BiddableAdGroupCriterion;
import com.google.api.ads.adwords.axis.v201708.cm.Keyword;
import com.google.api.ads.adwords.axis.v201708.cm.KeywordMatchType;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.axis.v201708.cm.Selector;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.selectorfields.v201708.cm.BatchJobField;
import com.google.api.ads.adwords.lib.utils.BatchJobUploadResponse;
import com.google.api.ads.adwords.lib.utils.BatchJobUploadStatus;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;
import com.google.common.collect.Sets;
import java.net.URI;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.concurrent.TimeoutException;

/**
 * This code sample illustrates how to perform asynchronous requests using BatchJobService
 * and incremental uploads of operations. It also demonstrates how to cancel a running
 * batch job.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class AddKeywordsUsingIncrementalBatchJob {

  private static final long NUMBER_OF_KEYWORDS_TO_ADD = 100;
  private static final int KEYWORDS_PER_UPLOAD = 10;
  private static final int MAX_POLL_ATTEMPTS = 5;
  private static final Set<BatchJobStatus> PENDING_STATUSES =
      Sets.newHashSet(
          BatchJobStatus.ACTIVE, BatchJobStatus.AWAITING_FILE, BatchJobStatus.CANCELING);

  private static class AddKeywordsUsingIncrementalBatchJobParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.AD_GROUP_ID, required = true)
    private Long adGroupId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    AddKeywordsUsingIncrementalBatchJobParams params =
        new AddKeywordsUsingIncrementalBatchJobParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.adGroupId = Long.parseLong("INSERT_AD_GROUP_ID_HERE");
    }

    runExample(adWordsServices, session, params.adGroupId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, Long adGroupId)
      throws Exception {
    // Get the BatchJobService.
    BatchJobServiceInterface batchJobService =
        adWordsServices.get(session, BatchJobServiceInterface.class);
    
    BatchJobOperation addOp = new BatchJobOperation();
    addOp.setOperator(Operator.ADD);
    addOp.setOperand(new BatchJob());

    BatchJob batchJob = batchJobService.mutate(new BatchJobOperation[] {addOp}).getValue(0);

    System.out.printf("Created BatchJob with ID %d, status '%s' and upload URL %s.%n",
        batchJob.getId(), batchJob.getStatus(), batchJob.getUploadUrl().getUrl());
    
    // Create a BatchJobHelper for uploading operations.
    BatchJobHelper batchJobHelper = adWordsServices.getUtility(session, BatchJobHelper.class);
    BatchJobUploadStatus batchJobUploadStatus = new BatchJobUploadStatus(0, 
        URI.create(batchJob.getUploadUrl().getUrl()));
    
    List<AdGroupCriterionOperation> operations = new ArrayList<AdGroupCriterionOperation>();

    // Create AdGroupCriterionOperations to add keywords, and upload every 10 operations
    // incrementally.
    for (int i = 0; i < NUMBER_OF_KEYWORDS_TO_ADD; i++) {
      // Create Keyword.
      String text = String.format("mars%d", i);

      // Make 10% of keywords invalid to demonstrate error handling.
      if (i % 10 == 0) {
        text = text + "!!!";
      }
      Keyword keyword = new Keyword();
      keyword.setText(text);
      keyword.setMatchType(KeywordMatchType.BROAD);

      // Create BiddableAdGroupCriterion.
      BiddableAdGroupCriterion bagc = new BiddableAdGroupCriterion();
      bagc.setAdGroupId(adGroupId);
      bagc.setCriterion(keyword);

      // Create AdGroupCriterionOperation.
      AdGroupCriterionOperation agco = new AdGroupCriterionOperation();
      agco.setOperand(bagc);
      agco.setOperator(Operator.ADD);

      // Add to the list of operations.
      operations.add(agco);
      
      // If the current list of operations has reached KEYWORDS_PER_UPLOAD or this is the last
      // operation, upload the current list of operations.
      boolean isLastOperation = i == NUMBER_OF_KEYWORDS_TO_ADD - 1;
      if (operations.size() == KEYWORDS_PER_UPLOAD || isLastOperation) {
        BatchJobUploadResponse uploadResponse =
            batchJobHelper.uploadIncrementalBatchJobOperations(
                operations, isLastOperation, batchJobUploadStatus);
        System.out.printf("Uploaded %d operations for batch job with ID %d.%n",
            operations.size(), batchJob.getId());
        
        // Set the batch job upload status and clear the operations list in preparation for the
        // next upload.
        batchJobUploadStatus = uploadResponse.getBatchJobUploadStatus();
        operations.clear();
      }
    }

    // Poll for completion of the batch job using an exponential back off.
    int pollAttempts = 0;
    boolean isPending = true;
    boolean wasCancelRequested = false;
    
    Selector selector =
        new SelectorBuilder()
            .fields(
                BatchJobField.Id,
                BatchJobField.Status,
                BatchJobField.DownloadUrl,
                BatchJobField.ProcessingErrors,
                BatchJobField.ProgressStats)
            .equalsId(batchJob.getId())
            .build();
    do {
      long sleepSeconds = (long) Math.scalb(30, pollAttempts);
      System.out.printf("Sleeping %d seconds...%n", sleepSeconds);
      Thread.sleep(sleepSeconds * 1000);

      batchJob = batchJobService.get(selector).getEntries(0);
      System.out.printf(
          "Batch job ID %d has status '%s'.%n", batchJob.getId(), batchJob.getStatus());

      pollAttempts++;
      isPending = PENDING_STATUSES.contains(batchJob.getStatus());
      
      // Optional: Cancel the job if it has not completed after polling MAX_POLL_ATTEMPTS
      // times.
      if (isPending && !wasCancelRequested && pollAttempts == MAX_POLL_ATTEMPTS) {
        batchJob.setStatus(BatchJobStatus.CANCELING);
        BatchJobOperation batchJobSetOperation = new BatchJobOperation();
        batchJobSetOperation.setOperand(batchJob);
        batchJobSetOperation.setOperator(Operator.SET);
        
        // Only request cancellation once per job.
        wasCancelRequested = true;
        try {
          batchJob =
              batchJobService.mutate(new BatchJobOperation[] {batchJobSetOperation}).getValue(0);
          System.out.printf("Requested cancellation of batch job with ID %d.%n", batchJob.getId());
        } catch (ApiException e) {
          if (e.getErrors() != null
              && e.getErrors().length > 0
              && e.getErrors(0) instanceof BatchJobError) {
            BatchJobError batchJobError = (BatchJobError) e.getErrors(0);
            if (BatchJobErrorReason.INVALID_STATE_CHANGE.equals(batchJobError.getReason())) {
              System.out.printf(
                  "Attempt to cancel batch job with ID %d was rejected because the job already "
                      + "completed or was canceled.",
                  batchJob.getId());
              continue;
            }
          }
          throw e;
        } finally {
          // Reset the poll attempt counter to wait for cancellation.
          pollAttempts = 0;
        }
      }
    } while (isPending && pollAttempts < MAX_POLL_ATTEMPTS);

    if (isPending) {
      throw new TimeoutException(
          "Job is still in pending state after polling " + MAX_POLL_ATTEMPTS + " times.");
    }

    if (batchJob.getProcessingErrors() != null) {
      int errorIndex = 0;
      for (BatchJobProcessingError processingError : batchJob.getProcessingErrors()) {
        System.out.printf(
            "  Processing error [%d]: errorType=%s, trigger=%s, errorString=%s, fieldPath=%s"
                + ", reason=%s%n",
            errorIndex++,
            processingError.getApiErrorType(),
            processingError.getTrigger(),
            processingError.getErrorString(),
            processingError.getFieldPath(),
            processingError.getReason());
      }
    } else {
      System.out.println("No processing errors found.");
    }

    if (batchJob.getDownloadUrl() != null && batchJob.getDownloadUrl().getUrl() != null) {
      BatchJobMutateResponse mutateResponse =
          batchJobHelper.downloadBatchJobMutateResponse(batchJob.getDownloadUrl().getUrl());
      System.out.printf("Downloaded results from %s:%n", batchJob.getDownloadUrl().getUrl());
      for (MutateResult mutateResult : mutateResponse.getMutateResults()) {
        String outcome = mutateResult.getErrorList() == null ? "SUCCESS" : "FAILURE";
        System.out.printf("  Operation [%d] - %s%n", mutateResult.getIndex(), outcome);
      }
    } else {
      System.out.println("No results available for download.");
    }
  }
}

Add a trial

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.utils.v201708.SelectorBuilder;
import com.google.api.ads.adwords.axis.v201708.cm.ApiError;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.axis.v201708.cm.Selector;
import com.google.api.ads.adwords.axis.v201708.cm.Trial;
import com.google.api.ads.adwords.axis.v201708.cm.TrialAsyncError;
import com.google.api.ads.adwords.axis.v201708.cm.TrialAsyncErrorPage;
import com.google.api.ads.adwords.axis.v201708.cm.TrialAsyncErrorServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.TrialOperation;
import com.google.api.ads.adwords.axis.v201708.cm.TrialServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.TrialStatus;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.selectorfields.v201708.cm.TrialAsyncErrorField;
import com.google.api.ads.adwords.lib.selectorfields.v201708.cm.TrialField;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example illustrates how to create a trial and wait for it to complete.
 *
 * <p>See the Campaign Drafts and Experiments guide for more information:
 * https://developers.google.com/adwords/api/docs/guides/campaign-drafts-experiments
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class AddTrial {

  /**
   * Maximum number of {@code TrialService.get} calls to make to query the progress of trial
   * creation.
   */
  private static final int MAX_POLL_ATTEMPTS = 6;

  private static class AddTrialParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.DRAFT_ID, required = true)
    private Long draftId;

    @Parameter(names = ArgumentNames.BASE_CAMPAIGN_ID, required = true)
    private Long baseCampaignId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    AddTrialParams params = new AddTrialParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.draftId = Long.parseLong("INSERT_DRAFT_ID_HERE");
      params.baseCampaignId = Long.parseLong("INSERT_BASE_CAMPAIGN_ID_HERE");
    }

    runExample(adWordsServices, session, params.draftId, params.baseCampaignId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices,
      AdWordsSession session,
      long draftId,
      long baseCampaignId)
      throws Exception {
    // Get the TrialService.
    TrialServiceInterface trialService = adWordsServices.get(session, TrialServiceInterface.class);

    Trial trial = new Trial();
    trial.setDraftId(draftId);
    trial.setBaseCampaignId(baseCampaignId);
    trial.setName("Test Trial #" + System.currentTimeMillis());
    trial.setTrafficSplitPercent(50);

    TrialOperation trialOperation = new TrialOperation();
    trialOperation.setOperator(Operator.ADD);
    trialOperation.setOperand(trial);

    long trialId = trialService.mutate(new TrialOperation[] {trialOperation}).getValue(0).getId();

    // Since creating a trial is asynchronous, we have to poll it to wait for it to finish.
    Selector trialSelector =
        new SelectorBuilder()
            .fields(
                TrialField.Id,
                TrialField.Status,
                TrialField.BaseCampaignId,
                TrialField.TrialCampaignId)
            .equalsId(trialId)
            .build();

    trial = null;
    boolean isPending = true;
    int pollAttempts = 0;
    do {
      long sleepSeconds = (long) Math.scalb(30d, pollAttempts);
      System.out.printf("Sleeping for %d seconds.%n", sleepSeconds);
      Thread.sleep(sleepSeconds * 1000);
      trial = trialService.get(trialSelector).getEntries(0);

      System.out.printf("Trial ID %d has status '%s'.%n", trial.getId(), trial.getStatus());
      pollAttempts++;
      isPending = TrialStatus.CREATING.equals(trial.getStatus());
    } while (isPending && pollAttempts < MAX_POLL_ATTEMPTS);

    if (TrialStatus.ACTIVE.equals(trial.getStatus())) {
      // The trial creation was successful.
      System.out.printf(
          "Trial created with ID %d and trial campaign ID %d.%n",
          trial.getId(),
          trial.getTrialCampaignId());
    } else if (TrialStatus.CREATION_FAILED.equals(trial.getStatus())) {
      // The trial creation failed, and errors can be fetched from the TrialAsyncErrorService.
      Selector errorsSelector =
          new SelectorBuilder()
              .fields(TrialAsyncErrorField.TrialId, TrialAsyncErrorField.AsyncError)
              .equals(TrialAsyncErrorField.TrialId, trial.getId().toString())
              .build();

      TrialAsyncErrorServiceInterface trialAsyncErrorService =
          adWordsServices.get(session, TrialAsyncErrorServiceInterface.class);
      TrialAsyncErrorPage trialAsyncErrorPage = trialAsyncErrorService.get(errorsSelector);
      if (trialAsyncErrorPage.getEntries() == null
          || trialAsyncErrorPage.getEntries().length == 0) {
        System.out.printf(
            "Could not retrieve errors for trial ID %d for draft ID %d.%n", trial.getId(), draftId);
      } else {
        System.out.printf(
            "Could not create trial ID %d for draft ID %d due to the following errors:%n",
            trial.getId(),
            draftId);
        int i = 0;
        for (TrialAsyncError error : trialAsyncErrorPage.getEntries()) {
          ApiError asyncError = error.getAsyncError();
          System.out.printf(
              "Error #%d: errorType='%s', errorString='%s', trigger='%s', fieldPath='%s'%n",
              i++,
              asyncError.getApiErrorType(),
              asyncError.getErrorString(),
              asyncError.getTrigger(),
              asyncError.getFieldPath());
        }
      }
    } else {
      // Most likely, the trial is still being created. You can continue polling,
      // but we have limited the number of attempts in the example.
      System.out.printf(
          "Timed out waiting to create trial from draft ID %d with base campaign ID %d.%n",
          draftId,
          baseCampaignId);
    }
  }
}

Get all disapproved ads in an ad group

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.utils.v201708.SelectorBuilder;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAd;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdPage;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdPolicySummary;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.PolicyApprovalStatus;
import com.google.api.ads.adwords.axis.v201708.cm.PolicyTopicEntry;
import com.google.api.ads.adwords.axis.v201708.cm.Selector;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.selectorfields.v201708.cm.AdGroupAdField;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example gets all disapproved ads in an ad group. To get ad groups, run GetAdGroups.java.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the "ads.properties" file.
 * See README for more info.
 */
public class GetAllDisapprovedAds {

  private static final int PAGE_SIZE = 100;
  
  private static class GetAllDisapprovedAdsParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.AD_GROUP_ID, required = true)
    private Long adGroupId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    GetAllDisapprovedAdsParams params = new GetAllDisapprovedAdsParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.adGroupId = Long.parseLong("INSERT_AD_GROUP_ID_HERE");
    }

    runExample(adWordsServices, session, params.adGroupId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, Long adGroupId)
      throws Exception {
    // Get the AdGroupAdService.
    AdGroupAdServiceInterface adGroupAdService =
        adWordsServices.get(session, AdGroupAdServiceInterface.class);

    int offset = 0;

    // Create selector.
    SelectorBuilder builder = new SelectorBuilder();
    Selector selector =
        builder
            .fields(AdGroupAdField.Id, AdGroupAdField.PolicySummary)
            .orderAscBy(AdGroupAdField.Id)
            .equals(AdGroupAdField.AdGroupId, adGroupId.toString())
            .equals(
                AdGroupAdField.CombinedApprovalStatus,
                PolicyApprovalStatus.DISAPPROVED.toString())
            .offset(offset)
            .limit(PAGE_SIZE)
            .build();

    // Get all disapproved ads.
    AdGroupAdPage page = null;
    int disapprovedAdsCount = 0;

    do {
      page = adGroupAdService.get(selector);

      // Display ads.
      for (AdGroupAd adGroupAd : page) {
        disapprovedAdsCount++;
        AdGroupAdPolicySummary policySummary = adGroupAd.getPolicySummary();
        System.out.printf(
            "Ad with ID %d and type '%s' was disapproved with the following "
                + "policy topic entries:%n",
            adGroupAd.getAd().getId(), adGroupAd.getAd().getAdType());
        for (PolicyTopicEntry policyTopicEntry : policySummary.getPolicyTopicEntries()) {
          System.out.printf(
              "  topic id: %s, topic name: '%s'%n",
              policyTopicEntry.getPolicyTopicId(), policyTopicEntry.getPolicyTopicName());
        }
      }
      offset += PAGE_SIZE;
      selector = builder.increaseOffsetBy(PAGE_SIZE).build();
    } while (offset < page.getTotalNumEntries());
    
    System.out.printf("%d disapproved ads were found.%n", disapprovedAdsCount);
  }
}

Get all disapproved ads in an ad group using AWQL

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAd;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdPage;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdPolicySummary;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.PolicyApprovalStatus;
import com.google.api.ads.adwords.axis.v201708.cm.PolicyTopicEntry;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example gets all disapproved ads in an ad group with AWQL. To get ad groups, run
 * GetAdGroups.java.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the "ads.properties" file.
 * See README for more info.
 */
public class GetAllDisapprovedAdsWithAwql {

  private static final int PAGE_SIZE = 100;
  
  private static class GetAllDisapprovedAdsWithAwqlParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.AD_GROUP_ID, required = true)
    private Long adGroupId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    GetAllDisapprovedAdsWithAwqlParams params = new GetAllDisapprovedAdsWithAwqlParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.adGroupId = Long.parseLong("INSERT_AD_GROUP_ID_HERE");
    }

    runExample(adWordsServices, session, params.adGroupId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, Long adGroupId)
      throws Exception {
    // Get the AdGroupAdService.
    AdGroupAdServiceInterface adGroupAdService =
        adWordsServices.get(session, AdGroupAdServiceInterface.class);

    int offset = 0;

    String query =
        String.format(
            "SELECT Id, PolicySummary "
                + "WHERE AdGroupId = %d AND CombinedApprovalStatus = %s ORDER BY Id",
            adGroupId, PolicyApprovalStatus.DISAPPROVED);

    // Get all disapproved ads.
    AdGroupAdPage page = null;
    int disapprovedAdsCount = 0;
    do {
      String pageQuery = query + String.format(" LIMIT %d, %d", offset, PAGE_SIZE);
      page = adGroupAdService.query(pageQuery);

      // Display ads.
      for (AdGroupAd adGroupAd : page) {
        disapprovedAdsCount++;
        AdGroupAdPolicySummary policySummary = adGroupAd.getPolicySummary();
        System.out.printf(
            "Ad with ID %d and type '%s' was disapproved with the following "
                + "policy topic entries:%n",
            adGroupAd.getAd().getId(), adGroupAd.getAd().getAdType());
        for (PolicyTopicEntry policyTopicEntry : policySummary.getPolicyTopicEntries()) {
          System.out.printf(
              "  topic id: %s, topic name: '%s'%n",
              policyTopicEntry.getPolicyTopicId(), policyTopicEntry.getPolicyTopicName());
        }
      }
      offset += PAGE_SIZE;
    } while (offset < page.getTotalNumEntries());

    System.out.printf("%d disapproved ads were found.%n", disapprovedAdsCount);
  }
}

Get all campaigns with a specific label

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.utils.v201708.SelectorBuilder;
import com.google.api.ads.adwords.axis.v201708.cm.Campaign;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignPage;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.Label;
import com.google.api.ads.adwords.axis.v201708.cm.Selector;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.selectorfields.v201708.cm.CampaignField;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;
import com.google.common.base.Function;
import com.google.common.base.Joiner;
import com.google.common.collect.Lists;

/**
 * This example gets all campaigns with a specific label. To add a label to campaigns,
 * run AddCampaignLabels.java.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class GetCampaignsByLabel {

  private static final int PAGE_SIZE = 100;

  private static class GetCampaignsByLabelParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.LABEL_ID, required = true)
    private Long labelId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    
    GetCampaignsByLabelParams params = new GetCampaignsByLabelParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.labelId = Long.parseLong("INSERT_LABEL_ID_HERE");
    }

    runExample(adWordsServices, session, params.labelId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, Long labelId)
      throws Exception {
    // Get the CampaignService.
    CampaignServiceInterface campaignService =
        adWordsServices.get(session, CampaignServiceInterface.class);

    int offset = 0;

    // Create selector.
    SelectorBuilder builder = new SelectorBuilder();
    Selector selector = builder
        .fields(CampaignField.Id, CampaignField.Name, CampaignField.Labels)
        // Labels filtering is performed by ID. You can use containsAny to select campaigns with
        // any of the label IDs, containsAll to select campaigns with all of the label IDs, or
        // containsNone to select campaigns with none of the label IDs.
        .containsAny(CampaignField.Labels, labelId.toString())
        .orderAscBy(CampaignField.Name)
        .offset(offset)
        .limit(PAGE_SIZE)
        .build();

    CampaignPage page = null;
    do {
      // Get all campaigns.
      page = campaignService.get(selector);

      // Display campaigns.
      if (page.getEntries() != null) {
        for (Campaign campaign : page.getEntries()) {
          String labels = Joiner.on(", ").join(Lists.transform(
              Lists.newArrayList(campaign.getLabels()), new Function<Label, String>() {
                @Override
                public String apply(Label label) {
                  return String.format("%d/%s", label.getId(), label.getName());
                }
              }));
          System.out.printf("Campaign found with name '%s' and ID %d and labels: %s.%n",
              campaign.getName(), campaign.getId(), labels);
        }
      } else {
        System.out.println("No campaigns were found.");
      }

      offset += PAGE_SIZE;
      selector = builder.increaseOffsetBy(PAGE_SIZE).build();
    } while (offset < page.getTotalNumEntries());
  }
}

Graduate a trial

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.Budget;
import com.google.api.ads.adwords.axis.v201708.cm.BudgetBudgetDeliveryMethod;
import com.google.api.ads.adwords.axis.v201708.cm.BudgetOperation;
import com.google.api.ads.adwords.axis.v201708.cm.BudgetServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.Money;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.axis.v201708.cm.Trial;
import com.google.api.ads.adwords.axis.v201708.cm.TrialOperation;
import com.google.api.ads.adwords.axis.v201708.cm.TrialServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.TrialStatus;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example illustrates how to graduate a trial.
 * 
 * <p>See the Campaign Drafts and Experiments guide for more information:
 * https://developers.google.com/adwords/api/docs/guides/campaign-drafts-experiments
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class GraduateTrial {

  private static class GraduateTrialParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.TRIAL_ID, required = true)
    private Long trialId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    GraduateTrialParams params = new GraduateTrialParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.trialId = Long.parseLong("INSERT_TRIAL_ID_HERE");
    }

    runExample(adWordsServices, session, params.trialId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, long trialId)
      throws Exception {
    // Get the TrialService and BudgetService.
    TrialServiceInterface trialService = adWordsServices.get(session, TrialServiceInterface.class);
    BudgetServiceInterface budgetService =
        adWordsServices.get(session, BudgetServiceInterface.class);

    // To graduate a trial, you must specify a different budget from the base campaign. The base
    // campaign (in order to have had a trial based on it) must have a non-shared budget, so it
    // cannot be shared with the new independent campaign created by graduation.
    Budget budget = new Budget();
    budget.setName("Budget #" + System.currentTimeMillis());
    Money budgetAmount = new Money();
    budgetAmount.setMicroAmount(50000000L);
    budget.setAmount(budgetAmount);
    budget.setDeliveryMethod(BudgetBudgetDeliveryMethod.STANDARD);

    BudgetOperation budgetOperation = new BudgetOperation();
    budgetOperation.setOperator(Operator.ADD);
    budgetOperation.setOperand(budget);

    // Add budget.
    long budgetId =
        budgetService.mutate(new BudgetOperation[] {budgetOperation}).getValue(0).getBudgetId();

    Trial trial = new Trial();
    trial.setId(trialId);
    trial.setBudgetId(budgetId);
    trial.setStatus(TrialStatus.GRADUATED);

    TrialOperation trialOperation = new TrialOperation();
    trialOperation.setOperator(Operator.SET);
    trialOperation.setOperand(trial);

    // Update the trial.
    trial = trialService.mutate(new TrialOperation[] {trialOperation}).getValue(0);

    // Graduation is a synchronous operation, so the campaign is already ready. If you promote
    // instead, make sure to see the polling scheme demonstrated in AddTrial.java to wait for the
    // asynchronous operation to finish.
    System.out.printf(
        "Trial ID %d graduated. Campaign ID %d was given a new budget ID %d and "
            + "is no longer dependent on this trial.%n",
        trial.getId(),
        trial.getTrialCampaignId(),
        budgetId);
  }
}

Set ad parameters

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.AdParam;
import com.google.api.ads.adwords.axis.v201708.cm.AdParamOperation;
import com.google.api.ads.adwords.axis.v201708.cm.AdParamServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example sets ad parameters for a keyword ad group criterion. To get ad
 * group criteria, run GetKeywords.java.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class SetAdParameters {

  private static class SetAdParametersParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.AD_GROUP_ID, required = true)
    private Long adGroupId;

    @Parameter(names = ArgumentNames.KEYWORD_ID, required = true)
    private Long keywordId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    SetAdParametersParams params = new SetAdParametersParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.adGroupId = Long.parseLong("INSERT_AD_GROUP_ID_HERE");
      params.keywordId = Long.parseLong("INSERT_KEYWORD_ID_HERE");
    }

    runExample(adWordsServices, session, params.adGroupId, params.keywordId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices,
      AdWordsSession session,
      Long adGroupId,
      Long keywordId)
      throws Exception {
    // Get the AdParamService.
    AdParamServiceInterface adParamService =
        adWordsServices.get(session, AdParamServiceInterface.class);

    // Create ad params.
    AdParam adParam1 = new AdParam();
    adParam1.setAdGroupId(adGroupId);
    adParam1.setCriterionId(keywordId);
    adParam1.setInsertionText("100");
    adParam1.setParamIndex(1);

    AdParam adParam2 = new AdParam();
    adParam2.setAdGroupId(adGroupId);
    adParam2.setCriterionId(keywordId);
    adParam2.setInsertionText("$40");
    adParam2.setParamIndex(2);

    // Create operations.
    AdParamOperation adParamOperation1 = new AdParamOperation();
    adParamOperation1.setOperand(adParam1);
    adParamOperation1.setOperator(Operator.SET);

    AdParamOperation adParamOperation2 = new AdParamOperation();
    adParamOperation2.setOperand(adParam2);
    adParamOperation2.setOperator(Operator.SET);

    AdParamOperation[] operations = new AdParamOperation[] {adParamOperation1, adParamOperation2};

    // Set ad parameters.
    AdParam[] adParams = adParamService.mutate(operations);

    // Display ad parameters.
    for (AdParam adParam : adParams) {
      System.out.printf("Ad parameter with ad group ID %d, criterion ID %d, insertion text "
          + "'%s', and parameter index %d was set.%n", adParam.getAdGroupId(), 
          adParam.getCriterionId(), adParam.getInsertionText(), adParam.getParamIndex());
    }
  }
}

Set bid modifier

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterion;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterionOperation;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterionReturnValue;
import com.google.api.ads.adwords.axis.v201708.cm.CampaignCriterionServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.axis.v201708.cm.Platform;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example sets a bid modifier for the mobile platform on given campaign.
 * To get campaigns, run basicoperations/GetCampaigns.java.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class SetBidModifier {

  private static final double BID_MODIFIER = 1.5;

  private static class SetBidModifierParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.CAMPAIGN_ID, required = true)
    private Long campaignId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    SetBidModifierParams params = new SetBidModifierParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.campaignId = Long.parseLong("INSERT_CAMPAIGN_ID_HERE");
    }

    runExample(adWordsServices, session, params.campaignId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, Long campaignId)
      throws Exception {
    // Get the CampaignCriterionService.
    CampaignCriterionServiceInterface campaignCriterionService =
        adWordsServices.get(session, CampaignCriterionServiceInterface.class);

    // Create mobile platform. The ID can be found in the documentation.
    // https://developers.google.com/adwords/api/docs/appendix/platforms
    Platform mobile = new Platform();
    mobile.setId(30001L);

    // Create criterion with modified bid.
    CampaignCriterion campaignCriterion = new CampaignCriterion();
    campaignCriterion.setCampaignId(campaignId);
    campaignCriterion.setCriterion(mobile);
    campaignCriterion.setBidModifier(BID_MODIFIER);

    // Create SET operation.
    CampaignCriterionOperation operation = new CampaignCriterionOperation();
    operation.setOperand(campaignCriterion);
    operation.setOperator(Operator.SET);

    // Update campaign criterion.
    CampaignCriterionReturnValue result =
        campaignCriterionService.mutate(new CampaignCriterionOperation[] {operation});
    for (CampaignCriterion campaignCriterionResult : result.getValue()) {
      System.out.printf("Campaign criterion with campaign ID %d, criterion ID %d, "
          + "and type '%s' was modified with bid %.4f.%n",
          campaignCriterionResult.getCampaignId(),
          campaignCriterionResult.getCriterion().getId(),
          campaignCriterionResult.getCriterion().getType(),
          campaignCriterionResult.getBidModifier());
    }
  }
}

Validate text ad

// Copyright 2017 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package adwords.axis.v201708.campaignmanagement;

import com.beust.jcommander.Parameter;
import com.google.api.ads.adwords.axis.factory.AdWordsServices;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAd;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdOperation;
import com.google.api.ads.adwords.axis.v201708.cm.AdGroupAdServiceInterface;
import com.google.api.ads.adwords.axis.v201708.cm.ApiException;
import com.google.api.ads.adwords.axis.v201708.cm.ExpandedTextAd;
import com.google.api.ads.adwords.axis.v201708.cm.Operator;
import com.google.api.ads.adwords.lib.client.AdWordsSession;
import com.google.api.ads.adwords.lib.factory.AdWordsServicesInterface;
import com.google.api.ads.adwords.lib.utils.examples.ArgumentNames;
import com.google.api.ads.common.lib.auth.OfflineCredentials;
import com.google.api.ads.common.lib.auth.OfflineCredentials.Api;
import com.google.api.ads.common.lib.utils.examples.CodeSampleParams;
import com.google.api.client.auth.oauth2.Credential;

/**
 * This example shows how to use the validate only header through the
 * {@link AdWordsSession#setValidateOnly(Boolean)} method. No objects will be
 * created, but exceptions will still be thrown.
 *
 * <p>Credentials and properties in {@code fromFile()} are pulled from the
 * "ads.properties" file. See README for more info.
 */
public class ValidateTextAd {

  private static class ValidateTextAdParams extends CodeSampleParams {
    @Parameter(names = ArgumentNames.AD_GROUP_ID, required = true)
    private Long adGroupId;
  }

  public static void main(String[] args) throws Exception {
    // Generate a refreshable OAuth2 credential.
    Credential oAuth2Credential = new OfflineCredentials.Builder()
        .forApi(Api.ADWORDS)
        .fromFile()
        .build()
        .generateCredential();

    // Construct an AdWordsSession.
    AdWordsSession session = new AdWordsSession.Builder()
        .fromFile()
        .withOAuth2Credential(oAuth2Credential)
        .build();

    AdWordsServicesInterface adWordsServices = AdWordsServices.getInstance();

    ValidateTextAdParams params = new ValidateTextAdParams();
    if (!params.parseArguments(args)) {
      // Either pass the required parameters for this example on the command line, or insert them
      // into the code here. See the parameter class definition above for descriptions.
      params.adGroupId = Long.parseLong("INSERT_AD_GROUP_ID_HERE");
    }

    runExample(adWordsServices, session, params.adGroupId);
  }

  public static void runExample(
      AdWordsServicesInterface adWordsServices, AdWordsSession session, Long adGroupId)
      throws Exception {
    // Enable validation.
    session.setValidateOnly(true);

    // Get the validation AdGroupAdService.
    AdGroupAdServiceInterface adGroupAdValidationService =
        adWordsServices.get(session, AdGroupAdServiceInterface.class);

    // Create text ad.
    ExpandedTextAd textAd1 = new ExpandedTextAd();
    textAd1.setHeadlinePart1("Luxury Cruise to Mars");
    textAd1.setHeadlinePart2("Visit the Red Planet in style.");
    textAd1.setDescription("Low-gravity fun for everyone!");
    textAd1.setFinalUrls(new String[] {"http://www.example.com"});

    // Create ad group ad.
    AdGroupAd textAdGroupAd1 = new AdGroupAd();
    textAdGroupAd1.setAdGroupId(adGroupId);
    textAdGroupAd1.setAd(textAd1);

    // Create operations.
    AdGroupAdOperation textAdGroupAdOperation1 = new AdGroupAdOperation();
    textAdGroupAdOperation1.setOperand(textAdGroupAd1);
    textAdGroupAdOperation1.setOperator(Operator.ADD);

    AdGroupAdOperation[] operations = new AdGroupAdOperation[] {textAdGroupAdOperation1};

    // Add ads.
    adGroupAdValidationService.mutate(operations);
    
    // No error means the request is valid.

    // Now let's check an invalid ad using a very long line to trigger an error.
    textAd1.setDescription("Low-gravity fun for all astronauts in orbit.");

    try {
      adGroupAdValidationService.mutate(operations);
    } catch (ApiException e) {
      System.err.printf("Validation failed for the following reason: %s%n", e.getMessage());
    }
  }
}

Send feedback about...

AdWords API
AdWords API
Need help? Visit our support page.