Hi,
We are trying to create a custom audience for one of our client and we are an issue.
We are able to create the custom audience using the following endpoint :
POST https://ads-api.twitter.com/9/accounts/${accountId}/custom_audiences?name=${audienceId}
However, when we want to populate this custom audience, using the endpoint POST https://ads-api.twitter.com/9/accounts/${accountId}/custom_audiences/${audienceId}/users
We receive an 401 - Unauthorized as a response to our request.
We checked at our permissions and we were considered as PARTNER_AUDIENCE_MANAGER. When tried to change the permission to AD_MANAGER but still facing the issue.
Is there any specific whitelisting needed to be able to populate a segment we have created on behalf of our client ?
Thanks for your help
Hey @CostiouVincent
Thanks for reaching out! There is an allowlisting process thats required to access the audience users endpoint. Can you provide the client app ID being used for to make the API requests so we can check?
Thanks!
Hi @imit8me
Our app ID is 15974058, and the name is mediarithmics-data-connector
Thanks,
Vincent
Thanks for those details! So it looks like your app has the appropriate permissions to use the Audience users endpoint.
Taking another look at the original question, it looks like you’re using the name set when creating the Audience as the audienceId in the users endpoint. This would be incorrect, when creating the audience the API response contains the id of the new audience. This would be the id that needs to be populated in the users endpoint. So, it would look something like:
POST https://ads-api.twitter.com/9/accounts/${accountId}/custom_audiences?name=${audienceName}
- Get the
id from the previous steps’ response
- Use the
id in the users endpoint like so, POST https://ads-api.twitter.com/9/accounts/${accountId}/custom_audiences/${id_from_step_1}/users
Thanks!
Hi @imit8me,
After checking this with my developer, he confirmed to me that he uses the name in the first request and the id received in the 1st response for the 2nd request.
Here is the result when we list the existing audiences :
{
targetable: false,
name: 'test_20200302_domino',
targetable_types: [ 'CRM', 'EXCLUDED_CRM' ],
audience_type: 'CRM',
description: null,
permission_level: 'READ_WRITE',
owner_account_id: 'xxxxxxxxx',
id: '3zt33',
reasons_not_targetable: [ 'TOO_SMALL' ],
created_at: '2021-07-08T16:18:24Z',
updated_at: '2021-07-08T23:46:05Z',
partner_source: 'OTHER',
deleted: false,
audience_size: null
}
And here is the second request, when we try to populate the segment, with the response at the bottom :
request data {
url: 'https://ads-api.twitter.com/9/accounts/xxxxxxxxx/custom_audiences/3zt33/users',
data: {
operation_type: 'Update',
params: {
effective_at: 2021-08-10T07:53:05.204Z,
expires_at: 2021-08-10T07:53:08.804Z,
users: [Array]
}
},
method: 'POST'
}
res : {"errors":[{"code":"UNAUTHORIZED_ACCESS","message":"This request is not properly authenticated"}],"request":{"params":{}}}
As you can see, the id is the same. I think the issue is elsewhere. Could you have another look at it ?
imit8me
#6
Hmm can you confirm that you’re using the Content-Type: application/json header in the request as well?
Hi @imit8me,
We didn’t but we tried it this morning and it doesn’t seems to work better :
{
Authorization:
'OAuth oauth_consumer_key="xxxx",
oauth_nonce="xxxx",
oauth_signature="xxxx",
oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1628845524",
oauth_token="xxxx",
oauth_version="1.0"
',
'Content-Type': 'application/json'
}
res : {"errors":[{"code":"UNAUTHORIZED_ACCESS","message":"This request is not properly authenticated"}],"request":{"params":{}}}
Hello @imit8me
Could you please come back to us regarding this matter?
We have not been able to activate audiences for our client for quite some time now.
Thanks a lot for your help.
BR,
Marie
Hey @CostiouVincent
Interesting, can you try making the request with twurl. Here’s a sample request if that’s helpful:
twurl -H 'ads-api.twitter.com' -X POST -A 'Content-Type: application/json' "/9/accounts/$account/custom_audiences/3yh16/users" -d '[{"operation_type":"Update","params":{"users":[{"email":["abc@twitter.com"],"phone_number":["9255551212","4255551212"]},{"email":["edf@twitter.com"],"phone_number":["9255551212","4255551212"]}]}},{"operation_type":"Update","params":{"users":[{"device_id":["123456"],"email":["abc@twitter.com"],"handle":["123333"],"phone_number":["9255551212","4255551212"],"twitter_id":["12346"]},{"email":["edf@twitter.com"],"phone_number":["9255551212","4255551212"]}]}}]' | jq .
If the request succeeds I’d recommend using the -t option to output the authorization headers and compare those against the ones in your request.
Thanks!
Hi @imit8me,
Thank you for the command, it seems it works better now.
We pushed a payload last tuesday, with one email hash on segment id 2gvbb.
data: { success_count: 1, total_count: 1 }
However, our client does not seems to see it yet this morning. Do you have an idea why ?
Thanks,
Vincent
Hi @imit8me,
Did you have a chance to look into my later comment ?
Thanks,
Vincent
imit8me
#12
Hey @CostiouVincent
So our matching logic is such that you need a minimum of 100 matched users for the audience to be targetable. Given this, sending just a single user is unlikely to show you any changes for the audiences. I’d recommend testing with a larger dataset of hashed emails.
Thanks!
Hi imit8me,
We managed to send data to our client. Everything seems to work fine now.
Thank you for your help.
Vincent
imit8me
#14
Sounds good! Thanks for following up!