ruby-box 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.
checksums.yaml ADDED
@@ -0,0 +1,15 @@
1
+ ---
2
+ !binary "U0hBMQ==":
3
+ metadata.gz: !binary |-
4
+ ODI5MWRhMWMwNjYwMDFhN2QyYTg3YzM1OTJhMWE2ZDM5NjMzODNjOQ==
5
+ data.tar.gz: !binary |-
6
+ YTM1OGYwMmMyOGU0Y2EyZmU0NGFjYWUyMTM0ZjQ2NDM0ZDllMmVhYg==
7
+ !binary "U0hBNTEy":
8
+ metadata.gz: !binary |-
9
+ NjgxZWMxODc2MzIyODg4YTAyMzIzMzg4NGI4MTM4NzdkYmFjNTBhNGFlYmY2
10
+ MjAxOGU0MmU4ZGYyYWU1MjQ4MWYzNWYxMTcyYmFlYWM3ZDgxMWFhMTcyZTQ3
11
+ OGMzYTQzMWQzZjAwYTliOGMxMjMwNTcwMWVmNzA0NzQ5MzJmNmQ=
12
+ data.tar.gz: !binary |-
13
+ YzhkODAxM2Q2YjZlMWVlMWE5YjAyNzFhMTcwOTA5YmE0MmQ5MzE0NmI0ZTMx
14
+ YmQxMTM4YTUyZjQ3YzJhM2NhNWJjMTAwZjk0MmNiY2I1NDRhODE4MjA1ZTNi
15
+ NmZmOGMyYTcxZmViOGZiZjQ3NjE2YzlkMTk4ODc1OTY2YmM2NDY=
data/.document ADDED
@@ -0,0 +1,5 @@
1
+ lib/**/*.rb
2
+ bin/*
3
+ -
4
+ features/**/*.feature
5
+ LICENSE.txt
data/.gitignore ADDED
@@ -0,0 +1,52 @@
1
+ account.yml
2
+
3
+ # rcov generated
4
+ coverage
5
+
6
+ # rdoc generated
7
+ rdoc
8
+
9
+ # yard generated
10
+ doc
11
+ .yardoc
12
+
13
+ # bundler
14
+ .bundle
15
+
16
+ # jeweler generated
17
+ pkg
18
+
19
+ # Have editor/IDE/OS specific files you need to ignore? Consider using a global gitignore:
20
+ #
21
+ # * Create a file at ~/.gitignore
22
+ # * Include files you want ignored
23
+ # * Run: git config --global core.excludesfile ~/.gitignore
24
+ #
25
+ # After doing this, these files will be ignored in all your git projects,
26
+ # saving you from having to 'pollute' every project you touch with them
27
+ #
28
+ # Not sure what to needs to be ignored for particular editors/OSes? Here's some ideas to get you started. (Remember, remove the leading # of the line)
29
+ #
30
+ # For MacOS:
31
+ #
32
+ #.DS_Store
33
+
34
+ # For TextMate
35
+ #*.tmproj
36
+ #tmtags
37
+
38
+ # For emacs:
39
+ #*~
40
+ #\#*
41
+ #.\#*
42
+
43
+ # For vim:
44
+ #*.swp
45
+
46
+ # For redcar:
47
+ #.redcar
48
+
49
+ # For rubinius:
50
+ #*.rbc
51
+ *.gem
52
+ .DS_Store
data/Gemfile ADDED
@@ -0,0 +1,11 @@
1
+ source "http://rubygems.org"
2
+
3
+ gem "multipart-post", "~> 1.1.5"
4
+ gem "oauth2"
5
+
6
+ group :development do
7
+ gem "rspec"
8
+ gem "bundler"
9
+ gem "jeweler", "~> 1.6.4"
10
+ gem "webmock"
11
+ end
data/Gemfile.lock ADDED
@@ -0,0 +1,48 @@
1
+ GEM
2
+ remote: http://rubygems.org/
3
+ specs:
4
+ addressable (2.2.8)
5
+ crack (0.3.1)
6
+ diff-lcs (1.1.3)
7
+ faraday (0.8.4)
8
+ multipart-post (~> 1.1)
9
+ git (1.2.5)
10
+ httpauth (0.2.0)
11
+ jeweler (1.6.4)
12
+ bundler (~> 1.0)
13
+ git (>= 1.2.5)
14
+ rake
15
+ jwt (0.1.5)
16
+ multi_json (>= 1.0)
17
+ multi_json (1.6.0)
18
+ multipart-post (1.1.5)
19
+ oauth2 (0.8.0)
20
+ faraday (~> 0.8)
21
+ httpauth (~> 0.1)
22
+ jwt (~> 0.1.4)
23
+ multi_json (~> 1.0)
24
+ rack (~> 1.2)
25
+ rack (1.4.5)
26
+ rake (0.9.2.2)
27
+ rspec (2.10.0)
28
+ rspec-core (~> 2.10.0)
29
+ rspec-expectations (~> 2.10.0)
30
+ rspec-mocks (~> 2.10.0)
31
+ rspec-core (2.10.0)
32
+ rspec-expectations (2.10.0)
33
+ diff-lcs (~> 1.1.3)
34
+ rspec-mocks (2.10.1)
35
+ webmock (1.8.7)
36
+ addressable (>= 2.2.7)
37
+ crack (>= 0.1.7)
38
+
39
+ PLATFORMS
40
+ ruby
41
+
42
+ DEPENDENCIES
43
+ bundler
44
+ jeweler (~> 1.6.4)
45
+ multipart-post (~> 1.1.5)
46
+ oauth2
47
+ rspec
48
+ webmock
data/LICENSE.txt ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2013 Attachments.me
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.markdown ADDED
@@ -0,0 +1,160 @@
1
+ ruby-box
2
+ --------
3
+
4
+ Mainted by: [Attachments.me](https://attachments.me)
5
+
6
+ RubyBox provides a simple, chainable, feature-rich client for [Box's 2.0 API](http://developers.box.com/docs/).
7
+
8
+ Authorization
9
+ =============
10
+
11
+ RubyBox uses Box's OAuth2 Implementaton, Here are the steps involved in authorizing a client:
12
+
13
+ __1)__ Get the authorization url.
14
+
15
+ ```ruby
16
+ require 'ruby-box'
17
+
18
+ session = RubyBox::Session.new({
19
+ client_id: 'your-client-id',
20
+ client_secret: 'your-client-secret'
21
+ })
22
+
23
+ authorize_url = session.authorize_url('https://redirect-url-in-app-settings')
24
+ ```
25
+
26
+ __2)__ After redirecting to the authorize_url, exchange the _code_ given for an _access\_token_
27
+
28
+ ```ruby
29
+ session.get_access_token('code-returned-to-redirect_url')
30
+ ```
31
+
32
+ __3)__ Create a client using a session initialized with the _access\_token_.
33
+
34
+ ```ruby
35
+ require 'ruby-box'
36
+
37
+ session = RubyBox::Session.new({
38
+ client_id: 'your-client-id',
39
+ client_secret: 'your-client-secret',
40
+ access_token: 'access-token'
41
+ })
42
+
43
+ client = RubyBox::Client.new(session)
44
+ ```
45
+
46
+ Usage
47
+ -----
48
+
49
+ Once you've created a client, you can start interacting with the Box API. What follows are some basic examples of RubyBox's usage:
50
+
51
+ Folders
52
+ =======
53
+
54
+ * Listing items in a folder:
55
+
56
+ ```ruby
57
+ files = client.folder('/image_folder').files # all files in a folder.
58
+ folders = client.root_folder.folders # all folders in the root directory.
59
+ files_and_folders = client.folder('files').items # all files and folders in /files
60
+ ```
61
+
62
+ * Creating a folder:
63
+
64
+ ```ruby
65
+ client.folder('image_folder').create_subfolder('subfolder')
66
+ ```
67
+
68
+ * Setting the description on a folder:
69
+
70
+ ```ruby
71
+ folder = client.folder('image_folder')
72
+ folder.description = 'Description on Folder'
73
+ folder.update
74
+ ```
75
+
76
+ * Listing the comments in a discussion surrounding a folder.
77
+
78
+ ```ruby
79
+ folder = client.folder('image_folder')
80
+ discussion = folder.discussions.first
81
+ discussion.comments.each {|comment| p comment.message}
82
+ ```
83
+
84
+ Files
85
+ =====
86
+
87
+ * Fetching a file's meta information.
88
+
89
+ ```ruby
90
+ file = client.file('/image_folder/an-image.jpg')
91
+ p file.name
92
+ p file.created_at
93
+ ```
94
+
95
+ * Uploading a file to a folder.
96
+
97
+ ```ruby
98
+ file = client.upload_file('./LICENSE.txt', '/license_folder')
99
+ ```
100
+
101
+ * Downloading a file.
102
+
103
+ ```ruby
104
+ f = open('./LOCAL.txt', 'w+')
105
+ f.write( client.file('/license_folder/LICENSE.txt').download )
106
+ f.close()
107
+ ```
108
+
109
+ * Deleting a file.
110
+
111
+ ```ruby
112
+ client.file('/license_folder/LICENSE.txt').delete
113
+ ```
114
+
115
+ * Displaying comments on a file.
116
+
117
+ ```ruby
118
+ comments = client.file('/image_folder/an-image.jpg').comments
119
+ comments.each do |comment|
120
+ p comment.message
121
+ end
122
+ ```
123
+
124
+ Search
125
+ ======
126
+
127
+ You can use RubyBox's search method to return files and folders that match a given query.
128
+
129
+ ```ruby
130
+ items = client.search('image')
131
+ items.each do |item|
132
+ p "type=#{item.type} name=#{item.name}"
133
+ end
134
+ ```
135
+
136
+ Contributors
137
+ ------------
138
+
139
+ * Benjamin Coe
140
+ * Larry Kang
141
+ * Dan Reed
142
+ * Jesse Miller
143
+
144
+ Contributing to ruby-box
145
+ -----------------------
146
+
147
+ RubyBox does not yet support all of Box's API Version 2.0 functionality, be liberal with your contributions.
148
+
149
+ * Rename account.example to account.yml and fill in your Box credentials
150
+ * Type bundle install
151
+ * Type rake.. tests should pass
152
+ * Add a failing test
153
+ * Make it pass
154
+ * Submit a pull request
155
+
156
+ Copyright
157
+ ---------
158
+
159
+ Copyright (c) 2012 Attachments.me. See LICENSE.txt for
160
+ further details.
data/Rakefile ADDED
@@ -0,0 +1,32 @@
1
+ # encoding: utf-8
2
+
3
+ require 'rubygems'
4
+ require 'bundler'
5
+ begin
6
+ Bundler.setup(:default, :development)
7
+ rescue Bundler::BundlerError => e
8
+ $stderr.puts e.message
9
+ $stderr.puts "Run `bundle install` to install missing gems"
10
+ exit e.status_code
11
+ end
12
+ require 'rake'
13
+
14
+ require 'rspec/core/rake_task'
15
+ RSpec::Core::RakeTask.new(:spec)
16
+
17
+ require 'jeweler'
18
+ Jeweler::Tasks.new do |gem|
19
+ # gem is a Gem::Specification... see http://docs.rubygems.org/read/chapter/20 for more options
20
+ gem.name = "ruby-box"
21
+ gem.homepage = "http://github.com/jessemiller/ruby-box"
22
+ gem.license = "MIT"
23
+ gem.summary = %Q{ruby gem for box.com 2.0 api}
24
+ gem.description = %Q{ruby gem for box.com 2.0 api}
25
+ gem.email = "millerjesse@gmail.com"
26
+ gem.authors = ["Jesse Miller"]
27
+ gem.files.exclude 'spec/*.test'
28
+ # dependencies defined in Gemfile
29
+ end
30
+ Jeweler::RubygemsDotOrgTasks.new
31
+
32
+ task :default => :spec
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 1.0.0
data/lib/ruby-box.rb ADDED
@@ -0,0 +1,16 @@
1
+ require 'ruby-box/client'
2
+ require 'ruby-box/session'
3
+
4
+ require 'ruby-box/item'
5
+ require 'ruby-box/file'
6
+ require 'ruby-box/folder'
7
+ require 'ruby-box/user'
8
+ require 'ruby-box/comment'
9
+ require 'ruby-box/discussion'
10
+ require 'ruby-box/exceptions'
11
+
12
+ module RubyBox
13
+ API_URL = 'https://api.box.com/2.0'
14
+ UPLOAD_URL = 'https://upload.box.com/api/2.0'
15
+ ISO_8601_TEST = Regexp.new(/^[0-9]{4}-[0-9]{2}-[0-9]{2}T/)
16
+ end
@@ -0,0 +1,97 @@
1
+ require 'uri'
2
+ require 'net/https'
3
+ require 'json'
4
+ require 'net/http/post/multipart'
5
+ require 'open-uri'
6
+
7
+ module RubyBox
8
+ class Client
9
+
10
+ def initialize(session)
11
+ @session = session
12
+ end
13
+
14
+ def root_folder
15
+ folder = Folder.new(@session, {'id' => '0'})
16
+ folder.reload_meta
17
+ end
18
+
19
+ def folder(path)
20
+ folder_from_split_path( split_path(path) )
21
+ end
22
+
23
+ def file(path)
24
+ path = split_path(path)
25
+ file_name = path.pop
26
+ folder = folder_from_split_path( path )
27
+ folder.files(file_name).first if folder
28
+ end
29
+
30
+ def download(path)
31
+ file = file(path)
32
+ file.download if file
33
+ end
34
+
35
+ def stream(path, opts={})
36
+ file = file(path)
37
+ file.stream(opts) if file
38
+ end
39
+
40
+ def search(query, item_limit=100, offset=0)
41
+ Enumerator.new do |yielder|
42
+ while true
43
+ url = "#{RubyBox::API_URL}/search?query=#{URI::encode(query)}&limit=#{item_limit}&offset=#{offset}"
44
+ resp = @session.get( url )
45
+ resp['entries'].each do |entry|
46
+ yielder.yield(RubyBox::Item.factory(@session, entry))
47
+ end
48
+ offset += resp['entries'].count
49
+ break if resp['offset'].to_i + resp['limit'].to_i >= resp['total_count'].to_i
50
+ end
51
+ end
52
+ end
53
+
54
+ def create_folder(path)
55
+ folder = root_folder
56
+ folder_names = split_path(path)
57
+ folder_names.each do |folder_name|
58
+ new_folder = folder.folders(folder_name).first
59
+ folder = new_folder ? new_folder : folder.create_subfolder(folder_name)
60
+ end
61
+ folder
62
+ end
63
+
64
+ def upload_data(path, data)
65
+ path = split_path(path)
66
+ file_name = path.pop
67
+ folder = create_folder(path.join('/'))
68
+ folder.upload_file(file_name, data) if folder
69
+ end
70
+
71
+ def upload_file(local_path, remote_path)
72
+ file_name = local_path.split('/').pop
73
+ folder = create_folder( remote_path )
74
+ return unless folder
75
+ ::File.open( local_path ) do |data|
76
+ folder.upload_file(file_name, data)
77
+ end
78
+ end
79
+
80
+ def split_path(path)
81
+ path.gsub!(/(^\/)|(\/$)/, '')
82
+ path.split('/')
83
+ end
84
+
85
+ private
86
+
87
+ def folder_from_split_path(path)
88
+ folder = root_folder
89
+ path.each do |folder_name|
90
+ folder = folder.folders(folder_name).first
91
+ return nil unless folder
92
+ end
93
+ folder
94
+ end
95
+
96
+ end
97
+ end