hyper_api 0.0.1 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 986c73fdfe7a49afe6537e0667029ce437b76f07
4
+ data.tar.gz: e4b30f076ef70dd52c935fb9ebeffcf9f6b6994b
5
+ SHA512:
6
+ metadata.gz: c1c2781278743784fdb2205807048e5271b6e7bb0a9c68d3b1af03d9296e224f711e929db5da9bba2a52f239573a84c7af20897b5a2593ce10ececda0ddb6528
7
+ data.tar.gz: d6ab8dbe662c43eac9b79b609c3cb174f8494f44bbd486b4a2428b0e18c57ecede79464ed4e8d9c9af2438768c9c6c89bdfeaa30eda68c1e418093ae28841494
data/.gitignore CHANGED
@@ -2,6 +2,8 @@
2
2
  *.rbc
3
3
  .bundle
4
4
  .config
5
+ .rspec
6
+ .ruby-version
5
7
  .yardoc
6
8
  Gemfile.lock
7
9
  InstalledFiles
data/Gemfile CHANGED
@@ -1,4 +1,3 @@
1
1
  source 'https://rubygems.org'
2
2
 
3
- # Specify your gem's dependencies in hyper_api.gemspec
4
3
  gemspec
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2014 Javier Saldana
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md CHANGED
@@ -16,7 +16,7 @@ The HyperAPI gem uses [Nokogiri](https://github.com/sparklemotion/nokogiri) to p
16
16
  Create objects on-the-go:
17
17
 
18
18
  ```ruby
19
- tpb_torrent = HyperAPI.new_class('TPB::Torrent') do
19
+ Torrent = HyperAPI.new_class do
20
20
  string title: 'div#title'
21
21
  string description: 'div.info'
22
22
  string hash: '#details dd'
@@ -24,26 +24,47 @@ tpb_torrent = HyperAPI.new_class('TPB::Torrent') do
24
24
  attribute('href').value
25
25
  end
26
26
  end
27
- # => TPB::Torrent
27
+ # => Torrent
28
+
29
+ fringe = Torrent.new(html_string)
30
+ # => #<TPB::Torrent title: 'Fringe Season 1', description: 'The complete season 1 of Fri...', imdb_id: 1119644>
31
+
32
+ torrent = HyperAPI.new_class do
33
+ string title: 'div#title'
34
+ string description: 'div.info'
35
+ string hash: '#details dd'
36
+ integer imdb_id: '#details a[title=IMDB]' do
37
+ attribute('href').value
38
+ end
39
+ end
40
+ # => #<Class:0x007fda34829c48> // (anonymous class)
41
+
42
+ fringe = torrent.new(html_string)
43
+ # => #<Class:0x007fda34829c48 title: 'Fringe Season 1', description: 'The complete season 1 of Fri...', imdb_id: 1119644>
28
44
 
29
- fringe = tpb_torrent.new(html)
30
- # => #<TPB::Torrent title: 'Fringe Season 1', description: 'The complete season 1 of Fri...', imdb_id: '1119644'>
31
45
  ```
32
46
 
33
47
  Or create a new class:
34
48
 
35
49
  ```ruby
36
- class TPB::Torrent < HyperApi::Base
50
+ class Torrent < HyperApi::Base
37
51
  string title: 'div#title'
38
52
  string description: 'div.info'
39
53
  string hash: '#details dd'
40
54
  integer imdb_id: '#details a[title=IMDB]' do
41
55
  attribute('href').value
42
56
  end
57
+
58
+ def some_calculated_method
59
+ "#{title}: #{hash}"
60
+ end
43
61
  end
44
62
 
45
- fringe = TPB::Torrent.new(html)
46
- # => #<TPB::Torrent title: 'Fringe Season 1', description: 'The complete season 1 of Fri...', imdb_id: '1119644'>
63
+ fringe = Torrent.new(html_string)
64
+ # => #<TPB::Torrent title: 'Fringe Season 1', description: 'The complete season 1 of Fri...', imdb_id: 1119644>
65
+
66
+ fringe.some_calculated_method
67
+ # => "Fringe Season 1: B4C04A34DD8824C28E9A8A528"
47
68
  ```
48
69
 
49
70
  ## Contributing
@@ -54,4 +75,4 @@ If you've found a bug or have a question, please open an issue on the [issue tra
54
75
 
55
76
  Copyright &copy; 2014 Javier Saldana
56
77
 
57
- Released under the MIT license. See [`LICENSE`]](LICENSE) for details.
78
+ Released under the MIT license. See [`LICENSE`](LICENSE) for details.
data/hyper_api.gemspec CHANGED
@@ -17,4 +17,7 @@ Gem::Specification.new do |spec|
17
17
  spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
