cloud_door 0.0.1 → 0.0.2

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: caf57815f0cdd5cd8a83a379407fa1025406ea4d
4
- data.tar.gz: 0121e8b37b6bde073502bd932b1e8cd6abeb231f
3
+ metadata.gz: 6024e618b2bcf7b05a0ce275a76b646220a10776
4
+ data.tar.gz: 8a1c39312082def8fe78e517702410081ec95542
5
5
  SHA512:
6
- metadata.gz: d74ad868c208e4f83b075d7e163b9e211955a5836adc207e886d0c36c4e54f403f53f93f62cc08aa65c63b3d75bc6f64a58115dba634bb58b4e47d4c6ea3a020
7
- data.tar.gz: e3dd3881346ddd873f9b04fdd98749c35d120326fa54f8be43aefcc72f3c8d89e821144d738dd0273cc792ea9d601fe2f2e1421c08c8f220507dbdac5b9168fe
6
+ metadata.gz: b03c5a3bb7bbf46bb22e0d9dd63dfb4a7cae57a5c9d506cbb57a00415352c1a3d16647cafdbecf77b74ad714d42b4b61260379bd2eeee2311cb78dcdd8b92ad6
7
+ data.tar.gz: 0af913126c0d27573c576f070ce15e8eaebc108f5aca2cd369dd675d480dadb6c0d12f48b44f3557498d6a73b9ef8d1ddd45cfe3ea24d92fcd8e182512255b88
data/README.md CHANGED
@@ -1,8 +1,7 @@
1
1
  # CloudDoor
2
2
 
3
3
  This gem can access different cloud storage through same interface.
4
- This gem supports OneDrive and Dropbox, now.
5
- It will be supported also google drive in the future.
4
+ This gem supports OneDrive, Dropbox and GoogleDrive.
6
5
 
7
6
 
8
7
  ## Installation
@@ -31,17 +30,18 @@ Please create application on below url.
31
30
  |-------|---|
32
31
  |OneDrive|https://account.live.com/developers/applications/index|
33
32
  |Dropbox|https://www.dropbox.com/developers/apps/create|
33
+ |GoogleDrive|https://console.developers.google.com/flows/enableapi?apiid=drive|
34
34
 
35
35
  ### configuration
36
36
  1. make "cloud_door_config.yml" on application root directory.
37
37
  2. write application settings to "cloud_door_config.yml".
38
38
  - all
39
39
  - data_path
40
- data_path is path to save data file.
40
+ data_path is path to save data file.
41
41
  application must have write permission to data_path.
42
42
  - session_flg
43
- Whether or not to switch the session for each user.
44
- "0" is "no" and "1" is "yes".
43
+ Whether or not to switch the session for each user.
44
+ "0" is "no" and "1" is "yes".
45
45
  must be a "1" in an environment where multiple users use application at same time.
46
46
  - onedrive
47
47
  - client_id
@@ -49,7 +49,7 @@ Please create application on below url.
49
49
  - client_secret
50
50
  OneDrive's client secret
51
51
  - redirect_url
52
- OneDrive's redirect url after login.
52
+ OneDrive's redirect url after login.
53
53
  please set to "https://login.live.com/oauth20_desktop.srf" for desktop apps.
54
54
  - dropbox
55
55
  - client_id
@@ -57,69 +57,78 @@ Please create application on below url.
57
57
  - client_secret
58
58
  Dropbox's client secret
59
59
  - redirect_url
60
- Dropbox's redirect url after login.
60
+ Dropbox's redirect url after login.
61
61
  please set to "https://localhost" for desktop apps.
