mygengo 1.0
Sign up to get free protection for your applications and to get access to all the features.
- data/README.md +52 -0
- data/Rakefile +10 -0
- data/lib/mygengo-ruby/api_handler.rb +286 -0
- data/lib/mygengo-ruby/mygengo_exception.rb +15 -0
- data/lib/mygengo.rb +16 -0
- data/licenses/LICENSE.txt +18 -0
- metadata +63 -0
data/README.md
ADDED
@@ -0,0 +1,52 @@
|
|
1
|
+
myGengo Ruby Library (for the [myGengo API](http://mygengo.com/))
|
2
|
+
========================================================================================================
|
3
|
+
Translating your tools and products helps people all over the world access them; this is, of course, a
|
4
|
+
somewhat tricky problem to solve. **[myGengo](http://mygengo.com/)** is a service that offers human-translation
|
5
|
+
(which is often a higher quality than machine translation), and an API to manage sending in work and watching
|
6
|
+
jobs. This is a ruby interface to make using the API simpler (some would say incredibly easy).
|
7
|
+
|
8
|
+
|
9
|
+
Installation & Requirements
|
10
|
+
-------------------------------------------------------------------------------------------------------
|
11
|
+
Installing myGengo is fairly simple:
|
12
|
+
|
13
|
+
gem install mygengo
|
14
|
+
|
15
|
+
|
16
|
+
Tests - Running Them, etc
|
17
|
+
------------------------------------------------------------------------------------------------------
|
18
|
+
myGengo has a full suite of tests, however they're not currently automated. Each script in the _examples_
|
19
|
+
directory tests a different myGengo API endpoint; run against those if you wish to test for now.
|
20
|
+
|
21
|
+
Question, Comments, Complaints, Praise?
|
22
|
+
------------------------------------------------------------------------------------------------------
|
23
|
+
If you have questions or comments and would like to reach us directly, please feel free to do
|
24
|
+
so at the following outlets. We love hearing from developers!
|
25
|
+
|
26
|
+
Email: ryan [at] mygengo dot com
|
27
|
+
Twitter: **[@mygengo_dev](http://twitter.com/mygengo_dev)**
|
28
|
+
|
29
|
+
If you come across any issues, please file them on the **[Github project issue tracker](https://github.com/myGengo/mygengo-ruby/issues)**. Thanks!
|
30
|
+
|
31
|
+
|
32
|
+
Documentation
|
33
|
+
------------------------------------------------------------------------------------------------------
|
34
|
+
The usage of the API is very simple - the most important part is getting authenticated. To do this is just
|
35
|
+
a few lines of code:
|
36
|
+
|
37
|
+
``` ruby
|
38
|
+
require 'mygengo'
|
39
|
+
|
40
|
+
mygengo = MyGengo::API.new({
|
41
|
+
:public_key => 'your_public_key',
|
42
|
+
:private_key => 'your_private_key',
|
43
|
+
:sandbox => true, # Or false, depending on your work
|
44
|
+
})
|
45
|
+
|
46
|
+
# Get some information
|
47
|
+
puts mygengo.getAccountBalance()
|
48
|
+
```
|
49
|
+
|
50
|
+
With that, you can call any number of methods supported by this library. The entire library is rdoc supported,
|
51
|
+
so you can look at more method information there - there's also a full suite of test code/examples, located in the 'examples'
|
52
|
+
directory. Good luck!
|
data/Rakefile
ADDED
@@ -0,0 +1,286 @@
|
|
1
|
+
# Encoding: UTF-8
|
2
|
+
|
3
|
+
require 'rubygems'
|
4
|
+
require 'net/http'
|
5
|
+
require 'uri'
|
6
|
+
require 'cgi'
|
7
|
+
require 'json'
|
8
|
+
require 'hmac-sha1'
|
9
|
+
require 'time'
|
10
|
+
|
11
|
+
module MyGengo
|
12
|
+
|
13
|
+
# The only real class that ever needs to be instantiated.
|
14
|
+
class API
|
15
|
+
attr_accessor :api_host
|
16
|
+
attr_accessor :debug
|
17
|
+
attr_accessor :client_info
|
18
|
+
|
19
|
+
# Creates a new API handler to shuttle calls/jobs/etc over to the myGengo translation API.
|
20
|
+
#
|
21
|
+
# Options:
|
22
|
+
# <tt>opts</tt> - A hash containing the api key, the api secret key, the API version (defaults to 1), whether to use
|
23
|
+
# the sandbox API, and an optional custom user agent to send.
|
24
|
+
def initialize(opts)
|
25
|
+
# Consider this an example of the object you need to pass.
|
26
|
+
@opts = {
|
27
|
+
:public_key => '',
|
28
|
+
:private_key => '',
|
29
|
+
:api_version => '1.1',
|
30
|
+
:sandbox => false,
|
31
|
+
:user_agent => "myGengo Ruby Library v#{MyGengo::Config::VERSION}",
|
32
|
+
:debug => false,
|
33
|
+
}.merge(opts)
|
34
|
+
|
35
|
+
# Let's go ahead and separate these out, for clarity...
|
36
|
+
@debug = @opts[:debug]
|
37
|
+
@api_host = (@opts[:sandbox] == true ? MyGengo::Config::SANDBOX_API_HOST : MyGengo::Config::API_HOST)
|
38
|
+
|
39
|
+
# More of a public "check this" kind of object.
|
40
|
+
@client_info = {"VERSION" => MyGengo::Config::VERSION}
|
41
|
+
end
|
42
|
+
|
43
|
+
# This is... hilariously awkward, but Ruby escapes things very differently from PHP/etc. This causes
|
44
|
+
# issues with de-escaping things on the backend over at myGengo; in the future this will become obsolete,
|
45
|
+
# but for now we'll just leave this here...
|
46
|
+
def urlencode(string)
|
47
|
+
string.gsub(/([^ a-zA-Z0-9_.-]+)/n) do
|
48
|
+
'%' + $1.unpack('H2' * $1.size).join('%').upcase
|
49
|
+
end.tr(' ', '+')
|
50
|
+
end
|
51
|
+
|
52
|
+
# Creates an HMAC::SHA1 signature, signing the timestamp with the private key.
|
53
|
+
def signature_of(pk, ts)
|
54
|
+
HMAC::SHA1.hexdigest @opts[:private_key], ts
|
55
|
+
end
|
56
|
+
|
57
|
+
# The "GET" method; handles requesting basic data sets from myGengo and converting
|
58
|
+
# the response to a Ruby hash/object.
|
59
|
+
#
|
60
|
+
# Options:
|
61
|
+
# <tt>endpoint</tt> - String/URL to request data from.
|
62
|
+
# <tt>params</tt> - Data necessary for request (keys, etc). Generally taken care of by the requesting instance.
|
63
|
+
def get_from_mygengo(endpoint, params = {})
|
64
|
+
# The first part of the object we're going to encode and use in our request to myGengo. The signing process
|
65
|
+
# is a little annoying at the moment, so bear with us...
|
66
|
+
query = {
|
67
|
+
:api_key => @opts[:public_key],
|
68
|
+
:ts => Time.now.gmtime.to_i.to_s
|
69
|
+
}
|
70
|
+
|
71
|
+
endpoint << "?api_sig=" + signature_of(query[:api_key], query[:ts])
|
72
|
+
endpoint << '&' + query.map { |k, v| "#{k}=#{urlencode(v)}" }.join('&')
|
73
|
+
|
74
|
+
resp = Net::HTTP.start(@api_host, 80) do |http|
|
75
|
+
http.request(Net::HTTP::Get.new("/v#{@opts[:api_version]}/" + endpoint, {
|
76
|
+
'Accept' => 'application/json',
|
77
|
+
'User-Agent' => @opts[:user_agent]
|
78
|
+
}))
|
79
|
+
end
|
80
|
+
|
81
|
+
json = JSON.parse(resp.body)
|
82
|
+
|
83
|
+
if json['opstat'] != 'ok'
|
84
|
+
raise MyGengo::Exception.new(json['opstat'], json['err']['code'].to_i, json['err']['msg'])
|
85
|
+
end
|
86
|
+
|
87
|
+
# Return it if there are no problems, nice...
|
88
|
+
json
|
89
|
+
end
|
90
|
+
|
91
|
+
# The "POST" method; handles shuttling up encoded job data to myGengo
|
92
|
+
# for translation and such. Somewhat similar to the above methods, but depending on the scenario
|
93
|
+
# can get some strange exceptions, so we're gonna keep them fairly separate for the time being. Consider
|
94
|
+
# for a merger down the road...
|
95
|
+
#
|
96
|
+
# Options:
|
97
|
+
# <tt>endpoint</tt> - String/URL to post data to.
|
98
|
+
# <tt>params</tt> - Data necessary for request (keys, etc). Generally taken care of by the requesting instance.
|
99
|
+
def send_to_mygengo(endpoint, params = {})
|
100
|
+
query = {
|
101
|
+
:api_key => @opts[:public_key],
|
102
|
+
:data => params.to_json.gsub('"', '\"'),
|
103
|
+
:ts => Time.now.gmtime.to_i.to_s
|
104
|
+
}
|
105
|
+
|
106
|
+
url = URI.parse("http://#{@api_host}/v#{@opts[:api_version]}/#{endpoint}")
|
107
|
+
http = Net::HTTP.new(url.host, url.port)
|
108
|
+
request = Net::HTTP::Post.new(url.path)
|
109
|
+
|
110
|
+
request.add_field('Accept', 'application/json')
|
111
|
+
request.add_field('User-Agent', @opts[:user_agent])
|
112
|
+
|
113
|
+
request.content_type = 'application/x-www-form-urlencoded'
|
114
|
+
request.body = {
|
115
|
+
"api_sig" => signature_of(query[:api_key], query[:ts]),
|
116
|
+
"api_key" => urlencode(@opts[:public_key]),
|
117
|
+
"data" => urlencode(params.to_json.gsub('\\', '\\\\')),
|
118
|
+
"ts" => Time.now.gmtime.to_i.to_s
|
119
|
+
}.map { |k, v| "#{k}=#{v}" }.flatten.join('&')
|
120
|
+
|
121
|
+
if @debug
|
122
|
+
http.set_debug_output($stdout)
|
123
|
+
end
|
124
|
+
|
125
|
+
resp = http.request(request)
|
126
|
+
|
127
|
+
case resp
|
128
|
+
when Net::HTTPSuccess, Net::HTTPRedirection
|
129
|
+
json = JSON.parse(resp.body)
|
130
|
+
|
131
|
+
if json['opstat'] != 'ok'
|
132
|
+
raise MyGengo::Exception.new(json['opstat'], json['err']['code'].to_i, json['err']['msg'])
|
133
|
+
end
|
134
|
+
|
135
|
+
# Return it if there are no problems, nice...
|
136
|
+
json
|
137
|
+
else
|
138
|
+
resp.error!
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
# Returns a Ruby-hash of the stats for the current account. No arguments required!
|
143
|
+
#
|
144
|
+
# Options:
|
145
|
+
# <tt>None</tt> - N/A
|
146
|
+
def getAccountStats(params = {})
|
147
|
+
self.get_from_mygengo('account/stats', params)
|
148
|
+
end
|
149
|
+
|
150
|
+
# Returns a Ruby-hash of the balance for the authenticated account. No args required!
|
151
|
+
#
|
152
|
+
# Options:
|
153
|
+
# <tt>None</tt> - N/A
|
154
|
+
def getAccountBalance(params = {})
|
155
|
+
self.get_from_mygengo('account/balance', params)
|
156
|
+
end
|
157
|
+
|
158
|
+
# Posts a translation job over to myGengo, returns a response indicating whether the submission was
|
159
|
+
# successful or not. Param list is quite expansive here, pay attention...
|
160
|
+
#
|
161
|
+
# Options:
|
162
|
+
# <tt>job</tt> - A job is a hash of data describing what you want translated. See the examples included for
|
163
|
+
# more information on what this should be. (type/slug/body_src/lc_src/lc_tgt/tier/auto_approve/comment/callback_url/custom_data)
|
164
|
+
def postTranslationJob(params = {})
|
165
|
+
self.send_to_mygengo('translate/job', params)
|
166
|
+
end
|
167
|
+
|
168
|
+
# Much like the above, but takes a hash titled "jobs" that is multiple jobs, each with their own unique key.
|
169
|
+
#
|
170
|
+
# Options:
|
171
|
+
# <tt>jobs</tt> - "Jobs" is a hash containing further hashes; each further hash is a job. This is best seen in the example code.
|
172
|
+
def postTranslationJobs(params = {})
|
173
|
+
self.send_to_mygengo('translate/jobs', params)
|
174
|
+
end
|
175
|
+
|
176
|
+
# Updates an already submitted job.
|
177
|
+
#
|
178
|
+
# Options:
|
179
|
+
# <tt>id</tt> - The ID of a job to update.
|
180
|
+
# <tt>action</tt> - A hash describing the update to this job. See the examples for further documentation.
|
181
|
+
def updateTranslationJob(params = {})
|
182
|
+
self.send_to_mygengo('translate/job/:id'.gsub(':id', params.delete(:id)), params)
|
183
|
+
end
|
184
|
+
|
185
|
+
# Given an ID, pulls down information concerning that job from myGengo.
|
186
|
+
#
|
187
|
+
# <tt>id</tt> - The ID of a job to check.
|
188
|
+
# <tt>pre_mt</tt> - Optional, get a machine translation if the human translation is not done.
|
189
|
+
def getTranslationJob(params = {})
|
190
|
+
self.get_from_mygengo('translate/job/:id'.gsub(':id', params.delete(:id)), params)
|
191
|
+
end
|
192
|
+
|
193
|
+
# Pulls down a list of recently submitted jobs, allows some filters.
|
194
|
+
#
|
195
|
+
# <tt>status</tt> - Optional. "unpaid", "available", "pending", "reviewable", "approved", "rejected", or "canceled".
|
196
|
+
# <tt>timestamp_after</tt> - Optional. Epoch timestamp from which to filter submitted jobs.
|
197
|
+
# <tt>count</tt> - Optional. Defaults to 10.
|
198
|
+
def getTranslationJobs(params = {})
|
199
|
+
self.get_from_mygengo('translate/jobs', params)
|
200
|
+
end
|
201
|
+
|
202
|
+
# Pulls a group of jobs that were previously submitted together.
|
203
|
+
#
|
204
|
+
# <tt>id</tt> - Required, the ID of a job that you want the batch/group of.
|
205
|
+
def getTranslationJobBatch(params = {})
|
206
|
+
self.get_from_mygengo('translate/jobs/:id'.gsub(':id', params.delete(:id)), params)
|
207
|
+
end
|
208
|
+
|
209
|
+
# Mirrors the bulk Translation call, but just returns an estimated cost.
|
210
|
+
def determineTranslationCost(params = {})
|
211
|
+
self.send_to_mygengo('translate/service/quote', params)
|
212
|
+
end
|
213
|
+
|
214
|
+
# Post a comment for a translator or myGengo on a job.
|
215
|
+
#
|
216
|
+
# Options:
|
217
|
+
# <tt>id</tt> - The ID of the job you're commenting on.
|
218
|
+
# <tt>comment</tt> - The comment to put on the job.
|
219
|
+
def postTranslationJobComment(params = {})
|
220
|
+
self.send_to_mygengo('translate/job/:id/comment'.gsub(':id', params.delete(:id)), params)
|
221
|
+
end
|
222
|
+
|
223
|
+
# Get all comments (the history) from a given job.
|
224
|
+
#
|
225
|
+
# Options:
|
226
|
+
# <tt>id</tt> - The ID of the job to get comments for.
|
227
|
+
def getTranslationJobComments(params = {})
|
228
|
+
self.get_from_mygengo('translate/job/:id/comments'.gsub(':id', params.delete(:id)), params)
|
229
|
+
end
|
230
|
+
|
231
|
+
# Returns the feedback you've submitted for a given job.
|
232
|
+
#
|
233
|
+
# Options:
|
234
|
+
# <tt>id</tt> - The ID of the translation job you're retrieving comments from.
|
235
|
+
def getTranslationJobFeedback(params = {})
|
236
|
+
self.get_from_mygengo('translate/job/:id/feedback'.gsub(':id', params.delete(:id)), params)
|
237
|
+
end
|
238
|
+
|
239
|
+
# Gets a list of the revision resources for a job. Revisions are created each time a translator updates the text.
|
240
|
+
#
|
241
|
+
# Options:
|
242
|
+
# <tt>id</tt> - The ID of the translation job you're getting revisions from.
|
243
|
+
def getTranslationJobRevisions(params = {})
|
244
|
+
self.get_from_mygengo('translate/job/:id/revisions'.gsub(':id', params.delete(:id)), params)
|
245
|
+
end
|
246
|
+
|
247
|
+
# Get a specific revision to a job.
|
248
|
+
#
|
249
|
+
# Options:
|
250
|
+
# <tt>id</tt> - The ID of the translation job you're getting revisions from.
|
251
|
+
# <tt>rev_id</tt> - The ID of the revision you're looking up.
|
252
|
+
def getTranslationJobRevision(params = {})
|
253
|
+
self.get_from_mygengo('translate/job/:id/revisions/:revision_id'.gsub(':id', params.delete(:id)).gsub(':rev_id', params.delete(:rev_id)), params)
|
254
|
+
end
|
255
|
+
|
256
|
+
# Returns a preview image for a job.
|
257
|
+
#
|
258
|
+
# Options:
|
259
|
+
# <tt>id</tt> - The ID of the job you want a preview image of.
|
260
|
+
def getTranslationJobPreviewImage(params = {})
|
261
|
+
self.get_from_mygengo('translate/job/:id/preview'.gsub(':id', params.delete(:id)), params)
|
262
|
+
end
|
263
|
+
|
264
|
+
# Deletes a job.
|
265
|
+
#
|
266
|
+
# Options:
|
267
|
+
# <tt>id</tt> - The ID of the job you want to delete.
|
268
|
+
def deleteTranslationJob(params = {})
|
269
|
+
self.send_to_mygengo('translate/job/:id'.gsub(':id', params.delete(:id)), params)
|
270
|
+
end
|
271
|
+
|
272
|
+
# Gets information about currently supported language pairs.
|
273
|
+
#
|
274
|
+
# Options:
|
275
|
+
# <tt>lc_src</tt> - Optional language code to filter on.
|
276
|
+
def getServiceLanguagePairs(params = {})
|
277
|
+
self.get_from_mygengo('translate/service/language_pairs', params)
|
278
|
+
end
|
279
|
+
|
280
|
+
# Pulls down currently supported languages.
|
281
|
+
def getServiceLanguages(params = {})
|
282
|
+
self.get_from_mygengo('translate/service/languages', params)
|
283
|
+
end
|
284
|
+
end
|
285
|
+
|
286
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module MyGengo
|
2
|
+
# Base Exception class and such.
|
3
|
+
class MyGengo::Exception < ::StandardError
|
4
|
+
attr_accessor :opstat, :code, :msg
|
5
|
+
|
6
|
+
# Pretty self explanatory stuff here...
|
7
|
+
def initialize(opstat, code, msg)
|
8
|
+
@opstat = opstat
|
9
|
+
@code = code
|
10
|
+
@msg = msg
|
11
|
+
|
12
|
+
puts msg
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
data/lib/mygengo.rb
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
require 'rubygems'
|
2
|
+
require 'mygengo-ruby/api_handler'
|
3
|
+
require 'mygengo-ruby/mygengo_exception'
|
4
|
+
|
5
|
+
module MyGengo
|
6
|
+
# Store global config objects here - e.g, urls, etc.
|
7
|
+
module Config
|
8
|
+
# API url endpoints; replace the version at function call time to
|
9
|
+
# allow for function-by-function differences in versioning.
|
10
|
+
API_HOST = 'api.mygengo.com'
|
11
|
+
SANDBOX_API_HOST = 'api.sandbox.mygengo.com'
|
12
|
+
|
13
|
+
# Pretty self explanatory.
|
14
|
+
VERSION = '1.1'
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
All code provided from the http://mygengo.com site, such as API example code and libraries, is provided under the New BSD license unless otherwise noted. Details are below.
|
2
|
+
|
3
|
+
New BSD License
|
4
|
+
Copyright (c) 2009-2011, myGengo, Inc.
|
5
|
+
All rights reserved.
|
6
|
+
|
7
|
+
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
|
8
|
+
|
9
|
+
Redistributions of source code must retain the above copyright notice,
|
10
|
+
this list of conditions and the following disclaimer.
|
11
|
+
Redistributions in binary form must reproduce the above copyright notice,
|
12
|
+
this list of conditions and the following disclaimer in the documentation
|
13
|
+
and/or other materials provided with the distribution.
|
14
|
+
Neither the name of myGengo, Inc. nor the names of its contributors may
|
15
|
+
be used to endorse or promote products derived from this software
|
16
|
+
without specific prior written permission.
|
17
|
+
|
18
|
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
metadata
ADDED
@@ -0,0 +1,63 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: mygengo
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
prerelease:
|
5
|
+
version: "1.0"
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Ryan McGrath <ryan@mygengo.com>
|
9
|
+
- Matthew Romaine
|
10
|
+
- Kim Alhstrom
|
11
|
+
autorequire:
|
12
|
+
bindir: bin
|
13
|
+
cert_chain: []
|
14
|
+
|
15
|
+
date: 2011-08-17 00:00:00 -04:00
|
16
|
+
default_executable:
|
17
|
+
dependencies: []
|
18
|
+
|
19
|
+
description: myGengo is a service that offers various translation APIs, both machine and high quality human-sourced. The mygengo gem lets you interface with the myGengo REST API (http://mygengo.com/services/api/dev-docs/).
|
20
|
+
email: ryan@mygengo.com
|
21
|
+
executables: []
|
22
|
+
|
23
|
+
extensions: []
|
24
|
+
|
25
|
+
extra_rdoc_files: []
|
26
|
+
|
27
|
+
files:
|
28
|
+
- lib/mygengo-ruby/api_handler.rb
|
29
|
+
- lib/mygengo-ruby/mygengo_exception.rb
|
30
|
+
- lib/mygengo.rb
|
31
|
+
- licenses/LICENSE.txt
|
32
|
+
- Rakefile
|
33
|
+
- README.md
|
34
|
+
has_rdoc: true
|
35
|
+
homepage: http://mygengo.com/services/api/dev-docs/
|
36
|
+
licenses: []
|
37
|
+
|
38
|
+
post_install_message:
|
39
|
+
rdoc_options: []
|
40
|
+
|
41
|
+
require_paths:
|
42
|
+
- lib
|
43
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
44
|
+
none: false
|
45
|
+
requirements:
|
46
|
+
- - ">="
|
47
|
+
- !ruby/object:Gem::Version
|
48
|
+
version: "0"
|
49
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
51
|
+
requirements:
|
52
|
+
- - ">="
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: "0"
|
55
|
+
requirements: []
|
56
|
+
|
57
|
+
rubyforge_project:
|
58
|
+
rubygems_version: 1.5.2
|
59
|
+
signing_key:
|
60
|
+
specification_version: 3
|
61
|
+
summary: A library for interfacing with the myGengo Translation API.
|
62
|
+
test_files: []
|
63
|
+
|