romloader 0.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/Gemfile +3 -0
- data/LICENSE +21 -0
- data/README.md +31 -0
- data/bin/romloader +3 -0
- data/lib/romloader/freeroms_scraper.rb +110 -0
- data/lib/romloader/game_rom.rb +53 -0
- data/lib/romloader/game_system.rb +92 -0
- data/lib/romloader/romloader_cli.rb +248 -0
- data/lib/romloader/scraping_error/no_element_found.rb +7 -0
- data/lib/romloader.rb +7 -0
- metadata +111 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 6f557300ce6914298480061925476c3bdb8e1b05
|
4
|
+
data.tar.gz: 19343b3980b59dc344cfb1c8e11182076d7f5009
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 10c416b0f71e1176aca6bb24c4dc68087ce1640a6feca1da6345edf01b2b96cbd922555f90e5958b45265c9a2f93ac98f80c75fce1e098494d158b23bd0c3656
|
7
|
+
data.tar.gz: c67d64422a5cd3c7a14497d49c7063656c9e7f87e9162a6e26cdbb0815587c52ba03c10d19fbf4e0a101f4c3b3ae75b26530bd396cb603bcf033fdd6327174de
|
data/Gemfile
ADDED
data/LICENSE
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
MIT License
|
2
|
+
|
3
|
+
Copyright (c) 2016 Efrain Perez Jr
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
7
|
+
in the Software without restriction, including without limitation the rights
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
10
|
+
furnished to do so, subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
13
|
+
copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
21
|
+
SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
# RomLoader
|
2
|
+
|
3
|
+
A Ruby Gem for downloading videogame roms, powered by freeroms.com.
|
4
|
+
|
5
|
+
## Installation
|
6
|
+
|
7
|
+
$ gem install romloader
|
8
|
+
|
9
|
+
## Usage
|
10
|
+
|
11
|
+
Type the command below into your shell and follow the on screen prompts.
|
12
|
+
|
13
|
+
$ romloader
|
14
|
+
|
15
|
+
## Development
|
16
|
+
|
17
|
+
To develop further upon this gem, fork and clone the repository located at https://github.com/jinstrider2000/romloader-cli-gem.
|
18
|
+
Be sure to have the Bundler gem installed, and run:
|
19
|
+
|
20
|
+
$ bundle install
|
21
|
+
|
22
|
+
This will download any dependencies for development. Rspec is among the dependencies, however, there are no tests included in the repo. I intend to add some eventually.
|
23
|
+
|
24
|
+
## Contributing
|
25
|
+
|
26
|
+
Bug reports and pull requests are welcome on GitHub at https://github.com/jinstrider2000/romloader-cli-gem.
|
27
|
+
|
28
|
+
|
29
|
+
## License
|
30
|
+
|
31
|
+
The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
|
data/bin/romloader
ADDED
@@ -0,0 +1,110 @@
|
|
1
|
+
require 'open-uri'
|
2
|
+
require 'nokogiri'
|
3
|
+
require 'cgi'
|
4
|
+
|
5
|
+
# The class which facilitates scraping freeroms.com. Uses the nokogiri gem to scrape the site
|
6
|
+
class FreeromsScraper
|
7
|
+
# Class Variables: none
|
8
|
+
#
|
9
|
+
# Instance Variables: none
|
10
|
+
|
11
|
+
# Purpose: To retrieve the names and main rom urls of the game systems currently begin served by freeroms.com. Returns this information in the form of an array of hashes
|
12
|
+
def self.system_scrape(url)
|
13
|
+
# Arguments:
|
14
|
+
# => 1. url (String): Contains the url "http://freeroms.com"
|
15
|
+
#
|
16
|
+
# Return:
|
17
|
+
# => Array<Hash>
|
18
|
+
system_list = Nokogiri::HTML(open(url)).css("dt.leftside > a")
|
19
|
+
[].tap do |game_system|
|
20
|
+
system_list.each do |system_info|
|
21
|
+
if system_info.text != "Links" && system_info.text != "Flash Games" && system_info.text != ""
|
22
|
+
system_name = system_info.text
|
23
|
+
begin
|
24
|
+
system_rom_url = system_info.attribute("href").value
|
25
|
+
rescue NoMethodError
|
26
|
+
#Do Nothing, catch the error and move on. This is fine, because the hash will not be added to the array being compiled.
|
27
|
+
else
|
28
|
+
game_system << {name: system_name, rom_index_url: system_rom_url}
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
# Purpose: To retrieve the names and main rom urls of the individual games currently begin served by freeroms.com. Returns this information in the form of an array of hashes
|
36
|
+
def self.rom_scrape(url)
|
37
|
+
# Arguments:
|
38
|
+
# => 1. url (String): Contains the url for each game
|
39
|
+
#
|
40
|
+
# Return:
|
41
|
+
# => Array<Hash>
|
42
|
+
game_list = Nokogiri::HTML(open(url)).css("tr[class^=\"game\"] > td[align=\"left\"]")
|
43
|
+
[].tap do |rom_list|
|
44
|
+
game_list.each do |game_info|
|
45
|
+
begin
|
46
|
+
download_link = game_info.css("a").attribute("href").value
|
47
|
+
rescue NoMethodError
|
48
|
+
#Do Nothing, catch the error and move on. This is fine, because the hash will not be added to the array being compiled.
|
49
|
+
else
|
50
|
+
game_name = game_info.css("span").text
|
51
|
+
unless game_name == ""
|
52
|
+
game_name.gsub!(/[[:space:]]{2,}/) {|white_spaces| " "}
|
53
|
+
download_link.gsub!(/[[:space:]]/) {|white_space| CGI::escape(white_space)} unless download_link.ascii_only?
|
54
|
+
rom_list << {name: game_name, rom_detail_url: download_link}
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
# Purpose: To retrieve the detailed information of individual games currently begin served by freeroms.com. Returns this information in the form of a hash
|
62
|
+
def self.rom_details(url)
|
63
|
+
# Arguments:
|
64
|
+
# => 1. url (String): Contains the url for each game
|
65
|
+
#
|
66
|
+
# Return:
|
67
|
+
# => Hash
|
68
|
+
direct_download = Nokogiri::HTML(open(url))
|
69
|
+
{}.tap do |game|
|
70
|
+
unless direct_download.css("td#romss > script").empty?
|
71
|
+
game_name = direct_download.css("tr.gametitle > td[colspan=\"2\"]").text
|
72
|
+
begin
|
73
|
+
game_url = /http:\/\/.+(\.zip|\.7z)/.match(direct_download.css("td#romss > script").first.children.first.text)
|
74
|
+
rescue NoMethodError
|
75
|
+
#Do Nothing, catch the error and move on. This is fine, because the hash will be empty, which can be handled by GameRom#set_rom_details
|
76
|
+
else
|
77
|
+
if game_url
|
78
|
+
game[:download_url] = game_url[0]
|
79
|
+
game[:file_ext] = game_url[1]
|
80
|
+
begin
|
81
|
+
game[:size] = direct_download.css("td#rom + td[colspan=\"2\"]").first.children.first.text.strip
|
82
|
+
rescue NoMethodError
|
83
|
+
game[:size] = "N/A"
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|
89
|
+
end
|
90
|
+
|
91
|
+
# Purpose: To retrieve the letter indices for the roms of the game systems currently begin served by freeroms.com. Returns this information in the form of a hash
|
92
|
+
def self.rom_index_scrape(url)
|
93
|
+
# Arguments:
|
94
|
+
# => 1. url (String): Contains the url for the letter indices
|
95
|
+
#
|
96
|
+
# Return:
|
97
|
+
# => Hash
|
98
|
+
rom_letter_list = Nokogiri::HTML(open(url)).css("tr.letters > td[align=\"center\"] > font > a")
|
99
|
+
{}.tap do |letter_hash|
|
100
|
+
rom_letter_list.each do |letter_list|
|
101
|
+
letter = letter_list.text.strip
|
102
|
+
begin
|
103
|
+
letter_hash[letter] = letter_list.attribute("href").value if letter =~ /\A[A-Z#]\Z/
|
104
|
+
rescue NoMethodError
|
105
|
+
#Do Nothing, catch the error and move on. This is fine, because the hash pair will not added.
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
109
|
+
end
|
110
|
+
end
|
@@ -0,0 +1,53 @@
|
|
1
|
+
|
2
|
+
# The class whose instances represent an individual game rom (e.g. Chrono Trigger object)
|
3
|
+
class GameRom
|
4
|
+
# Class Variables: none
|
5
|
+
#
|
6
|
+
# Instance Variables:
|
7
|
+
# => 1. name (String): Contains the system's name (e.g. "Sega Genesis")
|
8
|
+
# => 2. download_url (String): Contains a string with the url to download the game (e.g. "http://download.freeroms.com/genesis/a_roms/altered_beast.zip")
|
9
|
+
# => 3. rom_detail_url (String): Contains a string with the url to details of the game
|
10
|
+
# => 4. size (String): Contains a string with the size of download, as published on freeroms.com
|
11
|
+
# => 5. file_ext (String): Contains a string with the download file index (e.g. ".zip")
|
12
|
+
# => 6. system (GameSystem): Points to the GameSystem object that contains this GameRom instance
|
13
|
+
attr_accessor :name, :system
|
14
|
+
attr_reader :rom_detail_url ,:download_url, :size, :file_ext
|
15
|
+
|
16
|
+
# Purpose: Create individual game rom objects from information scraped from freeroms.com, and sets the required name and rom_detail_url instance variables
|
17
|
+
def initialize(name:, rom_detail_url:)
|
18
|
+
# Arguments:
|
19
|
+
# => 1. name (String): Contains the game's name (e.g. "Super Mario Bros 3")
|
20
|
+
# => 2. rom_detail_url (String): Contains a string with the url to details of the game
|
21
|
+
#
|
22
|
+
# Return:
|
23
|
+
# => GameRom object
|
24
|
+
@name = name
|
25
|
+
@rom_detail_url = rom_detail_url
|
26
|
+
end
|
27
|
+
|
28
|
+
# Purpose: Creates an array of GameRom objects from an array
|
29
|
+
def self.create_collection(game_array)
|
30
|
+
# Arguments:
|
31
|
+
# => 1. game_array (Array<Hash>): Contains the game's information
|
32
|
+
#
|
33
|
+
# Return:
|
34
|
+
# => Array<GameRom>
|
35
|
+
game_array.collect {|game_details| self.new(game_details)}
|
36
|
+
end
|
37
|
+
|
38
|
+
# Purpose: Sets all additional, optional rom details
|
39
|
+
def set_rom_details(download_url: nil, size: nil, file_ext: nil)
|
40
|
+
# Arguments:
|
41
|
+
# => 1. download_url [optional] (String): Contains a string with the url to download the game
|
42
|
+
# => 2. size [optional] (String): Contains a string with the size of download, as published on freeroms.com
|
43
|
+
# => 3. file_ext (String): Contains a string with the download file index (e.g. ".zip")
|
44
|
+
#
|
45
|
+
# Return:
|
46
|
+
# => nil
|
47
|
+
@download_url = download_url
|
48
|
+
@size = size
|
49
|
+
@file_ext = file_ext
|
50
|
+
nil
|
51
|
+
end
|
52
|
+
|
53
|
+
end
|
@@ -0,0 +1,92 @@
|
|
1
|
+
|
2
|
+
# The class whose instances represent an individual game system (e.g. Sega Genesis object)
|
3
|
+
class GameSystem
|
4
|
+
# Class Variables:
|
5
|
+
# => 1. all (Array<GameSystem>): Contains an array of all GameSystem objects that have been instantiated.
|
6
|
+
#
|
7
|
+
# Instance Variables:
|
8
|
+
# => 1. name (String): Contains the system's name (e.g. "Sega Genesis")
|
9
|
+
# => 2. rom_indices (Hash): Contains key/value pairs of a rom index letter and a url (e.g. {"A" => "http://freeroms.com/genesis_games_that_start_with_a.html"})
|
10
|
+
# => 3. roms (Hash): Contains key/value pairs of a rom index letter and an array of GameRom objects (e.g. {"S" => [Sonic the Hedgehog, Streets of Rage,...], "T" => [...], etc})
|
11
|
+
# => 4. rom_index_url (String): Contains the url that leads to the rom index for the given system on http://freeroms.com
|
12
|
+
|
13
|
+
attr_accessor :name, :rom_index_url
|
14
|
+
attr_writer :rom_indices
|
15
|
+
|
16
|
+
@@all = []
|
17
|
+
|
18
|
+
# Purpose: Create individual game system objects from information scraped from http://freeroms.com, sets all instance variables
|
19
|
+
def initialize(name:, rom_index_url:)
|
20
|
+
# Arguments:
|
21
|
+
# => 1. name (String): Contains the system's name (e.g. "Sega Genesis")
|
22
|
+
# => 2. rom_index_url (String): Contains the url that leads to the rom index for the given system on http://freeroms.com
|
23
|
+
#
|
24
|
+
# Return:
|
25
|
+
# => GameSystem object
|
26
|
+
@name = name
|
27
|
+
@rom_index_url = rom_index_url
|
28
|
+
@rom_indices = {}
|
29
|
+
@roms = {}
|
30
|
+
@@all << self
|
31
|
+
end
|
32
|
+
|
33
|
+
# Purpose: Creates multiple GameSystem objects from information scraped from http://freeroms.com
|
34
|
+
def self.create_from_collection(system_array)
|
35
|
+
# Arguments:
|
36
|
+
# => 1. system_array (Array<Hash>): Contains an array of key/value pairs of the GameSystem instance variables and values (e.g. [{:name =>"NES"...},{:name => "SNES"..,},etc])
|
37
|
+
#
|
38
|
+
# Return:
|
39
|
+
# => nil
|
40
|
+
system_array.each { |system_details| self.new(system_details)}
|
41
|
+
nil
|
42
|
+
end
|
43
|
+
|
44
|
+
# Purpose: Retrieves an array of all GameSystem objects
|
45
|
+
def self.all
|
46
|
+
# Arguments: None
|
47
|
+
#
|
48
|
+
# Return:
|
49
|
+
# => Array<GameSystem>
|
50
|
+
@@all
|
51
|
+
end
|
52
|
+
|
53
|
+
# Purpose: Retrieves an array of all GameRom objects starting which the provided letter index (e.g. [Sonic the Hedgehog, Streets of Rage,...])
|
54
|
+
def get_roms_by_letter(letter_index)
|
55
|
+
# Arguments:
|
56
|
+
# => 1. letter_index (String): Letter used as key to retrieve array
|
57
|
+
# Return:
|
58
|
+
# => Array<GameRom>
|
59
|
+
@roms[letter_index]
|
60
|
+
end
|
61
|
+
|
62
|
+
# Purpose: Retrieves an array of the indicies for the roms (i.e. ["A","B","C"...])
|
63
|
+
def get_rom_indices
|
64
|
+
# Arguments: None
|
65
|
+
#
|
66
|
+
# Return:
|
67
|
+
# => Array<String>
|
68
|
+
@rom_indices.keys
|
69
|
+
end
|
70
|
+
|
71
|
+
# Purpose: Retrieves the url for roms of a particular letter index (e.g. "A" => "http://freeroms.com/genesis_games_that_start_with_a.html")
|
72
|
+
def get_rom_collection_url(letter_index)
|
73
|
+
# Arguments:
|
74
|
+
# => 1. letter_index (String): Letter used as key to retrieve url
|
75
|
+
# Return:
|
76
|
+
# => String
|
77
|
+
@rom_indices[letter_index]
|
78
|
+
end
|
79
|
+
|
80
|
+
# Purpose: Add the game collection scraped from http://freeroms.com to the GameSystem object to the roms (Hash)
|
81
|
+
def add_roms_to_collection_by_letter(letter_index, game_obj_array)
|
82
|
+
# Arguments:
|
83
|
+
# => 1. letter_index (String): Letter to be used as a key for the roms Hash
|
84
|
+
# => 2. game_obj_array (Array<GameRom>): Contains array of GameRom objects (e.g. [Sonic the Hedgehog, Streets of Rage,...]
|
85
|
+
#
|
86
|
+
# Return:
|
87
|
+
# => Array<GameRom>
|
88
|
+
game_obj_array.each { |game| game.system = self }
|
89
|
+
@roms[letter_index] = game_obj_array
|
90
|
+
end
|
91
|
+
|
92
|
+
end
|
@@ -0,0 +1,248 @@
|
|
1
|
+
require_relative 'freeroms_scraper.rb'
|
2
|
+
require_relative 'game_rom.rb'
|
3
|
+
require_relative 'game_system.rb'
|
4
|
+
require_relative 'scraping_error/no_element_found.rb'
|
5
|
+
|
6
|
+
# The CLI class
|
7
|
+
class RomloaderCli
|
8
|
+
# Class Variables: none
|
9
|
+
#
|
10
|
+
# Instance Variables: none
|
11
|
+
|
12
|
+
# Purpose: Instantiates a GameSystem collection from information scraped from http://freeroms.com
|
13
|
+
def initialize
|
14
|
+
# Arguments: None
|
15
|
+
#
|
16
|
+
# Return:
|
17
|
+
# => RomloaderCli object
|
18
|
+
GameSystem.create_from_collection(FreeromsScraper.system_scrape("http://freeroms.com"))
|
19
|
+
raise ScrapingError::NoElementFound.exception("System index is currently unavailable. Exiting the program.") if GameSystem.all.size == 0
|
20
|
+
end
|
21
|
+
|
22
|
+
# Purpose: Starts the CLI, called in romloader.rb
|
23
|
+
def start
|
24
|
+
# Arguments: None
|
25
|
+
#
|
26
|
+
# Return:
|
27
|
+
# => nil
|
28
|
+
input_stack = []
|
29
|
+
control_flow_level = 1
|
30
|
+
|
31
|
+
puts "Thanks for using RomLoader, powered by freeroms.com!\nConnecting to freeroms.com and retrieving the system index...\n\n"
|
32
|
+
sleep 1
|
33
|
+
while control_flow_level > 0
|
34
|
+
case control_flow_level
|
35
|
+
when 1
|
36
|
+
list_systems
|
37
|
+
input = input_prompt("Select a system (1-#{GameSystem.all.size}) [exit]:",1..GameSystem.all.size)
|
38
|
+
if input == "exit"
|
39
|
+
control_flow_level = 0
|
40
|
+
else
|
41
|
+
input_stack.unshift(input)
|
42
|
+
control_flow_level += 1
|
43
|
+
end
|
44
|
+
when 2
|
45
|
+
system = select_system(input_stack[0].to_i)
|
46
|
+
list_system_index(system)
|
47
|
+
if system.get_rom_indices.empty?
|
48
|
+
begin
|
49
|
+
raise ScrapingError::NoElementFound.exception("Requested system is currently unavailable. Try another one.")
|
50
|
+
rescue
|
51
|
+
control_flow_level -= 1
|
52
|
+
input_stack.shift
|
53
|
+
end
|
54
|
+
else
|
55
|
+
input = input_prompt("Select a letter [back|exit]:", /[#{system.get_rom_indices.join.downcase}]/,control_flow_level)
|
56
|
+
control_flow_level = flow_controller(input,control_flow_level,input_stack)
|
57
|
+
end
|
58
|
+
when 3
|
59
|
+
game_collection = select_game_collection_by_index(system,input_stack[0].upcase)
|
60
|
+
if game_collection.empty?
|
61
|
+
begin
|
62
|
+
raise ScrapingError::NoElementFound.exception("Requested game index is currently unavailable. Try another one.")
|
63
|
+
rescue
|
64
|
+
control_flow_level -= 1
|
65
|
+
input_stack.shift
|
66
|
+
end
|
67
|
+
else
|
68
|
+
list_games(game_collection)
|
69
|
+
input = input_prompt("Select a game (1-#{game_collection.size}) [back|exit]", 1..game_collection.size,control_flow_level)
|
70
|
+
control_flow_level = flow_controller(input,control_flow_level,input_stack)
|
71
|
+
end
|
72
|
+
when 4
|
73
|
+
game = select_game(game_collection,input_stack[0].to_i)
|
74
|
+
if game.download_url == nil
|
75
|
+
begin
|
76
|
+
raise ScrapingError::NoElementFound.exception("Requested game is currently unavailable. Try another one.")
|
77
|
+
rescue
|
78
|
+
control_flow_level -= 1
|
79
|
+
input_stack.shift
|
80
|
+
end
|
81
|
+
else
|
82
|
+
display_rom_details(game)
|
83
|
+
input = input_prompt("Download (Y/n) [exit]:", /[yn]/, control_flow_level)
|
84
|
+
if input == 'y' || input == ""
|
85
|
+
download_rom(game)
|
86
|
+
end
|
87
|
+
input_stack.shift
|
88
|
+
input == "exit" ? control_flow_level = 0 : control_flow_level -= 1
|
89
|
+
end
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
puts "Happy Gaming!"
|
94
|
+
end
|
95
|
+
|
96
|
+
# Purpose: Sets control_flow_level in RomloaderCli#start, manipulates input_stack in RomloaderCli#start
|
97
|
+
def flow_controller(input,control_flow_level,input_stack)
|
98
|
+
# Arguments:
|
99
|
+
# => 1. input (String): Current user input from the CLI
|
100
|
+
# => 2. control_flow_level (Fixnum): Indicator of current user progress through the CLI
|
101
|
+
# => 3. input_stack (Array<String>): Buffer of previous user input from the CLI
|
102
|
+
#
|
103
|
+
# Return:
|
104
|
+
# => Fixnum
|
105
|
+
if input == "exit"
|
106
|
+
0
|
107
|
+
elsif input == "back"
|
108
|
+
input_stack.shift
|
109
|
+
control_flow_level - 1
|
110
|
+
else
|
111
|
+
input_stack.unshift(input)
|
112
|
+
control_flow_level + 1
|
113
|
+
end
|
114
|
+
end
|
115
|
+
|
116
|
+
# Purpose: Lists the game systems scraped from http://freeroms.com and saved in GameSystem.all (e.g. 1. Amiga, 2. Atari, etc...)
|
117
|
+
def list_systems
|
118
|
+
# Arguments: None
|
119
|
+
#
|
120
|
+
# Return:
|
121
|
+
# => nil
|
122
|
+
GameSystem.all.each_with_index { |game_system, index| puts "#{index+1}. #{game_system.name}"}
|
123
|
+
print "\n"
|
124
|
+
end
|
125
|
+
|
126
|
+
# Purpose: Retrieves an individual GameSystem object from GameSystem.all
|
127
|
+
def select_system(index)
|
128
|
+
# Arguments:
|
129
|
+
# => 1. index (Fixnum): Retrieved from user input
|
130
|
+
#
|
131
|
+
# Return:
|
132
|
+
# => GameSystem object
|
133
|
+
GameSystem.all[index-1]
|
134
|
+
end
|
135
|
+
|
136
|
+
# Purpose: List game index for the selected system by letter (e.g. A B C D...)
|
137
|
+
def list_system_index(selected_system)
|
138
|
+
# Arguments:
|
139
|
+
# => 1. selected_system (String): Retrieved from user input
|
140
|
+
#
|
141
|
+
# Return:
|
142
|
+
# => nil
|
143
|
+
if selected_system.get_rom_indices.empty?
|
144
|
+
selected_system.rom_indices = FreeromsScraper.rom_index_scrape(selected_system.rom_index_url)
|
145
|
+
end
|
146
|
+
|
147
|
+
puts "#{selected_system.name} index:"
|
148
|
+
selected_system.get_rom_indices.each {|letter| print letter + " "}
|
149
|
+
puts "\n\n"
|
150
|
+
end
|
151
|
+
|
152
|
+
# Purpose: Retrieves all the games available for the selected system under the selected index (e.g. NES,"G")
|
153
|
+
def select_game_collection_by_index(system, letter)
|
154
|
+
# Arguments:
|
155
|
+
# => 1. system (GameSystem): Selected by user through CLI
|
156
|
+
# => 2. letter (String): Retrieved from user input
|
157
|
+
#
|
158
|
+
# Return:
|
159
|
+
# => Array<GameRom>
|
160
|
+
puts "Loading roms...\n"
|
161
|
+
games_list = system.get_roms_by_letter(letter)
|
162
|
+
games_list ||= system.add_roms_to_collection_by_letter(letter,GameRom.create_collection(FreeromsScraper.rom_scrape(system.get_rom_collection_url(letter))))
|
163
|
+
end
|
164
|
+
|
165
|
+
# Purpose: List all the games available for the selected index (e.g. "S": 1. Super Castlevania, 2. Super Mario World, etc...)
|
166
|
+
def list_games(games)
|
167
|
+
# Arguments:
|
168
|
+
# => 1. games (Array<GameRom>): Selected by user through CLI
|
169
|
+
#
|
170
|
+
# Return:
|
171
|
+
# => nil
|
172
|
+
games.each_with_index {|game,index| puts "#{index+1}. #{game.name}"}
|
173
|
+
print "\n"
|
174
|
+
end
|
175
|
+
|
176
|
+
# Purpose: Selects an individual game from the provided collection via index
|
177
|
+
def select_game(game_collection,index)
|
178
|
+
# Arguments:
|
179
|
+
# => 1. game_collection (GameRom): Selected by user through CLI
|
180
|
+
# => 2. index (Fixnum): Retrieved from user input
|
181
|
+
#
|
182
|
+
# Return:
|
183
|
+
# => GameRom object
|
184
|
+
game_collection[index-1].set_rom_details(FreeromsScraper.rom_details(game_collection[index-1].rom_detail_url))
|
185
|
+
game_collection[index-1]
|
186
|
+
end
|
187
|
+
|
188
|
+
# Purpose: List the details of the selected game (e.g. Chrono Trigger | 5.38 MB | .zip)
|
189
|
+
def display_rom_details(game)
|
190
|
+
# Arguments:
|
191
|
+
# => 1. game (GameRom): Selected by user through CLI
|
192
|
+
#
|
193
|
+
# Return:
|
194
|
+
# => nil
|
195
|
+
puts "Rom details:"
|
196
|
+
puts "#{game.name} | System: #{game.system.name} | File size: #{game.size} | File type: #{game.file_ext}"
|
197
|
+
puts "NOTE: To uncompress 7-Zip (.7z) files, please download a system compatible version at http://www.7-zip.org/download.html" if game.file_ext == ".7z"
|
198
|
+
print "\n"
|
199
|
+
end
|
200
|
+
|
201
|
+
# Purpose: Prints a custom message, takes user input, asesses whether the input is valid, and returns the input
|
202
|
+
def input_prompt(message,accepted_input,control_flow_level=nil)
|
203
|
+
# Arguments:
|
204
|
+
# => 1. message (String): A custom message detailing the expected input
|
205
|
+
# => 2. accepted_input (Regexp or Range): Will be checked against the input to verify validity
|
206
|
+
# => 3. control_flow_level [optional] (Fixnum): Used to assess input in context specific situations (e.g. user providing "back" when CLI is on it's first screen)
|
207
|
+
#
|
208
|
+
# Return:
|
209
|
+
# => Fixnum
|
210
|
+
valid = false
|
211
|
+
until valid
|
212
|
+
print message + " "
|
213
|
+
input = gets.chomp.strip.downcase
|
214
|
+
if accepted_input.class == Regexp && accepted_input.match(input)
|
215
|
+
valid = true
|
216
|
+
elsif accepted_input.class == Range && /\A\d+\Z/.match(input) && accepted_input.include?(input.to_i)
|
217
|
+
valid = true
|
218
|
+
elsif input == "exit" || (input == "back" && control_flow_level && control_flow_level.between?(2,3))
|
219
|
+
valid = true
|
220
|
+
elsif input == "" && control_flow_level == 4
|
221
|
+
valid = true
|
222
|
+
else
|
223
|
+
print "Invalid input! "
|
224
|
+
end
|
225
|
+
end
|
226
|
+
print "\n"
|
227
|
+
input
|
228
|
+
end
|
229
|
+
|
230
|
+
# Purpose: Downloads the selected game to the local directory (~/videogame_roms)
|
231
|
+
def download_rom(game)
|
232
|
+
# Arguments:
|
233
|
+
# => 1. game (GameRom): Selected by user through CLI
|
234
|
+
#
|
235
|
+
# Return:
|
236
|
+
# => nil
|
237
|
+
puts "Downloading #{game.name} (#{game.size})..."
|
238
|
+
result = Dir.chdir(File.join(Dir.home,"videogame_roms")) do
|
239
|
+
system("curl -Og# \"#{game.download_url}\"")
|
240
|
+
end
|
241
|
+
result ? puts("Finished downloading to #{File.join(Dir.home,"videogame_roms")}.\n") : puts("An error occured, the rom couldn't be downloaded.\n")
|
242
|
+
sleep 3
|
243
|
+
puts "\n"
|
244
|
+
end
|
245
|
+
|
246
|
+
end
|
247
|
+
|
248
|
+
|
data/lib/romloader.rb
ADDED
metadata
ADDED
@@ -0,0 +1,111 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: romloader
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Efrain Perez Jr
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2016-10-01 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'
|
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'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: bundler
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '1.12'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '1.12'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: pry
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - "~>"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0.10'
|
48
|
+
type: :development
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - "~>"
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0.10'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: rspec
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - "~>"
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '3.1'
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - "~>"
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '3.1'
|
69
|
+
description: This gem allows you to convieniently download videogame roms from freeroms.com
|
70
|
+
to your home directory.
|
71
|
+
email: efrainperezjr@live.com
|
72
|
+
executables:
|
73
|
+
- romloader
|
74
|
+
extensions: []
|
75
|
+
extra_rdoc_files: []
|
76
|
+
files:
|
77
|
+
- Gemfile
|
78
|
+
- LICENSE
|
79
|
+
- README.md
|
80
|
+
- bin/romloader
|
81
|
+
- lib/romloader.rb
|
82
|
+
- lib/romloader/freeroms_scraper.rb
|
83
|
+
- lib/romloader/game_rom.rb
|
84
|
+
- lib/romloader/game_system.rb
|
85
|
+
- lib/romloader/romloader_cli.rb
|
86
|
+
- lib/romloader/scraping_error/no_element_found.rb
|
87
|
+
homepage: https://github.com/jinstrider2000/romloader-cli-gem
|
88
|
+
licenses:
|
89
|
+
- MIT
|
90
|
+
metadata: {}
|
91
|
+
post_install_message:
|
92
|
+
rdoc_options: []
|
93
|
+
require_paths:
|
94
|
+
- lib
|
95
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
96
|
+
requirements:
|
97
|
+
- - ">="
|
98
|
+
- !ruby/object:Gem::Version
|
99
|
+
version: '0'
|
100
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
101
|
+
requirements:
|
102
|
+
- - ">="
|
103
|
+
- !ruby/object:Gem::Version
|
104
|
+
version: '0'
|
105
|
+
requirements: []
|
106
|
+
rubyforge_project:
|
107
|
+
rubygems_version: 2.4.8
|
108
|
+
signing_key:
|
109
|
+
specification_version: 4
|
110
|
+
summary: A videogame rom downloader powered by freeroms.com!
|
111
|
+
test_files: []
|