gatherer_set_parser 0.0.1
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 +17 -0
- data/Gemfile +4 -0
- data/LICENSE +22 -0
- data/README.md +67 -0
- data/Rakefile +2 -0
- data/gatherer_set_parser.gemspec +25 -0
- data/lib/gatherer_set_parser/card_parser.rb +114 -0
- data/lib/gatherer_set_parser/fetch.rb +46 -0
- data/lib/gatherer_set_parser/query_string.rb +25 -0
- data/lib/gatherer_set_parser/version.rb +3 -0
- data/lib/gatherer_set_parser.rb +7 -0
- data/spec/gatherer_set_parser/card_parser_spec.rb +181 -0
- data/spec/gatherer_set_parser/fetch_spec.rb +30 -0
- data/spec/gatherer_set_parser/query_string_spec.rb +21 -0
- data/spec/gatherer_set_parser_spec.rb +2 -0
- data/spec/support/artifact.html +35 -0
- data/spec/support/dual_land.html +40 -0
- data/spec/support/enchant.html +40 -0
- data/spec/support/flipped_creature.html +35 -0
- data/spec/support/gold.html +35 -0
- data/spec/support/instant.html +35 -0
- data/spec/support/land.html +40 -0
- data/spec/support/legendary.html +35 -0
- data/spec/support/phyrexia.html +34 -0
- data/spec/support/planeswalker.html +35 -0
- data/spec/vcr_cassettes/dark_ascension.yml +17181 -0
- data/spec/vcr_setup.rb +10 -0
- metadata +176 -0
data/.gitignore
ADDED
data/Gemfile
ADDED
data/LICENSE
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
Copyright (c) 2012 David Ratajczak
|
2
|
+
|
3
|
+
MIT License
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
a copy of this software and associated documentation files (the
|
7
|
+
"Software"), to deal in the Software without restriction, including
|
8
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
the following conditions:
|
12
|
+
|
13
|
+
The above copyright notice and this permission notice shall be
|
14
|
+
included in all copies or substantial portions of the Software.
|
15
|
+
|
16
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,67 @@
|
|
1
|
+
# GathererSetParser
|
2
|
+
|
3
|
+
This is a tool for parsing the official Magic the Gathering card database for
|
4
|
+
a complete collection of cards belonging to a specific set. The cards of the
|
5
|
+
given set will be returned in an array of hashes.
|
6
|
+
|
7
|
+
This gem was extracted from a personal project, and hasn't been throughly
|
8
|
+
tested for every set in production. You'll likely want to refactor a lot of
|
9
|
+
the code before using it on a production server.
|
10
|
+
|
11
|
+
## Installation
|
12
|
+
|
13
|
+
Add this line to your application's Gemfile:
|
14
|
+
|
15
|
+
gem 'gatherer_set_parser'
|
16
|
+
|
17
|
+
And then execute:
|
18
|
+
|
19
|
+
$ bundle
|
20
|
+
|
21
|
+
Or install it yourself as:
|
22
|
+
|
23
|
+
$ gem install gatherer_set_parser
|
24
|
+
|
25
|
+
## Usage
|
26
|
+
|
27
|
+
This set requires you to pass in a case sensitive set name from the Gatherer
|
28
|
+
website. Here's an example:
|
29
|
+
|
30
|
+
```
|
31
|
+
# Create the array of cards from the given set name
|
32
|
+
cards = GathererSetParser::Fetch.new('Dark Ascension').cards
|
33
|
+
```
|
34
|
+
|
35
|
+
This will return an array of 171 cards. Here's an example of the output of
|
36
|
+
cards.first:
|
37
|
+
|
38
|
+
```
|
39
|
+
{ :title=> "Afflicted Deserter",
|
40
|
+
:card_type => "Creature",
|
41
|
+
:sub_type => "",
|
42
|
+
:power => 3,
|
43
|
+
:toughness => 2,
|
44
|
+
:cmc => 4,
|
45
|
+
:mana_cost => ["3", "R"],
|
46
|
+
:loyalty => nil,
|
47
|
+
:image_url => "http://gatherer.wizards.com/Handlers/Image.ashx?multiverseid=262675&type=card",
|
48
|
+
:text => "\r\n At the beginning of each upkeep, if no spells were cast last turn, transform Afflicted Deserter.",
|
49
|
+
:gatherer_url => "http://gatherer.wizards.com/Pages/Card/Details.aspx?multiverseid=262675",
|
50
|
+
:rarity => "Uncommon" }
|
51
|
+
```
|
52
|
+
|
53
|
+
## Contributing
|
54
|
+
|
55
|
+
1. Fork it
|
56
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
57
|
+
3. Commit your changes (`git commit -am 'Added some feature'`)
|
58
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
59
|
+
5. Create new Pull Request
|
60
|
+
|
61
|
+
## Contact
|
62
|
+
|
63
|
+
[david@mockra.com](mailto:david@mockra.com)
|
64
|
+
|
65
|
+
[@Mockra_](http://twitter.com/#!/mockra_)
|
66
|
+
|
67
|
+
[mockra.com](http://mockra.com)
|
data/Rakefile
ADDED
@@ -0,0 +1,25 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
require File.expand_path('../lib/gatherer_set_parser/version', __FILE__)
|
3
|
+
|
4
|
+
Gem::Specification.new do |gem|
|
5
|
+
gem.authors = ["David Ratajczak"]
|
6
|
+
gem.email = ["david@mockra.com"]
|
7
|
+
gem.description = %q{Parses the MTG Gatherer website for a collection of
|
8
|
+
cards from the provided set.}
|
9
|
+
gem.summary = %q{This gem will return an array of card hashes that you
|
10
|
+
can use to build a database of Magic the Gathering cards.}
|
11
|
+
gem.homepage = "https://github.com/mockra/gatherer_set_parser"
|
12
|
+
|
13
|
+
gem.files = `git ls-files`.split($\)
|
14
|
+
gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
|
15
|
+
gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
|
16
|
+
gem.name = "gatherer_set_parser"
|
17
|
+
gem.require_paths = ["lib"]
|
18
|
+
gem.version = GathererSetParser::VERSION
|
19
|
+
|
20
|
+
gem.add_development_dependency 'rake'
|
21
|
+
gem.add_development_dependency 'rspec'
|
22
|
+
gem.add_development_dependency 'fakeweb'
|
23
|
+
gem.add_development_dependency 'vcr'
|
24
|
+
gem.add_dependency 'nokogiri'
|
25
|
+
end
|
@@ -0,0 +1,114 @@
|
|
1
|
+
module GathererSetParser
|
2
|
+
class CardParser
|
3
|
+
|
4
|
+
attr_accessor :body
|
5
|
+
|
6
|
+
def initialize card
|
7
|
+
@body = card
|
8
|
+
end
|
9
|
+
|
10
|
+
def attributes
|
11
|
+
{ title: title,
|
12
|
+
card_type: type,
|
13
|
+
sub_type: sub_type,
|
14
|
+
power: power,
|
15
|
+
toughness: toughness,
|
16
|
+
cmc: cmc,
|
17
|
+
mana_cost: mana_cost,
|
18
|
+
loyalty: loyalty,
|
19
|
+
image_url: image_url,
|
20
|
+
text: text,
|
21
|
+
gatherer_url: gatherer_url,
|
22
|
+
rarity: rarity }
|
23
|
+
end
|
24
|
+
|
25
|
+
def title
|
26
|
+
body.css('.cardTitle > a').text
|
27
|
+
end
|
28
|
+
|
29
|
+
def type_box
|
30
|
+
body.css('span.typeLine').text.
|
31
|
+
gsub(/\n/, '').gsub(/[ ]{2,}/, ' ').strip.lstrip
|
32
|
+
end
|
33
|
+
|
34
|
+
def type
|
35
|
+
type_box.match(/[a-z0-9 ]*/i).to_s.strip
|
36
|
+
end
|
37
|
+
|
38
|
+
def sub_type
|
39
|
+
type_box.gsub(/\(.*\)/, '').
|
40
|
+
match(/ ([a-z0-9 ]*)\z/i)[1].to_s.lstrip.strip
|
41
|
+
rescue
|
42
|
+
nil
|
43
|
+
end
|
44
|
+
|
45
|
+
def power
|
46
|
+
type_box.match(/\(([0-9]*)\//)[1].to_i rescue nil
|
47
|
+
end
|
48
|
+
|
49
|
+
def toughness
|
50
|
+
type_box.match(/\/([0-9]*)\)/)[1].to_i rescue nil
|
51
|
+
end
|
52
|
+
|
53
|
+
def cmc
|
54
|
+
body.css('.convertedManaCost').text.to_i
|
55
|
+
end
|
56
|
+
|
57
|
+
def loyalty
|
58
|
+
type_box.match(/\(([0-9]*)\)/)[1].to_i rescue nil
|
59
|
+
end
|
60
|
+
|
61
|
+
def rarity
|
62
|
+
body.css('.rightCol > a').first.children.attribute('alt').text.
|
63
|
+
match(/\((.*)\)/)[1].to_s
|
64
|
+
end
|
65
|
+
|
66
|
+
def text
|
67
|
+
body.xpath('//div[@class="rulesText"]//img[@alt]').each{ |i| i.swap( i['alt'].parse_mana_cost ) }
|
68
|
+
body.css('.rulesText').text.gsub(/[ ]{2,}/, ' ')
|
69
|
+
end
|
70
|
+
|
71
|
+
def mana_cost
|
72
|
+
array = []
|
73
|
+
body.css('.manaCost >img').each do |img|
|
74
|
+
array << img.attribute('alt').text.parse_mana_cost
|
75
|
+
end
|
76
|
+
array
|
77
|
+
end
|
78
|
+
|
79
|
+
def image_url
|
80
|
+
'http://gatherer.wizards.com/' +
|
81
|
+
body.css('.leftCol > a > img').attribute('src').
|
82
|
+
text.gsub(/\.\.\//, '')
|
83
|
+
end
|
84
|
+
|
85
|
+
def gatherer_url
|
86
|
+
'http://gatherer.wizards.com/Pages/' +
|
87
|
+
body.css('.cardTitle > a').attribute('href').
|
88
|
+
text.gsub(/\.\.\//, '')
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
94
|
+
class String
|
95
|
+
def parse_mana_cost
|
96
|
+
extract_phyrexia.extract_colors.extract_unique_costs
|
97
|
+
end
|
98
|
+
|
99
|
+
def extract_phyrexia
|
100
|
+
gsub(/Phyrexian Blue/, 'U/P').gsub(/Phyrexian Black/, 'B/P').
|
101
|
+
gsub(/Phyrexian White/, 'W/P').gsub(/Phyrexian Red/, 'R/P').
|
102
|
+
gsub(/Phyrexian Green/, 'G/P')
|
103
|
+
end
|
104
|
+
|
105
|
+
def extract_colors
|
106
|
+
gsub(/Blue/, 'U').gsub(/Black/, 'B').gsub(/Red/, 'R').gsub(/Green/, 'G').
|
107
|
+
gsub(/White/, 'W')
|
108
|
+
end
|
109
|
+
|
110
|
+
def extract_unique_costs
|
111
|
+
gsub(/Variable Colorless/, 'X').gsub(/Two/, '2').gsub(/or/, '/').
|
112
|
+
gsub(/Snow/, 'S').gsub(/Tap/, 'T').gsub(/Untap/, 'Q')
|
113
|
+
end
|
114
|
+
end
|
@@ -0,0 +1,46 @@
|
|
1
|
+
require 'open-uri'
|
2
|
+
require 'nokogiri'
|
3
|
+
|
4
|
+
module GathererSetParser
|
5
|
+
class Fetch
|
6
|
+
|
7
|
+
include GathererSetParser::QueryString
|
8
|
+
|
9
|
+
attr_reader :set_name
|
10
|
+
|
11
|
+
def response_page page
|
12
|
+
Nokogiri::HTML open(gatherer_url page), nil, 'UTF-8'
|
13
|
+
end
|
14
|
+
|
15
|
+
def complete_set
|
16
|
+
@complete_set ||= gather_set
|
17
|
+
end
|
18
|
+
|
19
|
+
def gather_set
|
20
|
+
set, page = [], 0
|
21
|
+
current_page = response_page page
|
22
|
+
total_pages = current_page.css('.paging > a').count
|
23
|
+
begin
|
24
|
+
set << current_page
|
25
|
+
page += 1
|
26
|
+
current_page = response_page page
|
27
|
+
end while page < total_pages - 1
|
28
|
+
set
|
29
|
+
end
|
30
|
+
|
31
|
+
def cards
|
32
|
+
@cards ||= collect_cards
|
33
|
+
end
|
34
|
+
|
35
|
+
def collect_cards
|
36
|
+
collection = []
|
37
|
+
complete_set.each do |page|
|
38
|
+
page.css('.cardItemTable > tr > td > table').each do |card|
|
39
|
+
collection << CardParser.new(card).attributes
|
40
|
+
end
|
41
|
+
end
|
42
|
+
collection
|
43
|
+
end
|
44
|
+
|
45
|
+
end
|
46
|
+
end
|
@@ -0,0 +1,25 @@
|
|
1
|
+
module GathererSetParser
|
2
|
+
module QueryString
|
3
|
+
|
4
|
+
def initialize set
|
5
|
+
@set_name = set
|
6
|
+
end
|
7
|
+
|
8
|
+
def escaped_set
|
9
|
+
@query_string ||= URI.escape set_name
|
10
|
+
end
|
11
|
+
|
12
|
+
def query_string
|
13
|
+
"output=standard&set=[%22#{escaped_set}%22]"
|
14
|
+
end
|
15
|
+
|
16
|
+
def url
|
17
|
+
"http://gatherer.wizards.com/Pages/Search/Default.aspx?"
|
18
|
+
end
|
19
|
+
|
20
|
+
def gatherer_url page
|
21
|
+
url + query_string + "&page=#{page}"
|
22
|
+
end
|
23
|
+
|
24
|
+
end
|
25
|
+
end
|
@@ -0,0 +1,181 @@
|
|
1
|
+
require 'gatherer_set_parser_spec'
|
2
|
+
require 'fakeweb'
|
3
|
+
|
4
|
+
describe GathererSetParser::CardParser do
|
5
|
+
|
6
|
+
let(:parsed_card) { GathererSetParser::CardParser.new card }
|
7
|
+
|
8
|
+
describe '#parse_card' do
|
9
|
+
let(:card) { Nokogiri::HTML open('spec/support/flipped_creature.html') }
|
10
|
+
|
11
|
+
it 'should return a hash' do
|
12
|
+
parsed_card.attributes.should be_a Hash
|
13
|
+
end
|
14
|
+
|
15
|
+
it 'should have a title' do
|
16
|
+
parsed_card.attributes[:title].should_not be_nil
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
describe '#card_attributes' do
|
21
|
+
context 'back of flip card' do
|
22
|
+
let(:card) { Nokogiri::HTML open('spec/support/flipped_creature.html') }
|
23
|
+
|
24
|
+
it 'should return the correct title' do
|
25
|
+
parsed_card.title.should == "Tovolar's Magehunter"
|
26
|
+
end
|
27
|
+
|
28
|
+
it 'should return a card type' do
|
29
|
+
parsed_card.type.should == 'Creature'
|
30
|
+
end
|
31
|
+
|
32
|
+
it 'should match the species type' do
|
33
|
+
parsed_card.sub_type.should == 'Werewolf'
|
34
|
+
end
|
35
|
+
|
36
|
+
it 'should have the correct power' do
|
37
|
+
parsed_card.power.should == 5
|
38
|
+
end
|
39
|
+
|
40
|
+
it 'should have the correct toughness' do
|
41
|
+
parsed_card.toughness.should == 5
|
42
|
+
end
|
43
|
+
|
44
|
+
it 'should have no loyalty' do
|
45
|
+
parsed_card.loyalty.should be_nil
|
46
|
+
end
|
47
|
+
|
48
|
+
it 'should have a cmc' do
|
49
|
+
parsed_card.cmc.should == 0
|
50
|
+
end
|
51
|
+
|
52
|
+
it 'should have the correct rarity' do
|
53
|
+
parsed_card.rarity.should == 'Rare'
|
54
|
+
end
|
55
|
+
|
56
|
+
it 'should have text' do
|
57
|
+
parsed_card.text.should =~ /transform/i
|
58
|
+
end
|
59
|
+
|
60
|
+
it 'should have the correct mana cost' do
|
61
|
+
parsed_card.mana_cost.should == []
|
62
|
+
end
|
63
|
+
|
64
|
+
it 'should have the correct image url' do
|
65
|
+
parsed_card.image_url.should =~
|
66
|
+
/\/Handlers\/Image\.ashx\?multiverseid\=253429\&type\=card/
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
context 'an instant/sorcery' do
|
71
|
+
let(:card) { Nokogiri::HTML open('spec/support/instant.html') }
|
72
|
+
|
73
|
+
it 'should have no power' do
|
74
|
+
parsed_card.power.should be_nil
|
75
|
+
end
|
76
|
+
|
77
|
+
it 'should have no loyalty' do
|
78
|
+
parsed_card.loyalty.should be_nil
|
79
|
+
end
|
80
|
+
|
81
|
+
it 'should have the correct type' do
|
82
|
+
parsed_card.type.should == 'Instant'
|
83
|
+
end
|
84
|
+
|
85
|
+
it 'should have the correct rarity' do
|
86
|
+
parsed_card.rarity.should == 'Uncommon'
|
87
|
+
end
|
88
|
+
|
89
|
+
it 'should have the correct mana cost' do
|
90
|
+
parsed_card.mana_cost.should == %w[1 U]
|
91
|
+
end
|
92
|
+
|
93
|
+
it 'should have no sub type' do
|
94
|
+
parsed_card.sub_type.should be_nil
|
95
|
+
end
|
96
|
+
end
|
97
|
+
|
98
|
+
context 'land' do
|
99
|
+
let(:card) { Nokogiri::HTML open('spec/support/land.html') }
|
100
|
+
|
101
|
+
it 'should have the correct mana cost' do
|
102
|
+
parsed_card.mana_cost.should == []
|
103
|
+
end
|
104
|
+
|
105
|
+
it 'should have no power' do
|
106
|
+
parsed_card.power.should be_nil
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
context 'planeswalker' do
|
111
|
+
let(:card) { Nokogiri::HTML open('spec/support/planeswalker.html') }
|
112
|
+
|
113
|
+
it 'should have a title' do
|
114
|
+
parsed_card.title.should =~ /Tamiyo/i
|
115
|
+
end
|
116
|
+
|
117
|
+
it 'should have no power' do
|
118
|
+
parsed_card.power.should be_nil
|
119
|
+
end
|
120
|
+
|
121
|
+
it 'should have no toughness' do
|
122
|
+
parsed_card.power.should be_nil
|
123
|
+
end
|
124
|
+
|
125
|
+
it 'should have loyalty' do
|
126
|
+
parsed_card.loyalty.should == 4
|
127
|
+
end
|
128
|
+
|
129
|
+
it 'should have the correct type' do
|
130
|
+
parsed_card.type.should == 'Planeswalker'
|
131
|
+
end
|
132
|
+
|
133
|
+
it 'should have the correct rarity' do
|
134
|
+
parsed_card.rarity.should == 'Mythic Rare'
|
135
|
+
end
|
136
|
+
|
137
|
+
it 'should have the correct mana cost' do
|
138
|
+
parsed_card.mana_cost.should == %w[3 U U]
|
139
|
+
end
|
140
|
+
|
141
|
+
it 'should have correct gatherer url' do
|
142
|
+
parsed_card.gatherer_url.should =~
|
143
|
+
/Card\/Details\.aspx\?multiverseid\=240070/
|
144
|
+
end
|
145
|
+
end
|
146
|
+
|
147
|
+
context 'phyrexian' do
|
148
|
+
let(:card) { Nokogiri::HTML open('spec/support/phyrexia.html') }
|
149
|
+
|
150
|
+
it 'should have the correct mana cost' do
|
151
|
+
parsed_card.mana_cost.should == %w[X G/P]
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
155
|
+
context 'enchant' do
|
156
|
+
let(:card) { Nokogiri::HTML open('spec/support/enchant.html') }
|
157
|
+
|
158
|
+
it 'should have the correct mana cost' do
|
159
|
+
parsed_card.mana_cost.should == %w[4 B B]
|
160
|
+
end
|
161
|
+
end
|
162
|
+
|
163
|
+
context 'gold' do
|
164
|
+
end
|
165
|
+
|
166
|
+
context 'dual_land' do
|
167
|
+
let(:card) { Nokogiri::HTML open('spec/support/dual_land.html') }
|
168
|
+
|
169
|
+
it 'should have the correct text' do
|
170
|
+
parsed_card.text.should =~ /U/i
|
171
|
+
end
|
172
|
+
end
|
173
|
+
|
174
|
+
context 'legendary' do
|
175
|
+
end
|
176
|
+
|
177
|
+
context 'artifact' do
|
178
|
+
end
|
179
|
+
end
|
180
|
+
|
181
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
require 'gatherer_set_parser_spec'
|
2
|
+
|
3
|
+
describe GathererSetParser::Fetch do
|
4
|
+
|
5
|
+
let(:gatherer) { GathererSetParser::Fetch.new 'Dark Ascension' }
|
6
|
+
|
7
|
+
describe '.new' do
|
8
|
+
it 'should assign the set_name' do
|
9
|
+
gatherer.set_name.should == 'Dark Ascension'
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
describe '#response_body' do
|
14
|
+
use_vcr_cassette 'dark_ascension'
|
15
|
+
|
16
|
+
it 'should contain every page' do
|
17
|
+
gatherer.complete_set.count.should == 7
|
18
|
+
end
|
19
|
+
|
20
|
+
it 'should contain a magic card' do
|
21
|
+
gatherer.complete_set.last.text.should =~ /wakedancer/i
|
22
|
+
end
|
23
|
+
|
24
|
+
it 'should have the complete set of cards' do
|
25
|
+
gatherer.cards.count.should == 171
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
end
|
30
|
+
|
@@ -0,0 +1,21 @@
|
|
1
|
+
require 'gatherer_set_parser_spec'
|
2
|
+
|
3
|
+
describe GathererSetParser::QueryString do
|
4
|
+
|
5
|
+
let(:gatherer) { GathererSetParser::Fetch.new 'Dark Ascension' }
|
6
|
+
|
7
|
+
describe '#escaped_set' do
|
8
|
+
it 'should escape set_name to query string' do
|
9
|
+
gatherer.escaped_set.should == 'Dark%20Ascension'
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
describe '#query_string' do
|
14
|
+
it 'should contain the entire query' do
|
15
|
+
gatherer.query_string.should ==
|
16
|
+
'output=standard&set=[%22Dark%20Ascension%22]'
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
end
|
21
|
+
|
@@ -0,0 +1,35 @@
|
|
1
|
+
<table>
|
2
|
+
<tr class="cardItem evenItem">
|
3
|
+
<td class="leftCol">
|
4
|
+
<div class="clear"></div>
|
5
|
+
<a href="../Card/Details.aspx?multiverseid=230070" id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl00_cardImageLink" onclick="return CardLinkAction(event, this, 'SameWindow');">
|
6
|
+
<img src="../../Handlers/Image.ashx?multiverseid=230070&type=card" id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl00_cardImage" width="95" height="132" alt="Conversion Chamber" border="0" />
|
7
|
+
</a>
|
8
|
+
<div class="clear"></div>
|
9
|
+
</td>
|
10
|
+
<td class="middleCol">
|
11
|
+
<div class="clear"></div>
|
12
|
+
<div class="cardInfo">
|
13
|
+
<span class="cardTitle">
|
14
|
+
<a id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl00_cardTitle" onclick="return CardLinkAction(event, this, 'SameWindow');" href="../Card/Details.aspx?multiverseid=230070">Conversion Chamber</a></span> <span class="manaCost">
|
15
|
+
<img src="/Handlers/Image.ashx?size=small&name=3&type=symbol" alt="3" align="absbottom" /></span> (<span class="convertedManaCost">3</span>)
|
16
|
+
<br />
|
17
|
+
<span class="typeLine">
|
18
|
+
Artifact
|
19
|
+
</span>
|
20
|
+
<br />
|
21
|
+
<div class="rulesText">
|
22
|
+
<p><img src="/Handlers/Image.ashx?size=small&name=2&type=symbol" alt="2" align="absbottom" />, <img src="/Handlers/Image.ashx?size=small&name=tap&type=symbol" alt="Tap" align="absbottom" />: Exile target artifact card from a graveyard. Put a charge counter on Conversion Chamber.</p><p><img src="/Handlers/Image.ashx?size=small&name=2&type=symbol" alt="2" align="absbottom" />, <img src="/Handlers/Image.ashx?size=small&name=tap&type=symbol" alt="Tap" align="absbottom" />, Remove a charge counter from Conversion Chamber: Put a 3/3 colorless Golem artifact creature token onto the battlefield.</p></div>
|
23
|
+
</div>
|
24
|
+
</td>
|
25
|
+
<td class="rightCol setVersions">
|
26
|
+
<div class="clear"></div>
|
27
|
+
<div>
|
28
|
+
<div id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl00_cardSetCurrent" class="rightCol">
|
29
|
+
<a onclick="return CardLinkAction(event, this, 'SameWindow');" href="../Card/Details.aspx?multiverseid=230070"><img title="New Phyrexia (Uncommon)" src="../../Handlers/Image.ashx?type=symbol&set=NPH&size=small&rarity=U" alt="New Phyrexia (Uncommon)" style="border-width:0px;" /></a>
|
30
|
+
</div>
|
31
|
+
</div>
|
32
|
+
|
33
|
+
</td>
|
34
|
+
</tr>
|
35
|
+
</table>
|
@@ -0,0 +1,40 @@
|
|
1
|
+
<table>
|
2
|
+
<tr class="cardItem oddItem">
|
3
|
+
<td class="leftCol">
|
4
|
+
<div class="clear"></div>
|
5
|
+
<a href="../Card/Details.aspx?multiverseid=253682" id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl11_cardImageLink" onclick="return CardLinkAction(event, this, 'SameWindow');">
|
6
|
+
<img src="../../Handlers/Image.ashx?multiverseid=253682&type=card" id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl11_cardImage" width="95" height="132" alt="Steam Vents" border="0" />
|
7
|
+
</a>
|
8
|
+
<div class="clear"></div>
|
9
|
+
</td>
|
10
|
+
<td class="middleCol">
|
11
|
+
<div class="clear"></div>
|
12
|
+
<div class="cardInfo">
|
13
|
+
<span class="cardTitle">
|
14
|
+
<a id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl11_cardTitle" onclick="return CardLinkAction(event, this, 'SameWindow');" href="../Card/Details.aspx?multiverseid=253682">Steam Vents</a></span> <span class="manaCost">
|
15
|
+
</span> (<span class="convertedManaCost">0</span>)
|
16
|
+
<br />
|
17
|
+
<span class="typeLine">
|
18
|
+
Land — Island Mountain
|
19
|
+
</span>
|
20
|
+
<div class="rulesText">
|
21
|
+
<p><i>(<img src="/Handlers/Image.ashx?size=small&name=tap&type=symbol" alt="Tap" align="absbottom" />: Add <img src="/Handlers/Image.ashx?size=small&name=U&type=symbol" alt="Blue" align="absbottom" /> or <img src="/Handlers/Image.ashx?size=small&name=R&type=symbol" alt="Red" align="absbottom" /> to your mana pool.)</i></p><p>As Steam Vents enters the battlefield, you may pay 2 life. If you don't, Steam Vents enters the battlefield tapped.</p></div>
|
22
|
+
</div>
|
23
|
+
</td>
|
24
|
+
<td class="rightCol setVersions">
|
25
|
+
<div class="clear"></div>
|
26
|
+
<div>
|
27
|
+
<div id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl11_cardSetCurrent" class="rightCol">
|
28
|
+
<a onclick="return CardLinkAction(event, this, 'SameWindow');" href="../Card/Details.aspx?multiverseid=253682"><img title="Return to Ravnica (Rare)" src="../../Handlers/Image.ashx?type=symbol&set=RTR&size=small&rarity=R" alt="Return to Ravnica (Rare)" style="border-width:0px;" /></a>
|
29
|
+
</div>
|
30
|
+
</div>
|
31
|
+
<div id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl11_otherSetSection" class="otherSetSection">
|
32
|
+
<div>
|
33
|
+
<i>Other Versions</i></div>
|
34
|
+
<div id="ctl00_ctl00_ctl00_MainContent_SubContent_SubContent_ctl00_listRepeater_ctl11_cardSets" class="rightCol">
|
35
|
+
<a onclick="return CardLinkAction(event, this, 'SameWindow');" href="../Card/Details.aspx?multiverseid=96923"><img title="Guildpact (Rare)" src="../../Handlers/Image.ashx?type=symbol&set=GPT&size=small&rarity=R" alt="Guildpact (Rare)" style="border-width:0px;" /></a>
|
36
|
+
</div>
|
37
|
+
</div>
|
38
|
+
</td>
|
39
|
+
</tr>
|
40
|
+
</table>
|