62
-
63
- example
64
- ```
65
- all:
66
- data_path : './data/'
67
- web_app_flag: 0
68
- onedrive:
69
- client_id: onedrive
70
- client_secret: onedrive_secret
71
- redirect_url: https://login.live.com/oauth20_desktop.srf
72
- dropbox:
73
- client_id: dropbox
74
- client_secret: dropbox_secret
75
- redirect_url: http://localhost
76
- ```
62
+ - googledrive
63
+ - client_id
64
+ GoogleDrive's client id
65
+ - client_secret
66
+ GoogleDrive's client secret
67
+ - redirect_url
68
+ GoogleDrive's redirect url after login.
69
+ please set to "urn:ietf:wg:oauth:2.0:oob" for desktop apps.
70
+
71
+ example
72
+
73
+ all:
74
+ data_path : './data/'
75
+ web_app_flag: 0
76
+ onedrive:
77
+ client_id: onedrive
78
+ client_secret: onedrive_secret
79
+ redirect_url: https://login.live.com/oauth20_desktop.srf
80
+ dropbox:
81
+ client_id: dropbox
82
+ client_secret: dropbox_secret
83
+ redirect_url: http://localhost
84
+ googledrive:
85
+ client_id: googledrive
86
+ client_secret: googledrive_secret
87
+ redirect_url: urn:ietf:wg:oauth:2.0:oob
77
88
 
78
89
 
79
90
  ### example
80
91
 
81
- A.before login
82
- ```ruby
83
- require 'cloud_door'
84
- require 'pp'
85
-
86
- # make an instance for connecting to Onedrive
87
- storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive)
88
- # make an instance for connecting to Dropbox
89
- # storage = CloudDoor::CloudDoor.new(CloudDoor::Dropbox)
90
- # login
91
- storage.login('account', 'password')
92
- # show files
93
- files = storage.show_files
94
- pp files
95
- # upload file
96
- storage.upload_file('README.md')
97
- # download file
98
- storage.download_file('README.md')
99
- ```
100
-
101
- B.after login
102
- ```ruby
103
- require 'cloud_door'
104
-
105
- storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive)
106
- # load_token calls the login information of previous
107
- storage.load_token
108
- ```
109
-
110
- C.if session_flag is "1"(using session ID)
111
- ```ruby
112
- require 'cloud_door'
113
-
114
- # login
115
- storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive)
116
- session_id = storage.login('account', 'password')
117
-
118
- # load_token
119
- storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive, session_id)
120
- storage.load_token
121
-
122
- ```
92
+ A.before login
93
+
94
+ require 'cloud_door'
95
+ require 'pp'
96
+
97
+ # make an instance for connecting to Onedrive
98
+ storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive)
99
+ ## make an instance for connecting to Dropbox
100
+ ## storage = CloudDoor::CloudDoor.new(CloudDoor::Dropbox)
101
+ ## make an instance for connecting to GoogleDrive
102
+ ## storage = CloudDoor::CloudDoor.new(CloudDoor::GoogleDrive)
103
+ # login
104
+ storage.login('account', 'password')
105
+ # show files
106
+ files = storage.show_files
107
+ pp files
108
+ # upload file
109
+ storage.upload_file('README.md')
110
+ # download file
111
+ storage.download_file('README.md')
112
+
113
+ B.after login
114
+
115
+ require 'cloud_door'
116
+
117
+ storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive)
118
+ # load_token calls the login information of previous
119
+ storage.load_token
120
+
121
+ C.if session_flag is "1"(using session ID)
122
+
123
+ require 'cloud_door'
124
+
125
+ # login
126
+ storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive)
127
+ session_id = storage.login('account', 'password')
128
+
129
+ # load_token
130
+ storage = CloudDoor::CloudDoor.new(CloudDoor::OneDrive, session_id)
131
+ storage.load_token
123
132
 
124
133
 
125
134
  ### methods
