twitter-ads 0.3.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (94) hide show
  1. checksums.yaml +7 -0
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +2 -0
  4. data/CONTRIBUTING.md +77 -0
  5. data/LICENSE +22 -0
  6. data/README.md +111 -0
  7. data/Rakefile +86 -0
  8. data/bin/twitter-ads +42 -0
  9. data/lib/twitter-ads.rb +54 -0
  10. data/lib/twitter-ads/account.rb +229 -0
  11. data/lib/twitter-ads/audiences/tailored_audience.rb +177 -0
  12. data/lib/twitter-ads/campaign/app_list.rb +42 -0
  13. data/lib/twitter-ads/campaign/campaign.rb +40 -0
  14. data/lib/twitter-ads/campaign/funding_instrument.rb +33 -0
  15. data/lib/twitter-ads/campaign/line_item.rb +91 -0
  16. data/lib/twitter-ads/campaign/promotable_user.rb +28 -0
  17. data/lib/twitter-ads/campaign/targeting_criteria.rb +77 -0
  18. data/lib/twitter-ads/campaign/tweet.rb +83 -0
  19. data/lib/twitter-ads/client.rb +92 -0
  20. data/lib/twitter-ads/creative/app_download_card.rb +44 -0
  21. data/lib/twitter-ads/creative/image_app_download_card.rb +44 -0
  22. data/lib/twitter-ads/creative/image_conversation_card.rb +44 -0
  23. data/lib/twitter-ads/creative/lead_gen_card.rb +46 -0
  24. data/lib/twitter-ads/creative/promoted_account.rb +38 -0
  25. data/lib/twitter-ads/creative/promoted_tweet.rb +87 -0
  26. data/lib/twitter-ads/creative/video.rb +43 -0
  27. data/lib/twitter-ads/creative/video_app_download_card.rb +47 -0
  28. data/lib/twitter-ads/creative/video_conversation_card.rb +46 -0
  29. data/lib/twitter-ads/creative/website_card.rb +48 -0
  30. data/lib/twitter-ads/cursor.rb +127 -0
  31. data/lib/twitter-ads/enum.rb +135 -0
  32. data/lib/twitter-ads/error.rb +93 -0
  33. data/lib/twitter-ads/http/request.rb +127 -0
  34. data/lib/twitter-ads/http/response.rb +74 -0
  35. data/lib/twitter-ads/http/ton_upload.rb +140 -0
  36. data/lib/twitter-ads/legacy.rb +7 -0
  37. data/lib/twitter-ads/resources/analytics.rb +90 -0
  38. data/lib/twitter-ads/resources/dsl.rb +108 -0
  39. data/lib/twitter-ads/resources/persistence.rb +43 -0
  40. data/lib/twitter-ads/resources/resource.rb +92 -0
  41. data/lib/twitter-ads/targeting/reach_estimate.rb +69 -0
  42. data/lib/twitter-ads/utils.rb +76 -0
  43. data/lib/twitter-ads/version.rb +6 -0
  44. data/spec/fixtures/accounts_all.json +65 -0
  45. data/spec/fixtures/accounts_features.json +18 -0
  46. data/spec/fixtures/accounts_load.json +19 -0
  47. data/spec/fixtures/app_lists_all.json +22 -0
  48. data/spec/fixtures/app_lists_load.json +31 -0
  49. data/spec/fixtures/campaigns_all.json +208 -0
  50. data/spec/fixtures/campaigns_load.json +27 -0
  51. data/spec/fixtures/funding_instruments_all.json +74 -0
  52. data/spec/fixtures/funding_instruments_load.json +28 -0
  53. data/spec/fixtures/line_items_all.json +292 -0
  54. data/spec/fixtures/line_items_load.json +36 -0
  55. data/spec/fixtures/placements.json +35 -0
  56. data/spec/fixtures/promotable_users_all.json +57 -0
  57. data/spec/fixtures/promotable_users_load.json +18 -0
  58. data/spec/fixtures/promoted_tweets_all.json +212 -0
  59. data/spec/fixtures/promoted_tweets_load.json +19 -0
  60. data/spec/fixtures/reach_estimate.json +19 -0
  61. data/spec/fixtures/tailored_audiences_all.json +67 -0
  62. data/spec/fixtures/tailored_audiences_load.json +29 -0
  63. data/spec/fixtures/tweet_preview.json +24 -0
  64. data/spec/fixtures/videos_all.json +50 -0
  65. data/spec/fixtures/videos_load.json +22 -0
  66. data/spec/quality_spec.rb +15 -0
  67. data/spec/shared/properties.rb +20 -0
  68. data/spec/spec_helper.rb +61 -0
  69. data/spec/support/helpers.rb +42 -0
  70. data/spec/twitter-ads/account_spec.rb +315 -0
  71. data/spec/twitter-ads/audiences/tailored_audience_spec.rb +45 -0
  72. data/spec/twitter-ads/campaign/app_list_spec.rb +108 -0
  73. data/spec/twitter-ads/campaign/line_item_spec.rb +95 -0
  74. data/spec/twitter-ads/campaign/reach_estimate_spec.rb +98 -0
  75. data/spec/twitter-ads/campaign/targeting_criteria_spec.rb +39 -0
  76. data/spec/twitter-ads/campaign/tweet_spec.rb +83 -0
  77. data/spec/twitter-ads/client_spec.rb +115 -0
  78. data/spec/twitter-ads/creative/app_download_card_spec.rb +44 -0
  79. data/spec/twitter-ads/creative/image_app_download_card_spec.rb +43 -0
  80. data/spec/twitter-ads/creative/image_conversation_card_spec.rb +40 -0
  81. data/spec/twitter-ads/creative/lead_gen_card_spec.rb +46 -0
  82. data/spec/twitter-ads/creative/promoted_account_spec.rb +30 -0
  83. data/spec/twitter-ads/creative/promoted_tweet_spec.rb +46 -0
  84. data/spec/twitter-ads/creative/video_app_download_card_spec.rb +42 -0
  85. data/spec/twitter-ads/creative/video_conversation_card_spec.rb +52 -0
  86. data/spec/twitter-ads/creative/video_legacy_spec.rb +43 -0
  87. data/spec/twitter-ads/creative/video_spec.rb +43 -0
  88. data/spec/twitter-ads/creative/website_card_spec.rb +37 -0
  89. data/spec/twitter-ads/cursor_spec.rb +67 -0
  90. data/spec/twitter-ads/placements_spec.rb +36 -0
  91. data/spec/twitter-ads/utils_spec.rb +101 -0
  92. data/twitter-ads.gemspec +37 -0
  93. metadata +247 -0
  94. metadata.gz.sig +0 -0
