google_books 0.1.0
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.
- data/.gitignore +6 -0
- data/.rspec +1 -0
- data/.rvmrc +1 -0
- data/CHANGELOG.md +32 -0
- data/Gemfile +7 -0
- data/Gemfile.lock +65 -0
- data/LICENSE +24 -0
- data/README.md +75 -0
- data/Rakefile +11 -0
- data/examples/basics.rb +31 -0
- data/examples/special_keywords.rb +12 -0
- data/google_books.gemspec +27 -0
- data/lib/google_books.rb +9 -0
- data/lib/google_books/api.rb +45 -0
- data/lib/google_books/api/book.rb +71 -0
- data/lib/google_books/api/response.rb +23 -0
- data/lib/google_books/version.rb +3 -0
- data/spec/google_books/api/book_spec.rb +103 -0
- data/spec/google_books/api/response_spec.rb +20 -0
- data/spec/google_books/api_spec.rb +44 -0
- data/spec/spec_helper.rb +7 -0
- data/spec/support/vcr.rb +11 -0
- metadata +139 -0
data/.gitignore
ADDED
data/.rspec
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
-cfd
|
data/.rvmrc
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
rvm --create use 1.9.2@google_books
|
data/CHANGELOG.md
ADDED
@@ -0,0 +1,32 @@
|
|
1
|
+
CHANGELOG
|
2
|
+
=========
|
3
|
+
|
4
|
+
v0.0.1
|
5
|
+
------
|
6
|
+
This is the initial version of google_books
|
7
|
+
|
8
|
+
* `GoogleBooks::API` contains the search method which takes in 3 different options `count`, `page`, and `api_key`
|
9
|
+
* The `GoogleBooks::API.search` method returns a `GoogleBooks::API::Response`
|
10
|
+
|
11
|
+
* Iterate through the Response and each result is a `GoogleBooks::API::Book`
|
12
|
+
* Use the `total_results` method of the Response to get the total number of results that were found for your query (but not the count of books returned). This can be used for paging.
|
13
|
+
* The `GoogleBooks::API::Book` model handles the following attributes:
|
14
|
+
* `title` - *String*
|
15
|
+
* `authors` - *Array*
|
16
|
+
* `publisher` - *String*
|
17
|
+
* `published_date` - *Date*
|
18
|
+
* `isbn` - *String*
|
19
|
+
* `isbn_10` - *String*
|
20
|
+
* `page_count` - *FixNum*
|
21
|
+
* `categories` - *Array*
|
22
|
+
* `description` - *String*
|
23
|
+
* `average_rating` - *Float*
|
24
|
+
* `ratings_count` - *FixNum*
|
25
|
+
* `covers` - *Hash*, with the following keys:
|
26
|
+
* `:thumbnail`
|
27
|
+
* `:small`
|
28
|
+
* `:medium`
|
29
|
+
* `:large`
|
30
|
+
* `:extra_large`
|
31
|
+
* `preview_link` - *String*
|
32
|
+
* `info_link` - *String*
|
data/Gemfile
ADDED
data/Gemfile.lock
ADDED
@@ -0,0 +1,65 @@
|
|
1
|
+
PATH
|
2
|
+
remote: .
|
3
|
+
specs:
|
4
|
+
google_books (0.1)
|
5
|
+
hashie
|
6
|
+
httparty
|
7
|
+
|
8
|
+
GEM
|
9
|
+
remote: http://rubygems.org/
|
10
|
+
specs:
|
11
|
+
ZenTest (4.6.0)
|
12
|
+
addressable (2.2.6)
|
13
|
+
archive-tar-minitar (0.5.2)
|
14
|
+
autotest (4.4.6)
|
15
|
+
ZenTest (>= 4.4.1)
|
16
|
+
columnize (0.3.4)
|
17
|
+
crack (0.1.8)
|
18
|
+
diff-lcs (1.1.2)
|
19
|
+
hashie (1.1.0)
|
20
|
+
httparty (0.7.8)
|
21
|
+
crack (= 0.1.8)
|
22
|
+
linecache (0.46)
|
23
|
+
rbx-require-relative (> 0.0.4)
|
24
|
+
linecache19 (0.5.12)
|
25
|
+
ruby_core_source (>= 0.1.4)
|
26
|
+
rbx-require-relative (0.0.5)
|
27
|
+
rspec (2.6.0)
|
28
|
+
rspec-core (~> 2.6.0)
|
29
|
+
rspec-expectations (~> 2.6.0)
|
30
|
+
rspec-mocks (~> 2.6.0)
|
31
|
+
rspec-core (2.6.4)
|
32
|
+
rspec-expectations (2.6.0)
|
33
|
+
diff-lcs (~> 1.1.2)
|
34
|
+
rspec-mocks (2.6.0)
|
35
|
+
ruby-debug (0.10.4)
|
36
|
+
columnize (>= 0.1)
|
37
|
+
ruby-debug-base (~> 0.10.4.0)
|
38
|
+
ruby-debug-base (0.10.4)
|
39
|
+
linecache (>= 0.3)
|
40
|
+
ruby-debug-base19 (0.11.25)
|
41
|
+
columnize (>= 0.3.1)
|
42
|
+
linecache19 (>= 0.5.11)
|
43
|
+
ruby_core_source (>= 0.1.4)
|
44
|
+
ruby-debug19 (0.11.6)
|
45
|
+
columnize (>= 0.3.1)
|
46
|
+
linecache19 (>= 0.5.11)
|
47
|
+
ruby-debug-base19 (>= 0.11.19)
|
48
|
+
ruby_core_source (0.1.5)
|
49
|
+
archive-tar-minitar (>= 0.5.2)
|
50
|
+
vcr (1.10.3)
|
51
|
+
webmock (1.6.4)
|
52
|
+
addressable (~> 2.2, > 2.2.5)
|
53
|
+
crack (>= 0.1.7)
|
54
|
+
|
55
|
+
PLATFORMS
|
56
|
+
ruby
|
57
|
+
|
58
|
+
DEPENDENCIES
|
59
|
+
autotest
|
60
|
+
google_books!
|
61
|
+
rspec
|
62
|
+
ruby-debug
|
63
|
+
ruby-debug19
|
64
|
+
vcr
|
65
|
+
webmock
|
data/LICENSE
ADDED
@@ -0,0 +1,24 @@
|
|
1
|
+
Copyright (c) 2011, Visoft, Inc.
|
2
|
+
All rights reserved.
|
3
|
+
|
4
|
+
Redistribution and use in source and binary forms, with or without
|
5
|
+
modification, are permitted provided that the following conditions are met:
|
6
|
+
* Redistributions of source code must retain the above copyright
|
7
|
+
notice, this list of conditions and the following disclaimer.
|
8
|
+
* Redistributions in binary form must reproduce the above copyright
|
9
|
+
notice, this list of conditions and the following disclaimer in the
|
10
|
+
documentation and/or other materials provided with the distribution.
|
11
|
+
* Neither the name of Visoft, Inc. nor the
|
12
|
+
names of its contributors may be used to endorse or promote products
|
13
|
+
derived from this software without specific prior written permission.
|
14
|
+
|
15
|
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
16
|
+
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
17
|
+
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
18
|
+
DISCLAIMED. IN NO EVENT SHALL VISOFT, INC. BE LIABLE FOR ANY
|
19
|
+
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
20
|
+
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
21
|
+
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
22
|
+
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
23
|
+
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
24
|
+
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
data/README.md
ADDED
@@ -0,0 +1,75 @@
|
|
1
|
+
Google Books
|
2
|
+
============
|
3
|
+
|
4
|
+
Google Books is a Ruby wrapper to the [Google Books API](http://code.google.com/apis/books/docs/v1/getting_started.html)
|
5
|
+
The project was inspired by [google-book](https://github.com/papercavalier/google-book). It is a nice wrapper, however the [Google Book Search Data API](http://code.google.com/apis/books/docs/gdata/developers_guide_protocol.html) "is deprecated as of May 26, 2011 and will be fully retired on December 1, 2011."
|
6
|
+
|
7
|
+
Usage
|
8
|
+
-----
|
9
|
+
The usage is similar to that of [google-book](https://github.com/papercavalier/google-book), but the semantics are a little different
|
10
|
+
|
11
|
+
require 'google_books' # Or hey, add it to your Gemfile
|
12
|
+
|
13
|
+
books = GoogleBooks::API.search('Douglas Crockford')
|
14
|
+
book = books.first
|
15
|
+
puts book.title
|
16
|
+
#=> "JavaScript: The Good Parts"
|
17
|
+
puts book.isbn
|
18
|
+
#=> "9780596517748"
|
19
|
+
puts book.covers[:thumbnail]
|
20
|
+
#=> "http://bks8.books.google.com/books?id=..."
|
21
|
+
|
22
|
+
In addition to the query, the `GoogleBooks::API.search` method takes in a hash of 3 different options:
|
23
|
+
|
24
|
+
|
25
|
+
* `count`: The number of results that you want returned, currently the default is 10 (set by Google)
|
26
|
+
* `page`: The page of results that you want. Combine this with `total_results` method of the `GoogleBooks::API::Response`, and implement paging in your application
|
27
|
+
* `api_key`: For production apps, Google requires either [OAuth 2.0](http://code.google.com/apis/books/docs/v1/using.html#AboutAuthorization) or an [API key](http://code.google.com/apis/books/docs/v1/using.html#APIKey) to request public data. See the [API Documentation](http://code.google.com/apis/books/docs/v1/using.html#auth) for more information.
|
28
|
+
|
29
|
+
Queries
|
30
|
+
-------
|
31
|
+
Within your query that you pass to the search method, you can use special keywords as outlined in the [API Documentation](http://code.google.com/apis/books/docs/v1/using.html#q)
|
32
|
+
|
33
|
+
* `intitle`: Returns results where the text following this keyword is found in the title.
|
34
|
+
* `inauthor`: Returns results where the text following this keyword is found in the author.
|
35
|
+
* `inpublisher`: Returns results where the text following this keyword is found in the publisher.
|
36
|
+
* `subject`: Returns results where the text following this keyword is listed in the category list of the volume.
|
37
|
+
* `isbn`: Returns results where the text following this keyword is the ISBN number.
|
38
|
+
|
39
|
+
For example:
|
40
|
+
|
41
|
+
# Get the book with the isbn of 9781118035580
|
42
|
+
books = GoogleBooks::API.search('isbn:9781118035580')
|
43
|
+
book = books.first
|
44
|
+
|
45
|
+
puts book.title
|
46
|
+
#=> "Hands - on ASP.NET AJAX Control Toolkit"
|
47
|
+
puts book.authors.first
|
48
|
+
#=> "Damien White" (Shameless plug)
|
49
|
+
puts book.covers[:thumbnail]
|
50
|
+
#=> "http://bks7.books.google.com/books?id=..."
|
51
|
+
|
52
|
+
Book Attributes
|
53
|
+
---------------
|
54
|
+
* `title`: *String*
|
55
|
+
|
56
|
+
This will append a subtitle if one exists, like "JavaScript: The Good Parts"
|
57
|
+
|
58
|
+
* `authors`: *Array*
|
59
|
+
* `publisher`: *String*
|
60
|
+
* `published_date`: *Date*
|
61
|
+
* `isbn`: *String*
|
62
|
+
* `isbn_10`: *String*
|
63
|
+
* `page_count`: *FixNum*
|
64
|
+
* `categories`: *Array*
|
65
|
+
* `description`: *String*
|
66
|
+
* `average_rating`: *Float*
|
67
|
+
* `ratings_count`: *FixNum*
|
68
|
+
* `covers`: *Hash*
|
69
|
+
|
70
|
+
The keys are `:thumbnail`, `:small`, `:medium`, `:large`, `:extra_large`
|
71
|
+
|
72
|
+
Not all of the image URLs are guaranteed to return something. Stick with thumbnail or small for the best results
|
73
|
+
|
74
|
+
* `preview_link`: *String*
|
75
|
+
* `info_link`: *String*
|
data/Rakefile
ADDED
data/examples/basics.rb
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/../lib/google_books'
|
2
|
+
|
3
|
+
results = GoogleBooks::API.search('ruby')
|
4
|
+
|
5
|
+
# Get the total results (for the search, not the books returned)
|
6
|
+
puts "Total results for the term 'ruby': #{results.total_results}"
|
7
|
+
|
8
|
+
# Iterate through the books
|
9
|
+
for book in results
|
10
|
+
puts "\"#{book.title}\" by #{book.authors.join(', ')}"
|
11
|
+
end
|
12
|
+
|
13
|
+
puts '-'*80
|
14
|
+
|
15
|
+
# Want more than ten books at a time? Use the :count option
|
16
|
+
results = GoogleBooks::API.search('ruby', :count => 20)
|
17
|
+
puts "#{results.count} results returned instead of default 10"
|
18
|
+
|
19
|
+
puts '-'*80
|
20
|
+
|
21
|
+
# Implement paging...
|
22
|
+
results = GoogleBooks::API.search('ruby', :count => 5, :page => 1)
|
23
|
+
puts '* Page 1 ***********************************************'
|
24
|
+
for book in results
|
25
|
+
puts "\"#{book.title}\" by #{book.authors.join(', ')}"
|
26
|
+
end
|
27
|
+
results = GoogleBooks::API.search('ruby', :count => 5, :page => 2)
|
28
|
+
puts '* Page 2 ***********************************************'
|
29
|
+
for book in results
|
30
|
+
puts "\"#{book.title}\" by #{book.authors.join(', ')}"
|
31
|
+
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/../lib/google_books'
|
2
|
+
|
3
|
+
# Using the isbn keyword
|
4
|
+
books = GoogleBooks::API.search('isbn:9781118035580')
|
5
|
+
book = books.first
|
6
|
+
|
7
|
+
puts book.title
|
8
|
+
#=> "Hands - on ASP.NET AJAX Control Toolkit"
|
9
|
+
puts book.authors.first
|
10
|
+
#=> "Damien White" (Shameless plug)
|
11
|
+
puts book.covers[:thumbnail]
|
12
|
+
#=> "http://bks7.books.google.com/books?id=..."
|
@@ -0,0 +1,27 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
$:.push File.expand_path("../lib", __FILE__)
|
3
|
+
require "google_books/version"
|
4
|
+
|
5
|
+
Gem::Specification.new do |s|
|
6
|
+
s.name = "google_books"
|
7
|
+
s.version = GoogleBooks::VERSION
|
8
|
+
s.platform = Gem::Platform::RUBY
|
9
|
+
s.authors = ["Damien White"]
|
10
|
+
s.email = ["damien.white@visoftinc.com"]
|
11
|
+
s.homepage = "http://github.com/visoft/google_books"
|
12
|
+
s.summary = %q{A Ruby wrapper around the Google Books API}
|
13
|
+
s.description = %q{A Ruby wrapper that allows you to query the Google Books API. This project was inspired by google-book, see the README for more information}
|
14
|
+
|
15
|
+
s.add_dependency('httparty')
|
16
|
+
s.add_dependency('hashie')
|
17
|
+
|
18
|
+
s.add_development_dependency('autotest')
|
19
|
+
s.add_development_dependency('rspec')
|
20
|
+
s.add_development_dependency('webmock')
|
21
|
+
s.add_development_dependency('vcr')
|
22
|
+
|
23
|
+
s.files = `git ls-files`.split("\n")
|
24
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
25
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
26
|
+
s.require_paths = ["lib"]
|
27
|
+
end
|
data/lib/google_books.rb
ADDED
@@ -0,0 +1,45 @@
|
|
1
|
+
module GoogleBooks
|
2
|
+
# A simple wrapper around the Google Books API
|
3
|
+
module API
|
4
|
+
include HTTParty
|
5
|
+
class << self
|
6
|
+
|
7
|
+
# The search parameters.
|
8
|
+
attr_accessor :parameters
|
9
|
+
|
10
|
+
# Queries the Google Books API. Takes a query string and an
|
11
|
+
# optional options hash.
|
12
|
+
#
|
13
|
+
# The options hash respects the following members:
|
14
|
+
#
|
15
|
+
# * `:page`, which specifies the page.
|
16
|
+
#
|
17
|
+
# * `:count`, which specifies the number of results per page.
|
18
|
+
#
|
19
|
+
# * `:api_key`, your [API key](http://code.google.com/apis/books/docs/v1/using.html#auth) for making requests against the Google Books API.
|
20
|
+
def search(query, opts ={})
|
21
|
+
self.parameters = { 'q' => query }
|
22
|
+
parameters['startIndex'] = opts[:page] if opts[:page]
|
23
|
+
parameters['maxResults'] = opts[:count] if opts[:count]
|
24
|
+
parameters['key'] = opts[:api_key] if opts[:api_key]
|
25
|
+
|
26
|
+
result = get(url.to_s)
|
27
|
+
Response.new result
|
28
|
+
end
|
29
|
+
|
30
|
+
private
|
31
|
+
|
32
|
+
def query
|
33
|
+
parameters.
|
34
|
+
map { |k, v| "#{k}=#{CGI.escape(v.to_s)}" }.
|
35
|
+
join('&')
|
36
|
+
end
|
37
|
+
|
38
|
+
def url
|
39
|
+
URI::HTTPS.build(:host => 'www.googleapis.com',
|
40
|
+
:path => '/books/v1/volumes',
|
41
|
+
:query => query)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,71 @@
|
|
1
|
+
module GoogleBooks
|
2
|
+
module API
|
3
|
+
class Book
|
4
|
+
attr_reader :title, :authors, :publisher, :published_date,
|
5
|
+
:isbn, :isbn_10, :page_count, :categories,
|
6
|
+
:description, :average_rating, :ratings_count,
|
7
|
+
:covers, :preview_link, :info_link
|
8
|
+
|
9
|
+
def initialize(item)
|
10
|
+
return if item.nil?
|
11
|
+
parse_item(item)
|
12
|
+
end
|
13
|
+
|
14
|
+
private
|
15
|
+
|
16
|
+
def parse_item(item)
|
17
|
+
volume_info = item['volumeInfo']
|
18
|
+
@book = Hashie::Mash.new volume_info
|
19
|
+
if @book.subtitle.nil?
|
20
|
+
@title = @book.title
|
21
|
+
else
|
22
|
+
@title = "#{@book.title}: #{titlize(@book.subtitle)}"
|
23
|
+
end
|
24
|
+
@authors = @book.authors || []
|
25
|
+
@publisher = @book.publisher
|
26
|
+
@published_date = @book.publishedDate
|
27
|
+
@description = @book.description
|
28
|
+
@isbn = get_isbn_for_book
|
29
|
+
@isbn_10 = get_isbn_for_book(10)
|
30
|
+
@page_count = @book.pageCount
|
31
|
+
@categories = @book.categories
|
32
|
+
@average_rating = @book.averageRating
|
33
|
+
@ratings_count = @book.ratingsCount
|
34
|
+
@covers = fixup_covers
|
35
|
+
@preview_link = @book.previewLink
|
36
|
+
@info_link = @book.infoLink
|
37
|
+
end
|
38
|
+
|
39
|
+
def get_isbn_for_book(type=13)
|
40
|
+
return nil if @book.industryIdentifiers.nil?
|
41
|
+
isbn = @book.industryIdentifiers.find { |id| id.type == "ISBN_#{type}" }
|
42
|
+
return nil if isbn.nil?
|
43
|
+
isbn.identifier
|
44
|
+
end
|
45
|
+
|
46
|
+
def fixup_covers
|
47
|
+
return {} if @book.imageLinks.nil?
|
48
|
+
url = @book.imageLinks.first[1]
|
49
|
+
{
|
50
|
+
:thumbnail => cover_url(url, 5),
|
51
|
+
:small => cover_url(url, 1),
|
52
|
+
:medium => cover_url(url, 2),
|
53
|
+
:large => cover_url(url, 3),
|
54
|
+
:extra_large => cover_url(url, 6)
|
55
|
+
}
|
56
|
+
end
|
57
|
+
|
58
|
+
def titlize(word)
|
59
|
+
# From http://snippets.dzone.com/posts/show/294
|
60
|
+
non_capitalized = %w{of etc and by the for on is at to but nor or a via}
|
61
|
+
word.gsub(/\b[a-z]+/){ |w| non_capitalized.include?(w) ? w : w.capitalize }.sub(/^[a-z]/){|l| l.upcase }.sub(/\b[a-z][^\s]*?$/){|l| l.capitalize }
|
62
|
+
end
|
63
|
+
|
64
|
+
def cover_url(url, zoom)
|
65
|
+
url.
|
66
|
+
gsub(/zoom=\d/, "zoom=#{zoom}"). # Set the zoom level
|
67
|
+
gsub(/&edge=curl/, '') # Who wants the curl on their images
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module GoogleBooks
|
2
|
+
module API
|
3
|
+
class Response
|
4
|
+
include Enumerable
|
5
|
+
|
6
|
+
def initialize(results)
|
7
|
+
@results = results
|
8
|
+
end
|
9
|
+
|
10
|
+
# Iterator for looping through the results
|
11
|
+
def each(&block)
|
12
|
+
@results['items'].each do |item|
|
13
|
+
block.call(Book.new(item))
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
# The total number of results that were found for your query (not the count of the results returned)
|
18
|
+
def total_results
|
19
|
+
@results['totalItems'].to_i
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,103 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/../../spec_helper'
|
2
|
+
|
3
|
+
module GoogleBooks
|
4
|
+
module API
|
5
|
+
describe Book do
|
6
|
+
use_vcr_cassette 'google'
|
7
|
+
|
8
|
+
subject { API.search('isbn:9781935182320').first }
|
9
|
+
|
10
|
+
it "should be able to handle a nil object passed" do
|
11
|
+
lambda { Book.new(nil) }.should_not raise_error
|
12
|
+
end
|
13
|
+
|
14
|
+
it "should have a title" do
|
15
|
+
subject.title.should eq 'JQuery in Action'
|
16
|
+
end
|
17
|
+
|
18
|
+
it "should contain a subtitle in the title if there is one" do
|
19
|
+
book = API.search('isbn:9780596517748').first
|
20
|
+
book.title.should eq 'JavaScript: The Good Parts'
|
21
|
+
end
|
22
|
+
|
23
|
+
it "should have an array of authors with the correct names" do
|
24
|
+
subject.authors.length.should eq 2
|
25
|
+
subject.authors[0].should eq "Bear Bibeault"
|
26
|
+
subject.authors[1].should eq "Yehuda Katz"
|
27
|
+
end
|
28
|
+
|
29
|
+
it "should have a publisher" do
|
30
|
+
subject.publisher.should_not be_nil
|
31
|
+
subject.publisher.should include "Manning"
|
32
|
+
end
|
33
|
+
|
34
|
+
it "should have a published date in date format" do
|
35
|
+
subject.published_date.should be_a Date
|
36
|
+
subject.published_date.should eq Date.new(2010, 6, 30)
|
37
|
+
end
|
38
|
+
|
39
|
+
it "should have description (which may be blank)" do
|
40
|
+
subject.description.should_not be_nil
|
41
|
+
end
|
42
|
+
|
43
|
+
it "should have an ISBN (13)" do
|
44
|
+
subject.isbn.should eq '9781935182320'
|
45
|
+
end
|
46
|
+
|
47
|
+
it "should have an ISBN 10" do
|
48
|
+
subject.isbn_10.should eq '1935182323'
|
49
|
+
end
|
50
|
+
|
51
|
+
it "should have a page count" do
|
52
|
+
subject.page_count.should be_a Fixnum
|
53
|
+
subject.page_count.should eq 475
|
54
|
+
end
|
55
|
+
|
56
|
+
it "should have categories" do
|
57
|
+
subject.categories.should be_an Array
|
58
|
+
subject.categories.first.should eq "Computers"
|
59
|
+
end
|
60
|
+
|
61
|
+
it "should have an average rating" do
|
62
|
+
subject.average_rating.should be_a Float
|
63
|
+
end
|
64
|
+
|
65
|
+
it "should have an ratings count" do
|
66
|
+
subject.ratings_count.should be_a Fixnum
|
67
|
+
end
|
68
|
+
|
69
|
+
it "should contain a covers hash" do
|
70
|
+
subject.covers.should be_a Hash
|
71
|
+
subject.covers.keys.should include :thumbnail
|
72
|
+
subject.covers.keys.should include :small
|
73
|
+
subject.covers.keys.should include :medium
|
74
|
+
subject.covers.keys.should include :large
|
75
|
+
subject.covers.keys.should include :extra_large
|
76
|
+
end
|
77
|
+
|
78
|
+
it "should not have curls on the cover urls" do
|
79
|
+
subject.covers[:thumbnail].should_not include 'edge=curl'
|
80
|
+
subject.covers[:small].should_not include 'edge=curl'
|
81
|
+
subject.covers[:medium].should_not include 'edge=curl'
|
82
|
+
subject.covers[:large].should_not include 'edge=curl'
|
83
|
+
subject.covers[:extra_large].should_not include 'edge=curl'
|
84
|
+
end
|
85
|
+
|
86
|
+
it "should have the cover url zoom level" do
|
87
|
+
subject.covers[:thumbnail].should include 'zoom=5'
|
88
|
+
subject.covers[:small].should include 'zoom=1'
|
89
|
+
subject.covers[:medium].should include 'zoom=2'
|
90
|
+
subject.covers[:large].should include 'zoom=3'
|
91
|
+
subject.covers[:extra_large].should include 'zoom=6'
|
92
|
+
end
|
93
|
+
|
94
|
+
it "should contains a preview link" do
|
95
|
+
subject.preview_link.should_not be_nil
|
96
|
+
end
|
97
|
+
|
98
|
+
it "should contains an info link" do
|
99
|
+
subject.info_link.should_not be_nil
|
100
|
+
end
|
101
|
+
end
|
102
|
+
end
|
103
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/../../spec_helper'
|
2
|
+
|
3
|
+
module GoogleBooks
|
4
|
+
module API
|
5
|
+
describe Response do
|
6
|
+
use_vcr_cassette 'google'
|
7
|
+
|
8
|
+
it "should set total results" do
|
9
|
+
response = API.search('Damien White')
|
10
|
+
response.total_results.should > 0
|
11
|
+
end
|
12
|
+
|
13
|
+
it "should return books" do
|
14
|
+
response = API.search('Damien White')
|
15
|
+
response.first.should be_a Book
|
16
|
+
end
|
17
|
+
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,44 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/../spec_helper'
|
2
|
+
|
3
|
+
module GoogleBooks
|
4
|
+
describe API do
|
5
|
+
use_vcr_cassette 'google'
|
6
|
+
|
7
|
+
describe "search" do
|
8
|
+
it "should escape spaces" do
|
9
|
+
API.search('damien white')
|
10
|
+
API.send(:query).should include 'q=damien+white'
|
11
|
+
end
|
12
|
+
|
13
|
+
it "should set the page" do
|
14
|
+
API.search('damien white', :page => 2)
|
15
|
+
API.send(:query).should include 'startIndex=2'
|
16
|
+
end
|
17
|
+
|
18
|
+
it "should set the number of results per page" do
|
19
|
+
API.search('damien white', :count => 20)
|
20
|
+
API.send(:query).should include 'maxResults=20'
|
21
|
+
end
|
22
|
+
|
23
|
+
it "should accept in an API key" do
|
24
|
+
API.search('damien white', :api_key => 'ABCDEFG')
|
25
|
+
API.send(:query).should include 'key=ABCDEFG'
|
26
|
+
end
|
27
|
+
|
28
|
+
it "should join parameters" do
|
29
|
+
API.search('damien white', :count => 20, :page => 2)
|
30
|
+
API.send(:query).should include 'startIndex=2&maxResults=20'
|
31
|
+
end
|
32
|
+
|
33
|
+
it "should return the proper number results based on the count passed in" do
|
34
|
+
results = API.search('damien white', :count => 20)
|
35
|
+
results.count.should eq 20
|
36
|
+
end
|
37
|
+
|
38
|
+
it "should return a response" do
|
39
|
+
API.search('damien white').should be_a API::Response
|
40
|
+
end
|
41
|
+
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
data/spec/spec_helper.rb
ADDED
data/spec/support/vcr.rb
ADDED
@@ -0,0 +1,11 @@
|
|
1
|
+
require 'vcr'
|
2
|
+
|
3
|
+
VCR.config do |c|
|
4
|
+
c.cassette_library_dir = File.dirname(__FILE__) + '/../fixtures/cassette_library'
|
5
|
+
c.default_cassette_options = { :record => :new_episodes }
|
6
|
+
c.stub_with :webmock
|
7
|
+
end
|
8
|
+
|
9
|
+
RSpec.configure do |config|
|
10
|
+
config.extend VCR::RSpec::Macros
|
11
|
+
end
|
metadata
ADDED
@@ -0,0 +1,139 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: google_books
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
5
|
+
prerelease:
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Damien White
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2011-08-07 00:00:00.000000000Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: httparty
|
16
|
+
requirement: &70123559467780 !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
18
|
+
requirements:
|
19
|
+
- - ! '>='
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: '0'
|
22
|
+
type: :runtime
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: *70123559467780
|
25
|
+
- !ruby/object:Gem::Dependency
|
26
|
+
name: hashie
|
27
|
+
requirement: &70123559467360 !ruby/object:Gem::Requirement
|
28
|
+
none: false
|
29
|
+
requirements:
|
30
|
+
- - ! '>='
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '0'
|
33
|
+
type: :runtime
|
34
|
+
prerelease: false
|
35
|
+
version_requirements: *70123559467360
|
36
|
+
- !ruby/object:Gem::Dependency
|
37
|
+
name: autotest
|
38
|
+
requirement: &70123559466940 !ruby/object:Gem::Requirement
|
39
|
+
none: false
|
40
|
+
requirements:
|
41
|
+
- - ! '>='
|
42
|
+
- !ruby/object:Gem::Version
|
43
|
+
version: '0'
|
44
|
+
type: :development
|
45
|
+
prerelease: false
|
46
|
+
version_requirements: *70123559466940
|
47
|
+
- !ruby/object:Gem::Dependency
|
48
|
+
name: rspec
|
49
|
+
requirement: &70123559466520 !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
51
|
+
requirements:
|
52
|
+
- - ! '>='
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
type: :development
|
56
|
+
prerelease: false
|
57
|
+
version_requirements: *70123559466520
|
58
|
+
- !ruby/object:Gem::Dependency
|
59
|
+
name: webmock
|
60
|
+
requirement: &70123559466100 !ruby/object:Gem::Requirement
|
61
|
+
none: false
|
62
|
+
requirements:
|
63
|
+
- - ! '>='
|
64
|
+
- !ruby/object:Gem::Version
|
65
|
+
version: '0'
|
66
|
+
type: :development
|
67
|
+
prerelease: false
|
68
|
+
version_requirements: *70123559466100
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: vcr
|
71
|
+
requirement: &70123559465680 !ruby/object:Gem::Requirement
|
72
|
+
none: false
|
73
|
+
requirements:
|
74
|
+
- - ! '>='
|
75
|
+
- !ruby/object:Gem::Version
|
76
|
+
version: '0'
|
77
|
+
type: :development
|
78
|
+
prerelease: false
|
79
|
+
version_requirements: *70123559465680
|
80
|
+
description: A Ruby wrapper that allows you to query the Google Books API. This project
|
81
|
+
was inspired by google-book, see the README for more information
|
82
|
+
email:
|
83
|
+
- damien.white@visoftinc.com
|
84
|
+
executables: []
|
85
|
+
extensions: []
|
86
|
+
extra_rdoc_files: []
|
87
|
+
files:
|
88
|
+
- .gitignore
|
89
|
+
- .rspec
|
90
|
+
- .rvmrc
|
91
|
+
- CHANGELOG.md
|
92
|
+
- Gemfile
|
93
|
+
- Gemfile.lock
|
94
|
+
- LICENSE
|
95
|
+
- README.md
|
96
|
+
- Rakefile
|
97
|
+
- examples/basics.rb
|
98
|
+
- examples/special_keywords.rb
|
99
|
+
- google_books.gemspec
|
100
|
+
- lib/google_books.rb
|
101
|
+
- lib/google_books/api.rb
|
102
|
+
- lib/google_books/api/book.rb
|
103
|
+
- lib/google_books/api/response.rb
|
104
|
+
- lib/google_books/version.rb
|
105
|
+
- spec/google_books/api/book_spec.rb
|
106
|
+
- spec/google_books/api/response_spec.rb
|
107
|
+
- spec/google_books/api_spec.rb
|
108
|
+
- spec/spec_helper.rb
|
109
|
+
- spec/support/vcr.rb
|
110
|
+
homepage: http://github.com/visoft/google_books
|
111
|
+
licenses: []
|
112
|
+
post_install_message:
|
113
|
+
rdoc_options: []
|
114
|
+
require_paths:
|
115
|
+
- lib
|
116
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
117
|
+
none: false
|
118
|
+
requirements:
|
119
|
+
- - ! '>='
|
120
|
+
- !ruby/object:Gem::Version
|
121
|
+
version: '0'
|
122
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
123
|
+
none: false
|
124
|
+
requirements:
|
125
|
+
- - ! '>='
|
126
|
+
- !ruby/object:Gem::Version
|
127
|
+
version: '0'
|
128
|
+
requirements: []
|
129
|
+
rubyforge_project:
|
130
|
+
rubygems_version: 1.8.6
|
131
|
+
signing_key:
|
132
|
+
specification_version: 3
|
133
|
+
summary: A Ruby wrapper around the Google Books API
|
134
|
+
test_files:
|
135
|
+
- spec/google_books/api/book_spec.rb
|
136
|
+
- spec/google_books/api/response_spec.rb
|
137
|
+
- spec/google_books/api_spec.rb
|
138
|
+
- spec/spec_helper.rb
|
139
|
+
- spec/support/vcr.rb
|