data/bin/gdrive ADDED
@@ -0,0 +1,133 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'rubygems'
4
+ require 'commander/import'
5
+ require 'cloud_door'
6
+
7
+ program :version, '0.0.1'
8
+ program :description, 'access google drive from CLI'
9
+
10
+ command :config do |c|
11
+ c.syntax = 'gdrive config'
12
+ c.summary = 'configure the google drive connection'
13
+ c.description = 'configure the google drive connection'
14
+ c.example 'description', 'gdrive config'
15
+ c.option '-l'
16
+ c.action do |args, options|
17
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
18
+ console.config(options.l)
19
+ end
20
+ end
21
+
22
+ command :account do |c|
23
+ c.syntax = 'gdrive account'
24
+ c.summary = 'set account for the google drive connection'
25
+ c.description = 'set account for the google drive connection'
26
+ c.example 'description', 'gdrive accout'
27
+ # c.option '-b STR', String, 'Example of string'
28
+ c.option '-l'
29
+ c.action do |args, options|
30
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
31
+ console.account(options.l)
32
+ end
33
+ end
34
+
35
+ command :login do |c|
36
+ c.syntax = 'gdrive login'
37
+ c.summary = 'authentication for google drive'
38
+ c.description = 'authentication for google drive'
39
+ c.example 'description', 'gdrive login'
40
+ c.option '-d'
41
+ c.action do |args, options|
42
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
43
+ console.login(options.d)
44
+ end
45
+ end
46
+
47
+ command :ls do |c|
48
+ c.syntax = 'gdrive list [file_name]'
49
+ c.summary = 'list google drive files'
50
+ c.description = 'list google drive files'
51
+ c.example 'description', "gdrive list 'file'"
52
+ c.action do |args, options|
53
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
54
+ console.ls(args[0])
55
+ end
56
+ end
57
+
58
+ command :cd do |c|
59
+ c.syntax = 'gdrive cd [file_name]'
60
+ c.summary = 'change directory on google drive'
61
+ c.description = 'change directory on google drive'
62
+ c.example 'description', "gdrive cd 'file'"
63
+ c.action do |args, options|
64
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
65
+ console.cd(args[0])
66
+ end
67
+ end
68
+
69
+ command :info do |c|
70
+ c.syntax = 'gdrive info [file_name]'
71
+ c.summary = 'show google drive file information'
72
+ c.description = 'show google drive file information'
73
+ c.example 'description', "gdrive info 'file'"
74
+ c.action do |args, options|
75
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
76
+ console.info(args[0])
77
+ end
78
+ end
79
+
80
+ command :pwd do |c|
81
+ c.syntax = 'gdrive pwd'
82
+ c.summary = 'show current directory'
83
+ c.description = 'show current directory'
84
+ c.example 'description', "gdrive pwd"
85
+ c.action do |args, options|
86
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
87
+ console.pwd
88
+ end
89
+ end
90
+
91
+ command :download do |c|
92
+ c.syntax = 'gdrive download [file_name]'
93
+ c.summary = 'download file from google drive'
94
+ c.description = 'download file from google drive'
95
+ c.example 'description', "gdrive download 'file'"
96
+ c.action do |args, options|
97
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
98
+ console.download(args[0])
99
+ end
100
+ end
101
+
102
+ command :upload do |c|
103
+ c.syntax = 'gdrive upload [file_name]'
104
+ c.summary = 'upload file to google drive'
105
+ c.description = 'upload file to google drive'
106
+ c.example 'description', "gdrive upload 'file'"
107
+ c.action do |args, options|
108
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
109
+ console.upload(args[0])
110
+ end
111
+ end
112
+
113
+ command :rm do |c|
114
+ c.syntax = 'gdrive delete [file_name]'
115
+ c.summary = 'delete file on google drive'
116
+ c.description = 'delete file on google drive'
117
+ c.example 'description', "gdrive delete 'file'"
118
+ c.action do |args, options|
119
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
120
+ console.rm(args[0])
121
+ end
122
+ end
123
+
124
+ command :mkdir do |c|
125
+ c.syntax = 'gdrive mkdir [folder_name]'
126
+ c.summary = 'make directory on google drive'
127
+ c.description = 'make directory on google drive'
128
+ c.example 'description', "gdrive mkdir 'folder'"
129
+ c.action do |args, options|
130
+ console = CloudDoor::Console.new(CloudDoor::GoogleDrive)
131
+ console.mkdir(args[0])
132
+ end
133
+ end
data/cloud_door.gemspec CHANGED
@@ -28,11 +28,10 @@ It will be supported also google drive in the future.}
28
28
  spec.add_runtime_dependency 'watir', '~> 5.0', '>= 5.0.0'