@@ -0,0 +1,115 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Client do
7
+
8
+ let!(:consumer_key) { Faker::Lorem.characters(15) }
9
+ let!(:consumer_secret) { Faker::Lorem.characters(40) }
10
+ let!(:access_token) { "123456-#{Faker::Lorem.characters(40)}" }
11
+ let!(:access_token_secret) { Faker::Lorem.characters(40) }
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ consumer_key,
16
+ consumer_secret,
17
+ access_token,
18
+ access_token_secret
19
+ )
20
+ end
21
+
22
+ describe '#initialize' do
23
+
24
+ it 'requires a valid consumer_key' do
25
+ expect(client.consumer_key).not_to be_nil
26
+ expect(client.consumer_key).to eq(consumer_key)
27
+ expect {
28
+ Client.new(nil, consumer_secret, access_token, access_token_secret)
29
+ }.to raise_error(ArgumentError)
30
+ end
31
+
32
+ it 'requires a valid consumer_secret' do
33
+ expect(client.consumer_secret).not_to be_nil
34
+ expect(client.consumer_secret).to eq(consumer_secret)
35
+ expect {
36
+ Client.new(consumer_key, nil, access_token, access_token_secret)
37
+ }.to raise_error(ArgumentError)
38
+ end
39
+
40
+ it 'requires a valid access_token' do
41
+ expect(client.access_token).not_to be_nil
42
+ expect(client.access_token).to eq(access_token)
43
+ expect {
44
+ Client.new(consumer_key, consumer_secret, nil, access_token_secret)
45
+ }.to raise_error(ArgumentError)
46
+ end
47
+
48
+ it 'requires a valid access_token_secret' do
49
+ expect(client.access_token_secret).not_to be_nil
50
+ expect(client.access_token_secret).to eq(access_token_secret)
51
+ expect {
52
+ Client.new(consumer_key, consumer_secret, access_token, nil)
53
+ }.to raise_error(ArgumentError)
54
+ end
55
+
56
+ it 'allows additional options' do
57
+ expect {
58
+ Client.new(consumer_key, consumer_secret, access_token, {})
59
+ }.not_to raise_error
60
+ end
61
+
62
+ end
63
+
64
+ describe '#inspect' do
65
+
66
+ it 'includes the object id value' do
67
+ expect(client.inspect).to include(client.object_id.to_s)
68
+ end
69
+
70
+ it 'includes the consumer_key value' do
71
+ expect(client.inspect).to include(client.consumer_key)
72
+ end
73
+
74
+ it 'includes the class.name value' do
75
+ expect(client.inspect).to include(client.class.name)
76
+ end
77
+
78
+ end
79
+
80
+ describe '#accounts' do
81
+
82
+ context 'when called with no arguments' do
83
+
84
+ before(:all) do
85
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
86
+ end
87
+
88
+ it 'returns a Cursor object' do
89
+ cursor = client.accounts
90
+ expect(cursor.class.name).to eq('TwitterAds::Cursor')
91
+ expect(cursor.size).to eq(5)
92
+ expect(cursor.first.class.name).to eq('TwitterAds::Account')
93
+ end
94
+
95
+ end
96
+
97
+ context 'when called with an account id' do
98
+
99
+ let!(:account_id) { '2iqph' }
100
+
101
+ before(:all) do
102
+ stub_fixture(:get, :accounts_load, /(.*\/0\/accounts\/)([a-zA-Z0-9]*)\z/)
103
+ end
104
+
105
+ it 'returns a specific Account object' do
106
+ cursor = client.accounts(account_id)
107
+ expect(cursor.class.name).to eq('TwitterAds::Account')
108
+ expect(cursor.id).to eq(account_id)
109
+ end
110
+
111
+ end
112
+
113
+ end
114
+
115
+ end
@@ -0,0 +1,44 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::AppDownloadCard do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+ read = %w(id preview_url created_at updated_at deleted)
27
+
28
+ write = %w(
29
+ name
30
+ app_country_code
31
+ iphone_app_id
32
+ iphone_deep_link
33
+ ipad_app_id
34
+ ipad_deep_link
35
+ googleplay_app_id
36
+ googleplay_deep_link
37
+ app_cta
38
+ custom_icon_media_id
39
+ custom_app_description
40
+ )
41
+
42
+ include_examples 'object property check', read, write
43
+
44
+ end
@@ -0,0 +1,43 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::ImageAppDownloadCard do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+ read = %w(id preview_url created_at updated_at deleted)
27
+
28
+ write = %w(
29
+ name
30
+ app_country_code
31
+ iphone_app_id
32
+ iphone_deep_link
33
+ ipad_app_id
34
+ ipad_deep_link
35
+ googleplay_app_id
36
+ googleplay_deep_link
37
+ app_cta
38
+ wide_app_image_media_id
39
+ )
40
+
41
+ include_examples 'object property check', read, write
42
+
43
+ end
@@ -0,0 +1,40 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::ImageConversationCard do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+ read = %w(id preview_url image deleted created_at updated_at)
27
+ write = %w(
28
+ name
29
+ title
30
+ first_cta
31
+ first_cta_tweet
32
+ second_cta
33
+ second_cta_tweet
34
+ thank_you_text
35
+ thank_you_url
36
+ image_media_id
37
+ )
38
+ include_examples 'object property check', read, write
39
+
40
+ end
@@ -0,0 +1,46 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::LeadGenCard do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+ read = %w(id preview_url created_at updated_at deleted)
27
+
28
+ write = %w(
29
+ name
30
+ image_media_id
31
+ cta
32
+ fallback_url
33
+ privacy_policy_url
34
+ title
35
+ submit_url
36
+ submit_method
37
+ custom_destination_url
38
+ custom_destination_text
39
+ custom_key_screen_name
40
+ custom_key_name
41
+ custom_key_email
42
+ )
43
+
44
+ include_examples 'object property check', read, write
45
+
46
+ end
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::PromotedAccount do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+ read = %w(id approval_status created_at updated_at deleted)
27
+ write = %w(line_item_id user_id paused)
28
+ include_examples 'object property check', read, write
29
+
30
+ end
@@ -0,0 +1,46 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::PromotedTweet do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+ read = %w(id approval_status created_at updated_at deleted)
27
+ write = %w(line_item_id tweet_id paused)
28
+ include_examples 'object property check', read, write
29
+
30
+ describe '#save' do
31
+
32
+ it 'raises a client error when missing tweet_id' do
33
+ expect(subject).to receive(:validate).and_call_original
34
+ subject.line_item_id = '12345'
35
+ expect { subject.save }.to raise_error(TwitterAds::ClientError)
36
+ end
37
+
38
+ it 'raises a client error when missing line_item_id' do
39
+ expect(subject).to receive(:validate).and_call_original
40
+ subject.tweet_id = 99999999999999999999
41
+ expect { subject.save }.to raise_error(TwitterAds::ClientError)
42
+ end
43
+
44
+ end
45
+
46
+ end
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::VideoAppDownloadCard do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+ read = %w(id preview_url video_url video_poster_url deleted created_at updated_at)
27
+ write = %w(
28
+ name
29
+ app_country_code
30
+ iphone_app_id
31
+ iphone_deep_link
32
+ ipad_app_id
33
+ ipad_deep_link
34
+ googleplay_app_id
35
+ googleplay_deep_link
36
+ app_cta
37
+ image_media_id
38
+ video_id
39
+ )
40
+ include_examples 'object property check', read, write
41
+
42
+ end
@@ -0,0 +1,52 @@
1
+ # frozen_string_literal: true
2
+ # Copyright (C) 2015 Twitter, Inc.
3
+
4
+ require 'spec_helper'
5
+
6
+ describe TwitterAds::Creative::VideoConversationCard do
7
+
8
+ before(:each) do
9
+ stub_fixture(:get, :accounts_all, "#{ADS_API}/accounts")
10
+ stub_fixture(:get, :accounts_load, "#{ADS_API}/accounts/2iqph")
11
+ end
12
+
13
+ let(:client) do
14
+ Client.new(
15
+ Faker::Lorem.characters(15),
16
+ Faker::Lorem.characters(40),
17
+ "123456-#{Faker::Lorem.characters(40)}",
18
+ Faker::Lorem.characters(40)
19
+ )
20
+ end
21
+
22
+ let(:account) { client.accounts.first }
23
+
24
+ # check model properties
25
+ subject { described_class.new(account) }
26
+
27
+ read = %w(
28
+ id
29
+ preview_url
30
+ video_url
31
+ video_poster_url
32
+ deleted
33
+ created_at
34
+ updated_at
35
+ )
36
+
37
+ write = %w(
38
+ name
39
+ title
40
+ first_cta
41
+ first_cta_tweet
42
+ second_cta
43
+ second_cta_tweet
44
+ thank_you_text
45
+ thank_you_url
46
+ image_media_id
47
+ video_id
48
+ )
49
+
50
+ include_examples 'object property check', read, write
51
+
52
+ end