Commit | Line | Data |
---|---|---|
b3abd2c6 | 1 | <?php |
f675815e | 2 | require_once($CFG->libdir.'/portfolio/plugin.php'); |
67a87e7d | 3 | require_once($CFG->libdir.'/filelib.php'); |
615a2859 | 4 | require_once($CFG->libdir.'/boxlib.php'); |
67a87e7d | 5 | |
d96a1acc | 6 | class portfolio_plugin_boxnet extends portfolio_plugin_push_base { |
67a87e7d | 7 | |
7e95408b | 8 | public $boxclient; |
67a87e7d | 9 | private $ticket; |
10 | private $authtoken; | |
67a87e7d | 11 | private $folders; |
a226b58d | 12 | private $accounttree; |
67a87e7d | 13 | |
0f71f48b | 14 | public static function get_name() { |
15 | return get_string('pluginname', 'portfolio_boxnet'); | |
16 | } | |
17 | ||
d67bfc32 | 18 | public function prepare_package() { |
13e7e765 | 19 | // don't do anything for this plugin, we want to send all files as they are. |
20 | } | |
21 | ||
22 | public function send_package() { | |
53aa4841 | 23 | // if we need to create the folder, do it now |
24 | if ($newfolder = $this->get_export_config('newfolder')) { | |
5d37f13c | 25 | if (!$created = $this->boxclient->createFolder($newfolder, array('share' => (int)$this->get_export_config('sharefolder')))) { |
53aa4841 | 26 | throw new portfolio_plugin_exception('foldercreatefailed', 'portfolio_boxnet'); |
27 | } | |
2e6a355d | 28 | $this->folders[$created['folder_id']] = $created['folder_name']; |
53aa4841 | 29 | $this->set_export_config(array('folder' => $created['folder_id'])); |
30 | } | |
d67bfc32 | 31 | foreach ($this->exporter->get_tempfiles() as $file) { |
32 | $return = $this->boxclient->uploadFile( | |
67a87e7d | 33 | array( |
34 | 'file' => $file, | |
53aa4841 | 35 | 'folder_id' => $this->get_export_config('folder'), |
fd64f098 | 36 | 'share' => $this->get_export_config('sharefile'), |
67a87e7d | 37 | ) |
38 | ); | |
d67bfc32 | 39 | if (array_key_exists('status', $return) && $return['status'] == 'upload_ok' |
40 | && array_key_exists('id', $return) && count($return['id']) == 1) { | |
37f03ea0 | 41 | $this->rename_file($return['id'][array_pop(array_keys($return['id']))], $file->get_filename()); |
42 | // if this fails, the file was sent but not renamed - this triggers a warning but is not fatal. | |
d67bfc32 | 43 | } |
67a87e7d | 44 | } |
45 | if ($this->boxclient->isError()) { | |
37f03ea0 | 46 | throw new portfolio_plugin_exception('sendfailed', 'portfolio_boxnet', $this->boxclient->getErrorMsg()); |
67a87e7d | 47 | } |
67a87e7d | 48 | } |
49 | ||
67a87e7d | 50 | public function get_export_summary() { |
51 | $allfolders = $this->get_folder_list(); | |
53aa4841 | 52 | if ($newfolder = $this->get_export_config('newfolder')) { |
53 | $foldername = $newfolder . ' (' . get_string('tobecreated', 'portfolio_boxnet') . ')'; | |
447192d3 | 54 | } elseif ($this->get_export_config('folder')) { |
53aa4841 | 55 | $foldername = $allfolders[$this->get_export_config('folder')]; |
447192d3 | 56 | } else { |
57 | $foldername = ''; | |
53aa4841 | 58 | } |
67a87e7d | 59 | return array( |
53aa4841 | 60 | get_string('targetfolder', 'portfolio_boxnet') => $foldername |
67a87e7d | 61 | ); |
62 | } | |
63 | ||
5d0dbf13 | 64 | public function get_interactive_continue_url() { |
67a87e7d | 65 | return 'http://box.net/files#0:f:' . $this->get_export_config('folder'); |
66 | } | |
67 | ||
68 | public function expected_time($callertime) { | |
69 | return $callertime; | |
70 | } | |
71 | ||
72 | public static function has_admin_config() { | |
73 | return true; | |
74 | } | |
75 | ||
76 | public static function get_allowed_config() { | |
77 | return array('apikey'); | |
78 | } | |
79 | ||
80 | public function has_export_config() { | |
81 | return true; | |
82 | } | |
83 | ||
84 | public function get_allowed_user_config() { | |
85 | return array('authtoken', 'authtokenctime'); | |
86 | } | |
87 | ||
88 | public function get_allowed_export_config() { | |
fd64f098 | 89 | return array('folder', 'newfolder', 'sharefile', 'sharefolder'); |
67a87e7d | 90 | } |
91 | ||
92 | public function export_config_form(&$mform) { | |
93 | $folders = $this->get_folder_list(); | |
fd64f098 | 94 | $mform->addElement('checkbox', 'plugin_sharefile', get_string('sharefile', 'portfolio_boxnet')); |
67a87e7d | 95 | $mform->addElement('text', 'plugin_newfolder', get_string('newfolder', 'portfolio_boxnet')); |
fd64f098 | 96 | $mform->addElement('checkbox', 'plugin_sharefolder', get_string('sharefolder', 'portfolio_boxnet')); |
447192d3 | 97 | $folders[0] = '----'; |
98 | ksort($folders); | |
99 | $mform->addElement('select', 'plugin_folder', get_string('existingfolder', 'portfolio_boxnet'), $folders); | |
67a87e7d | 100 | } |
101 | ||
caee6e6c | 102 | public function export_config_validation(array $data) { |
67a87e7d | 103 | $allfolders = $this->get_folder_list(); |
104 | if (in_array($data['plugin_newfolder'], $allfolders)) { | |
105 | return array('plugin_newfolder' => get_string('folderclash', 'portfolio_boxnet')); | |
106 | } | |
107 | } | |
108 | ||
c17ec774 | 109 | public static function admin_config_form(&$mform) { |
89e12bd5 | 110 | global $CFG; |
ff347f99 | 111 | |
eefb011d DM |
112 | $mform->addElement('text', 'apikey', get_string('apikey', 'portfolio_boxnet')); |
113 | $mform->addRule('apikey', get_string('required'), 'required', null, 'client'); | |
114 | $a = new stdClass(); | |
115 | $a->servicesurl = 'http://www.box.net/developers/services'; | |
116 | $a->callbackurl = $CFG->wwwroot . '/portfolio/add.php?postcontrol=1&type=boxnet'; | |
117 | $mform->addElement('static', 'setupinfo', get_string('setupinfo', 'portfolio_boxnet'), | |
118 | get_string('setupinfodetails', 'portfolio_boxnet', $a)); | |
67a87e7d | 119 | } |
120 | ||
121 | public function steal_control($stage) { | |
122 | if ($stage != PORTFOLIO_STAGE_CONFIG) { | |
123 | return false; | |
124 | } | |
125 | if ($this->authtoken) { | |
126 | return false; | |
127 | } | |
128 | if (!$this->ensure_ticket()) { | |
34035201 | 129 | throw new portfolio_plugin_exception('noticket', 'portfolio_boxnet'); |
67a87e7d | 130 | } |
131 | $token = $this->get_user_config('authtoken', $this->get('user')->id); | |
132 | $ctime= $this->get_user_config('authtokenctime', $this->get('user')->id); | |
133 | if (!empty($token) && (($ctime + 60*60*20) > time())) { | |
134 | $this->authtoken = $token; | |
135 | $this->boxclient->auth_token = $token; | |
136 | return false; | |
137 | } | |
138 | return 'http://www.box.net/api/1.0/auth/'.$this->ticket; | |
139 | } | |
140 | ||
141 | public function post_control($stage, $params) { | |
142 | if ($stage != PORTFOLIO_STAGE_CONFIG) { | |
143 | return; | |
144 | } | |
145 | if (!array_key_exists('auth_token', $params) || empty($params['auth_token'])) { | |
34035201 | 146 | throw new portfolio_plugin_exception('noauthtoken', 'portfolio_boxnet'); |
67a87e7d | 147 | } |
148 | $this->authtoken = $params['auth_token']; | |
149 | $this->boxclient->auth_token = $this->authtoken; | |
150 | $this->set_user_config(array('authtoken' => $this->authtoken, 'authtokenctime' => time()), $this->get('user')->id); | |
151 | } | |
152 | ||
153 | private function ensure_ticket() { | |
154 | if (!empty($this->boxclient)) { | |
155 | return true; | |
156 | } | |
157 | $this->boxclient = new boxclient($this->get_config('apikey'), ''); | |
158 | $ticket_return = $this->boxclient->getTicket(); | |
159 | if ($this->boxclient->isError() || empty($ticket_return)) { | |
34035201 | 160 | throw new portfolio_plugin_exception('noticket', 'portfolio_boxnet'); |
67a87e7d | 161 | } |
162 | $this->ticket = $ticket_return['ticket']; | |
8801ab06 | 163 | return $this->ticket; |
67a87e7d | 164 | } |
165 | ||
a226b58d | 166 | private function ensure_account_tree() { |
167 | if (!empty($this->accounttree)) { | |
168 | return; | |
67a87e7d | 169 | } |
170 | if (empty($this->ticket) | |
171 | || empty($this->authtoken) | |
172 | || empty($this->boxclient)) { | |
173 | // if we don't have these we're pretty much screwed | |
34035201 | 174 | throw new portfolio_plugin_exception('folderlistfailed', 'portfolio_boxnet'); |
67a87e7d | 175 | return false; |
176 | } | |
a226b58d | 177 | $this->accounttree = $this->boxclient->getAccountTree(); |
67a87e7d | 178 | if ($this->boxclient->isError()) { |
34035201 | 179 | throw new portfolio_plugin_exception('folderlistfailed', 'portfolio_boxnet'); |
67a87e7d | 180 | } |
a226b58d | 181 | if (!is_array($this->accounttree)) { |
67a87e7d | 182 | return false; |
183 | } | |
a226b58d | 184 | } |
185 | ||
186 | private function get_folder_list() { | |
187 | if (!empty($this->folders)) { | |
188 | return $this->folders; | |
189 | } | |
190 | $this->ensure_account_tree(); | |
67a87e7d | 191 | $folders = array(); |
a226b58d | 192 | foreach ($this->accounttree['folder_id'] as $key => $id) { |
67a87e7d | 193 | if (empty($id)) { |
194 | continue; | |
195 | } | |
a226b58d | 196 | $name = $this->accounttree['folder_name'][$key]; |
197 | if (!empty($this->accounttree['shared'][$key])) { | |
67a87e7d | 198 | $name .= ' (' . get_string('sharedfolder', 'portfolio_boxnet') . ')'; |
199 | } | |
200 | $folders[$id] = $name; | |
201 | } | |
202 | $this->folders = $folders; | |
203 | return $folders; | |
204 | } | |
205 | ||
a226b58d | 206 | private function rename_file($fileid, $newname) { |
207 | // look at moving this to the boxnet client class | |
208 | $this->ensure_account_tree(); | |
209 | $count = 1; | |
210 | $bits = explode('.', $newname); | |
211 | $suffix = ''; | |
212 | if (count($bits) == 1) { | |
68b7eed0 | 213 | $prefix = $newname; |
a226b58d | 214 | } else { |
215 | $suffix = '.' . array_pop($bits); | |
216 | $prefix = implode('.', $bits); | |
217 | } | |
218 | while (true) { | |
899ffdfb | 219 | if (!array_key_exists('file_name', $this->accounttree) || !in_array($newname, $this->accounttree['file_name'])) { |
9b69a0ce | 220 | for ($i = 0; $i < 2; $i++) { |
221 | if ($this->boxclient->renameFile($fileid, $newname)) { | |
222 | return true; | |
223 | } | |
224 | } | |
225 | debugging("tried three times to rename file and failed"); | |
226 | return false; | |
a226b58d | 227 | } |
228 | $newname = $prefix . '(' . $count . ')' . $suffix; | |
229 | $count++; | |
230 | } | |
231 | return false; | |
232 | } | |
233 | ||
67a87e7d | 234 | public function instance_sanity_check() { |
235 | if (!$this->get_config('apikey')) { | |
236 | return 'err_noapikey'; | |
237 | } | |
238 | //@TODO see if we can verify the api key without actually getting an authentication token | |
239 | } | |
2f68e760 | 240 | |
384ba38a | 241 | public static function allows_multiple_instances() { |
2f68e760 | 242 | return false; |
243 | } | |
62e71954 | 244 | |
38652d90 | 245 | public function supported_formats() { |
24b69846 | 246 | return array(PORTFOLIO_FORMAT_FILE, PORTFOLIO_FORMAT_RICHHTML); |
62e71954 | 247 | } |
bd39808b PL |
248 | |
249 | /* | |
250 | * for now , boxnet doesn't support this, | |
251 | * because we can't dynamically construct return urls. | |
252 | */ | |
253 | public static function allows_multiple_exports() { | |
254 | return false; | |
255 | } | |
67a87e7d | 256 | } |