29
29
  spec.add_runtime_dependency 'watir-webdriver', '~> 0.6', '>= 0.6.9'
30
30
  spec.add_runtime_dependency 'dropbox-sdk', '~> 1.6', '>= 1.6.4'
31
+ spec.add_runtime_dependency 'google-api-client', '~> 0.7', '>= 0.7.1'
32
+ spec.add_runtime_dependency 'mimetype-fu', '~> 0.1', '>= 0.1.2'
31
33
  # test libraries
32
34
  spec.add_development_dependency 'rspec', '~> 2.99', '>= 2.99.0'
33
35
  spec.add_development_dependency 'webmock', '~> 1.18', '>= 1.18.0'
34
- spec.add_development_dependency 'guard-rspec', '~> 4.2', '>= 4.2.10'
35
- spec.add_development_dependency 'terminal-notifier-guard', '~> 1.5', '>= 1.5.3'
36
36
  spec.add_development_dependency 'fabrication', '~> 2.11', '>= 2.11.2'
37
- spec.add_development_dependency 'rubocop', '~> 0.23', '>= 0.23.0'
38
37
  end
@@ -10,3 +10,8 @@ dropbox:
10
10
  client_id:
11
11
  client_secret:
12
12
  redirect_url:
13
+ googledrive:
14
+ client_id:
15
+ client_secret:
16
+ redirect_url:
17
+
@@ -211,9 +211,9 @@ module CloudDoor
211
211
  @file_name = file_name
212
212
  raise SetIDException unless set_file_id
213
213
  return false if file?(file_name)
214
- info = show_property(file_name)
215
- raise NoDataException if info.nil? || !info.is_a?(Hash) || !info.key?('count')
216
- (info['count'] > 0)
214
+ items = pull_files
215
+ raise NoDataException if items.nil? || !items.is_a?(Hash)
216
+ (items.count > 0)
217
217
  rescue => e
218
218
  handle_exception(e)
219
219
  end
@@ -30,14 +30,17 @@ module CloudDoor
30
30
  @root_id = ROOT_ID
31
31
  @storage_name = STORAGE_NAME
32
32
  @session_id = session_id
33
+ @client = nil
33
34
  end
34
35
 
35
36
  def load_token
36
37
  token_file = File.basename(@token.token_file)
37
- @token = Token.load_token(token_file, @config.data_path, @session_id)
38
+ @token = Token.load_token(token_file, @config.data_path, @session_id)
39
+ @client = DropboxClient.new(@token.access_token)
40
+ @token
38
41
  end
39
42
 
40
- def login(login_account, login_password)
43
+ def login(login_account, login_password)
41
44
  @account.login_account = login_account
42
45
  @account.login_password = login_password
43
46
  flow = DropboxOAuth2FlowNoRedirect.new(@config.client_id, @config.client_secret)
@@ -45,6 +48,7 @@ module CloudDoor
45
48
  access_token, user_id = flow.finish(code)
46
49
  raise NoDataException if access_token.nil?
47
50
  @session_id = reset_token({'access_token' => access_token})
51
+ @client = DropboxClient.new(access_token)
48
52
  items = pull_files
49
53
  @file_list.delete_file
50
54
  @file_list.write_file_list(items)
@@ -60,57 +64,50 @@ module CloudDoor
60
64
  private
61
65
 
62
66
  def request_user
63
- client = DropboxClient.new(@token.access_token)
64
- info = client.account_info()
67
+ info = @client.account_info()
65
68
  raise NoDataException if info.nil? || info.empty?
66
69
  info
67
70
  end
68
71
 
69
72
  def request_dir
70
73
  file_id = @parent_id || @file_id || ROOT_ID
71
- client = DropboxClient.new(@token.access_token)
72
- client.metadata(file_id)
74
+ @client.metadata(file_id)
73
75
  end
74
76
 
75
77
  def request_file
