]> git.mxchange.org Git - friendica.git/blob - addon/js_upload/js_upload.php
06a907603f18a6bcab3753018aa518109ad1da7b
[friendica.git] / addon / js_upload / js_upload.php
1 <?php
2
3 /**
4  * Name: JS Uploader
5  * Description: JavaScript photo/image uploader. Uses Valum 'qq' Uploader.
6  * Version: 1.0
7  * Author: Chris Case <http://friendika.openmindspace.org/profile/chris_case>
8  */
9
10 /**
11  *
12  * JavaScript Photo/Image Uploader
13  *
14  * Uses Valum 'qq' Uploader. 
15  * Module Author: Chris Case
16  *
17  */
18
19
20 function js_upload_install() {
21         register_hook('photo_upload_form', 'addon/js_upload/js_upload.php', 'js_upload_form');
22         register_hook('photo_post_init',   'addon/js_upload/js_upload.php', 'js_upload_post_init');
23         register_hook('photo_post_file',   'addon/js_upload/js_upload.php', 'js_upload_post_file');
24         register_hook('photo_post_end',    'addon/js_upload/js_upload.php', 'js_upload_post_end');
25 }
26
27
28 function js_upload_uninstall() {
29         unregister_hook('photo_upload_form', 'addon/js_upload/js_upload.php', 'js_upload_form');
30         unregister_hook('photo_post_init',   'addon/js_upload/js_upload.php', 'js_upload_post_init');
31         unregister_hook('photo_post_file',   'addon/js_upload/js_upload.php', 'js_upload_post_file');
32         unregister_hook('photo_post_end',    'addon/js_upload/js_upload.php', 'js_upload_post_end');
33 }
34
35
36 function js_upload_form(&$a,&$b) {
37
38         $b['default_upload'] = false;
39
40         $b['addon_text'] .= '<link href="' . $a->get_baseurl() . '/addon/js_upload/file-uploader/client/fileuploader.css" rel="stylesheet" type="text/css">';
41         $b['addon_text'] .= '<script src="' . $a->get_baseurl() . '/addon/js_upload/file-uploader/client/fileuploader.js" type="text/javascript"></script>';
42    
43         $upload_msg = t('Upload a file');
44         $drop_msg = t('Drop files here to upload');
45         $cancel = t('Cancel');
46         $failed = t('Failed');
47
48         $b['addon_text'] .= <<< EOT
49         
50  <div id="file-uploader-demo1">         
51   <noscript>                    
52    <p>Please enable JavaScript to use file uploader.</p>
53    <!-- or put a simple form for upload here -->
54   </noscript> 
55  </div>
56
57 <script type="text/javascript">
58 var uploader = null;       
59 function getSelected(opt) {
60             var selected = new Array();
61             var index = 0;
62             for (var intLoop = 0; intLoop < opt.length; intLoop++) {
63                if ((opt[intLoop].selected) ||
64                    (opt[intLoop].checked)) {
65                   index = selected.length;
66                   //selected[index] = new Object;
67                   selected[index] = opt[intLoop].value;
68                   //selected[index] = intLoop;
69                }
70             }
71             return selected;
72          } 
73 function createUploader() {
74         uploader = new qq.FileUploader({
75                 element: document.getElementById('file-uploader-demo1'),
76                 action: '{$b['post_url']}',
77
78         template: '<div class="qq-uploader">' + 
79                 '<div class="qq-upload-drop-area"><span>$drop_msg</span></div>' +
80                 '<div class="qq-upload-button">$upload_msg</div>' +
81                 '<ul class="qq-upload-list"></ul>' + 
82              '</div>',
83
84         // template for one item in file list
85         fileTemplate: '<li>' +
86                 '<span class="qq-upload-file"></span>' +
87                 '<span class="qq-upload-spinner"></span>' +
88                 '<span class="qq-upload-size"></span>' +
89                 '<a class="qq-upload-cancel" href="#">$cancel</a>' +
90                 '<span class="qq-upload-failed-text">$failed</span>' +
91             '</li>',        
92
93                 debug: true,
94                 onSubmit: function(id,filename) {
95
96                         uploader.setParams( {
97                                 newalbum                :       document.getElementById('photos-upload-newalbum').value,
98                                 album                   :       document.getElementById('photos-upload-album-select').value,
99                                 group_allow             :       getSelected(document.getElementById('group_allow')).join(','),
100                                 contact_allow   :       getSelected(document.getElementById('contact_allow')).join(','),
101                                 group_deny              :       getSelected(document.getElementById('group_deny')).join(','),
102                                 contact_deny    :       getSelected(document.getElementById('contact_deny')).join(',')
103                         });
104                 }
105         });           
106 }
107
108
109 // in your app create uploader as soon as the DOM is ready
110 // don't wait for the window to load  
111 window.onload = createUploader;     
112
113
114 </script>
115  
116 EOT;
117
118
119 }
120
121 function js_upload_post_init(&$a,&$b) {
122
123         // list of valid extensions, ex. array("jpeg", "xml", "bmp")
124
125         $allowedExtensions = array("jpeg","gif","png","jpg");
126
127         // max file size in bytes
128
129         $sizeLimit = get_config('system','maximagesize'); //6 * 1024 * 1024;
130
131         $uploader = new qqFileUploader($allowedExtensions, $sizeLimit);
132
133         $result = $uploader->handleUpload();
134
135
136         // to pass data through iframe you will need to encode all html tags
137         $a->data['upload_jsonresponse'] =  htmlspecialchars(json_encode($result), ENT_NOQUOTES);
138
139         if(isset($result['error'])) {
140                 logger('mod/photos.php: photos_post(): error uploading photo: ' . $result['error'] , 'LOGGER_DEBUG');
141                 echo json_encode($result);
142                 killme();
143         }
144
145         $a->data['upload_result'] = $result;
146
147 }
148
149 function js_upload_post_file(&$a,&$b) {
150
151         $result = $a->data['upload_result'];
152
153         $b['src']               = $result['path'];
154         $b['filename']  = $result['filename'];
155         $b['filesize']  = filesize($b['src']);
156
157 }
158
159
160 function js_upload_post_end(&$a,&$b) {
161
162 logger('upload_post_end');
163         if(x($a->data,'upload_jsonresponse')) {
164                 echo $a->data['upload_jsonresponse'];
165                 killme();
166         }
167
168 }
169
170
171 /**
172  * Handle file uploads via XMLHttpRequest
173  */
174 class qqUploadedFileXhr {
175
176         private $pathnm = '';
177
178     /**
179      * Save the file in the temp dir.
180      * @return boolean TRUE on success
181      */
182     function save() {    
183         $input = fopen("php://input", "r");
184         $this->pathnm = tempnam(sys_get_temp_dir(),'frn');
185                 $temp = fopen($this->pathnm,"w");
186         $realSize = stream_copy_to_stream($input, $temp);
187
188         fclose($input);
189                 fclose($temp);
190         
191         if ($realSize != $this->getSize()){            
192             return false;
193         }
194         return true;
195     }
196
197         function getPath() {
198                 return $this->pathnm;
199         }
200
201     function getName() {
202         return $_GET['qqfile'];
203     }
204
205     function getSize() {
206         if (isset($_SERVER["CONTENT_LENGTH"])){
207             return (int)$_SERVER["CONTENT_LENGTH"];            
208         } else {
209             throw new Exception('Getting content length is not supported.');
210         }      
211     }   
212 }
213
214 /**
215  * Handle file uploads via regular form post (uses the $_FILES array)
216  */
217
218 class qqUploadedFileForm {  
219
220
221     /**
222      * Save the file to the specified path
223      * @return boolean TRUE on success
224      */
225
226
227     function save() {
228         return true;
229     }
230
231         function getPath() {
232                 return $_FILES['qqfile']['tmp_name'];
233         }
234
235     function getName() {
236         return $_FILES['qqfile']['name'];
237     }
238     function getSize() {
239         return $_FILES['qqfile']['size'];
240     }
241 }
242
243 class qqFileUploader {
244     private $allowedExtensions = array();
245     private $sizeLimit = 10485760;
246     private $file;
247
248     function __construct(array $allowedExtensions = array(), $sizeLimit = 10485760){        
249         $allowedExtensions = array_map("strtolower", $allowedExtensions);
250             
251         $this->allowedExtensions = $allowedExtensions;        
252         $this->sizeLimit = $sizeLimit;
253         
254         if (isset($_GET['qqfile'])) {
255             $this->file = new qqUploadedFileXhr();
256         } elseif (isset($_FILES['qqfile'])) {
257             $this->file = new qqUploadedFileForm();
258         } else {
259             $this->file = false; 
260         }
261
262     }
263     
264     
265     private function toBytes($str){
266         $val = trim($str);
267         $last = strtolower($str[strlen($str)-1]);
268         switch($last) {
269             case 'g': $val *= 1024;
270             case 'm': $val *= 1024;
271             case 'k': $val *= 1024;        
272         }
273         return $val;
274     }
275     
276     /**
277      * Returns array('success'=>true) or array('error'=>'error message')
278      */
279     function handleUpload(){
280         
281         if (!$this->file){
282             return array('error' => t('No files were uploaded.'));
283         }
284         
285         $size = $this->file->getSize();
286         
287         if ($size == 0) {
288             return array('error' => t('Uploaded file is empty'));
289         }
290         
291         if ($size > $this->sizeLimit) {
292
293             return array('error' => t('Uploaded file is too large'));
294         }
295         
296
297                 $maximagesize = get_config('system','maximagesize');
298
299                 if(($maximagesize) && ($size > $maximagesize)) {
300                         return array('error' => t('Image exceeds size limit of ') . $maximagesize );
301
302                 }
303
304         $pathinfo = pathinfo($this->file->getName());
305         $filename = $pathinfo['filename'];
306
307         $ext = $pathinfo['extension'];
308
309         if($this->allowedExtensions && !in_array(strtolower($ext), $this->allowedExtensions)){
310             $these = implode(', ', $this->allowedExtensions);
311             return array('error' => t('File has an invalid extension, it should be one of ') . $these . '.');
312         }
313         
314         if ($this->file->save()){
315             return array(
316                                 'success'=>true,
317                                 'path' => $this->file->getPath(), 
318                                 'filename' => $filename . '.' . $ext
319                         );
320         } else {
321             return array(
322                                 'error'=> t('Upload was cancelled, or server error encountered'),
323                                 'path' => $this->file->getPath(), 
324                                 'filename' => $filename . '.' . $ext
325                         );
326         }
327         
328     }    
329 }