18
18
  spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
19
  spec.require_paths = ['lib']
20
+
21
+ spec.add_dependency 'nokogiri', '~> 1.6.0'
22
+ spec.add_development_dependency 'rspec', '~> 3.0.0.beta1'
20
23
  end
@@ -1,3 +1,3 @@
1
1
  module HyperAPI
2
- VERSION = '0.0.1'
2
+ VERSION = '0.1.0'
3
3
  end
data/lib/hyper_api.rb CHANGED
@@ -1,5 +1,59 @@
1
- require "hyper_api/version"
1
+ require 'nokogiri'
2
+ require 'hyper_api/version'
2
3
 
3
4
  module HyperAPI
4
- # Code goes here...
5
+
6
+ def self.new_class(&block)
7
+ klass = Class.new(Base)
8
+ klass.class_eval(&block) if block_given?
9
+ klass
10
+ end
11
+
12
+ class Base
13
+ class << self
14
+ KNOWN_ATTRIBUTE_TYPES = %w(string integer float)
15
+
16
+ def known_attributes
17
+ @known_attributes ||= {}
18
+ end
19
+
20
+ KNOWN_ATTRIBUTE_TYPES.each do |attr_type|
21
+ # def string(name, path, &block)
22
+ # known_attributes[name] = ['string', path, block]
23
+ # end
24
+ class_eval <<-EOV, __FILE__, __LINE__ + 1
25
+ def #{attr_type}(attribute, &block)
26
+ name, path = attribute.to_a.flatten
27
+ known_attributes[name] = ['#{attr_type}', path, block]
28
+ end
29
+ EOV
30
+ end
31
+ end
32
+
33
+ def initialize(html_string)
34
+ html = ::Nokogiri::HTML(html_string)
35
+ load_attributes(html)
36
+ end
37
+
38
+ def load_attributes(html)
39
+ known_attributes.each do |attr, options|
40
+ type, path, block = options
41
+
42
+ value = html.css(path)
43
+ value = block ? value.instance_eval(&block) : value.text
44
+ value = value.send("to_#{type[0]}")
45
+
46
+ instance_variable_set("@#{attr}", value)
47
+
48
+ self.class.send :define_method, attr do
49
+ instance_variable_get("@#{attr}")
50
+ end
51
+ end
52
+ end
53
+
54
+ def known_attributes
55
+ self.class.known_attributes
56
+ end
57
+
58
+ end
5
59
  end