76
- client = DropboxClient.new(@token.access_token)
77
- client.metadata(@file_id)
78
+ @client.metadata(@file_id)
78
79
  end
79
80
 
80
81
  def request_download
81
- client = DropboxClient.new(@token.access_token)
82
- contents, metadata = client.get_file_and_metadata(@file_id)
82
+ contents, metadata = @client.get_file_and_metadata(@file_id)
83
83
  open(@file_name, 'w') {|f| f.puts contents }
84
84
  metadata
85
85
  end
86
86
 
87
87
  def request_upload(file_path)
88
- client = DropboxClient.new(@token.access_token)
89
88
  if @parent_id == ROOT_ID
90
89
  to_path = @parent_id + file_path
91
90
  else
92
91
  to_path = "#{@parent_id}/#{file_path}"
93
92
  end
94
- response = client.put_file(to_path, open(file_path))
93
+ response = @client.put_file(to_path, open(file_path))
95
94
  raise UploadFailedException if response.nil? || response.empty?
96
95
  response
97
96
  end
98
97
 
99
98
  def request_delete
100
- client = DropboxClient.new(@token.access_token)
101
- response = client.file_delete(@file_id)
99
+ response = @client.file_delete(@file_id)
102
100
  raise DeleteFailedException if response.nil? || response.empty?
103
101
  response
104
102
  end
105
103
 
106
104
  def request_mkdir
107
- client = DropboxClient.new(@token.access_token)
108
105
  if @parent_id == ROOT_ID
109
106
  path = @parent_id + @mkdir_name
110
107
  else
111
108
  path = "#{@parent_id}/#{@mkdir_name}"
112
109
  end
113
- response = client.file_create_folder(path)
110
+ response = @client.file_create_folder(path)
114
111
  raise MkdirFailedException if response.nil? || response.empty?
115
112
  response
116
113
  end
