adwords4r 0.7 → 11.0.2
Sign up to get free protection for your applications and to get access to all the features.
- data/Authors.txt +3 -1
- data/ChangeLog.txt +18 -1
- data/Rakefile +35 -50
- data/Readme.txt +28 -11
- data/Todo.txt +1 -9
- data/adwords.properties +7 -7
- data/examples/campaign.rb +7 -5
- data/examples/framework.rb +3 -1
- data/examples/get_free_usage_this_month.rb +3 -1
- data/examples/get_unit_count.rb +7 -2
- data/examples/keyword_tool_demo.rb +5 -2
- data/examples/traffic_estimator.rb +5 -2
- data/lib/adwords4r.rb +157 -147
- data/lib/adwords4r/credentials.rb +36 -36
- data/lib/adwords4r/services.rb +24 -32
- data/lib/adwords4r/v10/AccountService.rb +234 -0
- data/lib/adwords4r/v10/AccountServiceDriver.rb +77 -0
- data/lib/adwords4r/v10/AccountServiceMappingRegistry.rb +258 -0
- data/lib/adwords4r/v10/AdGroupService.rb +257 -0
- data/lib/adwords4r/v10/AdGroupServiceDriver.rb +109 -0
- data/lib/adwords4r/v10/AdGroupServiceMappingRegistry.rb +276 -0
- data/lib/adwords4r/v10/AdService.rb +757 -0
- data/lib/adwords4r/v10/AdServiceDriver.rb +125 -0
- data/lib/adwords4r/v10/AdServiceMappingRegistry.rb +805 -0
- data/lib/adwords4r/v10/CampaignService.rb +443 -0
- data/lib/adwords4r/v10/CampaignServiceDriver.rb +125 -0
- data/lib/adwords4r/v10/CampaignServiceMappingRegistry.rb +564 -0
- data/lib/adwords4r/v10/CriterionService.rb +442 -0
- data/lib/adwords4r/v10/CriterionServiceDriver.rb +117 -0
- data/lib/adwords4r/v10/CriterionServiceMappingRegistry.rb +507 -0
- data/lib/adwords4r/v10/InfoService.rb +242 -0
- data/lib/adwords4r/v10/InfoServiceDriver.rb +109 -0
- data/lib/adwords4r/v10/InfoServiceMappingRegistry.rb +228 -0
- data/lib/adwords4r/v10/KeywordToolService.rb +205 -0
- data/lib/adwords4r/{v6 → v10}/KeywordToolServiceDriver.rb +18 -12
- data/lib/adwords4r/v10/KeywordToolServiceMappingRegistry.rb +227 -0
- data/lib/adwords4r/{v6 → v10}/ReportService.rb +335 -472
- data/lib/adwords4r/v10/ReportServiceDriver.rb +93 -0
- data/lib/adwords4r/v10/ReportServiceMappingRegistry.rb +559 -0
- data/lib/adwords4r/v10/SiteSuggestionService.rb +242 -0
- data/lib/adwords4r/v10/SiteSuggestionServiceDriver.rb +77 -0
- data/lib/adwords4r/v10/SiteSuggestionServiceMappingRegistry.rb +271 -0
- data/lib/adwords4r/v10/TrafficEstimatorService.rb +312 -0
- data/lib/adwords4r/v10/TrafficEstimatorServiceDriver.rb +77 -0
- data/lib/adwords4r/v10/TrafficEstimatorServiceMappingRegistry.rb +483 -0
- data/lib/adwords4r/v11/AccountService.rb +215 -0
- data/lib/adwords4r/v11/AccountServiceDriver.rb +69 -0
- data/lib/adwords4r/v11/AccountServiceMappingRegistry.rb +243 -0
- data/lib/adwords4r/v11/AdGroupService.rb +257 -0
- data/lib/adwords4r/v11/AdGroupServiceDriver.rb +109 -0
- data/lib/adwords4r/v11/AdGroupServiceMappingRegistry.rb +276 -0
- data/lib/adwords4r/v11/AdService.rb +760 -0
- data/lib/adwords4r/v11/AdServiceDriver.rb +125 -0
- data/lib/adwords4r/v11/AdServiceMappingRegistry.rb +807 -0
- data/lib/adwords4r/v11/CampaignService.rb +443 -0
- data/lib/adwords4r/v11/CampaignServiceDriver.rb +125 -0
- data/lib/adwords4r/v11/CampaignServiceMappingRegistry.rb +564 -0
- data/lib/adwords4r/v11/CriterionService.rb +442 -0
- data/lib/adwords4r/v11/CriterionServiceDriver.rb +117 -0
- data/lib/adwords4r/v11/CriterionServiceMappingRegistry.rb +507 -0
- data/lib/adwords4r/v11/InfoService.rb +242 -0
- data/lib/adwords4r/v11/InfoServiceDriver.rb +109 -0
- data/lib/adwords4r/v11/InfoServiceMappingRegistry.rb +228 -0
- data/lib/adwords4r/v11/KeywordToolService.rb +205 -0
- data/lib/adwords4r/{v5 → v11}/KeywordToolServiceDriver.rb +18 -12
- data/lib/adwords4r/v11/KeywordToolServiceMappingRegistry.rb +227 -0
- data/lib/adwords4r/v11/ReportService.rb +322 -0
- data/lib/adwords4r/v11/ReportServiceDriver.rb +101 -0
- data/lib/adwords4r/v11/ReportServiceMappingRegistry.rb +298 -0
- data/lib/adwords4r/v11/SiteSuggestionService.rb +242 -0
- data/lib/adwords4r/v11/SiteSuggestionServiceDriver.rb +77 -0
- data/lib/adwords4r/v11/SiteSuggestionServiceMappingRegistry.rb +271 -0
- data/lib/adwords4r/v11/TrafficEstimatorService.rb +312 -0
- data/lib/adwords4r/v11/TrafficEstimatorServiceDriver.rb +77 -0
- data/lib/adwords4r/v11/TrafficEstimatorServiceMappingRegistry.rb +483 -0
- metadata +96 -74
- data/lib/adwords4r/v4/AccountService.rb +0 -709
- data/lib/adwords4r/v4/AccountServiceDriver.rb +0 -174
- data/lib/adwords4r/v4/AdGroupService.rb +0 -316
- data/lib/adwords4r/v4/AdGroupServiceDriver.rb +0 -97
- data/lib/adwords4r/v4/CampaignService.rb +0 -527
- data/lib/adwords4r/v4/CampaignServiceDriver.rb +0 -111
- data/lib/adwords4r/v4/CreativeService.rb +0 -368
- data/lib/adwords4r/v4/CreativeServiceDriver.rb +0 -104
- data/lib/adwords4r/v4/CriterionService.rb +0 -411
- data/lib/adwords4r/v4/CriterionServiceDriver.rb +0 -97
- data/lib/adwords4r/v4/InfoService.rb +0 -260
- data/lib/adwords4r/v4/InfoServiceDriver.rb +0 -90
- data/lib/adwords4r/v4/KeywordService.rb +0 -543
- data/lib/adwords4r/v4/KeywordServiceDriver.rb +0 -125
- data/lib/adwords4r/v4/KeywordToolService.rb +0 -227
- data/lib/adwords4r/v4/KeywordToolServiceDriver.rb +0 -55
- data/lib/adwords4r/v4/ReportService.rb +0 -575
- data/lib/adwords4r/v4/ReportServiceDriver.rb +0 -83
- data/lib/adwords4r/v4/TrafficEstimatorService.rb +0 -274
- data/lib/adwords4r/v4/TrafficEstimatorServiceDriver.rb +0 -62
- data/lib/adwords4r/v5/AccountService.rb +0 -853
- data/lib/adwords4r/v5/AccountServiceDriver.rb +0 -188
- data/lib/adwords4r/v5/AdGroupService.rb +0 -352
- data/lib/adwords4r/v5/AdGroupServiceDriver.rb +0 -97
- data/lib/adwords4r/v5/CampaignService.rb +0 -563
- data/lib/adwords4r/v5/CampaignServiceDriver.rb +0 -111
- data/lib/adwords4r/v5/CreativeService.rb +0 -404
- data/lib/adwords4r/v5/CreativeServiceDriver.rb +0 -104
- data/lib/adwords4r/v5/CriterionService.rb +0 -447
- data/lib/adwords4r/v5/CriterionServiceDriver.rb +0 -97
- data/lib/adwords4r/v5/InfoService.rb +0 -296
- data/lib/adwords4r/v5/InfoServiceDriver.rb +0 -90
- data/lib/adwords4r/v5/KeywordToolService.rb +0 -263
- data/lib/adwords4r/v5/ReportService.rb +0 -788
- data/lib/adwords4r/v5/ReportServiceDriver.rb +0 -83
- data/lib/adwords4r/v5/TrafficEstimatorService.rb +0 -310
- data/lib/adwords4r/v5/TrafficEstimatorServiceDriver.rb +0 -62
- data/lib/adwords4r/v6/AccountService.rb +0 -853
- data/lib/adwords4r/v6/AccountServiceDriver.rb +0 -188
- data/lib/adwords4r/v6/AdGroupService.rb +0 -352
- data/lib/adwords4r/v6/AdGroupServiceDriver.rb +0 -97
- data/lib/adwords4r/v6/CampaignService.rb +0 -563
- data/lib/adwords4r/v6/CampaignServiceDriver.rb +0 -111
- data/lib/adwords4r/v6/CreativeService.rb +0 -472
- data/lib/adwords4r/v6/CreativeServiceDriver.rb +0 -111
- data/lib/adwords4r/v6/CriterionService.rb +0 -447
- data/lib/adwords4r/v6/CriterionServiceDriver.rb +0 -97
- data/lib/adwords4r/v6/InfoService.rb +0 -343
- data/lib/adwords4r/v6/InfoServiceDriver.rb +0 -97
- data/lib/adwords4r/v6/KeywordToolService.rb +0 -263
- data/lib/adwords4r/v6/ReportServiceDriver.rb +0 -83
- data/lib/adwords4r/v6/TrafficEstimatorService.rb +0 -310
- data/lib/adwords4r/v6/TrafficEstimatorServiceDriver.rb +0 -62
data/Authors.txt
CHANGED
data/ChangeLog.txt
CHANGED
@@ -1,4 +1,21 @@
|
|
1
|
-
|
1
|
+
11.0.0
|
2
|
+
- Jeffrey Posnick (jeffy@google.com) takes over as maintainer of this project
|
3
|
+
- added support for AdWords API v11
|
4
|
+
- removed support for AdWords API v9
|
5
|
+
- added support for the ADWORDS4R_DEBUG environment variable--if set to TRUE, SOAP logs will be written to the current directory when the API is used
|
6
|
+
|
7
|
+
1.0
|
8
|
+
- added support for API v10
|
9
|
+
- removed support for APIs v6, v7 and v8
|
10
|
+
- used soap4r v1.5.6 to generate the API files from the WSDL
|
11
|
+
- added soap4r v1.5.6 and http-access2 v2.0.5 as gem dependencies
|
12
|
+
- cleaned up some of the kludges that were needed for older soap4r libraries
|
13
|
+
0.8
|
14
|
+
- Ryan Leavengood takes over as maintainer of this project
|
15
|
+
- added support for APIs v7, v8 and v9
|
16
|
+
- removed support for v4 and v5
|
17
|
+
- updated the examples amd made it so they will use the adwords4r in their parent directory
|
18
|
+
0.7
|
2
19
|
- added support for API v6
|
3
20
|
- uncommented clientEmail in sample property file
|
4
21
|
0.6
|
data/Rakefile
CHANGED
@@ -1,35 +1,26 @@
|
|
1
|
-
require 'wsdl/soap/wsdl2ruby'
|
2
|
-
require 'net/https'
|
3
1
|
require 'fileutils'
|
4
|
-
require '
|
2
|
+
require 'net/https'
|
5
3
|
require 'logger'
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
nil
|
17
|
-
end
|
4
|
+
require 'rake/clean'
|
5
|
+
|
6
|
+
require 'rubygems'
|
7
|
+
gem 'rake'
|
8
|
+
require 'rake/gempackagetask'
|
9
|
+
gem 'soap4r'
|
10
|
+
require 'wsdl/soap/wsdl2ruby'
|
11
|
+
require 'xsd/codegen/classdef'
|
12
|
+
|
13
|
+
require 'lib/adwords4r/services'
|
18
14
|
|
19
15
|
# Determine the current version of the software
|
20
16
|
|
21
17
|
CLOBBER.include('pkg')
|
22
18
|
|
23
|
-
CURRENT_VERSION = '0.
|
19
|
+
CURRENT_VERSION = '11.0.2'
|
24
20
|
PKG_VERSION = ENV['REL'] ? ENV['REL'] : CURRENT_VERSION
|
25
21
|
|
26
22
|
SRC_RB = FileList['lib/**/*.rb']
|
27
23
|
|
28
|
-
# The default task is run if rake is given no explicit arguments.
|
29
|
-
|
30
|
-
#desc "Default Task"
|
31
|
-
#task :default => :test_all
|
32
|
-
|
33
24
|
WSDLDIR = 'wsdl'
|
34
25
|
LIBDIR = 'lib'
|
35
26
|
GENDIR = LIBDIR + '/adwords4r'
|
@@ -68,6 +59,7 @@ task :generate do
|
|
68
59
|
worker.opt.update(getWsdlOpt(name))
|
69
60
|
worker.run
|
70
61
|
fixImport(v, File.join(gendir, "#{name}Driver.rb"))
|
62
|
+
fixImport(v, File.join(gendir, "#{name}MappingRegistry.rb"))
|
71
63
|
fixImport(v, File.join(gendir, "#{name}.rb"))
|
72
64
|
end
|
73
65
|
end
|
@@ -78,33 +70,28 @@ def fixImport(version, file)
|
|
78
70
|
tempfile = file + '.tmp'
|
79
71
|
outfile = File.new(tempfile,"w")
|
80
72
|
File.open(file, "r") do |infile|
|
81
|
-
outfile.puts "module AdWords"
|
82
|
-
#outfile.puts "module AdWordsV#{version}"
|
83
73
|
infile.each do |l|
|
84
|
-
if (l
|
85
|
-
|
86
|
-
outfile.puts l.gsub(/require \'(.*)Service.rb\'/, 'require \'adwords4r/' + vname + '/\1Service\'')
|
74
|
+
if (l =~ /require.*Service.*\.rb/) then
|
75
|
+
outfile.puts l.gsub(/require '(.*)Service(.*)\.rb'/, "require 'adwords4r/#{vname}/\\1Service\\2'")
|
87
76
|
else
|
88
77
|
outfile.puts l
|
89
78
|
end
|
90
79
|
end
|
91
|
-
outfile.puts "end"
|
92
80
|
end
|
93
81
|
outfile.close
|
94
82
|
File.rename(tempfile, file)
|
95
83
|
end
|
96
84
|
|
97
|
-
|
98
85
|
def getWsdlOpt(s)
|
99
86
|
optcmd= {}
|
100
87
|
s << "Service"
|
101
88
|
optcmd['classdef'] = s
|
102
|
-
#should work but doesn't, driver name is derived from classname
|
103
|
-
#if you specify both it breaks, same thing for client_skelton
|
104
|
-
#optcmd['driver'] = s
|
105
|
-
optcmd['driver'] = nil
|
106
|
-
#optcmd['client_skelton'] = nil
|
107
89
|
optcmd['force'] = true
|
90
|
+
optcmd['mapping_registry'] = true
|
91
|
+
optcmd['driver'] = nil
|
92
|
+
|
93
|
+
# Causes soap4r to wrap the classes it outputs into the given modules
|
94
|
+
optcmd['module_path'] = ['AdWords', s]
|
108
95
|
return optcmd
|
109
96
|
end
|
110
97
|
|
@@ -155,12 +142,12 @@ PKG_FILES = FileList[
|
|
155
142
|
'scripts/**/*.rb'
|
156
143
|
]
|
157
144
|
|
158
|
-
puts PKG_FILES
|
145
|
+
#puts PKG_FILES
|
159
146
|
|
160
147
|
PKG_FILES.exclude(/\._/)
|
161
148
|
|
162
149
|
if ! defined?(Gem)
|
163
|
-
puts "Package Target requires
|
150
|
+
puts "Package Target requires RubyGems"
|
164
151
|
else
|
165
152
|
spec = Gem::Specification.new do |s|
|
166
153
|
|
@@ -173,9 +160,8 @@ else
|
|
173
160
|
Adwords4r provides an easy to use way to access the AdWords API in ruby.\
|
174
161
|
Currently the following AdWords API versions are supported:\
|
175
162
|
\
|
176
|
-
*
|
177
|
-
*
|
178
|
-
* V6\
|
163
|
+
* V10\
|
164
|
+
* V11\
|
179
165
|
}
|
180
166
|
|
181
167
|
s.files = PKG_FILES.to_a
|
@@ -192,18 +178,17 @@ Currently the following AdWords API versions are supported:\
|
|
192
178
|
# '--main' << 'README' <<
|
193
179
|
# '--line-numbers'
|
194
180
|
|
195
|
-
s.author = "Patrick Chanezon"
|
196
|
-
s.email = "
|
197
|
-
s.homepage = "http://rubyforge.org/projects/
|
198
|
-
s.requirements << 'soap4r
|
199
|
-
s.requirements << '
|
200
|
-
s.rubyforge_project = '
|
181
|
+
s.author = "Jeffrey Posnick, Patrick Chanezon, Ryan Leavengood"
|
182
|
+
s.email = "jeffy@google.com"
|
183
|
+
s.homepage = "http://rubyforge.org/projects/google4r/"
|
184
|
+
s.requirements << 'soap4r v1.5.6 or greater'
|
185
|
+
s.requirements << 'httpclient v2.1.2 or greater'
|
186
|
+
s.rubyforge_project = 'google4r'
|
187
|
+
s.add_dependency('soap4r', '>= 1.5.6')
|
188
|
+
s.add_dependency('httpclient', '>= 2.1.2')
|
201
189
|
end
|
202
190
|
|
203
|
-
|
204
|
-
|
205
|
-
|
191
|
+
Rake::GemPackageTask.new(spec) do |t|
|
192
|
+
t.need_tar = true
|
193
|
+
end
|
206
194
|
end
|
207
|
-
|
208
|
-
#require 'scripts/publish'
|
209
|
-
|
data/Readme.txt
CHANGED
@@ -1,19 +1,31 @@
|
|
1
|
-
|
2
|
-
|
1
|
+
Google adwwords4r Library
|
2
|
+
-------------------------
|
3
3
|
|
4
|
-
Welcome to adwords4r
|
4
|
+
Welcome to adwords4r: Bringing the delights of ruby programming to the AdWords world!
|
5
5
|
|
6
|
-
|
6
|
+
AdWords::API.new.getAllAdWordsCampaigns(123).each {|c| puts c.name}
|
7
7
|
|
8
|
-
|
8
|
+
Documentation and comments are a work in progress.
|
9
|
+
|
10
|
+
|
11
|
+
Useful Web Resources
|
12
|
+
--------------------
|
13
|
+
|
14
|
+
- AdWords home: https://adwords.google.com/
|
15
|
+
- The AdWords API main documentation: http://www.google.com/apis/adwords/developer/index.html
|
16
|
+
- This project's Google Code page: http://code.google.com/p/google-api-adwords-ruby/
|
17
|
+
|
18
|
+
|
19
|
+
Docs for Users
|
9
20
|
--------------
|
10
21
|
|
11
22
|
adwords4r is a ruby gem. See http://docs.rubygems.org/read/book/1
|
23
|
+
|
12
24
|
Install it using the gem install command.
|
13
25
|
> gem install --remote adwords4r
|
14
26
|
|
15
27
|
Requirements are:
|
16
|
-
s.requirements << 'soap4r v 1.5.
|
28
|
+
s.requirements << 'soap4r v 1.5.6 or greater'
|
17
29
|
s.requirements << 'http-access2 v 2.0.5 or greater'
|
18
30
|
(see gem file for details)
|
19
31
|
|
@@ -45,7 +57,7 @@ adwords = AdWords::API.new(credentials, version)
|
|
45
57
|
|
46
58
|
In order to use the sandbox, you can add a credential named
|
47
59
|
alternateUrl, like:
|
48
|
-
alternateUrl=https://sandbox.google.com/api/adwords/
|
60
|
+
alternateUrl=https://sandbox.google.com/api/adwords/v11/
|
49
61
|
|
50
62
|
Then just use methods of the API against your driver.
|
51
63
|
adwords.getAllAdWordsCampaigns(123).each {|c| puts c.name}
|
@@ -57,8 +69,15 @@ Many: warning: already initialized constant XXX
|
|
57
69
|
A few: at depth 0 - 20: unable to get local issuer certificate
|
58
70
|
These are not serious: I need to make them go but they do not affect the correctness of the program.
|
59
71
|
|
60
|
-
|
72
|
+
It is often useful to see a trace of the raw SOAP XML being sent and received.
|
73
|
+
To enable this, set the ADWORDS4R_DEBUG environment variable to TRUE.
|
74
|
+
e.g. in the bash shell, 'export ADWORDS4R_DEBUG=TRUE'
|
75
|
+
The SOAP logs will be written to the current directory.
|
76
|
+
|
77
|
+
|
78
|
+
Docs for Developers
|
61
79
|
-------------------
|
80
|
+
|
62
81
|
rake getwsdl
|
63
82
|
to get the wsdl files
|
64
83
|
rake generate
|
@@ -79,6 +98,4 @@ CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
|
|
79
98
|
GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
80
99
|
HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
81
100
|
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
|
82
|
-
THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
83
|
-
|
84
|
-
It is fun to use adwords4r anyway...
|
101
|
+
THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
data/Todo.txt
CHANGED
@@ -18,12 +18,4 @@ SOAP::Property.loadproperty("adwords.properties")'
|
|
18
18
|
- pass in a hash for complex objects
|
19
19
|
- comments everywhere, rdoc
|
20
20
|
- documentation
|
21
|
-
- more samples: traffic_estimator, report,
|
22
|
-
|
23
|
-
OK- generate v4
|
24
|
-
OK- get rid of yaml dependency
|
25
|
-
OK- change the property file name to adwords.properties
|
26
|
-
OK- make it work with all generated classes in their own module
|
27
|
-
OK- fix bug in InfoService
|
28
|
-
OK- gem file
|
29
|
-
OK- traditional setup file
|
21
|
+
- more samples: traffic_estimator, report,
|
data/adwords.properties
CHANGED
@@ -1,7 +1,7 @@
|
|
1
|
-
token=
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
alternateUrl=https://sandbox.google.com/api/adwords/
|
1
|
+
token=DEVELOPER_TOKEN
|
2
|
+
applicationToken=APPLICATION_TOKEN
|
3
|
+
useragent=APPLICATION_NAME
|
4
|
+
password=ADWORDS_PASSWORD
|
5
|
+
email=ADWORDS_MCC_LOGIN
|
6
|
+
clientEmail=OPTIONAL_CLIENT_LOGIN
|
7
|
+
#alternateUrl=https://sandbox.google.com/api/adwords/v11/
|
data/examples/campaign.rb
CHANGED
@@ -1,7 +1,9 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
+
# Use adwords4r in parent dir
|
4
|
+
$LOAD_PATH.unshift '../lib/'
|
5
|
+
|
3
6
|
require 'adwords4r'
|
4
|
-
require 'pp'
|
5
7
|
|
6
8
|
SEP = "---"
|
7
9
|
|
@@ -20,14 +22,14 @@ end
|
|
20
22
|
begin
|
21
23
|
adwords = AdWords::API.new
|
22
24
|
|
23
|
-
res = adwords.getAllAdWordsCampaigns(123)
|
25
|
+
res = adwords.getAllAdWordsCampaigns(123).getAllAdWordsCampaignsReturn
|
24
26
|
res.each {|c| puts dumpObj(c)}
|
25
|
-
|
27
|
+
|
26
28
|
c = AdWords::Campaign.new
|
27
29
|
c.dailyBudget = 10000
|
28
30
|
c.status = 'Paused'
|
29
|
-
c.name = "Test
|
30
|
-
c.endDay = SOAP::SOAPDate.new("
|
31
|
+
c.name = "Test Campaign #{rand(10000)}"
|
32
|
+
c.endDay = SOAP::SOAPDate.new("2010-01-01")
|
31
33
|
puts dumpObj(adwords.addCampaign(c).addCampaignReturn)
|
32
34
|
|
33
35
|
rescue AdWords::Error::UnknownAPICall => e
|
data/examples/framework.rb
CHANGED
data/examples/get_unit_count.rb
CHANGED
@@ -1,11 +1,16 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
+
# Use adwords4r in parent dir
|
4
|
+
$LOAD_PATH.unshift '../lib/'
|
5
|
+
|
3
6
|
require 'adwords4r'
|
4
|
-
require 'pp'
|
5
7
|
|
6
8
|
begin
|
7
9
|
adwords = AdWords::API.new
|
8
|
-
|
10
|
+
# Get the units for the last month or so
|
11
|
+
end_date = Date.today
|
12
|
+
start_date = end_date - 31
|
13
|
+
puts "result = #{adwords.getUnitCount(start_date, end_date).getUnitCountReturn}"
|
9
14
|
|
10
15
|
rescue AdWords::Error::UnknownAPICall => e
|
11
16
|
puts e
|
@@ -1,5 +1,8 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
+
# Use adwords4r in parent dir
|
4
|
+
$LOAD_PATH.unshift '../lib/'
|
5
|
+
|
3
6
|
require 'adwords4r'
|
4
7
|
|
5
8
|
def printkw(kw, gname)
|
@@ -7,8 +10,8 @@ def printkw(kw, gname)
|
|
7
10
|
end
|
8
11
|
|
9
12
|
begin
|
10
|
-
if (ARGV.length < 1)
|
11
|
-
puts "
|
13
|
+
if (ARGV.length < 1)
|
14
|
+
puts "Usage: #$0 <url>"
|
12
15
|
exit
|
13
16
|
end
|
14
17
|
adwords = AdWords::API.new
|
@@ -1,7 +1,9 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
+
# Use adwords4r in parent dir
|
4
|
+
$LOAD_PATH.unshift '../lib/'
|
5
|
+
|
3
6
|
require 'adwords4r'
|
4
|
-
require 'pp'
|
5
7
|
|
6
8
|
SEP = "---"
|
7
9
|
|
@@ -20,7 +22,8 @@ end
|
|
20
22
|
begin
|
21
23
|
adwords = AdWords::API.new
|
22
24
|
|
23
|
-
res = adwords.estimateKeywordList(
|
25
|
+
res = adwords.estimateKeywordList(
|
26
|
+
[AdWords::KeywordRequest.new(nil, 50000, false, 'flowers', 'Broad')]).estimateKeywordListReturn
|
24
27
|
res.each {|c| puts dumpObj(c)}
|
25
28
|
|
26
29
|
rescue AdWords::Error::UnknownAPICall => e
|
data/lib/adwords4r.rb
CHANGED
@@ -1,162 +1,172 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
begin
|
3
|
+
gem 'soap4r'
|
4
|
+
rescue
|
5
|
+
require_gem 'soap4r'
|
6
|
+
end
|
1
7
|
require 'soap/soap'
|
8
|
+
require 'soap/mapping'
|
2
9
|
require 'adwords4r/credentials'
|
3
10
|
require 'adwords4r/services'
|
4
11
|
|
12
|
+
# Fix an issue with SOAPDate. Google complains if the dates have any timezone
|
13
|
+
# info in them. There are probably better ways to fix this.
|
14
|
+
module SOAP
|
15
|
+
class SOAPDate
|
16
|
+
def of2tz(offset)
|
17
|
+
diffmin = offset * 24 * 60
|
18
|
+
if diffmin.zero?
|
19
|
+
''
|
20
|
+
else
|
21
|
+
((diffmin < 0) ? '-' : '+') << format('%02d:%02d',
|
22
|
+
(diffmin.abs / 60.0).to_i, (diffmin.abs % 60.0).to_i)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
5
28
|
module AdWords
|
6
29
|
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
30
|
+
class API
|
31
|
+
attr_reader :credentials, :drivers, :version
|
32
|
+
@methodMap = Hash.new
|
33
|
+
|
34
|
+
def initialize(credentials = AdWordsCredentials.new, version = Service.getVersions.sort.last)
|
35
|
+
@credentials, @version = credentials, version
|
36
|
+
@drivers = Hash.new
|
37
|
+
prepareDrivers
|
38
|
+
end
|
39
|
+
|
40
|
+
def method_missing(m, *args)
|
41
|
+
methodName = m.id2name
|
42
|
+
requestName = AdWords::fix_case_up(m.id2name) # upper first character
|
43
|
+
if valid_call?(methodName)
|
44
|
+
driver = getDriver(methodName)
|
45
|
+
moduleName = driver.class.name.split("::")[0..-2].join("::")
|
46
|
+
constructor = eval("#{moduleName}::#{requestName}.method('new')")
|
47
|
+
req = constructor.call(*args)
|
48
|
+
return driver.send(methodName, req)
|
49
|
+
else
|
50
|
+
raise(Error::UnknownAPICall, "Unknown API Call: #{requestName}", caller)
|
51
|
+
end
|
52
|
+
# Handle AdWords Application-level error
|
53
|
+
rescue SOAP::FaultError => fault
|
54
|
+
raise(Error::ApiError.new(fault), "#{methodName} Call Failed: #{fault.faultstring.to_s}", caller)
|
55
|
+
end
|
56
|
+
|
57
|
+
def prepareDrivers()
|
58
|
+
Service.doRequire(@version)
|
59
|
+
Service.getServices(@version).each {|s| @drivers[s] = prepareDriver(s)}
|
60
|
+
@methodMap = Service.getMethodMap(@drivers)
|
61
|
+
end
|
62
|
+
|
63
|
+
#pass in call name, get the driver back
|
64
|
+
def getDriver(call)
|
65
|
+
return @methodMap[call]
|
66
|
+
end
|
67
|
+
|
68
|
+
def prepareDriver(s)
|
69
|
+
# Include the module for this service
|
70
|
+
AdWords.class_eval("include #{s}Service")
|
71
|
+
|
72
|
+
#set alternateurl if it has been set in credentials
|
73
|
+
if (@credentials.alternateUrl) then
|
74
|
+
endpointUrl = @credentials.alternateUrl + s + 'Service'
|
75
|
+
driver = eval("AdWords::#{getServiceName(s)}.new(\"#{endpointUrl}\")")
|
76
|
+
elsif
|
77
|
+
driver = eval("AdWords::#{getServiceName(s)}.new")
|
78
|
+
end
|
79
|
+
@credentials.handlers.each {|h| driver.headerhandler << h}
|
80
|
+
|
81
|
+
if ENV['ADWORDS4R_DEBUG'].upcase == 'TRUE'
|
82
|
+
driver.wiredump_file_base = "SOAP_#{$$}"
|
83
|
+
end
|
84
|
+
|
85
|
+
driver.options['protocol.http.ssl_config.verify_mode'] = nil
|
86
|
+
#set driver.proxy if you are behing a proxy
|
87
|
+
return driver
|
88
|
+
end
|
89
|
+
|
90
|
+
def getServiceName(s)
|
91
|
+
s + "Interface"
|
92
|
+
end
|
93
|
+
|
94
|
+
def valid_call?(call)
|
95
|
+
return @methodMap.has_key?(call)
|
96
|
+
end
|
97
|
+
|
98
|
+
end
|
99
|
+
|
100
|
+
class Error
|
101
|
+
class Error < StandardError; end
|
102
|
+
|
103
|
+
# Raised if a call is made to a method that does not exist in the AdWords SOAP API
|
104
|
+
class UnknownAPICall < Error; end
|
105
|
+
|
106
|
+
# Raised if an attempt is made to instantiate a type that does not exist in the AdWords SOAP API
|
107
|
+
class UnknownType < Error; end
|
108
|
+
|
109
|
+
# Raised if a call returns with a SOAP error, gives you easy access to adwords error fields
|
110
|
+
class ApiError < Error
|
111
|
+
|
112
|
+
attr_accessor :soap_faultcode
|
113
|
+
attr_accessor :soap_faultstring
|
114
|
+
attr_accessor :top_code
|
115
|
+
attr_accessor :internal
|
116
|
+
attr_accessor :message
|
117
|
+
attr_accessor :code
|
118
|
+
attr_accessor :detail
|
119
|
+
attr_accessor :field
|
120
|
+
attr_accessor :index
|
121
|
+
attr_accessor :isExemptable
|
122
|
+
attr_accessor :textIndex
|
123
|
+
attr_accessor :textLength
|
124
|
+
attr_accessor :trigger
|
125
|
+
|
126
|
+
def initialize(soap_fault)
|
127
|
+
@soap_faultcode = protect { soap_fault.faultcode }
|
128
|
+
@soap_faultstring = protect { soap_fault.faultstring }
|
129
|
+
if protect { soap_fault.detail and soap_fault.detail.fault }
|
130
|
+
fault = soap_fault.detail.fault
|
131
|
+
@top_code = protect { fault.code }
|
132
|
+
@internal = protect { fault.internal }
|
133
|
+
@message = protect { fault.message }
|
134
|
+
if protect { fault.errors and fault.errors.size > 0 }
|
135
|
+
error = fault.errors.first
|
136
|
+
@code = protect { error.code }
|
137
|
+
@detail = protect { error.detail }
|
138
|
+
@field = protect { error.field }
|
139
|
+
@index = protect { error.index }
|
140
|
+
@isExemptable = protect { error.isExemptable }
|
141
|
+
@textIndex = protect { error.textIndex }
|
142
|
+
@textLength = protect { error.textLength }
|
143
|
+
@trigger = protect { error.trigger }
|
59
144
|
end
|
60
|
-
}
|
61
|
-
|
62
|
-
SOAP::Mapping.module_eval(a)
|
63
145
|
end
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
def getDriver(call)
|
73
|
-
return @methodMap[call]
|
74
|
-
end
|
75
|
-
|
76
|
-
def prepareDriver(s)
|
77
|
-
#driver = eval("AdWordsV#{@version}::#{getServiceName(s)}.new")
|
78
|
-
#set alternateurl if it has been set in credentials
|
79
|
-
if (@credentials.alternateUrl) then
|
80
|
-
endpointUrl = @credentials.alternateUrl + s + 'Service'
|
81
|
-
driver = eval("#{getServiceName(s)}.new(\"#{endpointUrl}\")")
|
82
|
-
elsif
|
83
|
-
driver = eval("#{getServiceName(s)}.new")
|
84
|
-
end
|
85
|
-
@credentials.handlers.each {|h| driver.headerhandler << h}
|
86
|
-
#driver.wiredump_dev = STDOUT if @debug
|
87
|
-
driver.wiredump_file_base = "log"
|
88
|
-
driver.options['protocol.http.ssl_config.verify_mode'] = nil
|
89
|
-
#set driver.proxy if you are behing a proxy
|
90
|
-
return driver
|
91
|
-
end
|
92
|
-
|
93
|
-
#workaround the bug: some services do not follow the naming convention
|
94
|
-
def getServiceName(s)
|
95
|
-
if s == "TrafficEstimator" then "TrafficEstimatorInterface"
|
96
|
-
elsif s == "Report" then "ReportServiceInterface"
|
97
|
-
elsif s == "Info" then "InfoServiceInterface"
|
98
|
-
elsif s == "KeywordTool" then "KeywordToolInterface"
|
99
|
-
else (s + "Service")
|
100
|
-
end
|
101
|
-
end
|
102
|
-
|
103
|
-
def valid_call?(call)
|
104
|
-
return @methodMap.has_key?(call)
|
146
|
+
end
|
147
|
+
|
148
|
+
private
|
149
|
+
def protect(&block)
|
150
|
+
begin
|
151
|
+
block.call
|
152
|
+
rescue
|
153
|
+
nil
|
105
154
|
end
|
106
|
-
|
155
|
+
end
|
107
156
|
end
|
157
|
+
end
|
108
158
|
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
# Raised if a call is made to a method that does not exist in the AdWords SOAP API
|
116
|
-
class UnknownAPICall < Error; end
|
117
|
-
|
118
|
-
# Raised if an attempt is made to instantiate a type that does not exist in the AdWords SOAP API
|
119
|
-
class UnknownType < Error; end
|
120
|
-
|
121
|
-
# Raised if a call returns with a SOAP error, gives you easy access to adwords error fields
|
122
|
-
class ApiError < Error
|
123
|
-
|
124
|
-
attr_accessor :soap_faultcode
|
125
|
-
attr_accessor :soap_faultstring
|
126
|
-
attr_accessor :code
|
127
|
-
attr_accessor :internal
|
128
|
-
attr_accessor :message
|
129
|
-
attr_accessor :trigger
|
130
|
-
attr_accessor :violations
|
131
|
-
|
132
|
-
def initialize(fault)
|
133
|
-
@soap_faultcode = getOrNil(fault, 'faultcode')
|
134
|
-
@soap_faultstring = getOrNil(fault, 'faultstring')
|
135
|
-
@code = getOrNil(fault.detail, 'code')
|
136
|
-
@internal = getOrNil(fault.detail,'internal')
|
137
|
-
@message = getOrNil(fault.detail,'message')
|
138
|
-
@trigger = getOrNil(fault.detail,'trigger')
|
139
|
-
@violations = getOrNil(fault.detail,'violations')
|
140
|
-
end
|
141
|
-
|
142
|
-
private
|
143
|
-
def getOrNil(obj, meth)
|
144
|
-
obj.respond_to?(meth) ? eval("obj.#{meth}") : nil
|
145
|
-
end
|
146
|
-
end
|
159
|
+
# These class module methods are helper functions
|
160
|
+
class <<self
|
161
|
+
|
162
|
+
def fix_case_up(name)
|
163
|
+
name[0] = name[0, 1].upcase # upper first character
|
164
|
+
name
|
147
165
|
end
|
148
166
|
|
149
|
-
|
150
|
-
|
151
|
-
|
152
|
-
def fix_case_up(name)
|
153
|
-
name[0] = name[0,1].upcase # upper first character
|
154
|
-
name
|
155
|
-
end
|
156
|
-
|
157
|
-
def fix_case_down(name)
|
158
|
-
name[0] = name[0,1].downcase
|
159
|
-
name
|
160
|
-
end
|
167
|
+
def fix_case_down(name)
|
168
|
+
name[0] = name[0, 1].downcase
|
169
|
+
name
|
161
170
|
end
|
171
|
+
end
|
162
172
|
end
|