public EncTicketPart( TicketFlags param0, EncryptionKey param1, Realm param2, PrincipalName param3, TransitedEncoding param4, KerberosTime param5, KerberosTime param6, KerberosTime param7, KerberosTime param8, HostAddresses param9, AuthorizationData param10) { this.flags = param0; this.key = param1; this.crealm = param2; this.cname = param3; this.transited = param4; this.authtime = param5; this.starttime = param6; this.endtime = param7; this.renew_till = param8; this.caddr = param9; this.authorization_data = param10; }
public AD_AND_OR( KerbInt32 param0, AuthorizationData param1) { this.condition_count = param0; this.elements = param1; }
public AD_KDCIssued( Checksum param0, Realm param1, PrincipalName param2, AuthorizationData param3) { this.ad_checksum = param0; this.i_realm = param1; this.i_sname = param2; this.elements = param3; }
public Authenticator( Asn1Integer param0, Realm param1, PrincipalName param2, Checksum param3, Microseconds param4, KerberosTime param5, EncryptionKey param6, KerbUInt32 param7, AuthorizationData param8) { this.authenticator_vno = param0; this.crealm = param1; this.cname = param2; this.cksum = param3; this.cusec = param4; this.ctime = param5; this.subkey = param6; this.seq_number = param7; this.authorization_data = param8; }
private PA_DATA CreatePaTgsReq(ChecksumType checksumType, byte[] checksumBody, AuthorizationData data) { APOptions option = new APOptions(KerberosUtility.ConvertInt2Flags((int)ApOptions.None)); EncryptionKey key = Context.SessionKey; EncryptionKey subkey = null; Ticket ticket = Context.Ticket.Ticket; KerberosApRequest apRequest = CreateApRequest(option, Context.Ticket, subkey, data, KeyUsageNumber.TG_REQ_PA_TGS_REQ_padataOR_AP_REQ_Authenticator, checksumType, checksumBody); PaTgsReq paTgsReq = new PaTgsReq(apRequest.Request); return paTgsReq.Data; }
public async override Task RunAsync(AuthorizationData authorizationData) { try { ApiEnvironment environment = ((OAuthDesktopMobileAuthCodeGrant)authorizationData.Authentication).Environment; BulkServiceManager = new BulkServiceManager( authorizationData: authorizationData, apiEnvironment: environment); BulkServiceManager.StatusPollIntervalInMilliseconds = 5000; // Track download or upload progress var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(string.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); // Some BulkServiceManager operations can be cancelled after a time interval. var tokenSource = new CancellationTokenSource(); tokenSource.CancelAfter(TimeoutInMilliseconds); // Download all campaigns, ad groups, and ads in the account. var entities = new[] { DownloadEntity.Campaigns, DownloadEntity.AdGroups, DownloadEntity.Ads, }; // DownloadParameters is used for Option A below. var downloadParameters = new DownloadParameters { CampaignIds = null, DataScope = DataScope.EntityData | DataScope.QualityScoreData, DownloadEntities = entities, FileType = FileType, LastSyncTimeInUTC = null, ResultFileDirectory = FileDirectory, ResultFileName = DownloadFileName, OverwriteResultFile = true }; // SubmitDownloadParameters is used for Option B and Option C below. var submitDownloadParameters = new SubmitDownloadParameters { CampaignIds = null, DataScope = DataScope.EntityData | DataScope.QualityScoreData, DownloadEntities = entities, FileType = FileType, LastSyncTimeInUTC = null }; // Option A - Background Completion with BulkServiceManager // You can submit a download or upload request and the BulkServiceManager will automatically // return results. The BulkServiceManager abstracts the details of checking for result file // completion, and you don't have to write any code for results polling. OutputStatusMessage("-----\nAwaiting Background Completion with DownloadFileAsync..."); await BackgroundCompletionAsync( downloadParameters : downloadParameters, progress : progress, cancellationToken : tokenSource.Token); // Alternatively we can use DownloadEntitiesAsync if we want to work with the entities in memory. // If you enable this option the result file from BackgroundCompletionAsync will also be deleted // if written to the same working directory. OutputStatusMessage("-----\nAwaiting Background Completion with DownloadEntitiesAsync..."); var downloadEntities = await DownloadEntitiesAsync( downloadParameters : downloadParameters, progress : progress, cancellationToken : tokenSource.Token); // Option B - Submit and Download with BulkServiceManager // Submit the download request and then use the BulkDownloadOperation result to // track status until the download is complete e.g. either using // TrackAsync or GetStatusAsync. OutputStatusMessage("-----\nAwaiting Submit, Track, and Download..."); await SubmitTrackDownloadAsync( submitDownloadParameters : submitDownloadParameters, progress : progress, cancellationToken : tokenSource.Token); // A second variation of Option B. // See SubmitTrackDownloadAsync for details. OutputStatusMessage("-----\nAwaiting Submit, Poll, and Download..."); await SubmitTrackDownloadAsync( submitDownloadParameters : submitDownloadParameters, progress : progress, cancellationToken : tokenSource.Token); // Option C - Download Results with BulkServiceManager // If for any reason you have to resume from a previous application state, // you can use an existing download request identifier and use it // to download the result file. // For example you might have previously retrieved a request ID using SubmitDownloadAsync. var bulkDownloadOperation = await BulkServiceManager.SubmitDownloadAsync( parameters : submitDownloadParameters); var requestId = bulkDownloadOperation.RequestId; // Given the request ID above, you can resume the workflow and download the bulk file. // The download request identifier is valid for two days. // If you do not download the bulk file within two days, you must request it again. OutputStatusMessage("-----\nAwaiting Download Results..."); await DownloadResultsAsync( requestId : requestId, authorizationData : authorizationData, progress : progress, cancellationToken : tokenSource.Token); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.V13.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(String.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V13.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(String.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(String.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
private async Task <Token> AskServerForToken(string clientId, string secretId, AuthorizationData authData) { return(await Task.Run(async() => { Token token = null; Thread.Sleep(1000 * 15); var rtdf = "https://allegro.pl/auth/oauth/token?grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Adevice_code&device_code="; var url = new Uri(rtdf + authData.DeviceCode); var oAuth = getAuthParameters(clientId, secretId); while (true) { var res = await sendRequest(url, oAuth, "application/json", ""); if (res.ResultOk) { token = Utility.Deserialize <Token>(res.Stream); token.TimeCreated = DateTime.UtcNow; break; } Thread.Sleep(1000 * authData.Interval); } return token; })); }
public async override Task RunAsync(AuthorizationData authorizationData) { try { ApiEnvironment environment = ((OAuthDesktopMobileAuthCodeGrant)authorizationData.Authentication).Environment; CampaignManagementExampleHelper CampaignManagementExampleHelper = new CampaignManagementExampleHelper( OutputStatusMessageDefault: this.OutputStatusMessage); CampaignManagementExampleHelper.CampaignManagementService = new ServiceClient <ICampaignManagementService>( authorizationData: authorizationData, environment: environment); // Add a campaign that will later be associated with negative keywords. var campaigns = new[] { new Campaign { BudgetType = BudgetLimitType.DailyBudgetStandard, DailyBudget = 50, CampaignType = CampaignType.Search, Description = "Red shoes line.", Languages = new string[] { "All" }, Name = "Women's Shoes " + DateTime.UtcNow, TimeZone = "PacificTimeUSCanadaTijuana", }, }; OutputStatusMessage("-----\nAddCampaigns:"); AddCampaignsResponse addCampaignsResponse = await CampaignManagementExampleHelper.AddCampaignsAsync( accountId : authorizationData.AccountId, campaigns : campaigns, includeDynamicSearchAdsSource : false); long?[] campaignIds = addCampaignsResponse.CampaignIds.ToArray(); BatchError[] campaignErrors = addCampaignsResponse.PartialErrors.ToArray(); OutputStatusMessage("CampaignIds:"); CampaignManagementExampleHelper.OutputArrayOfLong(campaignIds); OutputStatusMessage("PartialErrors:"); CampaignManagementExampleHelper.OutputArrayOfBatchError(campaignErrors); long campaignId = (long)campaignIds[0]; // You may choose to associate an exclusive set of negative keywords to an individual campaign // or ad group. An exclusive set of negative keywords cannot be shared with other campaigns // or ad groups. This example only associates negative keywords with a campaign. var entityNegativeKeywords = new[] { new EntityNegativeKeyword { EntityId = campaignId, EntityType = "Campaign", NegativeKeywords = new[] { new NegativeKeyword { MatchType = MatchType.Phrase, Text = "auto" }, new NegativeKeyword { MatchType = MatchType.Exact, Text = "auto" }, } } }; OutputStatusMessage("-----\nAddNegativeKeywordsToEntities:"); AddNegativeKeywordsToEntitiesResponse addNegativeKeywordsToEntitiesResponse = await CampaignManagementExampleHelper.AddNegativeKeywordsToEntitiesAsync( entityNegativeKeywords : entityNegativeKeywords); OutputStatusMessage("Added an exclusive set of negative keywords to the Campaign"); OutputStatusMessage("NegativeKeywordIds:"); CampaignManagementExampleHelper.OutputArrayOfIdCollection(addNegativeKeywordsToEntitiesResponse.NegativeKeywordIds); OutputStatusMessage("NestedPartialErrors:"); CampaignManagementExampleHelper.OutputArrayOfBatchErrorCollection(addNegativeKeywordsToEntitiesResponse.NestedPartialErrors); // If you attempt to delete a negative keyword without an identifier the operation will return // partial errors corresponding to the index of the negative keyword that was not deleted. OutputStatusMessage("-----\nDeleteNegativeKeywordsFromEntities:"); BatchErrorCollection[] nestedPartialErrors = (await CampaignManagementExampleHelper.DeleteNegativeKeywordsFromEntitiesAsync( entityNegativeKeywords: entityNegativeKeywords)).NestedPartialErrors.ToArray(); OutputStatusMessage("Attempt to DeleteNegativeKeywordsFromEntities without NegativeKeyword identifier partially fails by design."); CampaignManagementExampleHelper.OutputArrayOfBatchErrorCollection(nestedPartialErrors); // Negative keywords can also be added and deleted from a shared negative keyword list. // The negative keyword list can be shared or associated with multiple campaigns. // NegativeKeywordList inherits from SharedList which inherits from SharedEntity. var negativeKeywordList = new NegativeKeywordList { Name = "My Negative Keyword List" + DateTime.UtcNow, Type = "NegativeKeywordList" }; SharedListItem[] negativeKeywords = { new NegativeKeyword { Text = "car", Type = "NegativeKeyword", MatchType = MatchType.Exact }, new NegativeKeyword { Text = "car", Type = "NegativeKeyword", MatchType = MatchType.Phrase } }; // Add a negative keyword list that can be shared. OutputStatusMessage("-----\nAddSharedEntity:"); var addSharedEntityResponse = await CampaignManagementExampleHelper.AddSharedEntityAsync( sharedEntity : negativeKeywordList, listItems : negativeKeywords); var sharedEntityId = addSharedEntityResponse.SharedEntityId; long[] listItemIds = addSharedEntityResponse.ListItemIds.ToArray(); OutputStatusMessage(string.Format( "NegativeKeywordList added to account library and assigned identifer {0}", sharedEntityId) ); // Negative keywords were added to the negative keyword list above. You can associate the // shared list of negative keywords with a campaign with or without negative keywords. // Shared negative keyword lists cannot be associated with an ad group. An ad group can only // be assigned an exclusive set of negative keywords. var associations = new[] { new SharedEntityAssociation { EntityId = campaignId, EntityType = "Campaign", SharedEntityId = sharedEntityId, SharedEntityType = "NegativeKeywordList" } }; OutputStatusMessage("-----\nSetSharedEntityAssociations:"); var partialErrors = (await CampaignManagementExampleHelper.SetSharedEntityAssociationsAsync( associations: associations)).PartialErrors; OutputStatusMessage(string.Format( "Associated CampaignId {0} with Negative Keyword List Id {1}.", campaignId, sharedEntityId) ); // Delete the campaign and everything it contains e.g., ad groups and ads. OutputStatusMessage("-----\nDeleteCampaigns:"); await CampaignManagementExampleHelper.DeleteCampaignsAsync( accountId : authorizationData.AccountId, campaignIds : new[] { (long)campaignIds[0] }); OutputStatusMessage(string.Format("Deleted Campaign Id {0}", campaignIds[0])); // DeleteCampaigns does not delete the negative keyword list from the account's library. // Call the DeleteSharedEntities operation to delete the negative keyword list. OutputStatusMessage("-----\nDeleteSharedEntities:"); partialErrors = (await CampaignManagementExampleHelper.DeleteSharedEntitiesAsync( sharedEntities: new SharedEntity[] { new NegativeKeywordList { Id = sharedEntityId } }))?.PartialErrors; OutputStatusMessage(string.Format("Deleted Negative Keyword List Id {0}", sharedEntityId)); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
public void ChannelBindingSuccess_Http() { base.Logging(); client = new KerberosTestClient(this.testConfig.LocalRealm.RealmName, this.testConfig.LocalRealm.User[1].Username, this.testConfig.LocalRealm.User[1].Password, KerberosAccountType.User, testConfig.LocalRealm.KDC[0].IPAddress, testConfig.LocalRealm.KDC[0].Port, testConfig.TransportType, testConfig.SupportedOid); // Kerberos Proxy Service is used if (this.testConfig.UseProxy) { BaseTestSite.Log.Add(LogEntryKind.Comment, "Initialize KKDCP Client ."); KKDCPClient proxyClient = new KKDCPClient(proxyClientConfig); proxyClient.TargetDomain = this.testConfig.LocalRealm.RealmName; client.UseProxy = true; client.ProxyClient = proxyClient; } //Create and send AS request KdcOptions options = KdcOptions.FORWARDABLE | KdcOptions.CANONICALIZE | KdcOptions.RENEWABLE; client.SendAsRequest(options, null); //Recieve preauthentication required error METHOD_DATA methodData; KerberosKrbError krbError = client.ExpectPreauthRequiredError(out methodData); //Create sequence of PA data string timeStamp = KerberosUtility.CurrentKerberosTime.Value; PaEncTimeStamp paEncTimeStamp = new PaEncTimeStamp(timeStamp, 0, client.Context.SelectedEType, this.client.Context.CName.Password, this.client.Context.CName.Salt); PaPacRequest paPacRequest = new PaPacRequest(true); Asn1SequenceOf<PA_DATA> seqOfPaData = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paEncTimeStamp.Data, paPacRequest.Data }); //Create and send AS request client.SendAsRequest(options, seqOfPaData); KerberosAsResponse asResponse = client.ExpectAsResponse(); BaseTestSite.Assert.IsNotNull(asResponse.Response.ticket, "AS response should contain a TGT."); //Create and send TGS request client.SendTgsRequest(this.testConfig.LocalRealm.WebServer[0].HttpServiceName, options); KerberosTgsResponse tgsResponse = client.ExpectTgsResponse(); BaseTestSite.Assert.IsNotNull(tgsResponse.Response.ticket, "Service ticket should not be null."); //AP exchange part AdAuthDataApOptions authApOptions = new AdAuthDataApOptions(KerberosConstValue.KERB_AP_OPTIONS_CBT); AdIfRelevent adIfRelevent = new AdIfRelevent(new AD_IF_RELEVANT(new AuthorizationDataElement[] { authApOptions.AuthDataElement })); AuthorizationData data = new AuthorizationData(new AuthorizationDataElement[] { adIfRelevent.AuthDataElement }); EncryptionKey subkey = KerberosUtility.GenerateKey(client.Context.SessionKey); byte[] token = client.CreateGssApiToken(ApOptions.MutualRequired, data, subkey, ChecksumFlags.GSS_C_MUTUAL_FLAG | ChecksumFlags.GSS_C_INTEG_FLAG); BaseTestSite.Log.Add(LogEntryKind.Comment, "Create and send Http request."); KerberosApResponse apRep = client.GetApResponseFromToken(SendAndRecieveHttpAp(this.testConfig.LocalRealm.WebServer[0], token)); BaseTestSite.Log.Add(LogEntryKind.Comment, "Recieve Http response."); }
/// <summary> /// Initializes a new instance of this class with the specified <paramref name="requestId"/> and <see cref="BingAds.AuthorizationData"/>. /// </summary> /// <param name="requestId">The identifier of a download request that has previously been submitted.</param> /// <param name="authorizationData"> /// Represents a user who intends to access the corresponding customer and account. /// </param> public ReportingDownloadOperation(string requestId, AuthorizationData authorizationData) : this(requestId, authorizationData, null, null) { }
public async override Task RunAsync(AuthorizationData authorizationData) { try { CampaignService = new ServiceClient <ICampaignManagementService>(authorizationData); BulkServiceManager = new BulkServiceManager(authorizationData); var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(string.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); OutputStatusMessage("Add and Update Criterions . . .\n"); await AddUpdateDeleteCriterions().ConfigureAwait(continueOnCapturedContext: false); } // Catch Microsoft Account authorization exceptions. catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.V11.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } finally { if (Reader != null) { Reader.Dispose(); } if (Writer != null) { Writer.Dispose(); } } }
internal ReportingDownloadOperation(string requestId, AuthorizationData authorizationData, string trackingId) : this(requestId, authorizationData, new ReportingStatusProvider(requestId), trackingId, null) { }
private KDC_REQ_BODY CreateKdcRequestBody( KdcOptions kdcOptions, PrincipalName sName, AuthorizationData data = null ) { KDC_REQ_BODY kdcReqBody = CreateKdcRequestBody(kdcOptions, sName); if (data == null) return kdcReqBody; Asn1BerEncodingBuffer asnBuffer = new Asn1BerEncodingBuffer(); // Fix me: NullReferenceException if data is null. if (data != null) data.BerEncode(asnBuffer, true); EncryptedData eData = new EncryptedData(); eData.etype = new KerbInt32(0); byte[] encAsnEncoded = asnBuffer.Data; if (Context.SessionKey != null && Context.SessionKey.keytype != null && Context.SessionKey.keyvalue != null && Context.SessionKey.keyvalue.Value != null) { encAsnEncoded = KerberosUtility.Encrypt((EncryptionType)Context.SessionKey.keytype.Value, Context.SessionKey.keyvalue.ByteArrayValue, asnBuffer.Data, (int)KeyUsageNumber.TGS_REQ_KDC_REQ_BODY_AuthorizationData); eData.etype = new KerbInt32(Context.SessionKey.keytype.Value); } eData.cipher = new Asn1OctetString(encAsnEncoded); kdcReqBody.enc_authorization_data = eData; return kdcReqBody; }
public async override Task RunAsync(AuthorizationData authorizationData) { try { ApiEnvironment environment = ((OAuthDesktopMobileAuthCodeGrant)authorizationData.Authentication).Environment; CustomerManagementExampleHelper CustomerManagementExampleHelper = new CustomerManagementExampleHelper(this.OutputStatusMessage); CustomerManagementExampleHelper.CustomerManagementService = new ServiceClient <ICustomerManagementService>(authorizationData, environment); var getUserResponse = await CustomerManagementExampleHelper.GetUserAsync(null, true); var user = getUserResponse.User; // Search for the Bing Ads accounts that the user can access. var predicate = new Predicate { Field = "UserId", Operator = PredicateOperator.Equals, Value = user.Id.ToString() }; var paging = new Paging { Index = 0, Size = 10 }; var request = new SearchAccountsRequest { Ordering = null, PageInfo = paging, Predicates = new[] { predicate } }; var accounts = (await CustomerManagementExampleHelper.SearchAccountsAsync( new[] { predicate }, null, paging ))?.Accounts.ToArray(); OutputStatusMessage("The user can access the following Bing Ads accounts: \n"); foreach (var account in accounts) { CustomerManagementExampleHelper.OutputAdvertiserAccount(account); // You can find out which pilot features the customer is able to use. // Each account could belong to a different customer, so use the customer ID in each account. var featurePilotFlags = (await CustomerManagementExampleHelper.GetCustomerPilotFeaturesAsync(account.ParentCustomerId)).FeaturePilotFlags; OutputStatusMessage("Customer Pilot flags:"); OutputStatusMessage(string.Join("; ", featurePilotFlags.Select(flag => string.Format("{0}", flag)))); } } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Customer Management service exceptions catch (FaultException <Microsoft.BingAds.V12.CustomerManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.CustomerManagement.ApiFault> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
/// <summary> /// Create authenticator for ChecksumType.ap_authenticator_8003 /// </summary> private Authenticator CreateAuthenticator( KerberosTicket ticket, AuthorizationData data, EncryptionKey subkey, ChecksumFlags checksumFlag ) { Authenticator plaintextAuthenticator = CreateAuthenticator(ticket, data, subkey); AuthCheckSum checksum = new AuthCheckSum(); checksum.Lgth = KerberosConstValue.AUTHENTICATOR_CHECKSUM_LENGTH; checksum.Bnd = new byte[checksum.Lgth]; checksum.Flags = (int)checksumFlag; byte[] checkData = ArrayUtility.ConcatenateArrays(BitConverter.GetBytes(checksum.Lgth), checksum.Bnd, BitConverter.GetBytes(checksum.Flags)); plaintextAuthenticator.cksum = new Checksum(new KerbInt32((int)ChecksumType.ap_authenticator_8003), new Asn1OctetString(checkData)); return plaintextAuthenticator; }
public void TokenRestrictionSameMachineId_Http() { base.Logging(); client = new KerberosTestClient( this.testConfig.LocalRealm.RealmName, this.testConfig.LocalRealm.User[1].Username, this.testConfig.LocalRealm.User[1].Password, KerberosAccountType.User, testConfig.LocalRealm.KDC[0].IPAddress, testConfig.LocalRealm.KDC[0].Port, testConfig.TransportType, testConfig.SupportedOid); // Kerberos Proxy Service is used if (this.testConfig.UseProxy) { BaseTestSite.Log.Add(LogEntryKind.Comment, "Initialize KKDCP Client ."); KKDCPClient proxyClient = new KKDCPClient(proxyClientConfig); proxyClient.TargetDomain = this.testConfig.LocalRealm.RealmName; client.UseProxy = true; client.ProxyClient = proxyClient; } //Create and send AS request KdcOptions options = KdcOptions.FORWARDABLE | KdcOptions.CANONICALIZE | KdcOptions.RENEWABLE; client.SendAsRequest(options, null); //Recieve preauthentication required error METHOD_DATA methodData; KerberosKrbError krbError = client.ExpectPreauthRequiredError(out methodData); //Create sequence of PA data string timeStamp = KerberosUtility.CurrentKerberosTime.Value; PaEncTimeStamp paEncTimeStamp = new PaEncTimeStamp(timeStamp, 0, client.Context.SelectedEType, this.client.Context.CName.Password, this.client.Context.CName.Salt); PaPacRequest paPacRequest = new PaPacRequest(true); Asn1SequenceOf<PA_DATA> seqOfPaData = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paEncTimeStamp.Data, paPacRequest.Data }); //Create and send AS request client.SendAsRequest(options, seqOfPaData); KerberosAsResponse asResponse = client.ExpectAsResponse(); BaseTestSite.Assert.IsNotNull(asResponse.Response.ticket, "AS response should contain a TGT."); //Create and send TGS request KerbAuthDataTokenRestrictions krbAuthDataTokenRestictions = new KerbAuthDataTokenRestrictions( 0, (uint)LSAP_TOKEN_INFO_INTEGRITY_Flags.FULL_TOKEN, (uint)LSAP_TOKEN_INFO_INTEGRITY_TokenIL.High, new Guid().ToString().Replace("-", "")); AdIfRelevent adIfRelevent = new AdIfRelevent(new AD_IF_RELEVANT(new AuthorizationDataElement[] { krbAuthDataTokenRestictions.AuthDataElement })); AuthorizationData data = new AuthorizationData(new AuthorizationDataElement[] { adIfRelevent.AuthDataElement }); client.SendTgsRequest(this.testConfig.LocalRealm.WebServer[0].HttpServiceName, options, null, null, null, data); BaseTestSite.Log.Add(LogEntryKind.Comment, "Create and send TGS request"); KerberosTgsResponse tgsResponse = client.ExpectTgsResponse(); BaseTestSite.Log.Add(LogEntryKind.Comment, "Recieve a TGS response."); BaseTestSite.Assert.IsNotNull(tgsResponse.Response.ticket, "Service ticket should not be null."); BaseTestSite.Assert.AreEqual(this.testConfig.LocalRealm.WebServer[0].HttpServiceName, KerberosUtility.PrincipalName2String(tgsResponse.Response.ticket.sname), "Service principal name in service ticket should match expected."); EncryptionKey key = testConfig.QueryKey(this.testConfig.LocalRealm.WebServer[0].HttpServiceName, this.testConfig.LocalRealm.RealmName, this.client.Context.SelectedEType); tgsResponse.DecryptTicket(key); //tgsResponse.DecryptTicket(testConfig.LocalRealm.WebServer[0].Password, testConfig.LocalRealm.WebServer[0].ServiceSalt); BaseTestSite.Assert.IsNotNull(tgsResponse.EncPart, "The encrypted part of TGS-REP is decrypted."); BaseTestSite.Assert.AreEqual(this.testConfig.LocalRealm.RealmName.ToLower(), tgsResponse.TicketEncPart.crealm.Value.ToLower(), "Realm name in service ticket encrypted part should match expected."); BaseTestSite.Assert.AreEqual(this.testConfig.LocalRealm.User[1].Username, KerberosUtility.PrincipalName2String(tgsResponse.TicketEncPart.cname), "Realm name in service ticket encrypted part should match expected."); //Assert authorization data LinkedList<IAuthDataElement> authDataList = new LinkedList<IAuthDataElement>(); BaseTestSite.Assert.IsNotNull(tgsResponse.TicketEncPart.authorization_data, "The ticket contains Authorization data."); KerbAuthDataTokenRestrictions tokenRestrictions = FindOneInAuthData<KerbAuthDataTokenRestrictions>(tgsResponse.TicketEncPart.authorization_data.Elements); BaseTestSite.Assert.IsNotNull(tokenRestrictions, "KerbAuthDataTokenRestrictions is inside the authorization data."); EncryptionKey subkey = KerberosUtility.GenerateKey(client.Context.SessionKey); byte[] token = client.CreateGssApiToken(ApOptions.MutualRequired, data, subkey, ChecksumFlags.GSS_C_MUTUAL_FLAG | ChecksumFlags.GSS_C_INTEG_FLAG); BaseTestSite.Log.Add(LogEntryKind.Comment, "Create and send Http request."); KerberosApResponse apRep = client.GetApResponseFromToken(SendAndRecieveHttpAp(this.testConfig.LocalRealm.WebServer[0], token)); BaseTestSite.Log.Add(LogEntryKind.Comment, "Recieve Http response."); }
private Authenticator CreateAuthenticator(PrincipalName cname, Realm realm, EncryptionKey subkey = null, AuthorizationData data = null) { BaseTestSite.Log.Add(LogEntryKind.TestStep, "Create authenticator"); Random r = new Random(); int seqNum = r.Next(); Authenticator plaintextAuthenticator = new Authenticator { authenticator_vno = new Asn1Integer(KerberosConstValue.KERBEROSV5), crealm = realm, cusec = new Microseconds(0), ctime = KerberosUtility.CurrentKerberosTime, seq_number = new KerbUInt32(seqNum), cname = cname, subkey = subkey, authorization_data = data }; AuthCheckSum checksum = new AuthCheckSum { Lgth = KerberosConstValue.AUTHENTICATOR_CHECKSUM_LENGTH }; checksum.Bnd = new byte[checksum.Lgth]; checksum.Flags = (int)(ChecksumFlags.GSS_C_MUTUAL_FLAG | ChecksumFlags.GSS_C_INTEG_FLAG); byte[] checkData = ArrayUtility.ConcatenateArrays(BitConverter.GetBytes(checksum.Lgth), checksum.Bnd, BitConverter.GetBytes(checksum.Flags)); plaintextAuthenticator.cksum = new Checksum(new KerbInt32((int)ChecksumType.ap_authenticator_8003), new Asn1OctetString(checkData)); return plaintextAuthenticator; }
private void AppendNewAuthDataElement(AuthorizationData originalAuthData, AuthorizationDataElement newElement) { int elementNum = originalAuthData.Elements.Length; AuthorizationDataElement[] elements = new AuthorizationDataElement[elementNum + 1]; originalAuthData.Elements.CopyTo(elements, 0); elements[elementNum] = newElement; originalAuthData.Elements = elements; }
/// <summary> /// Initializes a new instance of this class with the specified <see cref="AuthorizationData"/>. /// </summary> /// <param name="authorizationData">Represents a user who intends to access the corresponding customer and account. </param> public ReportingServiceManager(AuthorizationData authorizationData) : this(authorizationData, null) { }
public async override Task RunAsync(AuthorizationData authorizationData) { try { CampaignManagementExampleHelper CampaignManagementExampleHelper = new CampaignManagementExampleHelper(this.OutputStatusMessage); CampaignManagementExampleHelper.CampaignManagementService = new ServiceClient <ICampaignManagementService>(authorizationData); var offlineConversionGoalName = "My Offline Conversion Goal " + DateTime.UtcNow; var conversionGoals = new ConversionGoal[] { new OfflineConversionGoal { // Determines how long after a click that you want to count offline conversions. ConversionWindowInMinutes = 43200, // If the count type is 'Unique' then only the first offline conversion will be counted. // By setting the count type to 'All', then all offline conversions for the same // MicrosoftClickId with different conversion times will be added cumulatively. CountType = ConversionGoalCountType.All, Name = offlineConversionGoalName, // The default conversion currency code and value. Each offline conversion can override it. Revenue = new ConversionGoalRevenue { CurrencyCode = null, Type = ConversionGoalRevenueType.FixedValue, Value = 5.00m, }, Scope = EntityScope.Account, Status = ConversionGoalStatus.Active, TagId = null }, }; OutputStatusMessage("Add conversion goal...\n"); var addConversionGoalsResponse = await CampaignManagementExampleHelper.AddConversionGoalsAsync(conversionGoals); List <long> conversionGoalIds = GetNonNullableIds(addConversionGoalsResponse.ConversionGoalIds); var conversionGoalTypes = ConversionGoalType.OfflineConversion; var getConversionGoals = (await CampaignManagementExampleHelper.GetConversionGoalsByIdsAsync(conversionGoalIds, conversionGoalTypes)).ConversionGoals; CampaignManagementExampleHelper.OutputArrayOfConversionGoal(getConversionGoals); // Every time you create a new OfflineConversionGoal via either the Bing Ads web application or Campaign Management API, // the MSCLKIDAutoTaggingEnabled value of the corresponding AccountProperty is set to 'true' automatically. // We can confirm the setting now. var accountPropertyNames = new List <AccountPropertyName>(); accountPropertyNames.Add(AccountPropertyName.MSCLKIDAutoTaggingEnabled); OutputStatusMessage("Get account properties...\n"); var getAccountPropertiesResponse = await CampaignManagementExampleHelper.GetAccountPropertiesAsync(accountPropertyNames); CampaignManagementExampleHelper.OutputArrayOfAccountProperty(getAccountPropertiesResponse.AccountProperties); var offlineConversions = new[] { new OfflineConversion { // If you do not specify an offline conversion currency code, // then the 'CurrencyCode' element of the goal's 'ConversionGoalRevenue' is used. ConversionCurrencyCode = "USD", // The conversion name must match the 'Name' of the 'OfflineConversionGoal'. // If it does not match you won't observe any error, although the offline // conversion will not be counted. ConversionName = offlineConversionGoalName, // The date and time must be in UTC, should align to the date and time of the // recorded click (MicrosoftClickId), and cannot be in the future. ConversionTime = DateTime.UtcNow, // If you do not specify an offline conversion value, // then the 'Value' element of the goal's 'ConversionGoalRevenue' is used. ConversionValue = 10, MicrosoftClickId = "f894f652ea334e739002f7167ab8f8e3" } }; // After the OfflineConversionGoal is set up, wait two hours before sending Bing Ads the offline conversions. // This example would not succeed in production because we created the goal very recently i.e., // please see above call to AddConversionGoalsAsync. OutputStatusMessage("Apply the offline conversion...\n"); var applyOfflineConversionsResponse = await CampaignManagementExampleHelper.ApplyOfflineConversionsAsync(offlineConversions); CampaignManagementExampleHelper.OutputArrayOfOfflineConversion(offlineConversions); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
/// <summary> /// Create AP request and encode to GSSAPI token /// </summary> /// <param name="apOptions">AP options</param> /// <param name="data">Authorization data</param> /// <param name="subkey">Sub-session key in authenticator</param> /// <param name="checksumFlags">Checksum flags</param> /// <returns></returns> public byte[] CreateGssApiToken(ApOptions apOptions, AuthorizationData data, EncryptionKey subkey, ChecksumFlags checksumFlags, Microsoft.Protocols.TestTools.StackSdk.Security.KerberosLib.KerberosConstValue.GSSToken gssToken = KerberosConstValue.GSSToken.GSSSPNG) { APOptions options = new APOptions(KerberosUtility.ConvertInt2Flags((int)apOptions)); Authenticator authenticator = CreateAuthenticator(Context.Ticket, data, subkey, checksumFlags); KerberosApRequest request = new KerberosApRequest( Context.Pvno, options, Context.Ticket, authenticator, KeyUsageNumber.AP_REQ_Authenticator ); return KerberosUtility.AddGssApiTokenHeader(request, this.oidPkt, gssToken); }
/// <summary> /// Initializes a new instance of this class with the specified <paramref name="requestId"/> and <see cref="BingAds.AuthorizationData"/>. /// </summary> /// <param name="requestId">The identifier of a download request that has previously been submitted.</param> /// <param name="authorizationData"> /// Represents a user who intends to access the corresponding customer and account. /// </param> public ReportingDownloadOperation(string requestId, AuthorizationData authorizationData) : this(requestId, authorizationData, null, null) { }
/// <summary> /// Create and send TGS request /// </summary> /// <param name="sName">Service principal name</param> /// <param name="kdcOptions">KDC options</param> /// <param name="seqPadata">A sequence of preauthentication data</param> /// <param name="checksumType">Checksum type of PA-TGS-REQ</param> /// <param name="additionalTicket">Additional ticket</param> /// <param name="data">Authorization data</param> public void SendTgsRequest(string sName, KdcOptions kdcOptions, Asn1SequenceOf<PA_DATA> seqPadata = null, Ticket additionalTicket = null, AuthorizationData dataInAuthenticator = null, AuthorizationData dataInEncAuthData = null) { if (sName == null) { throw new ArgumentNullException("sName"); } PrincipalName sname = new PrincipalName( new KerbInt32((int)PrincipalType.NT_SRV_INST), KerberosUtility.String2SeqKerbString(sName.Split('/'))); KDC_REQ_BODY kdcReqBody = CreateKdcRequestBody(kdcOptions, sname, dataInEncAuthData); Asn1BerEncodingBuffer bodyBuffer = new Asn1BerEncodingBuffer(); kdcReqBody.BerEncode(bodyBuffer); ChecksumType checksumType = KerberosUtility.GetChecksumType(Context.SelectedEType); PA_DATA paTgsReq = CreatePaTgsReq(checksumType, bodyBuffer.Data, dataInAuthenticator); Asn1SequenceOf<PA_DATA> tempPaData = null; if (seqPadata == null || seqPadata.Elements == null || seqPadata.Elements.Length == 0) { tempPaData = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paTgsReq }); } else { PA_DATA[] paDatas = new PA_DATA[seqPadata.Elements.Length + 1]; Array.Copy(seqPadata.Elements, paDatas, seqPadata.Elements.Length); paDatas[seqPadata.Elements.Length] = paTgsReq; tempPaData = new Asn1SequenceOf<PA_DATA>(paDatas); } KerberosTgsRequest tgsRequest = new KerberosTgsRequest(KerberosConstValue.KERBEROSV5, kdcReqBody, tempPaData, Context.TransportType); this.SendPdu(tgsRequest); this.testSite.Log.Add(LogEntryKind.Debug, "Send TGS request."); }
public void AdFxFastArmorInAuthenticator() { base.Logging(); client = new KerberosTestClient( this.testConfig.LocalRealm.RealmName, this.testConfig.LocalRealm.ClientComputer.NetBiosName, this.testConfig.LocalRealm.ClientComputer.Password, KerberosAccountType.Device, testConfig.LocalRealm.KDC[0].IPAddress, testConfig.LocalRealm.KDC[0].Port, testConfig.TransportType, testConfig.SupportedOid, testConfig.LocalRealm.ClientComputer.AccountSalt); // Kerberos Proxy Service is used if (this.testConfig.UseProxy) { BaseTestSite.Log.Add(LogEntryKind.Comment, "Initialize KKDCP Client ."); KKDCPClient proxyClient = new KKDCPClient(proxyClientConfig); proxyClient.TargetDomain = this.testConfig.LocalRealm.RealmName; client.UseProxy = true; client.ProxyClient = proxyClient; } // AS_REQ and KRB-ERROR using device principal KdcOptions options = KdcOptions.FORWARDABLE | KdcOptions.CANONICALIZE | KdcOptions.RENEWABLE; client.SendAsRequest(options, null); METHOD_DATA methodData; KerberosKrbError krbError1 = client.ExpectPreauthRequiredError(out methodData); // AS_REQ and AS_REP using device principal string timeStamp = KerberosUtility.CurrentKerberosTime.Value; PaEncTimeStamp paEncTimeStamp = new PaEncTimeStamp( timeStamp, 0, client.Context.SelectedEType, this.client.Context.CName.Password, this.client.Context.CName.Salt); Asn1SequenceOf<PA_DATA> seqOfPaData = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paEncTimeStamp.Data }); client.SendAsRequest(options, seqOfPaData); KerberosAsResponse asResponse = client.ExpectAsResponse(); BaseTestSite.Log.Add( LogEntryKind.Comment, string.Format("The type of AS-REP encrypted part is {0}.", asResponse.EncPart.GetType().Name)); AdFxFastArmor adFxFastArmor = new AdFxFastArmor(); AuthorizationData authData = new AuthorizationData(new AuthorizationDataElement[] { adFxFastArmor.AuthDataElement }); client.SendTgsRequest(testConfig.LocalRealm.ClientComputer.DefaultServiceName, options, null, null, authData); BaseTestSite.Log.Add(LogEntryKind.Comment, "Receive TGS Error, KDC MUST reject the request."); KerberosKrbError krbError = client.ExpectKrbError(); }
/// <summary> /// Create and send FAST TGS request /// </summary> /// <param name="sName">Service principal name</param> /// <param name="kdcOptions">KDC options</param> /// <param name="innerSeqPaData">A sequence of preauthentication data in FAST request</param> /// <param name="outerSeqPaData">A sequence of preauthentication data</param> /// <param name="subKey">Sub-session key for authenticator in FAST armor field</param> /// <param name="fastOptions">FAST options</param> /// <param name="apOptions">AP options in FAST armor field</param> /// <param name="data">Authorization data</param> public void SendTgsRequestWithExplicitFast( string sName, KdcOptions kdcOptions, Asn1SequenceOf<PA_DATA> innerSeqPaData, Asn1SequenceOf<PA_DATA> outerSeqPaData, EncryptionKey subKey, FastOptions fastOptions, ApOptions apOptions, AuthorizationData data = null) { Context.Subkey = subKey; Context.ReplyKey = subKey; string domain = this.Context.Realm.Value; PrincipalName sname = new PrincipalName(new KerbInt32((int)PrincipalType.NT_SRV_INST), KerberosUtility.String2SeqKerbString(sName.Split('/'))); KDC_REQ_BODY kdcReqBody = CreateKdcRequestBody(kdcOptions, sname, data); Asn1BerEncodingBuffer bodyBuffer = new Asn1BerEncodingBuffer(); kdcReqBody.BerEncode(bodyBuffer); //Create PA-TGS-REQ APOptions option = new APOptions(KerberosUtility.ConvertInt2Flags((int)ApOptions.None)); ChecksumType checksumType = KerberosUtility.GetChecksumType(Context.SelectedEType); KerberosApRequest apRequest = CreateApRequest( option, Context.Ticket, subKey, data, KeyUsageNumber.TG_REQ_PA_TGS_REQ_padataOR_AP_REQ_Authenticator, checksumType, bodyBuffer.Data); PaTgsReq paTgsReq = new PaTgsReq(apRequest.Request); Asn1SequenceOf<PA_DATA> tempPaData = null; if (outerSeqPaData == null || outerSeqPaData.Elements == null || outerSeqPaData.Elements.Length == 0) { tempPaData = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paTgsReq.Data }); } else { tempPaData.Elements = new PA_DATA[outerSeqPaData.Elements.Length + 1]; Array.Copy(outerSeqPaData.Elements, tempPaData.Elements, outerSeqPaData.Elements.Length); tempPaData.Elements[outerSeqPaData.Elements.Length] = paTgsReq.Data; } //Create explicit FAST armor EncryptionKey explicitSubkey = KerberosUtility.MakeKey( Context.SelectedEType, "Password04!", "This is a salt"); Authenticator plaintextAuthenticator = CreateAuthenticator(Context.ArmorTicket, null, explicitSubkey); KerberosApRequest apReq = new KerberosApRequest(Context.Pvno, new APOptions(KerberosUtility.ConvertInt2Flags((int)apOptions)), Context.ArmorTicket, plaintextAuthenticator, KeyUsageNumber.AP_REQ_Authenticator); FastArmorApRequest explicitArmor = new FastArmorApRequest(apReq.Request); //Create armor key var armorKey = GetArmorKey(Context.ArmorSessionKey, subKey, explicitSubkey); Context.FastArmorkey = armorKey; //Create PA-FX-FAST var pafxfast = CreateTgsPaFxFast(armorKey, Context.ArmorTicket, fastOptions, apOptions, tempPaData, sName, paTgsReq.Data.padata_value.ByteArrayValue, explicitArmor); PA_DATA[] elements; if (outerSeqPaData != null && outerSeqPaData.Elements.Length > 0) { elements = new PA_DATA[outerSeqPaData.Elements.Length + 1]; Array.Copy(outerSeqPaData.Elements, elements, outerSeqPaData.Elements.Length); elements[outerSeqPaData.Elements.Length] = pafxfast.Data; elements[outerSeqPaData.Elements.Length + 1] = paTgsReq.Data; } else { elements = new PA_DATA[] { pafxfast.Data, paTgsReq.Data }; } Asn1SequenceOf<PA_DATA> seqPaData = new Asn1SequenceOf<PA_DATA>(); KerberosTgsRequest tgsRequest = new KerberosTgsRequest(KerberosConstValue.KERBEROSV5, kdcReqBody, new Asn1SequenceOf<PA_DATA>(elements), Context.TransportType); this.SendPdu(tgsRequest); this.testSite.Log.Add(LogEntryKind.Debug, "Send FAST TGS request."); }
internal ReportingDownloadOperation(string requestId, AuthorizationData authorizationData, string trackingId, ApiEnvironment? apiEnvironment) : this(requestId, authorizationData, new ReportingStatusProvider(requestId), trackingId, apiEnvironment) { }
/// <summary> /// Create and send FAST TGS request /// </summary> /// <param name="sName">Service principal name</param> /// <param name="kdcOptions">KDC options</param> /// <param name="innerSeqPaData">A sequence of preauthentication data in FAST request</param> /// <param name="outerSeqPaData">A sequence of preauthentication data</param> /// <param name="subKey">Sub-session key for authenticator in FAST armor field</param> /// <param name="fastOptions">FAST options</param> /// <param name="apOptions">AP options in FAST armor field</param> /// <param name="data">Authorization data</param> public void SendTgsRequestWithFastHideCName( string sName, PrincipalName cName, KdcOptions kdcOptions, Asn1SequenceOf<PA_DATA> innerSeqPaData, Asn1SequenceOf<PA_DATA> outerSeqPaData, EncryptionKey subKey, ApOptions apOptions, AuthorizationData data = null) { var fastOptions = new Protocols.TestTools.StackSdk.Security.KerberosV5.Preauth.FastOptions( KerberosUtility.ConvertInt2Flags((int)FastOptionFlags.Hide_Client_Names)); Context.Subkey = subKey; Context.ReplyKey = subKey; string domain = this.Context.Realm.Value; PrincipalName sname = new PrincipalName(new KerbInt32((int)PrincipalType.NT_SRV_INST), KerberosUtility.String2SeqKerbString(sName.Split('/'))); KDC_REQ_BODY kdcReqBody = CreateKdcRequestBody(kdcOptions, sname, data); kdcReqBody.cname = cName; Asn1BerEncodingBuffer bodyBuffer = new Asn1BerEncodingBuffer(); kdcReqBody.BerEncode(bodyBuffer); APOptions option = new APOptions(KerberosUtility.ConvertInt2Flags((int)ApOptions.None)); ChecksumType checksumType = KerberosUtility.GetChecksumType(Context.SelectedEType); KerberosApRequest apRequest = CreateApRequest( option, Context.Ticket, subKey, data, KeyUsageNumber.TG_REQ_PA_TGS_REQ_padataOR_AP_REQ_Authenticator, checksumType, bodyBuffer.Data); PaTgsReq paTgsReq = new PaTgsReq(apRequest.Request); Asn1SequenceOf<PA_DATA> tempPaData = null; if (outerSeqPaData == null || outerSeqPaData.Elements == null || outerSeqPaData.Elements.Length == 0) { tempPaData = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paTgsReq.Data }); } else { tempPaData.Elements = new PA_DATA[outerSeqPaData.Elements.Length + 1]; Array.Copy(outerSeqPaData.Elements, tempPaData.Elements, outerSeqPaData.Elements.Length); tempPaData.Elements[outerSeqPaData.Elements.Length] = paTgsReq.Data; } var armorKey = GetArmorKey(Context.SessionKey, subKey); var pafxfast = CreateTgsPaFxFast(armorKey, Context.Ticket, fastOptions, apOptions, tempPaData, sName, paTgsReq.Data.padata_value.ByteArrayValue); Context.FastArmorkey = armorKey; PA_DATA[] elements; if (outerSeqPaData != null && outerSeqPaData.Elements.Length > 0) { elements = new PA_DATA[outerSeqPaData.Elements.Length + 1]; Array.Copy(outerSeqPaData.Elements, elements, outerSeqPaData.Elements.Length); elements[outerSeqPaData.Elements.Length] = pafxfast.Data; elements[outerSeqPaData.Elements.Length + 1] = paTgsReq.Data; } else { elements = new PA_DATA[] { pafxfast.Data, paTgsReq.Data }; } Asn1SequenceOf<PA_DATA> seqPaData = new Asn1SequenceOf<PA_DATA>(); KerberosTgsRequest tgsRequest = new KerberosTgsRequest(KerberosConstValue.KERBEROSV5, kdcReqBody, new Asn1SequenceOf<PA_DATA>(elements), Context.TransportType); this.SendPdu(tgsRequest); this.testSite.Log.Add(LogEntryKind.Debug, "Send FAST TGS request."); }
public KileTgsResponse CreateTgsResponse( KileConnection kileConnection, _SeqOfPA_DATA seqOfPaData, EncTicketFlags encTicketFlags, EncryptionKey ticketEncryptKey, AuthorizationData ticketAuthorizationData) { KileServerContext serverContext = GetServerContextByKileConnection(kileConnection); if (ticketEncryptKey == null) { throw new ArgumentNullException("ticketEncryptKey"); } else { serverContext.TicketEncryptKey = ticketEncryptKey; } KileTgsResponse response = new KileTgsResponse(serverContext); // Construct a Ticket Ticket ticket = new Ticket(); ticket.tkt_vno = new Asn1Integer(ConstValue.KERBEROSV5); ticket.realm = new Realm(domain); ticket.sname = serverContext.SName; // Set EncTicketPart EncTicketPart encTicketPart = new EncTicketPart(); EncryptionType encryptionType = (EncryptionType)serverContext.EncryptType.elements[0].mValue; encTicketPart.key = new EncryptionKey((int)encryptionType, GetEncryptionKeyByType(encryptionType)); encTicketPart.flags = new TicketFlags(KileUtility.ConvertInt2Flags((int)encTicketFlags)); encTicketPart.crealm = serverContext.TgsTicket.crealm; encTicketPart.cname = serverContext.TgsTicket.cname; encTicketPart.transited = serverContext.TgsTicket.transited; encTicketPart.authtime = KileUtility.CurrentKerberosTime; encTicketPart.starttime = KileUtility.CurrentKerberosTime; encTicketPart.endtime = serverContext.TgsTicket.endtime; encTicketPart.renew_till = serverContext.TgsTicket.renew_till; encTicketPart.caddr = serverContext.Addresses; encTicketPart.authorization_data = ticketAuthorizationData; response.TicketEncPart = encTicketPart; // Set AS_REP response.Response.pvno = new Asn1Integer(ConstValue.KERBEROSV5); response.Response.msg_type = new Asn1Integer((int)MsgType.KRB_TGS_RESP); response.Response.padata = seqOfPaData; response.Response.crealm = serverContext.UserRealm; response.Response.cname = serverContext.UserName; response.Response.ticket = ticket; // Set EncASRepPart EncTGSRepPart encTGSRepPart = new EncTGSRepPart(); encTGSRepPart.key = encTicketPart.key; LastReq_element element = new LastReq_element(new Int32(0), KileUtility.CurrentKerberosTime); encTGSRepPart.last_req = new LastReq(new LastReq_element[] { element }); encTGSRepPart.nonce = serverContext.Nonce; encTGSRepPart.flags = encTicketPart.flags; encTGSRepPart.authtime = encTicketPart.authtime; encTGSRepPart.starttime = encTicketPart.starttime; encTGSRepPart.endtime = encTicketPart.endtime; encTGSRepPart.renew_till = encTicketPart.renew_till; encTGSRepPart.srealm = ticket.realm; encTGSRepPart.sname = ticket.sname; encTGSRepPart.caddr = encTicketPart.caddr; response.EncPart = encTGSRepPart; return response; }
private KerberosApRequest CreateApRequest(APOptions option, KerberosTicket ticket, EncryptionKey subkey, AuthorizationData data, KeyUsageNumber keyUsageNumber, ChecksumType checksumType, byte[] checksumBody) { Authenticator authenticator = CreateAuthenticator(ticket, data, subkey, checksumType, checksumBody); KerberosApRequest apReq = new KerberosApRequest(Context.Pvno, option, ticket, authenticator, keyUsageNumber); return apReq; }
public async override Task RunAsync(AuthorizationData authorizationData) { try { CustomerService = new ServiceClient <ICustomerManagementService>(authorizationData); var getUserResponse = await GetUserAsync(null); var user = getUserResponse.User; // Only a user with the aggregator role (33) can sign up new customers. // If the user does not have the aggregator role, then do not continue. if (!getUserResponse.Roles.Contains(33)) { OutputStatusMessage("Only a user with the aggregator role (33) can sign up new customers."); return; } // For Customer.CustomerAddress and Account.BusinessAddress, you can use the same address // as your aggregator user, although you must set Id and TimeStamp to null. var userAddress = user.ContactInfo.Address; userAddress.Id = null; userAddress.TimeStamp = null; var customer = new Customer { // The customer's business address. CustomerAddress = userAddress, // The list of key and value strings for forward compatibility. This element can be used // to avoid otherwise breaking changes when new elements are added in future releases. // There are currently no forward compatibility changes for the Customer object. ForwardCompatibilityMap = null, // The primary business segment of the customer, for example, automotive, food, or entertainment. Industry = Industry.Other, // The primary country where the customer operates. This country will be the // default country for ad groups in the customer’s campaigns. MarketCountry = "US", // The primary language that the customer uses. This language will be the // default language for ad groups in the customer’s campaigns. MarketLanguage = LanguageType.English, // The name of the customer. This element can contain a maximum of 100 characters. Name = "Child Customer " + DateTime.UtcNow, }; // Optionally you can set up each account with auto tagging. // The AutoTag key and value pair is an account level setting that determines whether to append or replace // the supported UTM tracking codes within the final URL of ads delivered. The default value is '0', and // Bing Ads will not append any UTM tracking codes to your ad or keyword final URL. var accountFCM = new List <KeyValuePair <string, string> >(); accountFCM.Add(new KeyValuePair <string, string>( "AutoTag", "0")); var account = new AdvertiserAccount { // The type of account. Bing Ads API only supports the Advertiser account. AccountType = AccountType.Advertiser, // The location where your business is legally registered. // The business address is used to determine your tax requirements. // BusinessAddress will be required in a future version of the Bing Ads API. // Please start using it. BusinessAddress = userAddress, // The type of currency that is used to settle the account. The service uses the currency information for billing purposes. CurrencyType = CurrencyType.USDollar, // The list of key and value strings for forward compatibility. This element can be used // to avoid otherwise breaking changes when new elements are added in future releases. ForwardCompatibilityMap = accountFCM, // The name of the account. The name can contain a maximum of 100 characters and must be unique within the customer. Name = "Child Account " + DateTime.UtcNow, // The identifier of the customer that owns the account. In the Bing Ads API operations // that require a customer identifier, this is the identifier that you set the CustomerId SOAP header to. ParentCustomerId = (long)user.CustomerId, // The list of key and value strings for tax information. // The TaxId (VAT identifier) is optional. If specified, The VAT identifier must be valid // in the country that you specified in the BusinessAddress element. Without a VAT registration // number or exemption certificate, taxes might apply based on your business location. TaxInformation = null, // The default time-zone value to use for campaigns in this account. // If not specified, the time zone will be set to PacificTimeUSCanadaTijuana by default. // TimeZone will be required in a future version of the Bing Ads API. // Please start using it. TimeZone = TimeZoneType.PacificTimeUSCanadaTijuana, }; // Signup a new customer and account for the reseller. var signupCustomerResponse = await SignupCustomerAsync( customer, account, user.CustomerId); OutputStatusMessage(string.Format("New Customer and Account:\n")); // This is the identifier that you will use to set the CustomerId // element in most of the Bing Ads API service operations. OutputStatusMessage(string.Format("\tCustomerId: {0}", signupCustomerResponse.CustomerId)); // The read-only system-generated customer number that is used in the Bing Ads web application. // The customer number is of the form, Cnnnnnnn, where nnnnnnn is a series of digits. OutputStatusMessage(string.Format("\tCustomerNumber: {0}", signupCustomerResponse.CustomerNumber)); // This is the identifier that you will use to set the AccountId and CustomerAccountId // elements in most of the Bing Ads API service operations. OutputStatusMessage(string.Format("\tAccountId: {0}", signupCustomerResponse.AccountId)); // The read-only system generated account number that is used to identify the account in the Bing Ads web application. // The account number has the form xxxxxxxx, where xxxxxxxx is a series of any eight alphanumeric characters. OutputStatusMessage(string.Format("\tAccountNumber: {0}", signupCustomerResponse.AccountNumber)); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Customer Management service exceptions catch (FaultException <Microsoft.BingAds.V11.CustomerManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CustomerManagement.ApiFault> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
private Authenticator CreateAuthenticator( KerberosTicket ticket, AuthorizationData data, EncryptionKey subkey ) { Authenticator plaintextAuthenticator = new Authenticator(); plaintextAuthenticator.authenticator_vno = new Asn1Integer(KerberosConstValue.KERBEROSV5); plaintextAuthenticator.crealm = Context.CName.Realm; plaintextAuthenticator.cusec = new Microseconds(0); plaintextAuthenticator.ctime = KerberosUtility.CurrentKerberosTime; plaintextAuthenticator.seq_number = new KerbUInt32(0); plaintextAuthenticator.cname = ticket.TicketOwner; plaintextAuthenticator.subkey = subkey; plaintextAuthenticator.authorization_data = data; return plaintextAuthenticator; }
public async override Task RunAsync(AuthorizationData authorizationData) { try { CampaignService = new ServiceClient <ICampaignManagementService>(authorizationData); // Add a campaign that will later be associated with negative keywords. var campaigns = new[] { new Campaign { Name = "Women's Shoes " + DateTime.UtcNow, Description = "Red shoes line.", // You must choose to set either the shared budget ID or daily amount. // You can set one or the other, but you may not set both. BudgetId = null, DailyBudget = 50, BudgetType = BudgetLimitType.DailyBudgetStandard, BiddingScheme = new EnhancedCpcBiddingScheme(), TimeZone = "PacificTimeUSCanadaTijuana", } }; AddCampaignsResponse addCampaignsResponse = await AddCampaignsAsync(authorizationData.AccountId, campaigns); long?[] campaignIds = addCampaignsResponse.CampaignIds.ToArray(); BatchError[] campaignErrors = addCampaignsResponse.PartialErrors.ToArray(); OutputIds(campaignIds); OutputPartialErrors(campaignErrors); long campaignId = (long)campaignIds[0]; // You may choose to associate an exclusive set of negative keywords to an individual campaign // or ad group. An exclusive set of negative keywords cannot be shared with other campaigns // or ad groups. This example only associates negative keywords with a campaign. var entityNegativeKeywords = new[] { new EntityNegativeKeyword { EntityId = campaignId, EntityType = "Campaign", NegativeKeywords = new[] { new NegativeKeyword { MatchType = MatchType.Phrase, Text = "auto" }, new NegativeKeyword { MatchType = MatchType.Phrase, Text = "auto" }, } } }; AddNegativeKeywordsToEntitiesResponse addNegativeKeywordsToEntitiesResponse = await AddNegativeKeywordsToEntitiesAsync(entityNegativeKeywords); OutputNegativeKeywordIds(addNegativeKeywordsToEntitiesResponse.NegativeKeywordIds); OutputBatchErrorCollections(addNegativeKeywordsToEntitiesResponse.NestedPartialErrors); if (addNegativeKeywordsToEntitiesResponse.NestedPartialErrors == null || addNegativeKeywordsToEntitiesResponse.NestedPartialErrors.Count == 0) { OutputStatusMessage("Added an exclusive set of negative keywords to the Campaign.\n"); OutputNegativeKeywordIds(addNegativeKeywordsToEntitiesResponse.NegativeKeywordIds); } else { OutputBatchErrorCollections(addNegativeKeywordsToEntitiesResponse.NestedPartialErrors); } GetNegativeKeywordsByEntityIdsResponse getNegativeKeywordsByEntityIdsResponse = await GetNegativeKeywordsByEntityIdsAsync(new[] { campaignId }, "Campaign", authorizationData.AccountId); OutputEntityNegativeKeywords(getNegativeKeywordsByEntityIdsResponse.EntityNegativeKeywords); OutputPartialErrors(getNegativeKeywordsByEntityIdsResponse.PartialErrors); if (getNegativeKeywordsByEntityIdsResponse.PartialErrors == null || getNegativeKeywordsByEntityIdsResponse.PartialErrors.Count == 0) { OutputStatusMessage("Retrieved an exclusive set of negative keywords for the Campaign.\n"); OutputEntityNegativeKeywords(getNegativeKeywordsByEntityIdsResponse.EntityNegativeKeywords); } else { OutputPartialErrors(getNegativeKeywordsByEntityIdsResponse.PartialErrors); } // If you attempt to delete a negative keyword without an identifier the operation will // succeed but will return partial errors corresponding to the index of the negative keyword // that was not deleted. var nestedPartialErrors = (BatchErrorCollection[])(await DeleteNegativeKeywordsFromEntitiesAsync(entityNegativeKeywords)).NestedPartialErrors; if (nestedPartialErrors == null || nestedPartialErrors.Length == 0) { OutputStatusMessage("Deleted an exclusive set of negative keywords from the Campaign.\n"); } else { OutputStatusMessage("Attempt to DeleteNegativeKeywordsFromEntities without NegativeKeyword identifier partially fails by design."); OutputBatchErrorCollections(nestedPartialErrors); } // Delete the negative keywords with identifiers that were returned above. nestedPartialErrors = (BatchErrorCollection[])(await DeleteNegativeKeywordsFromEntitiesAsync( getNegativeKeywordsByEntityIdsResponse.EntityNegativeKeywords)).NestedPartialErrors; if (nestedPartialErrors == null || nestedPartialErrors.Length == 0) { OutputStatusMessage("Deleted an exclusive set of negative keywords from the Campaign.\n"); } else { OutputBatchErrorCollections(nestedPartialErrors); } // Negative keywords can also be added and deleted from a shared negative keyword list. // The negative keyword list can be shared or associated with multiple campaigns. // NegativeKeywordList inherits from SharedList which inherits from SharedEntity. var negativeKeywordList = new NegativeKeywordList { Name = "My Negative Keyword List" + DateTime.UtcNow, Type = "NegativeKeywordList" }; SharedListItem[] negativeKeywords = { new NegativeKeyword { Text = "car", Type = "NegativeKeyword", MatchType = MatchType.Exact }, new NegativeKeyword { Text = "car", Type = "NegativeKeyword", MatchType = MatchType.Phrase } }; // You can create a new list for negative keywords with or without negative keywords. var addSharedEntityResponse = await AddSharedEntityAsync(negativeKeywordList, negativeKeywords); var sharedEntityId = addSharedEntityResponse.SharedEntityId; long[] listItemIds = addSharedEntityResponse.ListItemIds.ToArray(); OutputStatusMessage(string.Format("NegativeKeywordList successfully added to account library and assigned identifer {0}\n", sharedEntityId)); OutputNegativeKeywordsWithPartialErrors( sharedEntityId, negativeKeywords, listItemIds, addSharedEntityResponse.PartialErrors.ToArray()); OutputStatusMessage("Negative keywords currently in NegativeKeywordList:"); negativeKeywords = (SharedListItem[])(await GetListItemsBySharedListAsync(new NegativeKeywordList { Id = sharedEntityId })).ListItems; if (negativeKeywords == null || negativeKeywords.Length == 0) { OutputStatusMessage("None\n"); } else { OutputNegativeKeywords(negativeKeywords.Cast <NegativeKeyword>()); } // To update the list of negative keywords, you must either add or remove from the list // using the respective AddListItemsToSharedList or DeleteListItemsFromSharedList operations. // To remove the negative keywords from the list pass the negative keyword identifers // and negative keyword list (SharedEntity) identifer. var partialErrors = (await DeleteListItemsFromSharedListAsync(listItemIds, new NegativeKeywordList { Id = sharedEntityId }))?.PartialErrors; if (partialErrors == null || !partialErrors.Any()) { OutputStatusMessage("Deleted most recently added negative keywords from negative keyword list.\n"); } else { OutputPartialErrors(partialErrors); } OutputStatusMessage("Negative keywords currently in NegativeKeywordList:"); negativeKeywords = (SharedListItem[])(await GetListItemsBySharedListAsync(new NegativeKeywordList { Id = sharedEntityId })).ListItems; if (negativeKeywords == null || negativeKeywords.Length == 0) { OutputStatusMessage("None\n"); } else { OutputNegativeKeywords(negativeKeywords.Cast <NegativeKeyword>()); } // Whether you created the list with or without negative keywords, more can be added // using the AddListItemsToSharedList operation. negativeKeywords = new SharedListItem[] { new NegativeKeyword { Text = "auto", Type = "NegativeKeyword", MatchType = MatchType.Exact }, new NegativeKeyword { Text = "auto", Type = "NegativeKeyword", MatchType = MatchType.Phrase } }; var addListItemsToSharedListResponse = await AddListItemsToSharedListAsync( negativeKeywords, new NegativeKeywordList { Id = sharedEntityId }); listItemIds = addListItemsToSharedListResponse.ListItemIds.ToArray(); OutputNegativeKeywordsWithPartialErrors( sharedEntityId, negativeKeywords, listItemIds, addListItemsToSharedListResponse.PartialErrors.ToArray()); OutputStatusMessage("Negative keywords currently in NegativeKeywordList:"); negativeKeywords = (SharedListItem[])(await GetListItemsBySharedListAsync(new NegativeKeywordList { Id = sharedEntityId })).ListItems; if (negativeKeywords == null || negativeKeywords.Length == 0) { OutputStatusMessage("None\n"); } else { OutputNegativeKeywords(negativeKeywords.Cast <NegativeKeyword>()); } // You can update the name of the negative keyword list. negativeKeywordList = new NegativeKeywordList { Id = sharedEntityId, Name = "My Updated Negative Keyword List", Type = "NegativeKeywordList" }; partialErrors = (await UpdateSharedEntitiesAsync(new SharedEntity[] { negativeKeywordList })).PartialErrors; if (partialErrors == null || !partialErrors.Any()) { OutputStatusMessage(string.Format("Updated Negative Keyword List Name to {0}.\n", negativeKeywordList.Name)); } else { OutputPartialErrors(partialErrors); } // Get and output the negative keyword lists and store the list of identifiers. const string sharedEntityType = "NegativeKeywordList"; var sharedEntities = (await GetSharedEntitiesByAccountIdAsync(sharedEntityType)).SharedEntities; OutputSharedEntityIdentifiersAsync(sharedEntities); var sharedEntityIds = new long[sharedEntities.Count]; for (int index = 0; index < sharedEntities.Count; index++) { if (sharedEntities[index].Id != null) { sharedEntityIds[index] = (long)sharedEntities[index].Id; } } // Negative keywords were added to the negative keyword list above. You can associate the // shared list of negative keywords with a campaign with or without negative keywords. // Shared negative keyword lists cannot be associated with an ad group. An ad group can only // be assigned an exclusive set of negative keywords. var associations = new[] { new SharedEntityAssociation { EntityId = campaignId, EntityType = "Campaign", SharedEntityId = sharedEntityId, SharedEntityType = "NegativeKeywordList" } }; partialErrors = (await SetSharedEntityAssociationsAsync(associations)).PartialErrors; if (partialErrors == null || !partialErrors.Any()) { OutputStatusMessage(string.Format("Associated CampaignId {0} with Negative Keyword List Id {1}.\n", campaignId, sharedEntityId)); } else { OutputPartialErrors(partialErrors); } // Get and output the associations either by Campaign or NegativeKeywordList identifier. GetSharedEntityAssociationsByEntityIdsResponse getSharedEntityAssociationsByEntityIdsResponse = await GetSharedEntityAssociationsByEntityIdsAsync(new[] { campaignId }, "Campaign", "NegativeKeywordList"); OutputSharedEntityAssociations(getSharedEntityAssociationsByEntityIdsResponse.Associations); OutputPartialErrors(getSharedEntityAssociationsByEntityIdsResponse.PartialErrors); // Currently the GetSharedEntityAssociationsBySharedEntityIds operation accepts only one shared entity identifier in the list. GetSharedEntityAssociationsBySharedEntityIdsResponse getSharedEntityAssociationsBySharedEntityIdsResponse = await GetSharedEntityAssociationsBySharedEntityIdsAsync("Campaign", new[] { sharedEntityIds[sharedEntityIds.Length - 1] }, "NegativeKeywordList"); OutputSharedEntityAssociations(getSharedEntityAssociationsBySharedEntityIdsResponse.Associations); OutputPartialErrors(getSharedEntityAssociationsBySharedEntityIdsResponse.PartialErrors); // Explicitly delete the association between the campaign and the negative keyword list. partialErrors = (await DeleteSharedEntityAssociationsAsync(associations)).PartialErrors; if (partialErrors == null || !partialErrors.Any()) { OutputStatusMessage("Deleted NegativeKeywordList associations\n"); } else { OutputPartialErrors(partialErrors); } // Delete the campaign and any remaining assocations. await DeleteCampaignsAsync(authorizationData.AccountId, new[] { campaignId }); OutputStatusMessage(string.Format("Deleted Campaign Id {0}\n", campaignId)); // DeleteCampaigns does not delete the negative keyword list from the account's library. // Call the DeleteSharedEntities operation to delete the shared entities. partialErrors = (await DeleteSharedEntitiesAsync(new SharedEntity[] { new NegativeKeywordList { Id = sharedEntityId } }))?.PartialErrors; if (partialErrors == null || !partialErrors.Any()) { OutputStatusMessage(string.Format("Deleted Negative Keyword List (SharedEntity) Id {0}\n", sharedEntityId)); } else { OutputPartialErrors(partialErrors); } } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
private Authenticator CreateAuthenticator( KerberosTicket ticket, AuthorizationData data, EncryptionKey subkey, ChecksumType checksumType, byte[] checksumBody ) { Authenticator plaintextAuthenticator = CreateAuthenticator(ticket, data, subkey); byte[] checkData = KerberosUtility.GetChecksum(ticket.SessionKey.keyvalue.ByteArrayValue, checksumBody, (int)KeyUsageNumber.TGS_REQ_PA_TGS_REQ_adataOR_AP_REQ_Authenticator_cksum, checksumType); plaintextAuthenticator.cksum = new Checksum(new KerbInt32((int)checksumType), new Asn1OctetString(checkData)); return plaintextAuthenticator; }
public async override Task RunAsync(AuthorizationData authorizationData) { try { Service = new ServiceClient <ICampaignManagementService>(authorizationData); // Get a list of all Bing Merchant Center stores associated with your CustomerId IList <BMCStore> stores = await GetBMCStoresByCustomerIdAsync(); if (stores == null) { OutputStatusMessage( String.Format("You do not have any BMC stores registered for CustomerId {0}.\n", authorizationData.CustomerId) ); return; } #region ManageCampaign /* Add a new Bing Shopping campaign that will be associated with a ProductScope criterion. * - Set the CampaignType element of the Campaign to Shopping. * - Create a ShoppingSetting instance and set its Priority (0, 1, or 2), SalesCountryCode, and StoreId elements. * Add this shopping setting to the Settings list of the Campaign. */ var campaign = new Campaign { CampaignType = CampaignType.Shopping, Settings = new[] { new ShoppingSetting() { Priority = 0, SalesCountryCode = "US", StoreId = (int)stores[0].Id } }, Name = "Bing Shopping Campaign " + DateTime.UtcNow, Description = "Bing Shopping Campaign Example.", BudgetType = BudgetLimitType.MonthlyBudgetSpendUntilDepleted, MonthlyBudget = 1000.00, TimeZone = "PacificTimeUSCanadaTijuana", DaylightSaving = true, }; var campaignIds = await AddCampaignsAsync(authorizationData.AccountId, new[] { campaign }); OutputCampaignIdentifiers(campaignIds); /* Optionally, you can create a ProductScope criterion that will be associated with your Bing Shopping campaign. * Use the product scope criterion to include a subset of your product catalog, for example a specific brand, * category, or product type. A campaign can only be associated with one ProductScope, which contains a list * of up to 7 ProductCondition. You'll also be able to specify more specific product conditions for each ad group. */ var campaignCriterions = new CampaignCriterion[] { new CampaignCriterion() { CampaignId = campaignIds[0], BidAdjustment = null, // Reserved for future use Criterion = new ProductScope() { Conditions = new ProductCondition[] { new ProductCondition { Operand = "Condition", Attribute = "New" }, new ProductCondition { Operand = "CustomLabel0", Attribute = "MerchantDefinedCustomLabel" }, } }, } }; var addCampaignCriterionsResponse = await(AddCampaignCriterionsAsync( campaignCriterions, CampaignCriterionType.ProductScope) ); #endregion ManageCampaign #region ManageAdGroup // Specify one or more ad groups. var adGroup = new AdGroup { Name = "Product Categories", AdDistribution = AdDistribution.Search, BiddingModel = BiddingModel.Keyword, PricingModel = PricingModel.Cpc, StartDate = null, EndDate = new Date { Month = 12, Day = 31, Year = 2016 }, Language = "English" }; var adGroupIds = (long[]) await AddAdGroupsAsync(campaignIds[0], new[] { adGroup }); OutputAdGroupIdentifiers(adGroupIds); #region BidAllProducts var helper = new PartitionActionHelper(adGroupIds[0]); var root = helper.AddUnit( null, new ProductCondition { Operand = "All", Attribute = null }, 0.35, false ); OutputStatusMessage("Applying only the root as a Unit with a bid . . . \n"); var applyProductPartitionActionsResponse = await ApplyProductPartitionActionsAsync(helper.PartitionActions); var adGroupCriterions = await GetAdGroupCriterionsByAdGroupIdAsync( adGroupIds[0], CriterionType.ProductPartition ); OutputStatusMessage("The ad group's product partition only has a tree root node: \n"); OutputProductPartitions(adGroupCriterions); /* * Let's update the bid of the root Unit we just added. */ BiddableAdGroupCriterion updatedRoot = new BiddableAdGroupCriterion { Id = applyProductPartitionActionsResponse.AdGroupCriterionIds[0], CriterionBid = new FixedBid { Bid = new Bid { Amount = 0.45 } } }; helper = new PartitionActionHelper(adGroupIds[0]); helper.UpdatePartition(updatedRoot); OutputStatusMessage("Updating the bid for the tree root node . . . \n"); await ApplyProductPartitionActionsAsync(helper.PartitionActions); adGroupCriterions = await GetAdGroupCriterionsByAdGroupIdAsync( adGroupIds[0], CriterionType.ProductPartition ); OutputStatusMessage("Updated the bid for the tree root node: \n"); OutputProductPartitions(adGroupCriterions); #endregion BidAllProducts #region InitializeTree /* * Now we will overwrite any existing tree root, and build a product partition group tree structure in multiple steps. * You could build the entire tree in a single call since there are less than 5,000 nodes; however, * we will build it in steps to demonstrate how to use the results from ApplyProductPartitionActions to update the tree. * * For a list of validation rules, see the Bing Shopping Campaigns technical guide: * https://msdn.microsoft.com/en-US/library/bing-ads-campaign-management-bing-shopping-campaigns.aspx */ helper = new PartitionActionHelper(adGroupIds[0]); /* * Check whether a root node exists already. */ adGroupCriterions = await GetAdGroupCriterionsByAdGroupIdAsync( adGroupIds[0], CriterionType.ProductPartition ); var existingRoot = GetRootNode(adGroupCriterions); if (existingRoot != null) { helper.DeletePartition(existingRoot); } root = helper.AddSubdivision( null, new ProductCondition { Operand = "All", Attribute = null } ); /* * The direct children of any node must have the same Operand. * For this example we will use CategoryL1 nodes as children of the root. * For a list of valid CategoryL1 through CategoryL5 values, see the Bing Category Taxonomy: * http://advertise.bingads.microsoft.com/en-us/WWDocs/user/search/en-us/Bing_Category_Taxonomy.txt */ var animalsSubdivision = helper.AddSubdivision( root, new ProductCondition { Operand = "CategoryL1", Attribute = "Animals & Pet Supplies" } ); /* * If you use a CategoryL2 node, it must be a descendant (child or later) of a CategoryL1 node. * In other words you cannot have a CategoryL2 node as parent of a CategoryL1 node. * For this example we will a CategoryL2 node as child of the CategoryL1 Animals & Pet Supplies node. */ var petSuppliesSubdivision = helper.AddSubdivision( animalsSubdivision, new ProductCondition { Operand = "CategoryL2", Attribute = "Pet Supplies" } ); var brandA = helper.AddUnit( petSuppliesSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand A" }, 0.35, false ); /* * If you won't bid on Brand B, set the helper method's bidAmount to '0' and isNegative to true. * The helper method will create a NegativeAdGroupCriterion and apply the condition. */ var brandB = helper.AddUnit( petSuppliesSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand B" }, 0, true ); var otherBrands = helper.AddUnit( petSuppliesSubdivision, new ProductCondition { Operand = "Brand", Attribute = null }, 0.35, false ); var otherPetSupplies = helper.AddUnit( animalsSubdivision, new ProductCondition { Operand = "CategoryL2", Attribute = null }, 0.35, false ); var electronics = helper.AddUnit( root, new ProductCondition { Operand = "CategoryL1", Attribute = "Electronics" }, 0.35, false ); var otherCategoryL1 = helper.AddUnit( root, new ProductCondition { Operand = "CategoryL1", Attribute = null }, 0.35, false ); OutputStatusMessage("Applying product partitions to the ad group . . . \n"); applyProductPartitionActionsResponse = await ApplyProductPartitionActionsAsync(helper.PartitionActions); // To retrieve product partitions after they have been applied, call GetAdGroupCriterionsByAdGroupId. // The product partition with ParentCriterionId set to null is the root node. adGroupCriterions = await GetAdGroupCriterionsByAdGroupIdAsync( adGroupIds[0], CriterionType.ProductPartition ); /* * The product partition group tree now has 9 nodes. * * All other (Root Node) | +-- Animals & Pet Supplies (CategoryL1) | | | +-- Pet Supplies (CategoryL2) | | | | | +-- Brand A | | | | | +-- Brand B | | | | | +-- All other (Brand) | | | +-- All other (CategoryL2) | +-- Electronics (CategoryL1) | +-- All other (CategoryL1) | */ OutputStatusMessage("The product partition group tree now has 9 nodes: \n"); OutputProductPartitions(adGroupCriterions); #endregion InitializeTree #region UpdateTree /* * Let's replace the Electronics (CategoryL1) node created above with an Electronics (CategoryL1) node that * has children i.e. Brand C (Brand), Brand D (Brand), and All other (Brand) as follows: * * Electronics (CategoryL1) | +-- Brand C (Brand) | +-- Brand D (Brand) | +-- All other (Brand) | */ helper = new PartitionActionHelper(adGroupIds[0]); /* * To replace a node we must know its Id and its ParentCriterionId. In this case the parent of the node * we are replacing is All other (Root Node), and was created at Index 1 of the previous ApplyProductPartitionActions call. * The node that we are replacing is Electronics (CategoryL1), and was created at Index 8. */ var rootId = applyProductPartitionActionsResponse.AdGroupCriterionIds[1]; electronics.Id = applyProductPartitionActionsResponse.AdGroupCriterionIds[8]; helper.DeletePartition(electronics); var parent = new BiddableAdGroupCriterion() { Id = rootId }; var electronicsSubdivision = helper.AddSubdivision( parent, new ProductCondition { Operand = "CategoryL1", Attribute = "Electronics" } ); var brandC = helper.AddUnit( electronicsSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand C" }, 0.35, false ); var brandD = helper.AddUnit( electronicsSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand D" }, 0.35, false ); var otherElectronicsBrands = helper.AddUnit( electronicsSubdivision, new ProductCondition { Operand = "Brand", Attribute = null }, 0.35, false ); OutputStatusMessage( "Updating the product partition group to refine Electronics (CategoryL1) with 3 child nodes . . . \n" ); applyProductPartitionActionsResponse = await ApplyProductPartitionActionsAsync(helper.PartitionActions); adGroupCriterions = await GetAdGroupCriterionsByAdGroupIdAsync( adGroupIds[0], CriterionType.ProductPartition ); /* * The product partition group tree now has 12 nodes, including the children of Electronics (CategoryL1): * * All other (Root Node) | +-- Animals & Pet Supplies (CategoryL1) | | | +-- Pet Supplies (CategoryL2) | | | | | +-- Brand A | | | | | +-- Brand B | | | | | +-- All other (Brand) | | | +-- All other (CategoryL2) | +-- Electronics (CategoryL1) | | | +-- Brand C (Brand) | | | +-- Brand D (Brand) | | | +-- All other (Brand) | +-- All other (CategoryL1) | */ OutputStatusMessage( "The product partition group tree now has 12 nodes, including the children of Electronics (CategoryL1): \n" ); OutputProductPartitions(adGroupCriterions); #endregion UpdateTree #endregion ManageAdGroup #region ManageAds /* * Create a product ad. You must add at least one ProductAd to the corresponding ad group. * A ProductAd is not used directly for delivered ad copy. Instead, the delivery engine generates * product ads from the product details that it finds in your Bing Merchant Center store's product catalog. * The primary purpose of the ProductAd object is to provide promotional text that the delivery engine * adds to the product ads that it generates. For example, if the promotional text is set to * “Free shipping on $99 purchases”, the delivery engine will set the product ad’s description to * “Free shipping on $99 purchases.” */ var ads = new Ad[] { new ProductAd { PromotionalText = "Free shipping on $99 purchases." }, }; AddAdsResponse addAdsResponse = await AddAdsAsync(adGroupIds[0], ads); OutputAdResults(ads, addAdsResponse.AdIds, addAdsResponse.PartialErrors); #endregion ManageAds #region CleanUp /* Delete the campaign, ad group, criterion, and ad that were previously added. * You should remove this region if you want to view the added entities in the * Bing Ads web application or another tool. */ DeleteCampaignsAsync(authorizationData.AccountId, new[] { campaignIds[0] }); OutputStatusMessage(String.Format("Deleted CampaignId {0}\n", campaignIds[0])); #endregion CleanUp } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
internal BulkDownloadOperation(string requestId, AuthorizationData authorizationData, string trackingId, ApiEnvironment?apiEnvironment) : base(requestId, authorizationData, new DownloadStatusProvider(requestId), trackingId, apiEnvironment) { }
public async override Task RunAsync(AuthorizationData authorizationData) { try { OutputStatusMessage("You must edit the ManageClient.cs file to provide the ClientAccountId for " + "the client link."); OutputStatusMessage("When adding a client link, the client link's ManagingCustomerId is set to the CustomerId of the current " + "authenticated user, who must be a Super Admin of the agency."); OutputStatusMessage("Login as an agency Super Admin user to send a client link invitation, " + "or unlink an existing client link."); OutputStatusMessage("Login as a client Super Admin user to accept a client link invitation.\n"); Service = new ServiceClient <ICustomerManagementService>(authorizationData); UpdateClientLinksResponse updateClientLinksResponse = null; // Specify the client link search criteria var pageInfo = new Paging { Index = 0, // The first page Size = 100 // The first 100 client links for this page of results }; var ordering = new OrderBy { Field = OrderByField.Number, Order = SortOrder.Ascending }; var predicate = new Predicate { Field = "ClientAccountId", Operator = PredicateOperator.In, Value = ClientAccountId.ToString(CultureInfo.InvariantCulture) }; // Search for client links that match the specified criteria. var clientLinks = await SearchClientLinksAsync( new[] { ordering }, pageInfo, new[] { predicate }); // Determine whether the agency is already managing the specified client account. // If a link exists with status either Active, LinkInProgress, LinkPending, // UnlinkInProgress, or UnlinkPending, the agency may not initiate a duplicate client link. ClientLink clientLink; var newLinkRequired = true; if (clientLinks.Count > 0) { clientLink = clientLinks[0]; OutputStatusMessage(String.Format("Current ClientLink Status: {0}.\n", clientLink.Status)); switch (clientLink.Status) { // The agency may choose to initiate the unlink process, // which would terminate the existing relationship with the client. case ClientLinkStatus.Active: clientLink.Status = ClientLinkStatus.UnlinkRequested; updateClientLinksResponse = await UpdateClientLinksAsync(new[] { clientLink }); OutputStatusMessage("UpdateClientLinks : UnlinkRequested.\n"); newLinkRequired = false; break; // Waiting on a system status transition or waiting for the StartDate. case ClientLinkStatus.LinkAccepted: OutputStatusMessage("The status is transitioning towards LinkInProgress.\n"); newLinkRequired = false; break; // Waiting on a system status transition. case ClientLinkStatus.LinkInProgress: OutputStatusMessage("The status is transitioning towards Active.\n"); newLinkRequired = false; break; // When the status is LinkPending, either the agency or client may update the status. // The agency may choose to cancel the client link invitation; however, in this example // the client will accept the invitation. // If the client does not accept or decline the invitation within 30 days, and if the agency // does not update the status to LinkCanceled, the system updates the status to LinkExpired. case ClientLinkStatus.LinkPending: /* * clientLink.Status = ClientLinkStatus.LinkCanceled; * updateClientLinksResponse = UpdateClientLinks(new[] { clientLink }); * WriteMessage(String.Format("The agency updated status: LinkCanceled.\n"); */ clientLink.Status = ClientLinkStatus.LinkAccepted; updateClientLinksResponse = await UpdateClientLinksAsync(new[] { clientLink }); OutputStatusMessage("UpdateClientLinks: LinkAccepted.\n"); newLinkRequired = false; break; // Waiting on a system status transition. case ClientLinkStatus.UnlinkInProgress: OutputStatusMessage("The status is transitioning towards Inactive.\n"); newLinkRequired = false; break; // Waiting on a system status transition. case ClientLinkStatus.UnlinkPending: OutputStatusMessage("The status is transitioning towards Inactive.\n"); newLinkRequired = false; break; // The link lifecycle has ended. default: OutputStatusMessage("A new client link invitation is required.\n"); break; } // Print errors if any occurred when updating the client link. if (updateClientLinksResponse != null) { PrintPartialErrors(updateClientLinksResponse.OperationErrors, updateClientLinksResponse.PartialErrors); } } // If no links exist between the agency and specified client account, or a link exists with status // either Inactive, LinkCanceled, LinkDeclined, LinkExpired, or LinkFailed, then the agency must // initiate a new client link. if (newLinkRequired) { clientLink = new ClientLink { ClientAccountId = ClientAccountId, ManagingCustomerId = authorizationData.CustomerId, IsBillToClient = true, Name = "My Client Link", StartDate = null, SuppressNotification = true }; var addClientLinksResponse = await AddClientLinksAsync(new[] { clientLink }); // Print errors if any occurred when adding the client link. PrintPartialErrors(addClientLinksResponse.OperationErrors.ToArray(), addClientLinksResponse.PartialErrors.ToArray()); OutputStatusMessage(string.Format("The user attempted to add a new ClientLink.\n")); OutputStatusMessage(string.Format("Login as the client Super Admin to accept the agency's request to manage AccountId {0}.\n", ClientAccountId)); } // Get and print the current client link clientLinks = await SearchClientLinksAsync( new[] { ordering }, pageInfo, new[] { predicate }); PrintClientLinks(clientLinks); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Customer Management service exceptions catch (FaultException <Microsoft.BingAds.CustomerManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.CustomerManagement.ApiFault> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
public KileTgsRequest CreateTgsRequest( Realm cRealm, PrincipalName cName, PrincipalName sName, KRBFlags kdcOptions, KerbUInt32 nonce, Realm realm, Asn1SequenceOf <PA_DATA> paData, ChecksumType checksumType, Ticket additionalTicket, AuthorizationData authorizationData) { if (cRealm == null) { throw new ArgumentNullException("cRealm"); } if (cName == null) { throw new ArgumentNullException("cName"); } if (sName == null) { throw new ArgumentNullException("sName"); } if (realm == null) { throw new ArgumentNullException("realm"); } KileTgsRequest request = new KileTgsRequest(context); request.Request.msg_type = new Asn1Integer((int)MsgType.KRB_TGS_REQ); request.Request.pvno = new Asn1Integer(ConstValue.KERBEROSV5); #region construct req_body request.Request.req_body = new KDC_REQ_BODY(); request.Request.req_body.kdc_options = new KDCOptions(KileUtility.ConvertInt2Flags((int)kdcOptions)); request.Request.req_body.nonce = nonce; request.Request.req_body.till = new KerberosTime(ConstValue.TGT_TILL_TIME); request.Request.req_body.etype = context.ClientEncryptionTypes; request.Request.req_body.realm = realm; if (additionalTicket != null) { request.Request.req_body.additional_tickets = new Asn1SequenceOf <Ticket>(new Ticket[] { additionalTicket }); } request.Request.req_body.sname = sName; request.EncAuthorizationData = authorizationData; if (authorizationData != null) { Asn1BerEncodingBuffer asnBuffer = new Asn1BerEncodingBuffer(); authorizationData.BerEncode(asnBuffer, true); request.Request.req_body.enc_authorization_data = new EncryptedData(); request.Request.req_body.enc_authorization_data.etype = new KerbInt32(0); byte[] encAsnEncoded = asnBuffer.Data; if (context.TgsSessionKey != null && context.TgsSessionKey.keytype != null && context.TgsSessionKey.keyvalue != null && context.TgsSessionKey.keyvalue.Value != null) { encAsnEncoded = KileUtility.Encrypt((EncryptionType)context.TgsSessionKey.keytype.Value, context.TgsSessionKey.keyvalue.ByteArrayValue, asnBuffer.Data, (int)KeyUsageNumber.TGS_REQ_KDC_REQ_BODY_AuthorizationData); request.Request.req_body.enc_authorization_data.etype = new KerbInt32(context.TgsSessionKey.keytype.Value); } request.Request.req_body.enc_authorization_data.cipher = new Asn1OctetString(encAsnEncoded); } #endregion construct req_body #region construct PA_DATA Asn1BerEncodingBuffer bodyBuffer = new Asn1BerEncodingBuffer(); request.Request.req_body.BerEncode(bodyBuffer); PA_DATA tgsPaData = ConstructTgsPaData(cRealm, cName, checksumType, bodyBuffer.Data); request.Request.padata = new Asn1SequenceOf <PA_DATA>(); if (paData == null || paData.Elements == null || paData.Elements.Length == 0) { request.Request.padata.Elements = new PA_DATA[] { tgsPaData }; } else { request.Request.padata.Elements = new PA_DATA[paData.Elements.Length + 1]; Array.Copy(paData.Elements, request.Request.padata.Elements, paData.Elements.Length); request.Request.padata.Elements[paData.Elements.Length] = tgsPaData; } #endregion construct PA_DATA return(request); }
public async override Task RunAsync(AuthorizationData authorizationData) { try { ApiEnvironment environment = ((OAuthDesktopMobileAuthCodeGrant)authorizationData.Authentication).Environment; AdInsightExampleHelper AdInsightExampleHelper = new AdInsightExampleHelper(this.OutputStatusMessage); AdInsightExampleHelper.AdInsightService = new ServiceClient <IAdInsightService>(authorizationData, environment); CampaignManagementExampleHelper CampaignManagementExampleHelper = new CampaignManagementExampleHelper(this.OutputStatusMessage); BulkServiceManager = new BulkServiceManager(authorizationData, environment); var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(String.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); var uploadEntities = new List <BulkEntity>(); #region Add // To get started with dynamic search ads, first you'll need to add a new Campaign // with its type set to DynamicSearchAds. When you create the campaign, you'll need to // include a DynamicSearchAdsSetting that specifies the target website domain and language. var bulkCampaign = new BulkCampaign { ClientId = "YourClientIdGoesHere", Campaign = new Campaign { Id = campaignIdKey, CampaignType = CampaignType.DynamicSearchAds, Settings = new[] { new DynamicSearchAdsSetting { DomainName = "contoso.com", Language = "English" } }, Name = "Women's Shoes " + DateTime.UtcNow, Description = "Red shoes line.", // You must choose to set either the shared budget ID or daily amount. // You can set one or the other, but you may not set both. BudgetId = null, DailyBudget = 50, BudgetType = Microsoft.BingAds.V12.CampaignManagement.BudgetLimitType.DailyBudgetStandard, // You can set your campaign bid strategy to Enhanced CPC (EnhancedCpcBiddingScheme) // and then, at any time, set an individual ad group bid strategy to // Manual CPC (ManualCpcBiddingScheme). BiddingScheme = new EnhancedCpcBiddingScheme { }, TimeZone = "PacificTimeUSCanadaTijuana", // Used with CustomParameters defined in lower level entities such as ads. TrackingUrlTemplate = "http://tracker.example.com/?season={_season}&promocode={_promocode}&u={lpurl}" }, }; uploadEntities.Add(bulkCampaign); // Next, create a new AdGroup within the dynamic search ads campaign. var bulkAdGroup = new BulkAdGroup { CampaignId = campaignIdKey, AdGroup = new AdGroup { Id = adGroupIdKey, Name = "Women's Red Shoe Sale", StartDate = null, EndDate = new Microsoft.BingAds.V12.CampaignManagement.Date { Month = 12, Day = 31, Year = DateTime.UtcNow.Year + 1 }, Language = "English", Status = AdGroupStatus.Active, // For ad groups you can use either of the InheritFromParentBiddingScheme or ManualCpcBiddingScheme objects. // If you do not set this element, then InheritFromParentBiddingScheme is used by default. BiddingScheme = new ManualCpcBiddingScheme { }, }, }; uploadEntities.Add(bulkAdGroup); // You can add one or more Webpage criterion to each ad group that helps determine // whether or not to serve dynamic search ads. var adGroupWebpagePositivePageContent = new BulkAdGroupDynamicSearchAdTarget { BiddableAdGroupCriterion = new BiddableAdGroupCriterion { AdGroupId = adGroupIdKey, CriterionBid = new FixedBid { Amount = 0.50 }, Criterion = new Webpage { Parameter = new WebpageParameter { Conditions = new[] { new WebpageCondition { Argument = "flowers", Operand = WebpageConditionOperand.PageContent, } }, CriterionName = "Ad Group Webpage Positive Page Content Criterion" }, }, // DestinationUrl and FinalUrls are not supported with Webpage criterion. // The Final URL is dynamically created at the ad level. DestinationUrl = null, FinalUrls = null, // In this example we are deferring to the campaign level tracking template. TrackingUrlTemplate = null, // Set custom parameters that are specific to this webpage criterion. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "PROMO1" }, new CustomParameter() { Key = "season", Value = "summer" }, } } } }; uploadEntities.Add(adGroupWebpagePositivePageContent); // To discover the categories that you can use for Webpage criterion (positive or negative), // use the GetDomainCategories operation with the Ad Insight service. var getDomainCategoriesResponse = await AdInsightExampleHelper.GetDomainCategoriesAsync( categoryName : null, domainName : DOMAIN_NAME, language : LANGUAGE); var categories = getDomainCategoriesResponse.Categories; // If any categories are available let's use one as a condition. if (categories.Count > 0) { var adGroupWebpagePositiveCategory = new BulkAdGroupDynamicSearchAdTarget { BiddableAdGroupCriterion = new BiddableAdGroupCriterion { AdGroupId = adGroupIdKey, CriterionBid = new FixedBid { Amount = 0.50 }, Criterion = new Webpage { Parameter = new WebpageParameter { Conditions = new[] { new WebpageCondition { Argument = categories[0].CategoryName, Operand = WebpageConditionOperand.Category, } }, CriterionName = "Ad Group Webpage Positive Category Criterion" }, } } }; uploadEntities.Add(adGroupWebpagePositiveCategory); } // If you want to exclude certain portions of your website, you can add negative Webpage // criterion at the campaign and ad group level. var adGroupWebpageNegativeUrl = new BulkAdGroupNegativeDynamicSearchAdTarget { NegativeAdGroupCriterion = new NegativeAdGroupCriterion { AdGroupId = adGroupIdKey, Criterion = new Webpage { Parameter = new WebpageParameter { // You can choose whether you want the criterion argument to match partial URLs, // page content, page title, or categories that Bing thinks applies to your website. Conditions = new[] { new WebpageCondition { Argument = DOMAIN_NAME, Operand = WebpageConditionOperand.Url, } }, // If you do not specify any name, then it will be set to a concatenated list of conditions. CriterionName = null } } } }; uploadEntities.Add(adGroupWebpageNegativeUrl); // The negative Webpage criterion at the campaign level applies to all ad groups // within the campaign; however, if you define ad group level negative Webpage criterion, // the campaign criterion is ignored for that ad group. var campaignWebpageNegative = new BulkCampaignNegativeDynamicSearchAdTarget { NegativeCampaignCriterion = new NegativeCampaignCriterion { CampaignId = campaignIdKey, Criterion = new Webpage { Parameter = new WebpageParameter { Conditions = new[] { new WebpageCondition { Argument = DOMAIN_NAME + "\\seattle", Operand = WebpageConditionOperand.Url, } }, CriterionName = "Campaign Negative Webpage Url Criterion" } } } }; uploadEntities.Add(campaignWebpageNegative); // Finally you can add a DynamicSearchAd into the ad group. The ad title and display URL // are generated automatically based on the website domain and language that you want to target. var bulkDynamicSearchAd = new BulkDynamicSearchAd { ClientId = "here", AdGroupId = adGroupIdKey, DynamicSearchAd = new DynamicSearchAd { Text = "Find New Customers & Increase Sales! Start Advertising on Contoso Today.", Path1 = "seattle", Path2 = "shoe sale", // You cannot set FinalUrls. The Final URL will be a dynamically selected landing page. // The final URL is distinct from the path that customers will see and click on in your ad. FinalUrls = null, // In this example we are deferring to the campaign level tracking template. TrackingUrlTemplate = null, // Set custom parameters that are specific to this ad. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "PROMO1" }, new CustomParameter() { Key = "season", Value = "summer" }, } } }, }; uploadEntities.Add(bulkDynamicSearchAd); // Upload and write the output OutputStatusMessage("Adding campaign, ad group, criterions, and ads . . .\n"); var Reader = await WriteEntitiesAndUploadFileAsync(uploadEntities); var downloadEntities = Reader.ReadEntities().ToList(); var campaignResults = downloadEntities.OfType <BulkCampaign>().ToList(); OutputBulkCampaigns(campaignResults); var adGroupResults = downloadEntities.OfType <BulkAdGroup>().ToList(); OutputBulkAdGroups(adGroupResults); var campaignNegativeDynamicSearchAdTargetResults = downloadEntities.OfType <BulkCampaignNegativeDynamicSearchAdTarget>().ToList(); OutputBulkCampaignNegativeDynamicSearchAdTargets(campaignNegativeDynamicSearchAdTargetResults); var adGroupDynamicSearchAdTargetResults = downloadEntities.OfType <BulkAdGroupDynamicSearchAdTarget>().ToList(); OutputBulkAdGroupDynamicSearchAdTargets(adGroupDynamicSearchAdTargetResults); var adGroupNegativeDynamicSearchAdTargetResults = downloadEntities.OfType <BulkAdGroupNegativeDynamicSearchAdTarget>().ToList(); OutputBulkAdGroupNegativeDynamicSearchAdTargets(adGroupNegativeDynamicSearchAdTargetResults); var dynamicSearchAdResults = downloadEntities.OfType <BulkDynamicSearchAd>().ToList(); OutputBulkDynamicSearchAds(dynamicSearchAdResults); Reader.Dispose(); #endregion Add #region Update uploadEntities = new List <BulkEntity>(); // You can update the bid for BiddableAdGroupCriterion var updateBid = new FixedBid { Amount = 0.75 }; // You can update the Webpage criterion name but cannot update the conditions. // To update the conditions you must delete the criterion and add a new criterion. // This update attempt will return an error. var updateCriterionAttemptFailure = new Webpage { Parameter = new WebpageParameter { Conditions = new[] { new WebpageCondition { Argument = "Books", Operand = WebpageConditionOperand.PageContent, } }, CriterionName = "Update Attempt Failure" }, }; var updateCriterionAttemptSuccess = new Webpage { Parameter = new WebpageParameter { CriterionName = "Update Attempt Success" }, }; foreach (var adGroupDynamicSearchAdTargetResult in adGroupDynamicSearchAdTargetResults) { var biddableAdGroupCriterion = adGroupDynamicSearchAdTargetResult.BiddableAdGroupCriterion as BiddableAdGroupCriterion; if (biddableAdGroupCriterion != null) { ((BiddableAdGroupCriterion)adGroupDynamicSearchAdTargetResult.BiddableAdGroupCriterion).CriterionBid = updateBid; adGroupDynamicSearchAdTargetResult.BiddableAdGroupCriterion.Criterion = updateCriterionAttemptSuccess; uploadEntities.Add(adGroupDynamicSearchAdTargetResult); } } foreach (var adGroupNegativeDynamicSearchAdTargetResult in adGroupNegativeDynamicSearchAdTargetResults) { var negativeAdGroupCriterion = adGroupNegativeDynamicSearchAdTargetResult.NegativeAdGroupCriterion as NegativeAdGroupCriterion; if (negativeAdGroupCriterion != null) { adGroupNegativeDynamicSearchAdTargetResult.NegativeAdGroupCriterion.Criterion = updateCriterionAttemptFailure; uploadEntities.Add(adGroupNegativeDynamicSearchAdTargetResult); } } OutputStatusMessage("Updating Ad Group Webpage Criterion . . . \n"); Reader = await WriteEntitiesAndUploadFileAsync(uploadEntities); downloadEntities = Reader.ReadEntities().ToList(); adGroupDynamicSearchAdTargetResults = downloadEntities.OfType <BulkAdGroupDynamicSearchAdTarget>().ToList(); OutputBulkAdGroupDynamicSearchAdTargets(adGroupDynamicSearchAdTargetResults); adGroupNegativeDynamicSearchAdTargetResults = downloadEntities.OfType <BulkAdGroupNegativeDynamicSearchAdTarget>().ToList(); OutputBulkAdGroupNegativeDynamicSearchAdTargets(adGroupNegativeDynamicSearchAdTargetResults); Reader.Dispose(); #endregion Update #region Get var entities = new[] { DownloadEntity.AdGroupDynamicSearchAdTargets, DownloadEntity.AdGroupNegativeDynamicSearchAdTargets }; var downloadParameters = new DownloadParameters { CampaignIds = null, DataScope = DataScope.EntityData | DataScope.EntityPerformanceData, PerformanceStatsDateRange = new PerformanceStatsDateRange { PredefinedTime = ReportTimePeriod.LastFourWeeks }, DownloadEntities = entities, FileType = FileType, LastSyncTimeInUTC = null, ResultFileDirectory = FileDirectory, ResultFileName = DownloadFileName, OverwriteResultFile = true }; // You may optionally cancel the DownloadFileAsync operation after a specified time interval. var tokenSource = new CancellationTokenSource(); tokenSource.CancelAfter(TimeoutInMilliseconds); var resultFilePath = await BulkServiceManager.DownloadFileAsync(downloadParameters, progress, tokenSource.Token); OutputStatusMessage(String.Format("Download result file: {0}\n", resultFilePath)); #endregion Get #region CleanUp // Delete the campaign, ad group, criterion, and ad that were previously added. // You should remove this operation if you want to view the added entities in the // Bing Ads web application or another tool. // You must set the Id field to the corresponding entity identifier, and the Status field to Deleted. // When you delete a BulkCampaign, the dependent entities such as BulkAdGroup // are deleted without being specified explicitly. uploadEntities = new List <BulkEntity>(); foreach (var campaignResult in campaignResults) { campaignResult.Campaign.Status = CampaignStatus.Deleted; uploadEntities.Add(campaignResult); } OutputStatusMessage("\nDeleting DSA campaign, criterions, and ad . . .\n"); Reader = await WriteEntitiesAndUploadFileAsync(uploadEntities); downloadEntities = Reader.ReadEntities().ToList(); campaignResults = downloadEntities.OfType <BulkCampaign>().ToList(); OutputBulkCampaigns(campaignResults); Reader.Dispose(); #endregion Cleanup } // Catch Microsoft Account authorization exceptions. catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.V12.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } finally { if (Reader != null) { Reader.Dispose(); } if (Writer != null) { Writer.Dispose(); } } }
public async override Task RunAsync(AuthorizationData authorizationData) { try { CampaignManagementExampleHelper = new CampaignManagementExampleHelper(this.OutputStatusMessage); BulkServiceManager = new BulkServiceManager(authorizationData); var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(string.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); #region Add // Prepare the bulk entities that you want to upload. Each bulk entity contains the corresponding campaign management object, // and additional elements needed to read from and write to a bulk file. var bulkCampaign = new BulkCampaign { // ClientId may be used to associate records in the bulk upload file with records in the results file. The value of this field // is not used or stored by the server; it is simply copied from the uploaded record to the corresponding result record. // Note: This bulk file Client Id is not related to an application Client Id for OAuth. ClientId = "YourClientIdGoesHere", Campaign = new Campaign { // When using the Campaign Management service, the Id cannot be set. In the context of a BulkCampaign, the Id is optional // and may be used as a negative reference key during bulk upload. For example the same negative value set for the campaign Id // will be used when associating this new campaign with a new negative keyword in the BulkCampaignNegativeKeyword object below. Id = campaignIdKey, Name = "Women's Shoes " + DateTime.UtcNow, Description = "Red shoes line.", // You must choose to set either the shared budget ID or daily amount. // You can set one or the other, but you may not set both. BudgetId = null, DailyBudget = 50, BudgetType = BudgetLimitType.DailyBudgetStandard, BiddingScheme = new EnhancedCpcBiddingScheme(), TimeZone = "PacificTimeUSCanadaTijuana", } }; var bulkCampaignNegativeKeywords = new BulkCampaignNegativeKeyword[] { new BulkCampaignNegativeKeyword { CampaignId = campaignIdKey, NegativeKeyword = new NegativeKeyword { MatchType = MatchType.Phrase, Text = "auto", } }, new BulkCampaignNegativeKeyword { CampaignId = campaignIdKey, NegativeKeyword = new NegativeKeyword { MatchType = MatchType.Exact, Text = "auto", } }, new BulkCampaignNegativeKeyword { CampaignId = campaignIdKey, NegativeKeyword = new NegativeKeyword { MatchType = MatchType.Phrase, Text = "car", } }, new BulkCampaignNegativeKeyword { CampaignId = campaignIdKey, NegativeKeyword = new NegativeKeyword { MatchType = MatchType.Exact, Text = "car", } }, }; // Negative keywords can be added and deleted from a shared negative keyword list. The negative keyword list can be shared or associated with multiple campaigns. // You can create up to 20 negative keyword lists per account and share or associate them with any campaign in the same account. // To create a negative keyword list, upload a BulkNegativeKeywordList (Negative Keyword List record type). // For each negative keyword that you want to add to the list, upload a BulkSharedNegativeKeyword (Shared Negative Keyword record type). // To associate the negative keyword list with a campaign, also upload a BulkCampaignNegativeKeywordList (Campaign Negative Keyword List Association record type). var bulkNegativeKeywordList = new BulkNegativeKeywordList { NegativeKeywordList = new NegativeKeywordList { // Since we are adding the list and the negative keywords during the same upload, // we will use a reference key to the negative keyword list identifier. Id = negativeKeywordListIdKey, Name = "My NKW List", }, }; var bulkSharedNegativeKeywords = new BulkSharedNegativeKeyword[] { new BulkSharedNegativeKeyword { NegativeKeyword = new NegativeKeyword { MatchType = MatchType.Phrase, Text = "mobile", }, NegativeKeywordListId = negativeKeywordListIdKey, }, new BulkSharedNegativeKeyword { NegativeKeyword = new NegativeKeyword { MatchType = MatchType.Exact, Text = "mobile", }, NegativeKeywordListId = negativeKeywordListIdKey, }, }; var bulkCampaignNegativeKeywordList = new BulkCampaignNegativeKeywordList { SharedEntityAssociation = new SharedEntityAssociation { EntityId = campaignIdKey, EntityType = "Campaign", SharedEntityId = negativeKeywordListIdKey, SharedEntityType = "NegativeKeywordList", } }; var uploadEntities = new List <BulkEntity>(); uploadEntities.Add(bulkCampaign); foreach (var bulkCampaignNegativeKeyword in bulkCampaignNegativeKeywords) { uploadEntities.Add(bulkCampaignNegativeKeyword); } uploadEntities.Add(bulkNegativeKeywordList); foreach (var bulkSharedNegativeKeyword in bulkSharedNegativeKeywords) { uploadEntities.Add(bulkSharedNegativeKeyword); } uploadEntities.Add(bulkCampaignNegativeKeywordList); // Upload and write the output Reader = await WriteEntitiesAndUploadFileAsync(uploadEntities); var downloadEntities = Reader.ReadEntities().ToList(); var campaignResults = downloadEntities.OfType <BulkCampaign>().ToList(); OutputBulkCampaigns(campaignResults); var campaignNegativeKeywordResults = downloadEntities.OfType <BulkCampaignNegativeKeyword>().ToList(); OutputBulkCampaignNegativeKeywords(campaignNegativeKeywordResults); var negativeKeywordListResults = downloadEntities.OfType <BulkNegativeKeywordList>().ToList(); OutputBulkNegativeKeywordLists(negativeKeywordListResults); var sharedNegativeKeywordListResults = downloadEntities.OfType <BulkSharedNegativeKeyword>().ToList(); OutputBulkSharedNegativeKeywords(sharedNegativeKeywordListResults); var campaignNegativeKeywordListResults = downloadEntities.OfType <BulkCampaignNegativeKeywordList>().ToList(); OutputBulkCampaignNegativeKeywordLists(campaignNegativeKeywordListResults); Reader.Dispose(); #endregion Add #region CleanUp //Delete the campaign and negative keywords that were previously added. //You should remove this region if you want to view the added entities in the //Bing Ads web application or another tool. //You must set the Id field to the corresponding entity identifier, and the Status field to Deleted. //When you delete a BulkCampaign, the dependent entities such as BulkCampaignNegativeKeyword //are deleted without being specified explicitly. //When you delete a BulkNegativeKeywordList, the dependent entities such as BulkSharedNegativeKeyword //are deleted without being specified explicitly. uploadEntities = new List <BulkEntity>(); foreach (var campaignResult in campaignResults) { campaignResult.Campaign.Status = CampaignStatus.Deleted; uploadEntities.Add(campaignResult); } foreach (var negativeKeywordListResult in negativeKeywordListResults) { negativeKeywordListResult.Status = Status.Deleted; uploadEntities.Add(negativeKeywordListResult); } // Upload and write the output OutputStatusMessage("\nDeleting campaign and negative keywords . . .\n"); Reader = await WriteEntitiesAndUploadFileAsync(uploadEntities); downloadEntities = Reader.ReadEntities().ToList(); OutputBulkCampaigns(downloadEntities.OfType <BulkCampaign>().ToList()); OutputBulkNegativeKeywordLists(downloadEntities.OfType <BulkNegativeKeywordList>().ToList()); Reader.Dispose(); #endregion Cleanup } // Catch Microsoft Account authorization exceptions. catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.V12.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } finally { if (Reader != null) { Reader.Dispose(); } if (Writer != null) { Writer.Dispose(); } } }
public async override Task RunAsync(AuthorizationData authorizationData) { try { ApiEnvironment environment = ((OAuthDesktopMobileAuthCodeGrant)authorizationData.Authentication).Environment; // Used to output the Campaign Management objects within Bulk entities. CampaignManagementExampleHelper = new CampaignManagementExampleHelper( OutputStatusMessageDefault: this.OutputStatusMessage); BulkServiceManager = new BulkServiceManager( authorizationData: authorizationData, apiEnvironment: environment); var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(string.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); var tokenSource = new CancellationTokenSource(); tokenSource.CancelAfter(TimeoutInMilliseconds); // In this example we will download all ad groups in the account. var downloadParameters = new DownloadParameters { DataScope = DataScope.EntityData, DownloadEntities = new[] { DownloadEntity.AdGroups }, FileType = FileType, LastSyncTimeInUTC = null, ResultFileDirectory = FileDirectory, ResultFileName = DownloadFileName, OverwriteResultFile = true }; OutputStatusMessage("-----\nDownloading all ad groups in the account."); var bulkFilePath = await BulkServiceManager.DownloadFileAsync( parameters : downloadParameters, progress : progress, cancellationToken : tokenSource.Token); OutputStatusMessage("Download results:"); Reader = new BulkFileReader( filePath: bulkFilePath, resultFileType: ResultFileType.FullDownload, fileFormat: FileType); var bulkAdGroups = Reader.ReadEntities().ToList().OfType <BulkAdGroup>().ToList(); OutputBulkAdGroups(bulkAdGroups); Writer = new BulkFileWriter(FileDirectory + UploadFileName); // We will activate ad groups for one month starting from today as an example. var nextMonth = DateTime.UtcNow.AddMonths(1); // Within the downloaded records, find all ad groups that you want to update. foreach (var bulkAdGroup in bulkAdGroups) { var adGroup = bulkAdGroup.AdGroup; if (adGroup != null && bulkAdGroup.AdGroup.Status.ToString().CompareTo("Active") != 0) { // For best performance, only upload the properties that you want to update. Writer.WriteEntity(new BulkAdGroup { CampaignId = bulkAdGroup.CampaignId, AdGroup = new AdGroup { Id = adGroup.Id, EndDate = new Microsoft.BingAds.V12.CampaignManagement.Date { Month = nextMonth.Month, Day = nextMonth.Day, Year = nextMonth.Year }, Status = AdGroupStatus.Active, } }); } } Reader.Dispose(); Writer.Dispose(); // Upload the local file that we already prepared var fileUploadParameters = new FileUploadParameters { ResultFileDirectory = FileDirectory, CompressUploadFile = true, ResultFileName = ResultFileName, OverwriteResultFile = true, UploadFilePath = FileDirectory + UploadFileName, ResponseMode = ResponseMode.ErrorsAndResults }; OutputStatusMessage("-----\nActivating the ad groups..."); var resultFilePath = await BulkServiceManager.UploadFileAsync( parameters : fileUploadParameters, progress : progress, cancellationToken : tokenSource.Token); Reader = new BulkFileReader( filePath: resultFilePath, resultFileType: ResultFileType.Upload, fileFormat: FileType); OutputStatusMessage("Upload results:"); bulkAdGroups = Reader.ReadEntities().ToList().OfType <BulkAdGroup>().ToList(); OutputBulkAdGroups(bulkAdGroups); Reader.Dispose(); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.V12.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
public async override Task RunAsync(AuthorizationData authorizationData) { try { BulkService = new BulkServiceManager(authorizationData); BulkService.StatusPollIntervalInMilliseconds = 5000; var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(String.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); // In this example we will download all ads and keywords in the account. var entities = BulkDownloadEntity.Ads | BulkDownloadEntity.Keywords; // DownloadParameters is used for Option A below. var downloadParameters = new DownloadParameters { CampaignIds = null, DataScope = DataScope.EntityData | DataScope.EntityPerformanceData, PerformanceStatsDateRange = new PerformanceStatsDateRange { PredefinedTime = ReportTimePeriod.LastFourWeeks }, Entities = entities, FileType = FileType, LastSyncTimeInUTC = null, ResultFileDirectory = FileDirectory, ResultFileName = DownloadFileName, OverwriteResultFile = true }; // SubmitDownloadParameters is used for Option B and Option C below. var submitDownloadParameters = new SubmitDownloadParameters { CampaignIds = null, DataScope = DataScope.EntityData | DataScope.EntityPerformanceData, PerformanceStatsDateRange = new PerformanceStatsDateRange { PredefinedTime = ReportTimePeriod.LastFourWeeks }, Entities = entities, FileType = FileType, LastSyncTimeInUTC = null }; // Option A - Background Completion with BulkServiceManager // You can submit a download or upload request and the BulkServiceManager will automatically // return results. The BulkServiceManager abstracts the details of checking for result file // completion, and you don't have to write any code for results polling. OutputStatusMessage("Awaiting Background Completion . . ."); await BackgroundCompletionAsync(downloadParameters, progress); // Option B - Submit and Download with BulkServiceManager // Submit the download request and then use the BulkDownloadOperation result to // track status until the download is complete e.g. either using // TrackAsync or GetStatusAsync. //OutputStatusMessage("Awaiting Submit and Download . . ."); //await SubmitAndDownloadAsync(submitDownloadParameters); // Option C - Download Results with BulkServiceManager // If for any reason you have to resume from a previous application state, // you can use an existing download request identifier and use it // to download the result file. // For example you might have previously retrieved a request ID using SubmitDownloadAsync. //var bulkDownloadOperation = await BulkService.SubmitDownloadAsync(submitDownloadParameters); //var requestId = bulkDownloadOperation.RequestId; // Given the request ID above, you can resume the workflow and download the bulk file. // The download request identifier is valid for two days. // If you do not download the bulk file within two days, you must request it again. //OutputStatusMessage("Awaiting Download Results . . ."); //await DownloadResultsAsync(requestId, authorizationData); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(String.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.V10.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(String.Join("; ", ex.Detail.Errors.Select(error => String.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V10.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(String.Join("; ", ex.Detail.OperationErrors.Select(error => String.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(String.Join("; ", ex.Detail.BatchErrors.Select(error => String.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
public async override Task RunAsync(AuthorizationData authorizationData) { try { ApiEnvironment environment = ((OAuthDesktopMobileAuthCodeGrant)authorizationData.Authentication).Environment; CampaignManagementExampleHelper CampaignManagementExampleHelper = new CampaignManagementExampleHelper( OutputStatusMessageDefault: this.OutputStatusMessage); CampaignManagementExampleHelper.CampaignManagementService = new ServiceClient <ICampaignManagementService>( authorizationData: authorizationData, environment: environment); // Add an image to your media library. // The image asset is needed later to create the responsive ad. var landscapeImageMedia = GetImageMedia( "Image191x100", MediaFilePath + ResponsiveAdMediaFileName, System.Drawing.Imaging.ImageFormat.Png); var media = new Media[] { landscapeImageMedia, }; OutputStatusMessage("-----\nAddMedia:"); AddMediaResponse addMediaResponse = await CampaignManagementExampleHelper.AddMediaAsync( accountId : authorizationData.AccountId, media : media); long[] mediaIds = addMediaResponse.MediaIds.ToArray(); OutputStatusMessage("MediaIds:"); CampaignManagementExampleHelper.OutputArrayOfLong(mediaIds); // Create an Audience campaign with one ad group and a responsive ad. var campaigns = new[] { new Campaign { BudgetType = BudgetLimitType.DailyBudgetStandard, // CampaignType must be set for Audience campaigns CampaignType = CampaignType.Audience, DailyBudget = 50, // Languages must be set for Audience campaigns Languages = new string[] { "All" }, Name = "Women's Shoes " + DateTime.UtcNow, TimeZone = "PacificTimeUSCanadaTijuana", }, }; OutputStatusMessage("-----\nAddCampaigns:"); AddCampaignsResponse addCampaignsResponse = await CampaignManagementExampleHelper.AddCampaignsAsync( accountId : authorizationData.AccountId, campaigns : campaigns); long?[] campaignIds = addCampaignsResponse.CampaignIds.ToArray(); BatchError[] campaignErrors = addCampaignsResponse.PartialErrors.ToArray(); OutputStatusMessage("CampaignIds:"); CampaignManagementExampleHelper.OutputArrayOfLong(campaignIds); OutputStatusMessage("PartialErrors:"); CampaignManagementExampleHelper.OutputArrayOfBatchError(campaignErrors); // Add an ad group within the campaign. var adGroups = new[] { new AdGroup { Name = "Women's Red Shoe Sale", StartDate = null, EndDate = new Date { Month = 12, Day = 31, Year = DateTime.UtcNow.Year + 1 }, CpcBid = new Bid { Amount = 0.09 }, // Network cannot be set for ad groups in Audience campaigns Network = null, } }; OutputStatusMessage("-----\nAddAdGroups:"); AddAdGroupsResponse addAdGroupsResponse = await CampaignManagementExampleHelper.AddAdGroupsAsync( campaignId : (long)campaignIds[0], adGroups : adGroups, returnInheritedBidStrategyTypes : false); long?[] adGroupIds = addAdGroupsResponse.AdGroupIds.ToArray(); BatchError[] adGroupErrors = addAdGroupsResponse.PartialErrors.ToArray(); OutputStatusMessage("AdGroupIds:"); CampaignManagementExampleHelper.OutputArrayOfLong(adGroupIds); OutputStatusMessage("PartialErrors:"); CampaignManagementExampleHelper.OutputArrayOfBatchError(adGroupErrors); // Add a responsive ad within the ad group. var ads = new Ad[] { new ResponsiveAd { BusinessName = "Contoso", CallToAction = CallToAction.AddToCart, FinalUrls = new[] { "https://www.contoso.com/womenshoesale" }, Headline = "Fast & Easy Setup", Images = new [] { // You are only required to provide a landscape image asset. // Optionally you can include additional asset links, i.e., one image asset for each supported sub type. // For any image asset sub types that you do not explicitly set, // the service will automatically create image asset links by cropping the LandscapeImageMedia. new AssetLink { Asset = new ImageAsset { CropHeight = null, CropWidth = null, CropX = null, CropY = null, Id = mediaIds[0], Name = "My LandscapeImageMedia", SubType = "LandscapeImageMedia", }, }, }, LongHeadlineString = "Find New Customers & Increase Sales!", Text = "Find New Customers & Increase Sales! Start Advertising on Contoso Today.", }, }; OutputStatusMessage("-----\nAddAds:"); AddAdsResponse addAdsResponse = await CampaignManagementExampleHelper.AddAdsAsync( adGroupId : (long)adGroupIds[0], ads : ads); long?[] adIds = addAdsResponse.AdIds.ToArray(); BatchError[] adErrors = addAdsResponse.PartialErrors.ToArray(); OutputStatusMessage("AdIds:"); CampaignManagementExampleHelper.OutputArrayOfLong(adIds); OutputStatusMessage("PartialErrors:"); CampaignManagementExampleHelper.OutputArrayOfBatchError(adErrors); // Delete the account's media. OutputStatusMessage("-----\nDeleteMedia:"); await CampaignManagementExampleHelper.DeleteMediaAsync( accountId : authorizationData.AccountId, mediaIds : mediaIds); foreach (var id in mediaIds) { OutputStatusMessage(string.Format("Deleted Media Id {0}", id)); } // Delete the campaign and everything it contains e.g., ad groups and ads. OutputStatusMessage("-----\nDeleteCampaigns:"); await CampaignManagementExampleHelper.DeleteCampaignsAsync( accountId : authorizationData.AccountId, campaignIds : new[] { (long)campaignIds[0] }); OutputStatusMessage(string.Format("Deleted Campaign Id {0}", campaignIds[0])); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V13.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V13.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V13.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
public async override Task RunAsync(AuthorizationData authorizationData) { try { BulkService = new BulkServiceManager(authorizationData); var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(String.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); #region Add const int targetIdKey = -1; const int campaignIdKey = -123; // Prepare the bulk entities that you want to upload. Each bulk entity contains the corresponding campaign management object, // and additional elements needed to read from and write to a bulk file. var bulkCampaign = new BulkCampaign { // ClientId may be used to associate records in the bulk upload file with records in the results file. The value of this field // is not used or stored by the server; it is simply copied from the uploaded record to the corresponding result record. // Note: This bulk file Client Id is not related to an application Client Id for OAuth. ClientId = "YourClientIdGoesHere", Campaign = new Campaign { // When using the Campaign Management service, the Id cannot be set. In the context of a BulkCampaign, the Id is optional // and may be used as a negative reference key during bulk upload. For example the same negative value set for the campaign Id // will be used when associating this new campaign with a new call ad extension in the BulkCampaignCallAdExtension object below. Id = campaignIdKey, Name = "Women's Shoes " + DateTime.UtcNow, Description = "Red shoes line.", BudgetType = BudgetLimitType.MonthlyBudgetSpendUntilDepleted, MonthlyBudget = 1000.00, TimeZone = "PacificTimeUSCanadaTijuana", DaylightSaving = true } }; // Prepare targets for upload var bulkCampaignDayTimeTarget = new BulkCampaignDayTimeTarget { CampaignId = campaignIdKey, TargetId = targetIdKey, DayTimeTarget = new DayTimeTarget { Bids = new List <DayTimeTargetBid> { new DayTimeTargetBid { BidAdjustment = 10, Day = Day.Friday, FromHour = 11, FromMinute = Minute.Zero, ToHour = 13, ToMinute = Minute.Fifteen }, new DayTimeTargetBid { BidAdjustment = 20, Day = Day.Saturday, FromHour = 11, FromMinute = Minute.Zero, ToHour = 13, ToMinute = Minute.Fifteen } } } }; var bulkCampaignLocationTarget = new BulkCampaignLocationTarget { CampaignId = campaignIdKey, TargetId = targetIdKey, IntentOption = IntentOption.PeopleIn, CityTarget = new CityTarget { Bids = new List <CityTargetBid> { new CityTargetBid { BidAdjustment = 15, City = "Toronto, Toronto ON CA", IsExcluded = false } } }, CountryTarget = new CountryTarget { Bids = new List <CountryTargetBid> { new CountryTargetBid { BidAdjustment = 15, CountryAndRegion = "CA", IsExcluded = false } } }, MetroAreaTarget = new MetroAreaTarget { Bids = new List <MetroAreaTargetBid> { new MetroAreaTargetBid { BidAdjustment = 15, MetroArea = "Seattle-Tacoma, WA, WA US", IsExcluded = false } } }, StateTarget = new StateTarget { Bids = new List <StateTargetBid> { new StateTargetBid { BidAdjustment = 15, State = "US-WA", IsExcluded = false } } }, PostalCodeTarget = new PostalCodeTarget { Bids = new List <PostalCodeTargetBid> { new PostalCodeTargetBid { // Bid adjustments are not allowed for location exclusions. // If IsExcluded is true, this element will be ignored. BidAdjustment = 10, PostalCode = "98052, WA US", IsExcluded = false } } } }; var bulkCampaignRadiusTarget = new BulkCampaignRadiusTarget { CampaignId = campaignIdKey, TargetId = targetIdKey, RadiusTarget = new RadiusTarget2 { Bids = new List <RadiusTargetBid2> { new RadiusTargetBid2 { BidAdjustment = 50, LatitudeDegrees = 47.755367, LongitudeDegrees = -122.091827, Radius = 11, RadiusUnit = DistanceUnit.Kilometers } } } }; // Write the entities created above, to the specified file. // Dependent entities such as BulkCampaignLocationTarget must be written after any dependencies, // for example a BulkCampaign. Writer = new BulkFileWriter(FileDirectory + UploadFileName); Writer.WriteEntity(bulkCampaign); Writer.WriteEntity(bulkCampaignDayTimeTarget); Writer.WriteEntity(bulkCampaignLocationTarget); Writer.WriteEntity(bulkCampaignRadiusTarget); Writer.Dispose(); var fileUploadParameters = new FileUploadParameters { ResultFileDirectory = FileDirectory, ResultFileName = ResultFileName, OverwriteResultFile = true, UploadFilePath = FileDirectory + UploadFileName, ResponseMode = ResponseMode.ErrorsAndResults }; // UploadFileAsync will upload the file you finished writing and will download the results file OutputStatusMessage("Starting UploadFileAsync . . .\n"); var bulkFilePath = await BulkService.UploadFileAsync(fileUploadParameters, progress, CancellationToken.None); Reader = new BulkFileReader(bulkFilePath, ResultFileType.Upload, FileType); OutputStatusMessage("Upload Results Bulk File Path" + Reader.BulkFilePath + "\n"); OutputStatusMessage("Added Entities\n"); // Write the upload output var bulkEntities = Reader.ReadEntities().ToList(); var campaignResults = bulkEntities.OfType <BulkCampaign>().ToList(); OutputBulkCampaigns(campaignResults); var campaignDayTimeTargetResults = bulkEntities.OfType <BulkCampaignDayTimeTarget>().ToList(); OutputBulkCampaignDayTimeTargets(campaignDayTimeTargetResults); var campaignLocationTargetResults = bulkEntities.OfType <BulkCampaignLocationTarget>().ToList(); OutputBulkCampaignLocationTargets(campaignLocationTargetResults); var campaignRadiusTargetResults = bulkEntities.OfType <BulkCampaignRadiusTarget>().ToList(); OutputBulkCampaignRadiusTargets(campaignRadiusTargetResults); Reader.Dispose(); #endregion Add #region Update // Update the day and time target. // Do not create a BulkAdGroupDayTimeTarget for update, unless you want to replace all existing DayTime target bids // with the specified day and time target set for the current bulk upload. // Instead you should upload one or more bids as a list of BulkCampaignDayTimeTargetBid. var bulkCampaignDayTimeTargetBids = new List <BulkCampaignDayTimeTargetBid> { new BulkCampaignDayTimeTargetBid { CampaignId = campaignDayTimeTargetResults[0].CampaignId, TargetId = targetIdKey, DayTimeTargetBid = new DayTimeTargetBid { BidAdjustment = 15, Day = Day.Friday, FromHour = 11, FromMinute = Minute.Zero, ToHour = 13, ToMinute = Minute.Fifteen } } }; // Write the updated target to the file Writer = new BulkFileWriter(FileDirectory + UploadFileName); foreach (var bulkCampaignDayTimeTargetBid in bulkCampaignDayTimeTargetBids) { Writer.WriteEntity(bulkCampaignDayTimeTargetBid); } Writer.Dispose(); fileUploadParameters = new FileUploadParameters { ResultFileDirectory = FileDirectory, ResultFileName = ResultFileName, OverwriteResultFile = true, UploadFilePath = FileDirectory + UploadFileName, ResponseMode = ResponseMode.ErrorsAndResults }; // UploadFileAsync will upload the file you finished writing and will download the results file OutputStatusMessage("Starting UploadFileAsync . . .\n"); bulkFilePath = await BulkService.UploadFileAsync(fileUploadParameters, progress, CancellationToken.None); Reader = new BulkFileReader(bulkFilePath, ResultFileType.Upload, FileType); OutputStatusMessage("Upload Results Bulk File Path: " + Reader.BulkFilePath + "\n"); OutputStatusMessage("Updated Entities\n"); // Write any upload errors var campaignDayTimeTargetBidResults = Reader.ReadEntities().OfType <BulkCampaignDayTimeTargetBid>().ToList(); OutputBulkCampaignDayTimeTargetBids(campaignDayTimeTargetBidResults); Reader.Dispose(); #endregion Update #region Delete // Prepare the bulk entities that you want to delete. You must set the Id field to the corresponding // entity identifier, and the Status field to Deleted. var campaignId = campaignResults[0].Campaign.Id; bulkCampaign = new BulkCampaign { Campaign = new Campaign { Id = campaignId, Status = CampaignStatus.Deleted } }; var targetId = campaignDayTimeTargetResults[0].TargetId; bulkCampaignDayTimeTarget = new BulkCampaignDayTimeTarget { Status = Status.Deleted, CampaignId = campaignId, TargetId = targetId }; bulkCampaignLocationTarget = new BulkCampaignLocationTarget { Status = Status.Deleted, CampaignId = campaignId, TargetId = targetId }; bulkCampaignRadiusTarget = new BulkCampaignRadiusTarget { Status = Status.Deleted, CampaignId = campaignId, TargetId = targetId }; // Write the entities that you want deleted, to the specified file. Writer = new BulkFileWriter(FileDirectory + UploadFileName); Writer.WriteEntity(bulkCampaign); Writer.WriteEntity(bulkCampaignDayTimeTarget); Writer.WriteEntity(bulkCampaignLocationTarget); Writer.WriteEntity(bulkCampaignRadiusTarget); Writer.Dispose(); fileUploadParameters = new FileUploadParameters { ResultFileDirectory = FileDirectory, ResultFileName = ResultFileName, OverwriteResultFile = true, UploadFilePath = FileDirectory + UploadFileName, ResponseMode = ResponseMode.ErrorsAndResults }; // UploadFileAsync will upload the file you finished writing and will download the results file OutputStatusMessage("Starting UploadFileAsync . . .\n"); bulkFilePath = await BulkService.UploadFileAsync(fileUploadParameters, progress, CancellationToken.None); Reader = new BulkFileReader(bulkFilePath, ResultFileType.Upload, FileType); OutputStatusMessage("Upload Results Bulk File Path" + Reader.BulkFilePath + "\n"); OutputStatusMessage("Deleted Entities\n"); // Write the upload output bulkEntities = Reader.ReadEntities().ToList(); campaignResults = bulkEntities.OfType <BulkCampaign>().ToList(); OutputBulkCampaigns(campaignResults); campaignDayTimeTargetResults = bulkEntities.OfType <BulkCampaignDayTimeTarget>().ToList(); OutputBulkCampaignDayTimeTargets(campaignDayTimeTargetResults); campaignLocationTargetResults = bulkEntities.OfType <BulkCampaignLocationTarget>().ToList(); OutputBulkCampaignLocationTargets(campaignLocationTargetResults); campaignRadiusTargetResults = bulkEntities.OfType <BulkCampaignRadiusTarget>().ToList(); OutputBulkCampaignRadiusTargets(campaignRadiusTargetResults); Reader.Dispose(); #endregion Delete } // Catch Microsoft Account authorization exceptions. catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } finally { if (Reader != null) { Reader.Dispose(); } if (Writer != null) { Writer.Dispose(); } } }
public async override Task RunAsync(AuthorizationData authorizationData) { try { Service = new ServiceClient <ICampaignManagementService>(authorizationData); // Specify a campaign. var campaign = new Campaign { Name = "Women's Shoes" + DateTime.UtcNow, Description = "Red shoes line.", BudgetType = BudgetLimitType.MonthlyBudgetSpendUntilDepleted, MonthlyBudget = 1000.00, TimeZone = "PacificTimeUSCanadaTijuana", DaylightSaving = true }; // Specify an ad group. var adGroup = new AdGroup { Name = "Women's Red Shoe Sale", AdDistribution = AdDistribution.Search, BiddingModel = BiddingModel.Keyword, PricingModel = PricingModel.Cpc, StartDate = null, EndDate = new Date { Month = 12, Day = 31, Year = 2015 }, ExactMatchBid = new Bid { Amount = 0.09 }, PhraseMatchBid = new Bid { Amount = 0.07 }, Language = "English" }; // Add the campaign and ad group var campaignIds = (long[]) await AddCampaignsAsync(authorizationData.AccountId, new[] { campaign }); var adGroupIds = (long[]) await AddAdGroupsAsync(campaignIds[0], new[] { adGroup }); // Print the new assigned campaign and ad group identifiers PrintCampaignIdentifiers(campaignIds); PrintAdGroupIdentifiers(adGroupIds); // Bing Ads API Version 9 supports both Target and Target2 objects. You should use Target2. // This example compares Target and Target2, and demonstrates the impact of updating the // DayTimeTarget, IntentOption, and RadiusTarget2 nested in a Target2 object. var campaignTarget = new Target { Name = "My Campaign Target", Day = new DayTarget { Bids = new[] { new DayTargetBid { BidAdjustment = 10, Day = Day.Friday } } }, Hour = new HourTarget { Bids = new[] { new HourTargetBid { BidAdjustment = 10, Hour = HourRange.ElevenAMToTwoPM } } }, Location = new LocationTarget { HasPhysicalIntent = true, MetroAreaTarget = new MetroAreaTarget { Bids = new List <MetroAreaTargetBid> { new MetroAreaTargetBid { BidAdjustment = 15, MetroArea = "Seattle-Tacoma, WA, WA US", IsExcluded = false } } }, RadiusTarget = new RadiusTarget { Bids = new[] { new RadiusTargetBid { BidAdjustment = 50, LatitudeDegrees = 47.755367, LongitudeDegrees = -122.091827, Radius = 5 } } } } }; var adGroupTarget = new Target { Name = "My Ad Group Target", Hour = new HourTarget { Bids = new[] { new HourTargetBid { BidAdjustment = 10, Hour = HourRange.SixPMToElevenPM } } } }; // Each customer has a target library that can be used to set up targeting for any campaign // or ad group within the specified customer. // Add a target to the library and associate it with the campaign. var campaignTargetId = (await AddTargetsToLibraryAsync(new[] { campaignTarget }))[0]; OutputStatusMessage(String.Format("Added Target Id: {0}\n", campaignTargetId)); SetTargetToCampaignAsync(campaignIds[0], campaignTargetId); OutputStatusMessage(String.Format("Associated CampaignId {0} with TargetId {1}.\n", campaignIds[0], campaignTargetId)); // Get and print the Target with the legacy GetTargetsByIds operation OutputStatusMessage("Get Campaign Target: \n"); var targets = await GetTargetsByIdsAsync(new[] { campaignTargetId }); PrintTarget(targets[0]); // Get and print the Target2 with the new GetTargetsByIds2 operation OutputStatusMessage("Get Campaign Target2: \n"); var targets2 = await GetTargetsByIds2Async(new[] { campaignTargetId }); PrintTarget2(targets2[0]); // Add a target to the library and associate it with the ad group. var adGroupTargetId = (await AddTargetsToLibraryAsync(new[] { adGroupTarget }))[0]; OutputStatusMessage(String.Format("Added Target Id: {0}\n", adGroupTargetId)); SetTargetToAdGroupAsync(adGroupIds[0], adGroupTargetId); OutputStatusMessage(String.Format("Associated AdGroupId {0} with TargetId {1}.\n", adGroupIds[0], adGroupTargetId)); // Get and print the Target with the legacy GetTargetsByIds operation OutputStatusMessage("Get AdGroup Target: \n"); targets = await GetTargetsByIdsAsync(new[] { adGroupTargetId }); PrintTarget(targets[0]); // Get and print the Target2 with the new GetTargetsByIds2 operation OutputStatusMessage("Get AdGroup Target2: \n"); targets2 = await GetTargetsByIds2Async(new[] { adGroupTargetId }); PrintTarget2(targets2[0]); // Update the ad group's target as a Target2 object with additional target types. // Existing target types such as DayTime, Location, and Radius must be specified // or they will not be included in the updated target. var target2 = new Target2 { Id = adGroupTargetId, Name = "My Target2", Age = new AgeTarget { Bids = new[] { new AgeTargetBid { BidAdjustment = 10, Age = AgeRange.EighteenToTwentyFive } } }, DayTime = new DayTimeTarget { Bids = new[] { new DayTimeTargetBid { BidAdjustment = 10, Day = Day.Friday, FromHour = 1, ToHour = 12, FromMinute = Minute.Zero, ToMinute = Minute.FortyFive } } }, DeviceOS = new DeviceOSTarget { Bids = new[] { new DeviceOSTargetBid { BidAdjustment = 20, DeviceName = "Tablets", } }, }, Gender = new GenderTarget { Bids = new[] { new GenderTargetBid { BidAdjustment = 10, Gender = GenderType.Female } } }, Location = new LocationTarget2 { IntentOption = IntentOption.PeopleSearchingForOrViewingPages, CountryTarget = new CountryTarget { Bids = new[] { new CountryTargetBid { BidAdjustment = 10, CountryAndRegion = "US", IsExcluded = false } } }, MetroAreaTarget = new MetroAreaTarget { Bids = new List <MetroAreaTargetBid> { new MetroAreaTargetBid { BidAdjustment = 15, MetroArea = "Seattle-Tacoma, WA, WA US", IsExcluded = false } } }, PostalCodeTarget = new PostalCodeTarget { Bids = new[] { new PostalCodeTargetBid { // Bid adjustments are not allowed for location exclusions. // If IsExcluded is true, this element will be ignored. BidAdjustment = 10, PostalCode = "98052, WA US", IsExcluded = true } } }, RadiusTarget = new RadiusTarget2 { Bids = new[] { new RadiusTargetBid2 { BidAdjustment = 50, LatitudeDegrees = 47.755367, LongitudeDegrees = -122.091827, Radius = 11, RadiusUnit = DistanceUnit.Kilometers } } } } }; // Update the same identified target as a Target2 object. // Going forward when getting the specified target Id, the Day and Hour elements of the legacy // Target object will be nil, since the target is being updated with a DayTime target. UpdateTargetsInLibrary2Async(new[] { target2 }); OutputStatusMessage("Updated the ad group level target as a Target2 object.\n"); // Get and print the Target with the legacy GetTargetsByIds operation OutputStatusMessage("Get Campaign Target: \n"); targets = await GetTargetsByIdsAsync(new[] { campaignTargetId }); PrintTarget(targets[0]); // Get and print the Target2 with the new GetTargetsByIds2 operation OutputStatusMessage("Get Campaign Target2: \n"); targets2 = await GetTargetsByIds2Async(new[] { campaignTargetId }); PrintTarget2(targets2[0]); // Get and print the Target with the legacy GetTargetsByIds operation OutputStatusMessage("Get AdGroup Target: \n"); targets = await GetTargetsByIdsAsync(new[] { adGroupTargetId }); PrintTarget(targets[0]); // Get and print the Target2 with the new GetTargetsByIds2 operation OutputStatusMessage("Get AdGroup Target2: \n"); targets2 = await GetTargetsByIds2Async(new[] { adGroupTargetId }); PrintTarget2(targets2[0]); // Get all new and existing targets in the customer library, whether or not they are // associated with campaigns or ad groups. var allTargetsInfo = await GetTargetsInfoFromLibraryAsync(); OutputStatusMessage("All target identifiers and names from the customer library: \n"); PrintTargetsInfo(allTargetsInfo); // Delete the campaign, ad group, and targets that were previously added. // DeleteCampaigns would remove the campaign and ad group, as well as the association // between ad groups and campaigns. To explicitly delete the association between an entity // and the target, use DeleteTargetFromCampaign and DeleteTargetFromAdGroup respectively. DeleteTargetFromCampaignAsync(campaignIds[0]); DeleteTargetFromAdGroupAsync(adGroupIds[0]); DeleteCampaignsAsync(authorizationData.AccountId, new[] { campaignIds[0] }); OutputStatusMessage(String.Format("Deleted CampaignId {0}\n", campaignIds[0])); // DeleteCampaigns deletes the association between the campaign and target, but does not // delete the target from the customer library. // Call the DeleteTargetsFromLibrary operation for each target that you want to delete. // You must specify an array with exactly one item. DeleteTargetsFromLibraryAsync(new[] { campaignTargetId }); OutputStatusMessage(String.Format("Deleted TargetId {0}\n", campaignTargetId)); DeleteTargetsFromLibraryAsync(new[] { adGroupTargetId }); OutputStatusMessage(String.Format("Deleted TargetId {0}\n", adGroupTargetId)); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
private Authenticator CreateAuthenticator(PrincipalName cname, Realm realm, EncryptionKey subkey = null, AuthorizationData data = null) { BaseTestSite.Log.Add(LogEntryKind.TestStep, "Create authenticator"); Random r = new Random(); int seqNum = r.Next(); Authenticator plaintextAuthenticator = new Authenticator { authenticator_vno = new Asn1Integer(KerberosConstValue.KERBEROSV5), crealm = realm, cusec = new Microseconds(0), ctime = KerberosUtility.CurrentKerberosTime, seq_number = new KerbUInt32(seqNum), cname = cname, subkey = subkey, authorization_data = data }; AuthCheckSum checksum = new AuthCheckSum { Lgth = KerberosConstValue.AUTHENTICATOR_CHECKSUM_LENGTH }; checksum.Bnd = new byte[checksum.Lgth]; checksum.Flags = (int)(ChecksumFlags.GSS_C_MUTUAL_FLAG | ChecksumFlags.GSS_C_INTEG_FLAG); byte[] checkData = ArrayUtility.ConcatenateArrays(BitConverter.GetBytes(checksum.Lgth), checksum.Bnd, BitConverter.GetBytes(checksum.Flags)); plaintextAuthenticator.cksum = new Checksum(new KerbInt32((int)ChecksumType.ap_authenticator_8003), new Asn1OctetString(checkData)); return(plaintextAuthenticator); }
/// <summary> /// Initializes a new instance of this class with the specified <paramref name="requestId"/>, <see cref="BingAds.AuthorizationData"/> and <paramref name="apiEnvironment"/>. /// </summary> /// <param name="requestId">The identifier of a download request that has previously been submitted.</param> /// <param name="authorizationData"> /// Represents a user who intends to access the corresponding customer and account. /// </param> /// <param name="apiEnvironment">Bing Ads API environment</param> public ReportingDownloadOperation(string requestId, AuthorizationData authorizationData, ApiEnvironment?apiEnvironment) : this(requestId, authorizationData, null, apiEnvironment) { }
public async override Task RunAsync(AuthorizationData authorizationData) { try { CampaignService = new ServiceClient <ICampaignManagementService>(authorizationData); // Specify one or more campaigns. var campaigns = new[] { new Campaign { Name = "Women's Shoes " + DateTime.UtcNow, Description = "Red shoes line.", DailyBudget = 50, BudgetType = BudgetLimitType.DailyBudgetStandard, TimeZone = "PacificTimeUSCanadaTijuana", }, }; var adGroups = new[] { new AdGroup { Name = "Women's Red Shoe Sale", AdDistribution = AdDistribution.Search, StartDate = null, EndDate = new Microsoft.BingAds.V11.CampaignManagement.Date { Month = 12, Day = 31, Year = DateTime.UtcNow.Year + 1 }, SearchBid = new Bid { Amount = 0.09 }, Language = "English", } }; var keywords = new[] { new Keyword { Bid = new Bid { Amount = 0.47 }, Param2 = "10% Off", MatchType = MatchType.Phrase, Text = "Brand-A Shoes", }, }; var ads = new Ad[] { new ExpandedTextAd { TitlePart1 = "Contoso", TitlePart2 = "Fast & Easy Setup", Text = "Find New Customers & Increase Sales! Start Advertising on Contoso Today.", Path1 = "seattle", Path2 = "shoe sale", FinalUrls = new[] { "http://www.contoso.com/womenshoesale" }, }, }; var random = new Random(); var labels = new List <Label>(); for (var labelIndex = 0; labelIndex < 50; labelIndex++) { var color = string.Format("#{0:X6}", random.Next(0x100000)); labels.Add(new Label { ColorCode = color, Description = "Label Description", Name = "Label Name " + color + " " + DateTime.UtcNow }); } AddLabelsResponse addLabelsResponse = await AddLabelsAsync(labels); long?[] nullableLabelIds = addLabelsResponse.LabelIds.ToArray(); BatchError[] labelErrors = addLabelsResponse.PartialErrors.ToArray(); OutputStatusMessage("New Label Ids:"); OutputIds(nullableLabelIds); OutputPartialErrors(labelErrors); AddCampaignsResponse addCampaignsResponse = await AddCampaignsAsync(authorizationData.AccountId, campaigns); long?[] nullableCampaignIds = addCampaignsResponse.CampaignIds.ToArray(); BatchError[] campaignErrors = addCampaignsResponse.PartialErrors.ToArray(); OutputStatusMessage("New Campaign Ids:"); OutputIds(nullableCampaignIds); OutputPartialErrors(campaignErrors); AddAdGroupsResponse addAdGroupsResponse = await AddAdGroupsAsync((long)nullableCampaignIds[0], adGroups); long?[] nullableAdGroupIds = addAdGroupsResponse.AdGroupIds.ToArray(); BatchError[] adGroupErrors = addAdGroupsResponse.PartialErrors.ToArray(); OutputStatusMessage("New Ad Group Ids:"); OutputIds(nullableAdGroupIds); OutputPartialErrors(adGroupErrors); AddKeywordsResponse addKeywordsResponse = await AddKeywordsAsync((long)nullableAdGroupIds[0], keywords); long?[] nullableKeywordIds = addKeywordsResponse.KeywordIds.ToArray(); BatchError[] keywordErrors = addKeywordsResponse.PartialErrors.ToArray(); OutputStatusMessage("New Keyword Ids:"); OutputIds(nullableKeywordIds); OutputPartialErrors(keywordErrors); AddAdsResponse addAdsResponse = await AddAdsAsync((long)nullableAdGroupIds[0], ads); long?[] nullableAdIds = addAdsResponse.AdIds.ToArray(); BatchError[] adErrors = addAdsResponse.PartialErrors.ToArray(); OutputStatusMessage("New Ad Ids:"); OutputIds(nullableAdIds); OutputPartialErrors(adErrors); var labelIds = GetNonNullableIds(nullableLabelIds); OutputStatusMessage("\nGet all the labels that we added above..."); var getLabelsByIdsResponse = await GetLabelsByIdsAsync( labelIds, new Paging { Index = 0, Size = MaxGetLabelsByIds } ); OutputLabels(getLabelsByIdsResponse.Labels); OutputStatusMessage("\nUpdate the label color and then retrieve the labels again to confirm the changes...."); var updateLabels = new List <Label>(); foreach (var label in getLabelsByIdsResponse.Labels) { label.ColorCode = string.Format("#{0:X6}", random.Next(0x100000)); updateLabels.Add(label); } var updateLabelsResponse = await UpdateLabelsAsync(updateLabels); getLabelsByIdsResponse = await GetLabelsByIdsAsync( labelIds, new Paging { Index = 0, Size = MaxGetLabelsByIds } ); OutputLabels(getLabelsByIdsResponse.Labels); var campaignLabelAssociations = CreateExampleLabelAssociationsByEntityId((long)nullableCampaignIds[0], labelIds); OutputStatusMessage("\nAssociating all of the labels with a campaign..."); OutputLabelAssociations(campaignLabelAssociations); var setLabelAssociationsResponse = await SetLabelAssociationsAsync(campaignLabelAssociations, EntityType.Campaign); var adGroupLabelAssociations = CreateExampleLabelAssociationsByEntityId((long)nullableAdGroupIds[0], labelIds); OutputStatusMessage("\nAssociating all of the labels with an ad group..."); OutputLabelAssociations(adGroupLabelAssociations); setLabelAssociationsResponse = await SetLabelAssociationsAsync(adGroupLabelAssociations, EntityType.AdGroup); var keywordLabelAssociations = CreateExampleLabelAssociationsByEntityId((long)nullableKeywordIds[0], labelIds); OutputStatusMessage("\nAssociating all of the labels with a keyword..."); OutputLabelAssociations(keywordLabelAssociations); setLabelAssociationsResponse = await SetLabelAssociationsAsync(keywordLabelAssociations, EntityType.Keyword); var adLabelAssociations = CreateExampleLabelAssociationsByEntityId((long)nullableAdIds[0], labelIds); OutputStatusMessage("\nAssociating all of the labels with an ad..."); OutputLabelAssociations(adLabelAssociations); setLabelAssociationsResponse = await SetLabelAssociationsAsync(adLabelAssociations, EntityType.Ad); OutputStatusMessage("\nUse paging to get all campaign label associations..."); var getLabelAssociationsByLabelIds = await GetLabelAssociationsByLabelIdsHelperAsync(labelIds, EntityType.Campaign); OutputLabelAssociations(getLabelAssociationsByLabelIds); OutputStatusMessage("\nUse paging to get all ad group label associations..."); getLabelAssociationsByLabelIds = await GetLabelAssociationsByLabelIdsHelperAsync(labelIds, EntityType.AdGroup); OutputLabelAssociations(getLabelAssociationsByLabelIds); OutputStatusMessage("\nUse paging to get all keyword label associations..."); getLabelAssociationsByLabelIds = await GetLabelAssociationsByLabelIdsHelperAsync(labelIds, EntityType.Keyword); OutputLabelAssociations(getLabelAssociationsByLabelIds); OutputStatusMessage("\nUse paging to get all ad label associations..."); getLabelAssociationsByLabelIds = await GetLabelAssociationsByLabelIdsHelperAsync(labelIds, EntityType.Ad); OutputLabelAssociations(getLabelAssociationsByLabelIds); OutputStatusMessage("\nGet all label associations for all specified campaigns..."); var getLabelAssociationsByEntityIds = await GetLabelAssociationsByEntityIdsHelperAsync( GetNonNullableIds(nullableCampaignIds), EntityType.Campaign ); OutputLabelAssociations(getLabelAssociationsByEntityIds); OutputStatusMessage("\nGet all label associations for all specified ad groups..."); getLabelAssociationsByEntityIds = await GetLabelAssociationsByEntityIdsHelperAsync( GetNonNullableIds(nullableAdGroupIds), EntityType.AdGroup ); OutputLabelAssociations(getLabelAssociationsByEntityIds); OutputStatusMessage("\nGet all label associations for all specified keywords..."); getLabelAssociationsByEntityIds = await GetLabelAssociationsByEntityIdsHelperAsync( GetNonNullableIds(nullableKeywordIds), EntityType.Keyword ); OutputLabelAssociations(getLabelAssociationsByEntityIds); OutputStatusMessage("\nGet all label associations for all specified ads..."); getLabelAssociationsByEntityIds = await GetLabelAssociationsByEntityIdsHelperAsync( GetNonNullableIds(nullableAdIds), EntityType.Ad ); OutputLabelAssociations(getLabelAssociationsByEntityIds); OutputStatusMessage("\nDelete all label associations that we set above...."); // This is not necessary if you are deleting the corresponding campaign(s), as the // contained ad groups, keywords, ads, and associations would also be deleted. var deleteLabelAssociationsResponse = await DeleteLabelAssociationsAsync(campaignLabelAssociations, EntityType.Campaign); deleteLabelAssociationsResponse = await DeleteLabelAssociationsAsync(adGroupLabelAssociations, EntityType.AdGroup); deleteLabelAssociationsResponse = await DeleteLabelAssociationsAsync(keywordLabelAssociations, EntityType.Keyword); deleteLabelAssociationsResponse = await DeleteLabelAssociationsAsync(adLabelAssociations, EntityType.Ad); OutputStatusMessage("\nDelete all labels that we added above...."); // Deleting the campaign(s) removes the corresponding label associations but not remove the labels. var deleteLabelsResponse = await DeleteLabelsAsync(labelIds); OutputStatusMessage("\nDelete the campaign, ad group, keyword, and ad that were added above...."); await DeleteCampaignsAsync(authorizationData.AccountId, new[] { (long)nullableCampaignIds[0] }); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V11.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
public void AdFxFastUsedInAuthenticator() { base.Logging(); client = new KerberosTestClient( this.testConfig.LocalRealm.RealmName, this.testConfig.LocalRealm.ClientComputer.NetBiosName, this.testConfig.LocalRealm.ClientComputer.Password, KerberosAccountType.Device, testConfig.LocalRealm.KDC[0].IPAddress, testConfig.LocalRealm.KDC[0].Port, testConfig.TransportType, testConfig.SupportedOid, testConfig.LocalRealm.ClientComputer.AccountSalt); // Kerberos Proxy Service is used if (this.testConfig.UseProxy) { BaseTestSite.Log.Add(LogEntryKind.Comment, "Initialize KKDCP Client ."); KKDCPClient proxyClient = new KKDCPClient(proxyClientConfig); proxyClient.TargetDomain = this.testConfig.LocalRealm.RealmName; client.UseProxy = true; client.ProxyClient = proxyClient; } // AS_REQ and KRB-ERROR using device principal KdcOptions options = KdcOptions.FORWARDABLE | KdcOptions.CANONICALIZE | KdcOptions.RENEWABLE; client.SendAsRequest(options, null); METHOD_DATA methodData; KerberosKrbError krbError1 = client.ExpectPreauthRequiredError(out methodData); // AS_REQ and AS_REP using device principal string timeStamp = KerberosUtility.CurrentKerberosTime.Value; PaEncTimeStamp paEncTimeStamp = new PaEncTimeStamp( timeStamp, 0, client.Context.SelectedEType, this.client.Context.CName.Password, this.client.Context.CName.Salt); Asn1SequenceOf<PA_DATA> seqOfPaData = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paEncTimeStamp.Data }); client.SendAsRequest(options, seqOfPaData); KerberosAsResponse asResponse = client.ExpectAsResponse(); BaseTestSite.Assert.IsNotNull(asResponse.Response.ticket, "AS response should contain a TGT."); BaseTestSite.Log.Add( LogEntryKind.Comment, string.Format("The type of AS-REP encrypted part is {0}.", asResponse.EncPart.GetType().Name)); // Switch to user principal client = new KerberosTestClient( this.testConfig.LocalRealm.RealmName, this.testConfig.LocalRealm.User[1].Username, this.testConfig.LocalRealm.User[1].Password, KerberosAccountType.User, client.Context.Ticket, client.Context.SessionKey, testConfig.LocalRealm.KDC[0].IPAddress, testConfig.LocalRealm.KDC[0].Port, testConfig.TransportType, testConfig.SupportedOid); // Kerberos Proxy Service is used if (this.testConfig.UseProxy) { BaseTestSite.Log.Add(LogEntryKind.Comment, "Initialize KKDCP Client ."); KKDCPClient proxyClient = new KKDCPClient(proxyClientConfig); proxyClient.TargetDomain = this.testConfig.LocalRealm.RealmName; client.UseProxy = true; client.ProxyClient = proxyClient; } // FAST armored AS_REQ and KRB-ERROR using user principal //Create a "random" key. var subkey = KerberosUtility.MakeKey(client.Context.SelectedEType, "Password02!", "this is a salt"); var fastOptions = new Protocols.TestTools.StackSdk.Security.KerberosV5.Preauth.FastOptions(KerberosUtility.ConvertInt2Flags((int)0)); var apOptions = ApOptions.None; Asn1SequenceOf<PA_DATA> seqOfPaData2 = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { new PA_DATA(new KerbInt32((long)PaDataType.PA_FX_FAST), null) }); client.SendAsRequestWithFast(options, seqOfPaData2, null, subkey, fastOptions, apOptions); KerberosKrbError krbError2 = client.ExpectKrbError(); BaseTestSite.Assert.AreEqual(krbError2.ErrorCode, KRB_ERROR_CODE.KDC_ERR_PREAUTH_REQUIRED, "Pre-authentication required."); // FAST armored AS_REQ and AS_REP using user principal var userKey = KerberosUtility.MakeKey( client.Context.SelectedEType, client.Context.CName.Password, client.Context.CName.Salt); PaEncryptedChallenge paEncTimeStamp3 = new PaEncryptedChallenge( client.Context.SelectedEType, KerberosUtility.CurrentKerberosTime.Value, 0, client.Context.FastArmorkey, userKey); Asn1SequenceOf<PA_DATA> seqOfPaData3 = new Asn1SequenceOf<PA_DATA>(new PA_DATA[] { paEncTimeStamp3.Data }); client.SendAsRequestWithFast(options, seqOfPaData3, null, subkey, fastOptions, apOptions); KerberosAsResponse userKrbAsRep = client.ExpectAsResponse(); BaseTestSite.Assert.IsNotNull(userKrbAsRep.Response.ticket, "AS response should contain a TGT."); BaseTestSite.Log.Add( LogEntryKind.Comment, string.Format("The type of AS-REP encrypted part is {0}.", userKrbAsRep.EncPart.GetType().Name)); // FAST armored TGS_REQ and TGS_REP using user principal subkey = KerberosUtility.MakeKey(client.Context.SelectedEType, "Password03!", "this is a salt"); BaseTestSite.Log.Add(LogEntryKind.Comment, "Create and send unarmored TGS request with AD-fx-fast-used."); AdFxFastUsed adFxFastUsed = new AdFxFastUsed(); AuthorizationData authData = new AuthorizationData(new AuthorizationDataElement[] { adFxFastUsed.AuthDataElement }); client.SendTgsRequest(testConfig.LocalRealm.ClientComputer.DefaultServiceName, options, null, null, authData); BaseTestSite.Log.Add(LogEntryKind.Comment, "Receive TGS Error, KDC MUST reject the request."); KerberosKrbError krbError = client.ExpectKrbError(); }
public async override Task RunAsync(AuthorizationData authorizationData) { try { ApiEnvironment environment = ((OAuthDesktopMobileAuthCodeGrant)authorizationData.Authentication).Environment; CampaignManagementExampleHelper CampaignManagementExampleHelper = new CampaignManagementExampleHelper(this.OutputStatusMessage); CampaignManagementExampleHelper.CampaignManagementService = new ServiceClient <ICampaignManagementService>(authorizationData, environment); // Get a list of all Bing Merchant Center stores associated with your CustomerId IList <BMCStore> stores = (await CampaignManagementExampleHelper.GetBMCStoresByCustomerIdAsync())?.BMCStores; if (stores == null) { OutputStatusMessage( string.Format("You do not have any BMC stores registered for CustomerId {0}.\n", authorizationData.CustomerId) ); return; } #region ManageCampaign /* Add a new Bing Shopping campaign that will be associated with a ProductScope criterion. * - Set the CampaignType element of the Campaign to Shopping. * - Create a ShoppingSetting instance and set its Priority (0, 1, or 2), SalesCountryCode, and StoreId elements. * Add this shopping setting to the Settings list of the Campaign. */ var campaigns = new[] { new Campaign { CampaignType = CampaignType.Shopping, Settings = new[] { new ShoppingSetting() { Priority = 0, SalesCountryCode = "US", StoreId = (int)stores[0].Id } }, Name = "Bing Shopping Campaign " + DateTime.UtcNow, Description = "Bing Shopping Campaign Example.", // You must choose to set either the shared budget ID or daily amount. // You can set one or the other, but you may not set both. BudgetId = null, DailyBudget = 50, BudgetType = BudgetLimitType.DailyBudgetStandard, TimeZone = "PacificTimeUSCanadaTijuana", // Used with CustomParameters defined in lower level entities such as ad group criterion. TrackingUrlTemplate = "http://tracker.example.com/?season={_season}&promocode={_promocode}&u={lpurl}" } }; AddCampaignsResponse addCampaignsResponse = await CampaignManagementExampleHelper.AddCampaignsAsync(authorizationData.AccountId, campaigns); long?[] campaignIds = addCampaignsResponse.CampaignIds.ToArray(); BatchError[] campaignErrors = addCampaignsResponse.PartialErrors.ToArray(); CampaignManagementExampleHelper.OutputArrayOfLong(campaignIds); CampaignManagementExampleHelper.OutputArrayOfBatchError(campaignErrors); long campaignId = (long)campaignIds[0]; /* Optionally, you can create a ProductScope criterion that will be associated with your Bing Shopping campaign. * Use the product scope criterion to include a subset of your product catalog, for example a specific brand, * category, or product type. A campaign can only be associated with one ProductScope, which contains a list * of up to 7 ProductCondition. You'll also be able to specify more specific product conditions for each ad group. */ var campaignCriterions = new BiddableCampaignCriterion[] { new BiddableCampaignCriterion() { CampaignId = campaignId, CriterionBid = null, // Not applicable for product scope Criterion = new ProductScope() { Conditions = new ProductCondition[] { new ProductCondition { Operand = "Condition", Attribute = "New" }, new ProductCondition { Operand = "CustomLabel0", Attribute = "MerchantDefinedCustomLabel" }, } }, } }; var addCampaignCriterionsResponse = await(CampaignManagementExampleHelper.AddCampaignCriterionsAsync( campaignCriterions, CampaignCriterionType.ProductScope) ); #endregion ManageCampaign #region ManageAdGroup // Create the ad group that will have the product partitions. var adGroups = new[] { new AdGroup { Name = "Product Categories", StartDate = null, EndDate = new Microsoft.BingAds.V12.CampaignManagement.Date { Month = 12, Day = 31, Year = DateTime.UtcNow.Year + 1 }, Language = "English", CpcBid = new Bid { Amount = 0.090 } } }; AddAdGroupsResponse addAdGroupsResponse = await CampaignManagementExampleHelper.AddAdGroupsAsync((long)campaignId, adGroups, null); long?[] adGroupIds = addAdGroupsResponse.AdGroupIds.ToArray(); BatchError[] adGroupErrors = addAdGroupsResponse.PartialErrors.ToArray(); CampaignManagementExampleHelper.OutputArrayOfLong(adGroupIds); CampaignManagementExampleHelper.OutputArrayOfBatchError(adGroupErrors); long adGroupId = (long)adGroupIds[0]; #region BidAllProducts var helper = new PartitionActionHelper(adGroupId); var root = helper.AddUnit( null, new ProductCondition { Operand = "All", Attribute = null }, 0.35, false ); OutputStatusMessage("Applying only the root as a Unit with a bid . . . \n"); var applyProductPartitionActionsResponse = await CampaignManagementExampleHelper.ApplyProductPartitionActionsAsync(helper.PartitionActions); var adGroupCriterions = await CampaignManagementExampleHelper.GetAdGroupCriterionsByIdsAsync( null, adGroupId, AdGroupCriterionType.ProductPartition ); OutputStatusMessage("The ad group's product partition only has a tree root node: \n"); OutputProductPartitions(adGroupCriterions?.AdGroupCriterions); /* * Let's update the bid of the root Unit we just added. */ BiddableAdGroupCriterion updatedRoot = new BiddableAdGroupCriterion { Id = applyProductPartitionActionsResponse.AdGroupCriterionIds[0], CriterionBid = new FixedBid { Amount = 0.45 } }; helper = new PartitionActionHelper(adGroupId); helper.UpdatePartition(updatedRoot); OutputStatusMessage("Updating the bid for the tree root node . . . \n"); await CampaignManagementExampleHelper.ApplyProductPartitionActionsAsync(helper.PartitionActions); adGroupCriterions = await CampaignManagementExampleHelper.GetAdGroupCriterionsByIdsAsync( null, adGroupId, AdGroupCriterionType.ProductPartition ); OutputStatusMessage("Updated the bid for the tree root node: \n"); OutputProductPartitions(adGroupCriterions?.AdGroupCriterions); #endregion BidAllProducts #region InitializeTree /* * Now we will overwrite any existing tree root, and build a product partition group tree structure in multiple steps. * You could build the entire tree in a single call since there are less than 5,000 nodes; however, * we will build it in steps to demonstrate how to use the results from ApplyProductPartitionActions to update the tree. * * For a list of validation rules, see the Product Ads technical guide: * https://docs.microsoft.com/en-us/bingads/guides/product-ads */ helper = new PartitionActionHelper(adGroupId); /* * Check whether a root node exists already. */ adGroupCriterions = await CampaignManagementExampleHelper.GetAdGroupCriterionsByIdsAsync( null, adGroupId, AdGroupCriterionType.ProductPartition ); var existingRoot = GetRootNode(adGroupCriterions?.AdGroupCriterions); if (existingRoot != null) { helper.DeletePartition(existingRoot); } root = helper.AddSubdivision( null, new ProductCondition { Operand = "All", Attribute = null } ); /* * The direct children of any node must have the same Operand. * For this example we will use CategoryL1 nodes as children of the root. * For a list of valid CategoryL1 through CategoryL5 values, see the Bing Category Taxonomy: * http://go.microsoft.com/fwlink?LinkId=507666 */ var animalsSubdivision = helper.AddSubdivision( root, new ProductCondition { Operand = "CategoryL1", Attribute = "Animals & Pet Supplies" } ); /* * If you use a CategoryL2 node, it must be a descendant (child or later) of a CategoryL1 node. * In other words you cannot have a CategoryL2 node as parent of a CategoryL1 node. * For this example we will a CategoryL2 node as child of the CategoryL1 Animals & Pet Supplies node. */ var petSuppliesSubdivision = helper.AddSubdivision( animalsSubdivision, new ProductCondition { Operand = "CategoryL2", Attribute = "Pet Supplies" } ); var brandA = helper.AddUnit( petSuppliesSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand A" }, 0.35, false ); /* * If you won't bid on Brand B, set the helper method's bidAmount to '0' and isNegative to true. * The helper method will create a NegativeAdGroupCriterion and apply the condition. */ var brandB = helper.AddUnit( petSuppliesSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand B" }, 0, true ); var otherBrands = helper.AddUnit( petSuppliesSubdivision, new ProductCondition { Operand = "Brand", Attribute = null }, 0.35, false ); var otherPetSupplies = helper.AddUnit( animalsSubdivision, new ProductCondition { Operand = "CategoryL2", Attribute = null }, 0.35, false ); var electronics = helper.AddUnit( root, new ProductCondition { Operand = "CategoryL1", Attribute = "Electronics" }, 0.35, false ); var otherCategoryL1 = helper.AddUnit( root, new ProductCondition { Operand = "CategoryL1", Attribute = null }, 0.35, false ); OutputStatusMessage("Applying product partitions to the ad group . . . \n"); applyProductPartitionActionsResponse = await CampaignManagementExampleHelper.ApplyProductPartitionActionsAsync(helper.PartitionActions); // To retrieve product partitions after they have been applied, call GetAdGroupCriterionsByIds. // The product partition with ParentCriterionId set to null is the root node. adGroupCriterions = await CampaignManagementExampleHelper.GetAdGroupCriterionsByIdsAsync( null, adGroupId, AdGroupCriterionType.ProductPartition ); /* * The product partition group tree now has 9 nodes. * * All other (Root Node) | +-- Animals & Pet Supplies (CategoryL1) | | | +-- Pet Supplies (CategoryL2) | | | | | +-- Brand A | | | | | +-- Brand B | | | | | +-- All other (Brand) | | | +-- All other (CategoryL2) | +-- Electronics (CategoryL1) | +-- All other (CategoryL1) | */ OutputStatusMessage("The product partition group tree now has 9 nodes: \n"); OutputProductPartitions(adGroupCriterions?.AdGroupCriterions); #endregion InitializeTree #region UpdateTree /* * Let's replace the Electronics (CategoryL1) node created above with an Electronics (CategoryL1) node that * has children i.e. Brand C (Brand), Brand D (Brand), and All other (Brand) as follows: * * Electronics (CategoryL1) | +-- Brand C (Brand) | +-- Brand D (Brand) | +-- All other (Brand) | */ helper = new PartitionActionHelper(adGroupId); /* * To replace a node we must know its Id and its ParentCriterionId. In this case the parent of the node * we are replacing is All other (Root Node), and was created at Index 1 of the previous ApplyProductPartitionActions call. * The node that we are replacing is Electronics (CategoryL1), and was created at Index 8. */ var rootId = applyProductPartitionActionsResponse.AdGroupCriterionIds[1]; electronics.Id = applyProductPartitionActionsResponse.AdGroupCriterionIds[8]; helper.DeletePartition(electronics); var parent = new BiddableAdGroupCriterion() { Id = rootId }; var electronicsSubdivision = helper.AddSubdivision( parent, new ProductCondition { Operand = "CategoryL1", Attribute = "Electronics" } ); var brandC = helper.AddUnit( electronicsSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand C" }, 0.35, false ); var brandD = helper.AddUnit( electronicsSubdivision, new ProductCondition { Operand = "Brand", Attribute = "Brand D" }, 0.35, false ); var otherElectronicsBrands = helper.AddUnit( electronicsSubdivision, new ProductCondition { Operand = "Brand", Attribute = null }, 0.35, false ); OutputStatusMessage( "Updating the product partition group to refine Electronics (CategoryL1) with 3 child nodes . . . \n" ); applyProductPartitionActionsResponse = await CampaignManagementExampleHelper.ApplyProductPartitionActionsAsync(helper.PartitionActions); adGroupCriterions = await CampaignManagementExampleHelper.GetAdGroupCriterionsByIdsAsync( null, adGroupId, AdGroupCriterionType.ProductPartition ); /* * The product partition group tree now has 12 nodes, including the children of Electronics (CategoryL1): * * All other (Root Node) | +-- Animals & Pet Supplies (CategoryL1) | | | +-- Pet Supplies (CategoryL2) | | | | | +-- Brand A | | | | | +-- Brand B | | | | | +-- All other (Brand) | | | +-- All other (CategoryL2) | +-- Electronics (CategoryL1) | | | +-- Brand C (Brand) | | | +-- Brand D (Brand) | | | +-- All other (Brand) | +-- All other (CategoryL1) | */ OutputStatusMessage( "The product partition group tree now has 12 nodes, including the children of Electronics (CategoryL1): \n" ); OutputProductPartitions(adGroupCriterions?.AdGroupCriterions); #endregion UpdateTree #endregion ManageAdGroup #region ManageAds /* * Create a product ad. You must add at least one product ad to the ad group. * The product ad identifier can be used for reporting analytics. * Use Merchant Promotions if you want tags to appear at the bottom of your product ad * as "special offer" links, helping to increase customer engagement. For details * on Merchant Promotions see https://help.bingads.microsoft.com/#apex/3/en/56805/0. */ var ads = new Ad[] { new ProductAd { } }; AddAdsResponse addAdsResponse = await CampaignManagementExampleHelper.AddAdsAsync((long)adGroupIds[0], ads); long?[] adIds = addAdsResponse.AdIds.ToArray(); BatchError[] adErrors = addAdsResponse.PartialErrors.ToArray(); CampaignManagementExampleHelper.OutputArrayOfLong(adIds); CampaignManagementExampleHelper.OutputArrayOfBatchError(adErrors); #endregion ManageAds #region CleanUp /* Delete the campaign, ad group, criterion, and ad that were previously added. * You should remove this region if you want to view the added entities in the * Bing Ads web application or another tool. */ await CampaignManagementExampleHelper.DeleteCampaignsAsync(authorizationData.AccountId, new[] { campaignId }); OutputStatusMessage(string.Format("Deleted Campaign Id {0}\n", campaignId)); #endregion CleanUp } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
public async override Task RunAsync(AuthorizationData authorizationData) { try { CampaignManagementExampleHelper = new CampaignManagementExampleHelper(this.OutputStatusMessage); BulkServiceManager = new BulkServiceManager(authorizationData); var progress = new Progress <BulkOperationProgressInfo>(x => OutputStatusMessage(string.Format("{0} % Complete", x.PercentComplete.ToString(CultureInfo.InvariantCulture)))); var downloadParameters = new DownloadParameters { DownloadEntities = new[] { DownloadEntity.AdGroupProductPartitions }, ResultFileDirectory = FileDirectory, ResultFileName = DownloadFileName, OverwriteResultFile = true, LastSyncTimeInUTC = null }; // Download all product partitions across all ad groups in the account. var bulkFilePath = await BulkServiceManager.DownloadFileAsync(downloadParameters); OutputStatusMessage("Downloaded all product partitions across all ad groups in the account.\n"); Reader = new BulkFileReader(bulkFilePath, ResultFileType.FullDownload, FileType); var bulkAdGroupProductPartitions = Reader.ReadEntities().ToList().OfType <BulkAdGroupProductPartition>().ToList(); OutputBulkAdGroupProductPartitions(bulkAdGroupProductPartitions); var uploadEntities = new List <BulkEntity>(); // Within the downloaded records, find all product partition leaf nodes that have bids. foreach (var bulkAdGroupProductPartition in bulkAdGroupProductPartitions) { var biddableAdGroupCriterion = (bulkAdGroupProductPartition).AdGroupCriterion as BiddableAdGroupCriterion; if (biddableAdGroupCriterion != null && (((ProductPartition)biddableAdGroupCriterion.Criterion).PartitionType == ProductPartitionType.Unit)) { // We will increase all bids by some predetermined amount or percentage as an example. // For best performance, only upload the properties that you want to update. uploadEntities.Add(new BulkAdGroupProductPartition { AdGroupCriterion = new BiddableAdGroupCriterion { AdGroupId = bulkAdGroupProductPartition.AdGroupCriterion.AdGroupId, CriterionBid = new FixedBid { Amount = ((FixedBid)biddableAdGroupCriterion.CriterionBid).Amount + 0.01 }, Id = bulkAdGroupProductPartition.AdGroupCriterion.Id, } }); } } Reader.Dispose(); if (uploadEntities.Count > 0) { OutputStatusMessage("Changed local bid of all product partitions. Starting upload.\n"); Reader = await WriteEntitiesAndUploadFileAsync(uploadEntities); bulkAdGroupProductPartitions = Reader.ReadEntities().ToList().OfType <BulkAdGroupProductPartition>().ToList(); OutputBulkAdGroupProductPartitions(bulkAdGroupProductPartitions); Reader.Dispose(); } else { OutputStatusMessage("No product partitions in account. \n"); } OutputStatusMessage("Program execution completed\n"); } // Catch Microsoft Account authorization exceptions. catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Bulk service exceptions catch (FaultException <Microsoft.BingAds.V12.Bulk.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.Bulk.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V12.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationInProgressException ex) { OutputStatusMessage("The result file for the bulk operation is not yet available for download."); OutputStatusMessage(ex.Message); } catch (BulkOperationCouldNotBeCompletedException <DownloadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (BulkOperationCouldNotBeCompletedException <UploadStatus> ex) { OutputStatusMessage(string.Join("; ", ex.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } finally { if (Reader != null) { Reader.Dispose(); } if (Writer != null) { Writer.Dispose(); } } }
private void DAC_Smb2_AccessFile(string RealmName, User user, Computer kdc, TransportType transportType, FileServer fileserver, string filePath, string fileName, bool expectAccessDeny) { base.Logging(); client = new KerberosTestClient(RealmName, user.Username, user.Password, KerberosAccountType.User, kdc.IPAddress, kdc.Port, transportType, testConfig.SupportedOid); //Create and send AS request KdcOptions options = KdcOptions.FORWARDABLE | KdcOptions.CANONICALIZE | KdcOptions.RENEWABLE; client.SendAsRequest(options, null); //Recieve preauthentication required error METHOD_DATA methodData; KerberosKrbError krbError = client.ExpectPreauthRequiredError(out methodData); //Create sequence of PA data string timeStamp = KerberosUtility.CurrentKerberosTime.Value; PaEncTimeStamp paEncTimeStamp = new PaEncTimeStamp(timeStamp, 0, client.Context.SelectedEType, this.client.Context.CName.Password, this.client.Context.CName.Salt); PaPacRequest paPacRequest = new PaPacRequest(true); Asn1SequenceOf <PA_DATA> seqOfPaData = new Asn1SequenceOf <PA_DATA>(new PA_DATA[] { paEncTimeStamp.Data, paPacRequest.Data }); //Create and send AS request client.SendAsRequest(options, seqOfPaData); KerberosAsResponse asResponse = client.ExpectAsResponse(); BaseTestSite.Assert.IsNotNull(asResponse.Response.ticket, "AS response should contain a TGT."); //Create and send TGS request client.SendTgsRequest(fileserver.Smb2ServiceName, options); KerberosTgsResponse tgsResponse = client.ExpectTgsResponse(); BaseTestSite.Assert.AreEqual(fileserver.Smb2ServiceName, KerberosUtility.PrincipalName2String(tgsResponse.Response.ticket.sname), "Service principal name in service ticket should match expected."); EncryptionKey key = testConfig.QueryKey(fileserver.Smb2ServiceName, client.Context.Realm.ToString(), client.Context.SelectedEType); tgsResponse.DecryptTicket(key); BaseTestSite.Assert.AreEqual(RealmName.ToLower(), tgsResponse.TicketEncPart.crealm.Value.ToLower(), "Realm name in service ticket encrypted part should match expected."); BaseTestSite.Assert.AreEqual(user.Username.ToLower(), KerberosUtility.PrincipalName2String(tgsResponse.TicketEncPart.cname).ToLower(), "User name in service ticket encrypted part should match expected."); //Assert authorization data if (this.testConfig.IsKileImplemented) { BaseTestSite.Assert.IsNotNull(tgsResponse.TicketEncPart.authorization_data, "The ticket contains Authorization data."); AdWin2KPac adWin2kPac = FindOneInAuthData <AdWin2KPac>(tgsResponse.TicketEncPart.authorization_data.Elements); BaseTestSite.Assert.IsNotNull(adWin2kPac, "The Authorization data contains AdWin2KPac."); } AuthorizationData data = null; EncryptionKey subkey = KerberosUtility.GenerateKey(client.Context.SessionKey); byte[] token = client.CreateGssApiToken(ApOptions.MutualRequired, data, subkey, ChecksumFlags.GSS_C_MUTUAL_FLAG | ChecksumFlags.GSS_C_INTEG_FLAG); BaseTestSite.Log.Add(LogEntryKind.Comment, "Logon to fileserver and Access File."); AccessFile(filePath, fileName, fileserver, token, tgsResponse.EncPart.key, expectAccessDeny); }
/// <summary> /// Initializes a new instance of this class with the specified <paramref name="requestId"/>, <see cref="BingAds.AuthorizationData"/> and <paramref name="apiEnvironment"/>. /// </summary> /// <param name="requestId">The identifier of a download request that has previously been submitted.</param> /// <param name="authorizationData"> /// Represents a user who intends to access the corresponding customer and account. /// </param> /// <param name="apiEnvironment">Bing Ads API environment</param> public ReportingDownloadOperation(string requestId, AuthorizationData authorizationData, ApiEnvironment? apiEnvironment) : this(requestId, authorizationData, null, apiEnvironment) { }
private void CBAC_Smb2_AccessFile(string RealmName, User user, Computer kdc, TransportType transportType, FileServer fileserver, string filePath, string fileName, bool expectAccessDeny) { base.Logging(); client = new KerberosTestClient(RealmName, user.Username, user.Password, KerberosAccountType.User, kdc.IPAddress, kdc.Port, transportType, testConfig.SupportedOid); KdcOptions options = KdcOptions.FORWARDABLE | KdcOptions.CANONICALIZE | KdcOptions.RENEWABLE; client.SendAsRequest(options, null); METHOD_DATA methodData; KerberosKrbError krbError = client.ExpectPreauthRequiredError(out methodData); BaseTestSite.Log.Add(LogEntryKind.Comment, "Create and send AS request with PaEncTimeStamp, PaPacRequest and paPacOptions."); string timeStamp = KerberosUtility.CurrentKerberosTime.Value; PaEncTimeStamp paEncTimeStamp = new PaEncTimeStamp(timeStamp, 0, client.Context.SelectedEType, client.Context.CName.Password, this.client.Context.CName.Salt); PaPacRequest paPacRequest = new PaPacRequest(true); PaPacOptions paPacOptions = new PaPacOptions(PacOptions.Claims | PacOptions.ForwardToFullDc); Asn1SequenceOf <PA_DATA> seqOfPaData = new Asn1SequenceOf <PA_DATA>(new PA_DATA[] { paEncTimeStamp.Data, paPacRequest.Data, paPacOptions.Data }); client.SendAsRequest(options, seqOfPaData); KerberosAsResponse asResponse = client.ExpectAsResponse(); //Verify encrypted padata PaSupportedEncTypes paSupportedEncTypes = null; BaseTestSite.Assert.IsNotNull(asResponse.EncPart, "The encrypted part of AS-REP is decrypted."); BaseTestSite.Assert.IsNotNull(asResponse.EncPart.pa_datas, "The encrypted padata is not null."); if (this.testConfig.IsKileImplemented) { foreach (var padata in asResponse.EncPart.pa_datas.Elements) { var parsedPadata = PaDataParser.ParseRepPaData(padata); if (parsedPadata is PaSupportedEncTypes) { paSupportedEncTypes = parsedPadata as PaSupportedEncTypes; } } BaseTestSite.Assert.IsNotNull(paSupportedEncTypes, "The encrypted padata of AS-REP contains PA_SUPPORTED_ENCTYPES."); if (this.testConfig.IsClaimSupported) { BaseTestSite.Assert.IsTrue( paSupportedEncTypes.SupportedEncTypes.HasFlag(SupportedEncryptionTypes.Claims_Supported), "Claims is supported."); } } //TGS exchange BaseTestSite.Log.Add(LogEntryKind.Comment, "Create and send FAST armored TGS request: {0}.", fileserver.Smb2ServiceName); Asn1SequenceOf <PA_DATA> seqOfPaData2 = new Asn1SequenceOf <PA_DATA>(new PA_DATA[] { paPacRequest.Data, paPacOptions.Data }); client.SendTgsRequest(fileserver.Smb2ServiceName, options, seqOfPaData2); KerberosTgsResponse tgsResponse = client.ExpectTgsResponse(); EncryptionKey key = testConfig.QueryKey(fileserver.Smb2ServiceName, client.Context.Realm.ToString(), client.Context.SelectedEType); tgsResponse.DecryptTicket(key); BaseTestSite.Assert.IsNotNull(tgsResponse.EncPart, "The encrypted part of TGS-REP is decrypted."); //Verify TGS encryped padata paSupportedEncTypes = null; BaseTestSite.Assert.IsNotNull(tgsResponse.EncPart, "The encrypted part of TGS-REP is decrypted."); BaseTestSite.Assert.IsNotNull(tgsResponse.EncPart.pa_datas, "The encrypted padata of TGS-REP is not null."); if (this.testConfig.IsKileImplemented) { foreach (var padata in tgsResponse.EncPart.pa_datas.Elements) { var parsedPadata = PaDataParser.ParseRepPaData(padata); if (parsedPadata is PaSupportedEncTypes) { paSupportedEncTypes = parsedPadata as PaSupportedEncTypes; } } BaseTestSite.Assert.IsNotNull(paSupportedEncTypes, "The encrypted padata of TGS-REP contains PA_SUPPORTED_ENCTYPES."); } if (this.testConfig.IsKileImplemented) { BaseTestSite.Assert.IsNotNull(tgsResponse.TicketEncPart.authorization_data, "The ticket contains Authorization data."); AdWin2KPac adWin2kPac = FindOneInAuthData <AdWin2KPac>(tgsResponse.TicketEncPart.authorization_data.Elements); BaseTestSite.Assert.IsNotNull(adWin2kPac, "The Authorization data contains AdWin2KPac."); } AuthorizationData data = null; EncryptionKey subkey = KerberosUtility.GenerateKey(client.Context.SessionKey); byte[] token = client.CreateGssApiToken(ApOptions.MutualRequired, data, subkey, ChecksumFlags.GSS_C_MUTUAL_FLAG | ChecksumFlags.GSS_C_INTEG_FLAG); BaseTestSite.Log.Add(LogEntryKind.Comment, "Logon to fileserver and Access File."); AccessFile(filePath, fileName, fileserver, token, tgsResponse.EncPart.key, expectAccessDeny); }
internal ReportingDownloadOperation(string requestId, AuthorizationData authorizationData, ReportingStatusProvider statusProvider, string trackingId, ApiEnvironment? apiEnvironment) { RequestId = requestId; AuthorizationData = authorizationData; _statusProvider = statusProvider; TrackingId = trackingId; StatusPollIntervalInMilliseconds = ReportingServiceManager.DefaultStatusPollIntervalInMilliseconds; _reportingServiceClient = new ServiceClient<IReportingService>(authorizationData, apiEnvironment); ZipExtractor = new ZipExtractor(); HttpService = new HttpService(); FileSystem = new FileSystem(); }
private void CrossRealm_Smb2_AccessFile(string localRealmName, string trustuedRealmName, User localUser, Computer localKDC, Computer trustedKDC, TransportType transportType, FileServer fileserverInTrustedRealm, string filePath, string fileName, bool expectAccessDeny) { base.Logging(); client = new KerberosTestClient(localRealmName, localUser.Username, localUser.Password, KerberosAccountType.User, localKDC.IPAddress, localKDC.Port, transportType, testConfig.SupportedOid); //Create and send AS request KdcOptions options = KdcOptions.FORWARDABLE | KdcOptions.CANONICALIZE | KdcOptions.RENEWABLE; client.SendAsRequest(options, null); //Recieve preauthentication required error METHOD_DATA methodData; KerberosKrbError krbError = client.ExpectPreauthRequiredError(out methodData); //Create sequence of PA data string timeStamp = KerberosUtility.CurrentKerberosTime.Value; PaEncTimeStamp paEncTimeStamp = new PaEncTimeStamp(timeStamp, 0, this.client.Context.SelectedEType, this.client.Context.CName.Password, this.client.Context.CName.Salt); PaPacRequest paPacRequest = new PaPacRequest(true); Asn1SequenceOf <PA_DATA> seqOfPaData = new Asn1SequenceOf <PA_DATA>(new PA_DATA[] { paEncTimeStamp.Data, paPacRequest.Data }); //Create and send AS request client.SendAsRequest(options, seqOfPaData); KerberosAsResponse asResponse = client.ExpectAsResponse(); //Create and send TGS request if (this.testConfig.TrustType == Adapter.TrustType.Forest) { client.SendTgsRequest(fileserverInTrustedRealm.Smb2ServiceName, options); } else if (this.testConfig.TrustType == Adapter.TrustType.Realm) { client.SendTgsRequest(trustedKDC.DefaultServiceName, options); } BaseTestSite.Log.Add(LogEntryKind.Comment, "Create and send TGS request"); KerberosTgsResponse tgsResponse = client.ExpectTgsResponse(); BaseTestSite.Log.Add(LogEntryKind.Comment, "Receive a referral TGS response."); BaseTestSite.Assert.AreEqual(trustedKDC.DefaultServiceName, KerberosUtility.PrincipalName2String(tgsResponse.Response.ticket.sname), "The service principal name in referral ticket should match expected."); BaseTestSite.Assert.AreEqual(localRealmName.ToLower(), tgsResponse.Response.ticket.realm.Value.ToLower(), "The realm name in referral ticket should match expected."); //Change realm client.ChangeRealm(trustuedRealmName, trustedKDC.IPAddress, trustedKDC.Port, this.testConfig.TransportType); //Create and send referral TGS request client.SendTgsRequest(fileserverInTrustedRealm.Smb2ServiceName, options); KerberosTgsResponse refTgsResponse = client.ExpectTgsResponse(); BaseTestSite.Assert.AreEqual(fileserverInTrustedRealm.Smb2ServiceName, KerberosUtility.PrincipalName2String(refTgsResponse.Response.ticket.sname), "The service principal name in service ticket should match expected."); BaseTestSite.Assert.AreEqual(trustuedRealmName.ToLower(), refTgsResponse.Response.ticket.realm.Value.ToLower(), "The realm name in service ticket should match expected."); EncryptionKey key = testConfig.QueryKey(fileserverInTrustedRealm.Smb2ServiceName, client.Context.Realm.ToString(), client.Context.SelectedEType); refTgsResponse.DecryptTicket(key); BaseTestSite.Assert.AreEqual(localRealmName.ToLower(), refTgsResponse.TicketEncPart.crealm.Value.ToLower(), "Realm name in service ticket encrypted part should match expected."); BaseTestSite.Assert.AreEqual(localUser.Username.ToLower(), KerberosUtility.PrincipalName2String(refTgsResponse.TicketEncPart.cname).ToLower(), "User name in service ticket encrypted part should match expected."); AuthorizationData data = null; EncryptionKey subkey = KerberosUtility.GenerateKey(client.Context.SessionKey); byte[] token = client.CreateGssApiToken(ApOptions.MutualRequired, data, subkey, ChecksumFlags.GSS_C_MUTUAL_FLAG | ChecksumFlags.GSS_C_INTEG_FLAG); BaseTestSite.Log.Add(LogEntryKind.Comment, "Logon to fileserver and Access File."); AccessFile(filePath, fileName, fileserverInTrustedRealm, token, refTgsResponse.EncPart.key, expectAccessDeny); }
public KileAsResponse CreateAsResponse( KileConnection kileConnection, KerberosAccountType accountType, string password, _SeqOfPA_DATA SeqofPaData, EncTicketFlags encTicketFlags, AuthorizationData ticketAuthorizationData) { KileServerContext serverContext = GetServerContextByKileConnection(kileConnection); string cName = serverContext.UserName.name_string.elements[0].mValue; string cRealm = serverContext.UserRealm.mValue; serverContext.Salt = GenerateSalt(cRealm, cName, accountType); serverContext.TicketEncryptKey = new EncryptionKey((int)EncryptionType.RC4_HMAC, GetEncryptionKeyByType(EncryptionType.RC4_HMAC)); if (password == null) { throw new ArgumentNullException("password"); } else { serverContext.Password = password; } KileAsResponse response = new KileAsResponse(serverContext); // Construct a Ticket Ticket ticket = new Ticket(); ticket.tkt_vno = new Asn1Integer(ConstValue.KERBEROSV5); ticket.realm = new Realm(domain); ticket.sname = serverContext.SName; // Set EncTicketPart EncTicketPart encTicketPart = new EncTicketPart(); EncryptionType encryptionType = (EncryptionType)serverContext.EncryptType.elements[0].mValue; encTicketPart.key = new EncryptionKey((int)encryptionType, GetEncryptionKeyByType(encryptionType)); encTicketPart.flags = new TicketFlags(KileUtility.ConvertInt2Flags((int)encTicketFlags)); encTicketPart.crealm = serverContext.UserRealm; encTicketPart.cname = serverContext.UserName; encTicketPart.transited = new TransitedEncoding(4, null); encTicketPart.authtime = KileUtility.CurrentKerberosTime; encTicketPart.starttime = KileUtility.CurrentKerberosTime; encTicketPart.endtime = serverContext.endTime; encTicketPart.renew_till = serverContext.rtime ?? encTicketPart.endtime; encTicketPart.caddr = serverContext.Addresses; encTicketPart.authorization_data = ticketAuthorizationData; response.TicketEncPart = encTicketPart; // Set AS_REP response.Response.pvno = new Asn1Integer(ConstValue.KERBEROSV5); response.Response.msg_type = new Asn1Integer((int)MsgType.KRB_AS_RESP); response.Response.padata = SeqofPaData; response.Response.crealm = serverContext.UserRealm; response.Response.cname = serverContext.UserName; response.Response.ticket = ticket; // Set EncASRepPart EncASRepPart encASRepPart = new EncASRepPart(); encASRepPart.key = encTicketPart.key; LastReq_element element = new LastReq_element(new Int32(0), KileUtility.CurrentKerberosTime); encASRepPart.last_req = new LastReq(new LastReq_element[] { element }); encASRepPart.nonce = serverContext.Nonce; encASRepPart.flags = encTicketPart.flags; encASRepPart.authtime = encTicketPart.authtime; encASRepPart.starttime = encTicketPart.starttime; encASRepPart.endtime = encTicketPart.endtime; encASRepPart.renew_till = encTicketPart.renew_till; encASRepPart.srealm = ticket.realm; encASRepPart.sname = ticket.sname; encASRepPart.caddr = encTicketPart.caddr; response.EncPart = encASRepPart; return response; }
public async override Task RunAsync(AuthorizationData authorizationData) { try { Service = new ServiceClient <ICampaignManagementService>(authorizationData); // Specify one or more campaigns. var campaigns = new[] { new Campaign { Name = "Women's Shoes" + DateTime.UtcNow, Description = "Red shoes line.", BudgetType = BudgetLimitType.MonthlyBudgetSpendUntilDepleted, MonthlyBudget = 1000.00, TimeZone = "PacificTimeUSCanadaTijuana", DaylightSaving = true, // You can set your campaign bid strategy to Enhanced CPC (EnhancedCpcBiddingScheme) // and then, at any time, set an individual ad group or keyword bid strategy to // Manual CPC (ManualCpcBiddingScheme). // For campaigns you can use either of the EnhancedCpcBiddingScheme or ManualCpcBiddingScheme objects. // If you do not set this element, then ManualCpcBiddingScheme is used by default. BiddingScheme = new EnhancedCpcBiddingScheme { }, // Used with FinalUrls shown in the text ads that we will add below. TrackingUrlTemplate = "http://tracker.example.com/?season={_season}&promocode={_promocode}&u={lpurl}" }, }; // Specify one or more ad groups. var adGroups = new[] { new AdGroup { Name = "Women's Red Shoe Sale", AdDistribution = AdDistribution.Search, BiddingModel = BiddingModel.Keyword, PricingModel = PricingModel.Cpc, StartDate = null, EndDate = new Microsoft.BingAds.V10.CampaignManagement.Date { Month = 12, Day = 31, Year = DateTime.UtcNow.Year + 1 }, SearchBid = new Bid { Amount = 0.09 }, Language = "English", // For ad groups you can use either of the InheritFromParentBiddingScheme or ManualCpcBiddingScheme objects. // If you do not set this element, then InheritFromParentBiddingScheme is used by default. BiddingScheme = new ManualCpcBiddingScheme { }, // You could use a tracking template which would override the campaign level // tracking template. Tracking templates defined for lower level entities // override those set for higher level entities. // In this example we are using the campaign level tracking template. TrackingUrlTemplate = null, } }; // In this example only the second keyword should succeed. The Text of the first keyword exceeds the limit, // and the third keyword is a duplicate of the second keyword. var keywords = new[] { new Keyword { Bid = new Bid { Amount = 0.47 }, Param2 = "10% Off", MatchType = MatchType.Broad, Text = "Brand-A Shoes Brand-A Shoes Brand-A Shoes Brand-A Shoes Brand-A Shoes " + "Brand-A Shoes Brand-A Shoes Brand-A Shoes Brand-A Shoes Brand-A Shoes " + "Brand-A Shoes Brand-A Shoes Brand-A Shoes Brand-A Shoes Brand-A Shoes", // For keywords you can use either of the InheritFromParentBiddingScheme or ManualCpcBiddingScheme objects. // If you do not set this element, then InheritFromParentBiddingScheme is used by default. BiddingScheme = new InheritFromParentBiddingScheme { }, }, new Keyword { Bid = new Bid { Amount = 0.47 }, Param2 = "10% Off", MatchType = MatchType.Phrase, Text = "Brand-A Shoes", // For keywords you can use either of the InheritFromParentBiddingScheme or ManualCpcBiddingScheme objects. // If you do not set this element, then InheritFromParentBiddingScheme is used by default. BiddingScheme = new InheritFromParentBiddingScheme { }, }, new Keyword { Bid = new Bid { Amount = 0.47 }, Param2 = "10% Off", MatchType = MatchType.Phrase, Text = "Brand-A Shoes", // For keywords you can use either of the InheritFromParentBiddingScheme or ManualCpcBiddingScheme objects. // If you do not set this element, then InheritFromParentBiddingScheme is used by default. BiddingScheme = new InheritFromParentBiddingScheme { }, } }; // In this example only the first 3 ads should succeed. // The Title of the fourth ad is empty and not valid, // and the fifth ad is a duplicate of the second ad. var ads = new Ad[] { new TextAd { Title = "Women's Shoe Sale", Text = "Huge Savings on red shoes.", DisplayUrl = "Contoso.com", // If you are currently using Destination URLs, you must replace them with Final URLs. // Here is an example of a DestinationUrl you might have used previously. // DestinationUrl = "http://www.contoso.com/womenshoesale/?season=spring&promocode=PROMO123", // To migrate from DestinationUrl to FinalUrls for existing ads, you can set DestinationUrl // to an empty string when updating the ad. If you are removing DestinationUrl, // then FinalUrls is required. // DestinationUrl = "", // With FinalUrls you can separate the tracking template, custom parameters, and // landing page URLs. FinalUrls = new[] { "http://www.contoso.com/womenshoesale" }, // Final Mobile URLs can also be used if you want to direct the user to a different page // for mobile devices. FinalMobileUrls = new[] { "http://mobile.contoso.com/womenshoesale" }, // You could use a tracking template which would override the campaign level // tracking template. Tracking templates defined for lower level entities // override those set for higher level entities. // In this example we are using the campaign level tracking template. TrackingUrlTemplate = null, // Set custom parameters that are specific to this ad, // and can be used by the ad, ad group, campaign, or account level tracking template. // In this example we are using the campaign level tracking template. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "PROMO1" }, new CustomParameter() { Key = "season", Value = "summer" }, } } }, new TextAd { Title = "Women's Super Shoe Sale", Text = "Huge Savings on red shoes.", DisplayUrl = "Contoso.com", // If you are currently using Destination URLs, you must replace them with Final URLs. // Here is an example of a DestinationUrl you might have used previously. // DestinationUrl = "http://www.contoso.com/womenshoesale/?season=spring&promocode=PROMO123", // To migrate from DestinationUrl to FinalUrls for existing ads, you can set DestinationUrl // to an empty string when updating the ad. If you are removing DestinationUrl, // then FinalUrls is required. // DestinationUrl = "", // With FinalUrls you can separate the tracking template, custom parameters, and // landing page URLs. FinalUrls = new[] { "http://www.contoso.com/womenshoesale" }, // Final Mobile URLs can also be used if you want to direct the user to a different page // for mobile devices. FinalMobileUrls = new[] { "http://mobile.contoso.com/womenshoesale" }, // You could use a tracking template which would override the campaign level // tracking template. Tracking templates defined for lower level entities // override those set for higher level entities. // In this example we are using the campaign level tracking template. TrackingUrlTemplate = null, // Set custom parameters that are specific to this ad, // and can be used by the ad, ad group, campaign, or account level tracking template. // In this example we are using the campaign level tracking template. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "PROMO2" }, new CustomParameter() { Key = "season", Value = "summer" }, } }, }, new TextAd { Title = "Women's Red Shoe Sale", Text = "Huge Savings on red shoes.", DisplayUrl = "Contoso.com", // If you are currently using Destination URLs, you must replace them with Final URLs. // Here is an example of a DestinationUrl you might have used previously. // DestinationUrl = "http://www.contoso.com/womenshoesale/?season=spring&promocode=PROMO123", // To migrate from DestinationUrl to FinalUrls for existing ads, you can set DestinationUrl // to an empty string when updating the ad. If you are removing DestinationUrl, // then FinalUrls is required. // DestinationUrl = "", // With FinalUrls you can separate the tracking template, custom parameters, and // landing page URLs. FinalUrls = new[] { "http://www.contoso.com/womenshoesale" }, // Final Mobile URLs can also be used if you want to direct the user to a different page // for mobile devices. FinalMobileUrls = new[] { "http://mobile.contoso.com/womenshoesale" }, // You could use a tracking template which would override the campaign level // tracking template. Tracking templates defined for lower level entities // override those set for higher level entities. // In this example we are using the campaign level tracking template. TrackingUrlTemplate = null, // Set custom parameters that are specific to this ad, // and can be used by the ad, ad group, campaign, or account level tracking template. // In this example we are using the campaign level tracking template. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "PROMO3" }, new CustomParameter() { Key = "season", Value = "summer" }, } }, }, new TextAd { Title = "", Text = "Huge Savings on red shoes.", DisplayUrl = "Contoso.com", // If you are currently using Destination URLs, you must replace them with Final URLs. // Here is an example of a DestinationUrl you might have used previously. // DestinationUrl = "http://www.contoso.com/womenshoesale/?season=spring&promocode=PROMO123", // To migrate from DestinationUrl to FinalUrls for existing ads, you can set DestinationUrl // to an empty string when updating the ad. If you are removing DestinationUrl, // then FinalUrls is required. // DestinationUrl = "", // With FinalUrls you can separate the tracking template, custom parameters, and // landing page URLs. FinalUrls = new[] { "http://www.contoso.com/womenshoesale" }, // Final Mobile URLs can also be used if you want to direct the user to a different page // for mobile devices. FinalMobileUrls = new[] { "http://mobile.contoso.com/womenshoesale" }, // You could use a tracking template which would override the campaign level // tracking template. Tracking templates defined for lower level entities // override those set for higher level entities. // In this example we are using the campaign level tracking template. TrackingUrlTemplate = null, // Set custom parameters that are specific to this ad, // and can be used by the ad, ad group, campaign, or account level tracking template. // In this example we are using the campaign level tracking template. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "PROMO4" }, new CustomParameter() { Key = "season", Value = "summer" }, } }, }, new TextAd { Title = "Women's Super Shoe Sale", Text = "Huge Savings on red shoes.", DisplayUrl = "Contoso.com", // If you are currently using Destination URLs, you must replace them with Final URLs. // Here is an example of a DestinationUrl you might have used previously. // DestinationUrl = "http://www.contoso.com/womenshoesale/?season=spring&promocode=PROMO123", // To migrate from DestinationUrl to FinalUrls for existing ads, you can set DestinationUrl // to an empty string when updating the ad. If you are removing DestinationUrl, // then FinalUrls is required. // DestinationUrl = "", // With FinalUrls you can separate the tracking template, custom parameters, and // landing page URLs. FinalUrls = new[] { "http://www.contoso.com/womenshoesale" }, // Final Mobile URLs can also be used if you want to direct the user to a different page // for mobile devices. FinalMobileUrls = new[] { "http://mobile.contoso.com/womenshoesale" }, // You could use a tracking template which would override the campaign level // tracking template. Tracking templates defined for lower level entities // override those set for higher level entities. // In this example we are using the campaign level tracking template. TrackingUrlTemplate = null, // Set custom parameters that are specific to this ad, // and can be used by the ad, ad group, campaign, or account level tracking template. // In this example we are using the campaign level tracking template. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "PROMO5" }, new CustomParameter() { Key = "season", Value = "summer" }, } }, }, }; // Add the campaign, ad group, keywords, and ads AddCampaignsResponse addCampaignsResponse = await AddCampaignsAsync(authorizationData.AccountId, campaigns); long?[] campaignIds = addCampaignsResponse.CampaignIds.ToArray(); BatchError[] campaignErrors = addCampaignsResponse.PartialErrors.ToArray(); AddAdGroupsResponse addAdGroupsResponse = await AddAdGroupsAsync((long)campaignIds[0], adGroups); long?[] adGroupIds = addAdGroupsResponse.AdGroupIds.ToArray(); BatchError[] adGroupErrors = addAdGroupsResponse.PartialErrors.ToArray(); AddKeywordsResponse addKeywordsResponse = await AddKeywordsAsync((long)adGroupIds[0], keywords); long?[] keywordIds = addKeywordsResponse.KeywordIds.ToArray(); BatchError[] keywordErrors = addKeywordsResponse.PartialErrors.ToArray(); AddAdsResponse addAdsResponse = await AddAdsAsync((long)adGroupIds[0], ads); long?[] adIds = addAdsResponse.AdIds.ToArray(); BatchError[] adErrors = addAdsResponse.PartialErrors.ToArray(); // Output the new assigned entity identifiers, as well as any partial errors OutputCampaignsWithPartialErrors(campaigns, campaignIds, campaignErrors); OutputAdGroupsWithPartialErrors(adGroups, adGroupIds, adGroupErrors); OutputKeywordsWithPartialErrors(keywords, keywordIds, keywordErrors); OutputAdsWithPartialErrors(ads, adIds, adErrors); // Here is a simple example that updates the campaign budget. var updateCampaign = new Campaign { Id = campaignIds[0], MonthlyBudget = 500, }; // As an exercise you can step through using the debugger and view the results. await GetCampaignsByIdsAsync( authorizationData.AccountId, new [] { (long)campaignIds[0] }, CampaignType.SearchAndContent | CampaignType.Shopping, CampaignAdditionalField.BiddingScheme ); await UpdateCampaignsAsync(authorizationData.AccountId, new[] { updateCampaign }); await GetCampaignsByIdsAsync( authorizationData.AccountId, new[] { (long)campaignIds[0] }, CampaignType.SearchAndContent | CampaignType.Shopping, CampaignAdditionalField.BiddingScheme ); // Update the Text for the 3 successfully created ads, and update some UrlCustomParameters. var updateAds = new Ad[] { new TextAd { Id = adIds[0], Text = "Huge Savings on All Red Shoes.", // Set the UrlCustomParameters element to null or empty to retain any // existing custom parameters. UrlCustomParameters = null, }, new TextAd { Id = adIds[1], Text = "Huge Savings on All Red Shoes.", // To remove all custom parameters, set the Parameters element of the // CustomParameters object to null or empty. UrlCustomParameters = new CustomParameters { Parameters = null, }, }, new TextAd { Id = adIds[2], Text = "Huge Savings on All Red Shoes.", // To remove a subset of custom parameters, specify the custom parameters that // you want to keep in the Parameters element of the CustomParameters object. UrlCustomParameters = new CustomParameters { Parameters = new[] { new CustomParameter() { Key = "promoCode", Value = "updatedpromo" }, } } }, }; // As an exercise you can step through using the debugger and view the results. await GetAdsByAdGroupIdAsync((long)adGroupIds[0]); var updateAdsResponse = await UpdateAdsAsync((long)adGroupIds[0], updateAds); await GetAdsByAdGroupIdAsync((long)adGroupIds[0]); // Here is a simple example that updates the keyword bid to use the ad group bid. var updateKeyword = new Keyword { // Set Bid.Amount null (new empty Bid) to use the ad group bid. // If the Bid property is null, your keyword bid will not be updated. Bid = new Bid(), Id = keywordIds[1], }; // As an exercise you can step through using the debugger and view the results. await GetKeywordsByAdGroupIdAsync((long)adGroupIds[0], KeywordAdditionalField.BiddingScheme); await UpdateKeywordsAsync((long)adGroupIds[0], new[] { updateKeyword }); await GetKeywordsByAdGroupIdAsync((long)adGroupIds[0], KeywordAdditionalField.BiddingScheme); // Delete the campaign, ad group, keyword, and ad that were previously added. // You should remove this line if you want to view the added entities in the // Bing Ads web application or another tool. await DeleteCampaignsAsync(authorizationData.AccountId, new[] { (long)campaignIds[0] }); OutputStatusMessage(String.Format("Deleted CampaignId {0}\n", campaignIds[0])); } // Catch authentication exceptions catch (OAuthTokenRequestException ex) { OutputStatusMessage(string.Format("Couldn't get OAuth tokens. Error: {0}. Description: {1}", ex.Details.Error, ex.Details.Description)); } // Catch Campaign Management service exceptions catch (FaultException <Microsoft.BingAds.V10.CampaignManagement.AdApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.Errors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V10.CampaignManagement.ApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (FaultException <Microsoft.BingAds.V10.CampaignManagement.EditorialApiFaultDetail> ex) { OutputStatusMessage(string.Join("; ", ex.Detail.OperationErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); OutputStatusMessage(string.Join("; ", ex.Detail.BatchErrors.Select(error => string.Format("{0}: {1}", error.Code, error.Message)))); } catch (Exception ex) { OutputStatusMessage(ex.Message); } }
/// <summary> /// Initializes a new instance of this class with the specified <see cref="AuthorizationData"/>. /// </summary> /// <param name="authorizationData">Represents a user who intends to access the corresponding customer and account. </param> public ReportingServiceManager(AuthorizationData authorizationData) { if (authorizationData == null) { throw new ArgumentNullException("authorizationData"); } _authorizationData = authorizationData; HttpService = new HttpService(); ZipExtractor = new ZipExtractor(); FileSystem = new FileSystem(); StatusPollIntervalInMilliseconds = DefaultStatusPollIntervalInMilliseconds; WorkingDirectory = Path.Combine(Path.GetTempPath(), "BingAdsSDK", "Reporting"); }
/// <summary> /// Initializes a new instance of this class with the specified <see cref="AuthorizationData"/> and <paramref name="apiEnvironment"/>. /// </summary> /// <param name="authorizationData">Represents a user who intends to access the corresponding customer and account. </param> /// <param name="apiEnvironment">Bing Ads API environment</param> public ReportingServiceManager(AuthorizationData authorizationData, ApiEnvironment? apiEnvironment) { if (authorizationData == null) { throw new ArgumentNullException("authorizationData"); } _authorizationData = authorizationData; HttpService = new HttpService(); ZipExtractor = new ZipExtractor(); FileSystem = new FileSystem(); StatusPollIntervalInMilliseconds = DefaultStatusPollIntervalInMilliseconds; DownloadHttpTimeout = TimeSpan.FromMilliseconds(DefaultHttpClientTimeoutInMillseconds); WorkingDirectory = Path.Combine(Path.GetTempPath(), "BingAdsSDK", "Reporting"); if (apiEnvironment != null) _apiEnvironment = apiEnvironment.Value; }