@@ -0,0 +1,169 @@
1
+ require 'cloud_door/cloud_storage'
2
+ require 'cloud_door/google_drive_bridge'
3
+
4
+ module CloudDoor
5
+ class GoogleDrive < CloudStorage
6
+ attr_accessor :token, :file_list, :file_id, :file_name,
7
+ :up_file_name, :mkdir_name, :parent_id
8
+ attr_reader :config, :account
9
+
10
+ # google drive login site components
11
+ LOGIN_COMPONENTS = {
12
+ 'account_text_id' => 'Email',
13
+ 'password_text_id' => 'Passwd',
14
+ 'signin_button_id' => 'signIn',
15
+ 'accept_button_id' => 'submit_approve_access',
16
+ 'auth_code_id' => 'code'
17
+ }
18
+
19
+ TIME_PROPERTY_PAT = /Date$/
20
+ CONTENTS_KEY = 'contents'
21
+ ROOT_ID = '/'
22
+ STORAGE_NAME = 'Google Drive'
23
+ OAUTH_SCOPE = 'https://www.googleapis.com/auth/drive'
24
+
25
+ def initialize(session_id = nil)
26
+ @config = Config.new('googledrive')
27
+ @account = Account.new('googledrive', @config.data_path)
28
+ @token = Token.new('googledrive_token', @config.data_path, session_id)
29
+ @file_list = FileList.new('googledrive_list', @config.data_path, session_id)
30
+ @file_id = nil
31
+ @root_id = ROOT_ID
32
+ @storage_name = STORAGE_NAME
33
+ @session_id = session_id
34
+ @client = nil
35
+ end
36
+
37
+ def load_token
38
+ token_file = File.basename(@token.token_file)
39
+ @token = Token.load_token(token_file, @config.data_path, @session_id)
40
+ @client = GoogleDriveBridge.new(Marshal.load(@token.credentials))
41
+ @root_id = request_root_id
42
+ @token
43
+ end
44
+
45
+ def login(login_account, login_password)
46
+ @account.login_account = login_account
47
+ @account.login_password = login_password
48
+ client = create_login_client
49
+ code = login_browser(client.authorization.authorization_uri.to_s)
50
+ client.authorization.code = code
51
+ client.authorization.fetch_access_token!
52
+ credentials = client.authorization
53
+ raise NoDataException if credentials.nil?
54
+ @session_id = reset_token({'credentials' => Marshal.dump(credentials)})
55
+ @client = GoogleDriveBridge.new(credentials)
56
+ @root_id = request_root_id
57
+ items = pull_files
58
+ @file_list.delete_file
59
+ @file_list.write_file_list(items)
60
+ if @config.session_use?
61
+ @session_id
62
+ else
63
+ true
64
+ end
65
+ rescue => e
66
+ handle_exception(e)
67
+ end
68
+
69
+ def create_login_client
70
+ client = Google::APIClient.new
71
+ client.authorization.client_id = @config.client_id
72
+ client.authorization.client_secret = @config.client_secret
73
+ client.authorization.scope = OAUTH_SCOPE
74
+ client.authorization.redirect_uri = @config.redirect_url
75
+ client
76
+ end
77
+
78
+ private
79
+
80
+ def request_user
81
+ @client.request_user
82
+ end
83
+
84
+ def request_root_id
85
+ @client.request_root_id
86
+ end
87
+
88
+ def request_dir
89
+ file_id = @parent_id || @file_id || @root_id
90
+ @client.request_dir(file_id)
91
+ end
92
+
93
+ def request_file
94
+ @client.request_file(@file_id)
95
+ end
96
+
97
+ def request_download
98
+ body = @client.request_download(@file_id)
99
+ if body
100
+ open(@file_name, 'w') {|f| f.puts body }
101
+ end
102
+ end
103
+
104
+ def request_upload(file_path)
105
+ @client.request_upload(file_path, @parent_id)
106
+ end
107
+
108
+ def request_delete
109
+ @client.request_delete(@file_id)
110
+ true
111
+ rescue => e
112
+ false
113
+ end
114
+
115
+ def request_mkdir
116
+ @client.request_mkdir(@mkdir_name, @parent_id)
117
+ end
118
+
119
+ def pull_files
120
+ dir = request_dir
121
+ return {} if dir.nil? || !dir.is_a?(Array) || dir.count == 0
122
+ items = {}
123
+ dir.each do |item|
124
+ id = item['id']
125
+ name = item['title']
126
+ type = (item['mimeType'] == 'application/vnd.google-apps.folder') ? 'folder' : 'file'
127
+ items[name] = {'id' => id, 'type' => type}
128
+ end
129
+ items
130
+ end
131
+
132
+ def format_property(info)
133
+ items = {}
134
+ items['name'] = info['title']
135
+ info.each do |key, val|
136
+ if key =~ TIME_PROPERTY_PAT
137
+ items[key] = DateTime.parse(val).strftime('%Y-%m-%d %H:%M:%S')
138
+ elsif key == CONTENTS_KEY
139
+ items['count'] = val.count
140
+ else
141
+ items[key] = val
142
+ end
143
+ end
144
+ items
145
+ end
146
+
147
+ def login_browser(auth_url)
148
+ browser = Watir::Browser.new :phantomjs
149
+
150
+ # input account
151
+ browser.goto(auth_url)
152
+ browser.wait
153
+ browser.text_field(:id, LOGIN_COMPONENTS['account_text_id']).set @account.login_account
154
+ browser.text_field(:id, LOGIN_COMPONENTS['password_text_id']).set @account.login_password
155
+ browser.button(:id, LOGIN_COMPONENTS['signin_button_id']).click
156
+ # allow access
157
+ Watir::Wait.until { browser.button(:id => LOGIN_COMPONENTS['accept_button_id']).enabled? }
158
+ browser.button(:id, LOGIN_COMPONENTS['accept_button_id']).click
159
+ browser.wait
160
+ # get code
161
+ code = browser.text_field(:id, LOGIN_COMPONENTS['auth_code_id']).value
162
+ browser.close
163
+ code
164
+ rescue => e
165
+ handle_exception(e)
166
+ end
167
+ end
168
+
169
+ end