@@ -0,0 +1,58 @@
1
+ require 'spec_helper'
2
+
3
+ describe HyperAPI do
4
+
5
+ describe '.new_class' do
6
+ it 'inherits HyperAPI::Base' do
7
+ foo = HyperAPI.new_class
8
+ expect(foo.superclass).to eq(HyperAPI::Base)
9
+ end
10
+ end
11
+
12
+ it 'loads attributes from html string'do
13
+ person = HyperAPI.new_class do
14
+ string name: 'div#name'
15
+ integer imdb_id: 'div#imdb'
16
+ end
17
+
18
+ bob = person.new('<div id="name">Bob</div><div id="imdb">111999</div>')
19
+
20
+ expect(bob.name).to eq('Bob')
21
+ expect(bob.imdb_id).to eq(111999)
22
+ end
23
+
24
+ it 'takes a block to extract complex attributes' do
25
+ SomeLinkClass = HyperAPI.new_class do
26
+ string url: 'a' do
27
+ attribute('href').text
28
+ end
29
+ end
30
+
31
+ google = SomeLinkClass.new('<a href="http://google.com">Google</a>')
32
+
33
+ expect(google.url).to eq('http://google.com')
34
+ end
35
+
36
+ it 'supports custom classes' do
37
+ class Person < HyperAPI::Base
38
+ integer imdb_id: 'div#imdb'
39
+ string name: 'div#name'
40
+ string url: 'a' do
41
+ attribute('href').value
42
+ end
43
+
44
+ def some_method
45
+ "#{name}: #{url}"
46
+ end
47
+ end
48
+
49
+ b = '<div id="name">B</div><div id="imdb">1</div><a href="http://google.com">G</a>'
50
+ bob = Person.new(b)
51
+
52
+ expect(bob.name).to eq('B')
53
+ expect(bob.url).to eq('http://google.com')
54
+ expect(bob.imdb_id).to eq(1)
55
+ expect(bob.some_method).to eq('B: http://google.com')
56
+ end
57
+
58
+ end
@@ -0,0 +1,25 @@
1
+ require 'hyper_api'
2
+
3
+ # This file was generated by the `rspec --init` command. Conventionally, all
4
+ # specs live under a `spec` directory, which RSpec adds to the `$LOAD_PATH`.
5
+ # Require this file using `require "spec_helper"` to ensure that it is only
6
+ # loaded once.
7
+ #
8
+ # See http://rubydoc.info/gems/rspec-core/RSpec/Core/Configuration
9
+ RSpec.configure do |config|
10
+ # Limit the spec run to only specs with the focus metadata. If no specs have
11
+ # the filtering metadata and `run_all_when_everything_filtered = true` then
12
+ # all specs will run.
13
+ config.filter_run :focus
14
+
15
+ # Run all specs when none match the provided filter. This works well in
16
+ # conjunction with `config.filter_run :focus`, as it will run the entire
17
+ # suite when no specs have `:filter` metadata.
18
+ config.run_all_when_everything_filtered = true
19
+
20
+ # Run specs in random order to surface order dependencies. If you find an
21
+ # order dependency and want to debug it, you can fix the order by providing
22
+ # the seed, which is printed after each run.
23
+ # --seed 1234
24
+ config.order = 'random'
25
+ end
metadata CHANGED
@@ -1,16 +1,43 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: hyper_api
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
5
- prerelease:
4
+ version: 0.1.0
6
5
  platform: ruby
7
6
  authors:
8
7
  - Javier Saldana
9
8
  autorequire:
10
9
  bindir: bin
11
10
  cert_chain: []
12
- date: 2014-02-15 00:00:00.000000000 Z
13
- dependencies: []
11
+ date: 2014-02-16 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: nokogiri
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ~>
18
+ - !ruby/object:Gem::Version
19
+ version: 1.6.0
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ~>
25
+ - !ruby/object:Gem::Version
26
+ version: 1.6.0
27
+ - !ruby/object:Gem::Dependency
28
+ name: rspec
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ~>
32
+ - !ruby/object:Gem::Version
33
+ version: 3.0.0.beta1
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ~>
39
+ - !ruby/object:Gem::Version
40
+ version: 3.0.0.beta1
14
41
  description:
15
42
  email:
16
43
  - javier@javiersaldana.com
@@ -20,35 +47,39 @@ extra_rdoc_files: []
20
47
  files:
21
48
  - .gitignore
22
49
  - Gemfile
50
+ - LICENSE
23
51
  - LICENSE.txt
24
52
  - README.md
25
53
  - Rakefile
26
54
  - hyper_api.gemspec
27
55
  - lib/hyper_api.rb
28
56
  - lib/hyper_api/version.rb
57
+ - spec/hyper_api_spec.rb
58
+ - spec/spec_helper.rb
29
59
  homepage: https://github.com/jassa/hyper_api
30
60
  licenses:
31
61
  - MIT
62
+ metadata: {}
32
63
  post_install_message:
33
64
  rdoc_options: []
34
65
  require_paths:
35
66
  - lib
36
67
  required_ruby_version: !ruby/object:Gem::Requirement
37
- none: false
38
68
  requirements:
39
- - - ! '>='
69
+ - - '>='
40
70
  - !ruby/object:Gem::Version
41
71
  version: '0'
42
72
  required_rubygems_version: !ruby/object:Gem::Requirement
43
- none: false
44
73
  requirements:
45
- - - ! '>='
74
+ - - '>='
46
75
  - !ruby/object:Gem::Version
47
76
  version: '0'
48
77
  requirements: []
49
78
  rubyforge_project:
50
- rubygems_version: 1.8.23
79
+ rubygems_version: 2.0.3
51
80
  signing_key:
52
- specification_version: 3
81
+ specification_version: 4
53
82
  summary: Hypertext API. A sweet DSL to create objects off HTML.
54
- test_files: []
83
+ test_files:
84
+ - spec/hyper_api_spec.rb
85
+ - spec/spec_helper.rb