get_them_all 1.0.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.
@@ -0,0 +1,27 @@
1
+ module GetThemAll
2
+ class Storage
3
+
4
+ class StorageError < RuntimeError; end
5
+ class WriteError < StorageError; end
6
+ class ReadError < StorageError; end
7
+
8
+ def initialize(options = {})
9
+ @root = options.delete(:root)
10
+ @folder_name = options.delete(:folder_name)
11
+ raise "missing required option: folder_name" unless @folder_name
12
+ raise "missing required option: root" unless @root
13
+
14
+ @root = File.join(@root, @folder_name)
15
+ raise "missing required option: root" unless @root
16
+ end
17
+
18
+ def working?
19
+ false
20
+ end
21
+
22
+ def build_destpath(path)
23
+ File.join(@root, path)
24
+ end
25
+
26
+ end
27
+ end
@@ -0,0 +1,114 @@
1
+ require 'stringio'
2
+ require 'dropbox'
3
+ require 'girl_friday'
4
+
5
+ module GetThemAll
6
+ class DropboxStorage < Storage
7
+
8
+
9
+ # def self.deserialize(data)
10
+ # consumer_key, consumer_secret, authorized, token, token_secret, ssl, mode = YAML.load(StringIO.new(data))
11
+ # raise ArgumentError, "Must provide a properly serialized #{self.to_s} instance" unless [ consumer_key, consumer_secret, token, token_secret ].all? and authorized == true or authorized == false
12
+ #
13
+ # session = self.new(consumer_key, consumer_secret, :ssl => ssl, :already_authorized => authorized)
14
+ # if authorized then
15
+ # session.set_access_token token, token_secret
16
+ # else
17
+ # session.set_request_token token, token_secret
18
+ # end
19
+ # session.mode = mode if mode
20
+ #
21
+ # return session
22
+ # end
23
+
24
+ def initialize(options = {})
25
+ super
26
+
27
+ session_data = options.delete(:session)
28
+ raise "session missing" unless session_data
29
+
30
+ consumer_key, consumer_secret, authorized, token, token_secret, ssl, mode = session_data
31
+
32
+ @session = Dropbox::Session.new(consumer_key, consumer_secret, :ssl => ssl, :already_authorized => authorized)
33
+ @session.set_access_token(token, token_secret)
34
+ @session.mode = mode.to_sym
35
+
36
+ @queue = GirlFriday::WorkQueue.new(:dropbox_upload, :size => 1) do |msg|
37
+ # puts "Uploading file #{msg[:path]}..."
38
+ write(msg[:path], msg[:data], false, msg[:deferrable])
39
+ # puts "Upload ok."
40
+ end
41
+ end
42
+
43
+ ##
44
+ # Can we exit or is there still some work to do ?
45
+ #
46
+ # @return [Boolean]
47
+ #
48
+ def working?
49
+ s = @queue.status['dropbox_upload']
50
+ (s[:backlog] > 0) || (s[:busy] > 0)
51
+ end
52
+
53
+ ##
54
+ # Check if the remote file/folder exists,
55
+ # there may be a better way but it works.
56
+ #
57
+ # @return [Boolean] true if the remote path exists
58
+ #
59
+ def exist?(path)
60
+ destpath = build_destpath(path)
61
+
62
+ metadata = @session.metadata(destpath)
63
+ if metadata.respond_to?(:is_deleted) && metadata.is_deleted
64
+ false
65
+ else
66
+ true
67
+ end
68
+ rescue Dropbox::FileNotFoundError
69
+ false
70
+ end
71
+
72
+ ##
73
+ # Write data in a remote file.
74
+ # Folders in the path will be automatically created as
75
+ # needed.
76
+ #
77
+ def write(path, data, delay = true, deferrable = EM::DefaultDeferrable.new)
78
+ retries = 0
79
+
80
+ if delay
81
+ @queue.push(:path => path, :data => data, :deferrable => deferrable)
82
+ else
83
+ destpath = build_destpath(path)
84
+ filename, dirname = File.basename(destpath), File.dirname(destpath)
85
+ @session.upload(StringIO.new(data), dirname, :as => filename)
86
+ EM::next_tick{ deferrable.succeed }
87
+ end
88
+
89
+ deferrable
90
+ rescue => err
91
+ if retries < 4
92
+ # puts "[#{retries}] Upload error, retrying: #{err}"
93
+ retries += 1
94
+ retry
95
+ else
96
+ EM::next_tick{ deferrable.fail }
97
+ raise WriteError, "cannot write file: #{err}"
98
+ end
99
+ end
100
+
101
+ ##
102
+ # Read file's content and return it.
103
+ #
104
+ # @return [String] file's content
105
+ #
106
+ def read(path)
107
+ destpath = build_destpath(path)
108
+ @session.download(destpath)
109
+ rescue => err
110
+ raise ReadError, "cannot read file: #{err}"
111
+ end
112
+
113
+ end
114
+ end
@@ -0,0 +1,40 @@
1
+ module GetThemAll
2
+ class FileStorage < Storage
3
+
4
+ # def initialize(options = {})
5
+ # super
6
+ # end
7
+
8
+ def exist?(path)
9
+ destpath = build_destpath(path)
10
+ File.exist?(destpath)
11
+ end
12
+
13
+ def write(path, data)
14
+ deferrable = EM::DefaultDeferrable.new
15
+
16
+ destpath = build_destpath(path)
17
+ FileUtils.mkdir_p( File.dirname(destpath) )
18
+ open(destpath, "wb") do |f|
19
+ f.write( data )
20
+ end
21
+
22
+ deferrable.succeed
23
+ deferrable
24
+
25
+ rescue Errno::EINVAL
26
+ deferrable.fail
27
+ raise Storage::WriteError("cannot write file")
28
+ end
29
+
30
+ def read(path)
31
+ destpath = build_destpath(path)
32
+ if File.readable?(destpath)
33
+ File.read(destpath)
34
+ else
35
+ raise Storage::ReadError("cannot open file")
36
+ end
37
+ end
38
+
39
+ end
40
+ end
@@ -0,0 +1,3 @@
1
+ module GetThemAll
2
+ VERSION = "1.0.0"
3
+ end
@@ -0,0 +1,48 @@
1
+ module GetThemAll
2
+ #
3
+ # workers are created to follow a queue
4
+ # each time an action is put in the queue it will handle it
5
+ #
6
+ class Worker
7
+ attr_reader :type, :index
8
+
9
+ def initialize(type, index, downloader, queue)
10
+ @type = type
11
+ @index = index
12
+
13
+ @downloader = downloader
14
+ @queue = queue
15
+
16
+ @queue.pop do |action|
17
+ handle_action(action)
18
+ end
19
+
20
+ end
21
+
22
+ ##
23
+ # Take the next action in queue
24
+ #
25
+ def take_next_job
26
+ EM::next_tick do
27
+ @queue.pop{|act| handle_action(act) }
28
+ end
29
+ end
30
+
31
+
32
+ def handle_action(action)
33
+ action.callback( &method(:take_next_job) )
34
+ action.errback do
35
+ # in case of failure, try again later (with slightly lower priority)
36
+ EM::add_timer(50) do
37
+ @queue.push(action, [action.level - 1, 0].max)
38
+ end
39
+
40
+ # and take the next job
41
+ take_next_job()
42
+ end
43
+
44
+ action.do_action(self)
45
+ end
46
+
47
+ end
48
+ end
metadata ADDED
@@ -0,0 +1,172 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: get_them_all
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Julien Ammous
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2011-10-16 00:00:00.000000000Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: thor
16
+ requirement: &70256844459680 !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: *70256844459680
25
+ - !ruby/object:Gem::Dependency
26
+ name: em-http-request
27
+ requirement: &70256844459180 !ruby/object:Gem::Requirement
28
+ none: false
29
+ requirements:
30
+ - - ~>
31
+ - !ruby/object:Gem::Version
32
+ version: 1.0.0
33
+ type: :runtime
34
+ prerelease: false
35
+ version_requirements: *70256844459180
36
+ - !ruby/object:Gem::Dependency
37
+ name: em-priority-queue
38
+ requirement: &70256844458680 !ruby/object:Gem::Requirement
39
+ none: false
40
+ requirements:
41
+ - - ~>
42
+ - !ruby/object:Gem::Version
43
+ version: 0.0.2
44
+ type: :runtime
45
+ prerelease: false
46
+ version_requirements: *70256844458680
47
+ - !ruby/object:Gem::Dependency
48
+ name: hpricot
49
+ requirement: &70256844458220 !ruby/object:Gem::Requirement
50
+ none: false
51
+ requirements:
52
+ - - ~>
53
+ - !ruby/object:Gem::Version
54
+ version: 0.8.1
55
+ type: :runtime
56
+ prerelease: false
57
+ version_requirements: *70256844458220
58
+ - !ruby/object:Gem::Dependency
59
+ name: i18n
60
+ requirement: &70256844457840 !ruby/object:Gem::Requirement
61
+ none: false
62
+ requirements:
63
+ - - ! '>='
64
+ - !ruby/object:Gem::Version
65
+ version: '0'
66
+ type: :runtime
67
+ prerelease: false
68
+ version_requirements: *70256844457840
69
+ - !ruby/object:Gem::Dependency
70
+ name: activesupport
71
+ requirement: &70256844457300 !ruby/object:Gem::Requirement
72
+ none: false
73
+ requirements:
74
+ - - ~>
75
+ - !ruby/object:Gem::Version
76
+ version: 3.1.0
77
+ type: :runtime
78
+ prerelease: false
79
+ version_requirements: *70256844457300
80
+ - !ruby/object:Gem::Dependency
81
+ name: therubyracer
82
+ requirement: &70256844456800 !ruby/object:Gem::Requirement
83
+ none: false
84
+ requirements:
85
+ - - ~>
86
+ - !ruby/object:Gem::Version
87
+ version: 0.9.8
88
+ type: :runtime
89
+ prerelease: false
90
+ version_requirements: *70256844456800
91
+ - !ruby/object:Gem::Dependency
92
+ name: dropbox
93
+ requirement: &70256844456420 !ruby/object:Gem::Requirement
94
+ none: false
95
+ requirements:
96
+ - - ! '>='
97
+ - !ruby/object:Gem::Version
98
+ version: '0'
99
+ type: :runtime
100
+ prerelease: false
101
+ version_requirements: *70256844456420
102
+ - !ruby/object:Gem::Dependency
103
+ name: girl_friday
104
+ requirement: &70256844455800 !ruby/object:Gem::Requirement
105
+ none: false
106
+ requirements:
107
+ - - ! '>='
108
+ - !ruby/object:Gem::Version
109
+ version: '0'
110
+ type: :runtime
111
+ prerelease: false
112
+ version_requirements: *70256844455800
113
+ description: Mass downloader useable as standalone or as a library
114
+ email: []
115
+ executables:
116
+ - gta
117
+ extensions: []
118
+ extra_rdoc_files: []
119
+ files:
120
+ - LICENSE
121
+ - README.md
122
+ - get_them_all.gemspec
123
+ - lib/get_them_all.rb
124
+ - lib/get_them_all/action.rb
125
+ - lib/get_them_all/actions/download_action.rb
126
+ - lib/get_them_all/actions/examine_action.rb
127
+ - lib/get_them_all/extension.rb
128
+ - lib/get_them_all/extensions/action_logger.rb
129
+ - lib/get_them_all/extensions/gauge_display.rb
130
+ - lib/get_them_all/extensions/graph_builder.rb
131
+ - lib/get_them_all/history.rb
132
+ - lib/get_them_all/javascript_loader.rb
133
+ - lib/get_them_all/logger.rb
134
+ - lib/get_them_all/notifier.rb
135
+ - lib/get_them_all/site_downloader.rb
136
+ - lib/get_them_all/storage.rb
137
+ - lib/get_them_all/storage/dropbox_storage.rb
138
+ - lib/get_them_all/storage/file_storage.rb
139
+ - lib/get_them_all/version.rb
140
+ - lib/get_them_all/worker.rb
141
+ - bin/gta
142
+ homepage: ''
143
+ licenses: []
144
+ post_install_message:
145
+ rdoc_options: []
146
+ require_paths:
147
+ - lib
148
+ required_ruby_version: !ruby/object:Gem::Requirement
149
+ none: false
150
+ requirements:
151
+ - - ! '>='
152
+ - !ruby/object:Gem::Version
153
+ version: '0'
154
+ segments:
155
+ - 0
156
+ hash: 3600791884245333025
157
+ required_rubygems_version: !ruby/object:Gem::Requirement
158
+ none: false
159
+ requirements:
160
+ - - ! '>='
161
+ - !ruby/object:Gem::Version
162
+ version: '0'
163
+ segments:
164
+ - 0
165
+ hash: 3600791884245333025
166
+ requirements: []
167
+ rubyforge_project: get_them_all
168
+ rubygems_version: 1.8.11
169
+ signing_key:
170
+ specification_version: 3
171
+ summary: Mass downloader
172
+ test_files: []