Translated using Weblate (Estonian)
[phpmyadmin.git] / js / common.js
blobe19a18099f9e2085c874c68472bb3c470c91abd4
1 /* vim: set expandtab sw=4 ts=4 sts=4: */
3 $(function () {
4     checkNumberOfFields();
5 });
7 /**
8  * Holds common parameters such as server, db, table, etc
9  *
10  * The content for this is normally loaded from Header.php or
11  * Response.php and executed by ajax.js
12  */
13 var PMA_commonParams = (function () {
14     /**
15      * @var hash params An associative array of key value pairs
16      * @access private
17      */
18     var params = {};
19     // The returned object is the public part of the module
20     return {
21         /**
22          * Saves all the key value pair that
23          * are provided in the input array
24          *
25          * @param obj hash The input array
26          *
27          * @return void
28          */
29         setAll: function (obj) {
30             var reload = false;
31             var updateNavigation = false;
32             for (var i in obj) {
33                 if (params[i] !== undefined && params[i] !== obj[i]) {
34                     if (i === 'db' || i === 'table') {
35                         updateNavigation = true;
36                     }
37                     reload = true;
38                 }
39                 params[i] = obj[i];
40             }
41             if (updateNavigation &&
42                     $('#pma_navigation_tree').hasClass('synced')
43             ) {
44                 PMA_showCurrentNavigation();
45             }
46         },
47         /**
48          * Retrieves a value given its key
49          * Returns empty string for undefined values
50          *
51          * @param name string The key
52          *
53          * @return string
54          */
55         get: function (name) {
56             return params[name];
57         },
58         /**
59          * Saves a single key value pair
60          *
61          * @param name  string The key
62          * @param value string The value
63          *
64          * @return self For chainability
65          */
66         set: function (name, value) {
67             var updateNavigation = false;
68             if (name === 'db' || name === 'table' &&
69                 params[name] !== value
70             ) {
71                 updateNavigation = true;
72             }
73             params[name] = value;
74             if (updateNavigation &&
75                     $('#pma_navigation_tree').hasClass('synced')
76             ) {
77                 PMA_showCurrentNavigation();
78             }
79             return this;
80         },
81         /**
82          * Returns the url query string using the saved parameters
83          *
84          * @return string
85          */
86         getUrlQuery: function () {
87             var common = this.get('common_query');
88             var separator = '?';
89             if (common.length > 0) {
90                 separator = '&';
91             }
92             return PMA_sprintf(
93                 '%s%sserver=%s&db=%s&table=%s',
94                 this.get('common_query'),
95                 separator,
96                 encodeURIComponent(this.get('server')),
97                 encodeURIComponent(this.get('db')),
98                 encodeURIComponent(this.get('table'))
99             );
100         }
101     };
102 }());
105  * Holds common parameters such as server, db, table, etc
107  * The content for this is normally loaded from Header.php or
108  * Response.php and executed by ajax.js
109  */
110 var PMA_commonActions = {
111     /**
112      * Saves the database name when it's changed
113      * and reloads the query window, if necessary
114      *
115      * @param new_db string new_db The name of the new database
116      *
117      * @return void
118      */
119     setDb: function (new_db) {
120         if (new_db !== PMA_commonParams.get('db')) {
121             PMA_commonParams.setAll({ 'db': new_db, 'table': '' });
122         }
123     },
124     /**
125      * Opens a database in the main part of the page
126      *
127      * @param new_db string The name of the new database
128      *
129      * @return void
130      */
131     openDb: function (new_db) {
132         PMA_commonParams
133             .set('db', new_db)
134             .set('table', '');
135         this.refreshMain(
136             PMA_commonParams.get('opendb_url')
137         );
138     },
139     /**
140      * Refreshes the main frame
141      *
142      * @param mixed url Undefined to refresh to the same page
143      *                  String to go to a different page, e.g: 'index.php'
144      *
145      * @return void
146      */
147     refreshMain: function (url, callback) {
148         if (! url) {
149             url = $('#selflink').find('a').attr('href');
150             url = url.substring(0, url.indexOf('?'));
151         }
152         url += PMA_commonParams.getUrlQuery();
153         $('<a />', { href: url })
154             .appendTo('body')
155             .click()
156             .remove();
157         AJAX._callback = callback;
158     }
162  * Class to handle PMA Drag and Drop Import
163  *      feature
164  */
165 PMA_DROP_IMPORT = {
166     /**
167      * @var int, count of total uploads in this view
168      */
169     uploadCount: 0,
170     /**
171      * @var int, count of live uploads
172      */
173     liveUploadCount: 0,
174     /**
175      * @var  string array, allowed extensions
176      */
177     allowedExtensions: ['sql', 'xml', 'ldi', 'mediawiki', 'shp'],
178     /**
179      * @var  string array, allowed extensions for compressed files
180      */
181     allowedCompressedExtensions: ['gz', 'bz2', 'zip'],
182     /**
183      * @var obj array to store message returned by import_status.php
184      */
185     importStatus: [],
186     /**
187      * Checks if any dropped file has valid extension or not
188      *
189      * @param file filename
190      *
191      * @return string, extension for valid extension, '' otherwise
192      */
193     _getExtension: function (file) {
194         var arr = file.split('.');
195         ext = arr[arr.length - 1];
197         // check if compressed
198         if (jQuery.inArray(ext.toLowerCase(),
199             PMA_DROP_IMPORT.allowedCompressedExtensions) !== -1) {
200             ext = arr[arr.length - 2];
201         }
203         // Now check for extension
204         if (jQuery.inArray(ext.toLowerCase(),
205             PMA_DROP_IMPORT.allowedExtensions) !== -1) {
206             return ext;
207         }
208         return '';
209     },
210     /**
211      * Shows upload progress for different sql uploads
212      *
213      * @param: hash (string), hash for specific file upload
214      * @param: percent (float), file upload percentage
215      *
216      * @return void
217      */
218     _setProgress: function (hash, percent) {
219         $('.pma_sql_import_status div li[data-hash="' + hash + '"]')
220             .children('progress').val(percent);
221     },
222     /**
223      * Function to upload the file asynchronously
224      *
225      * @param formData FormData object for a specific file
226      * @param hash hash of the current file upload
227      *
228      * @return void
229      */
230     _sendFileToServer: function (formData, hash) {
231         var uploadURL = './import.php'; // Upload URL
232         var extraData = {};
233         var jqXHR = $.ajax({
234             xhr: function () {
235                 var xhrobj = $.ajaxSettings.xhr();
236                 if (xhrobj.upload) {
237                     xhrobj.upload.addEventListener('progress', function (event) {
238                         var percent = 0;
239                         var position = event.loaded || event.position;
240                         var total = event.total;
241                         if (event.lengthComputable) {
242                             percent = Math.ceil(position / total * 100);
243                         }
244                         // Set progress
245                         PMA_DROP_IMPORT._setProgress(hash, percent);
246                     }, false);
247                 }
248                 return xhrobj;
249             },
250             url: uploadURL,
251             type: 'POST',
252             contentType:false,
253             processData: false,
254             cache: false,
255             data: formData,
256             success: function (data) {
257                 PMA_DROP_IMPORT._importFinished(hash, false, data.success);
258                 if (!data.success) {
259                     PMA_DROP_IMPORT.importStatus[PMA_DROP_IMPORT.importStatus.length] = {
260                         hash: hash,
261                         message: data.error
262                     };
263                 }
264             }
265         });
267         // -- provide link to cancel the upload
268         $('.pma_sql_import_status div li[data-hash="' + hash +
269             '"] span.filesize').html('<span hash="' +
270             hash + '" class="pma_drop_file_status" task="cancel">' +
271             PMA_messages.dropImportMessageCancel + '</span>');
273         // -- add event listener to this link to abort upload operation
274         $('.pma_sql_import_status div li[data-hash="' + hash +
275             '"] span.filesize span.pma_drop_file_status')
276             .on('click', function () {
277                 if ($(this).attr('task') === 'cancel') {
278                     jqXHR.abort();
279                     $(this).html('<span>' + PMA_messages.dropImportMessageAborted + '</span>');
280                     PMA_DROP_IMPORT._importFinished(hash, true, false);
281                 } else if ($(this).children('span').html() ===
282                     PMA_messages.dropImportMessageFailed) {
283                     // -- view information
284                     var $this = $(this);
285                     $.each(PMA_DROP_IMPORT.importStatus,
286                         function (key, value) {
287                             if (value.hash === hash) {
288                                 $('.pma_drop_result:visible').remove();
289                                 var filename = $this.parent('span').attr('data-filename');
290                                 $('body').append('<div class="pma_drop_result"><h2>' +
291                                 PMA_messages.dropImportImportResultHeader + ' - ' +
292                                 filename + '<span class="close">x</span></h2>' + value.message + '</div>');
293                                 $('.pma_drop_result').draggable();  // to make this dialog draggable
294                             }
295                         });
296                 }
297             });
298     },
299     /**
300      * Triggered when an object is dragged into the PMA UI
301      *
302      * @param event obj
303      *
304      * @return void
305      */
306     _dragenter : function (event) {
307         // We don't want to prevent users from using
308         // browser's default drag-drop feature on some page(s)
309         if ($('.noDragDrop').length !== 0) {
310             return;
311         }
313         event.stopPropagation();
314         event.preventDefault();
315         if (!PMA_DROP_IMPORT._hasFiles(event)) {
316             return;
317         }
318         if (PMA_commonParams.get('db') === '') {
319             $('.pma_drop_handler').html(PMA_messages.dropImportSelectDB);
320         } else {
321             $('.pma_drop_handler').html(PMA_messages.dropImportDropFiles);
322         }
323         $('.pma_drop_handler').fadeIn();
324     },
325     /**
326      * Check if dragged element contains Files
327      *
328      * @param event the event object
329      *
330      * @return bool
331      */
332     _hasFiles: function (event) {
333         return !(typeof event.originalEvent.dataTransfer.types === 'undefined' ||
334             $.inArray('Files', event.originalEvent.dataTransfer.types) < 0 ||
335             $.inArray(
336                 'application/x-moz-nativeimage',
337                 event.originalEvent.dataTransfer.types
338             ) >= 0);
339     },
340     /**
341      * Triggered when dragged file is being dragged over PMA UI
342      *
343      * @param event obj
344      *
345      * @return void
346      */
347     _dragover: function (event) {
348         // We don't want to prevent users from using
349         // browser's default drag-drop feature on some page(s)
350         if ($('.noDragDrop').length !== 0) {
351             return;
352         }
354         event.stopPropagation();
355         event.preventDefault();
356         if (!PMA_DROP_IMPORT._hasFiles(event)) {
357             return;
358         }
359         $('.pma_drop_handler').fadeIn();
360     },
361     /**
362      * Triggered when dragged objects are left
363      *
364      * @param event obj
365      *
366      * @return void
367      */
368     _dragleave: function (event) {
369         // We don't want to prevent users from using
370         // browser's default drag-drop feature on some page(s)
371         if ($('.noDragDrop').length !== 0) {
372             return;
373         }
374         event.stopPropagation();
375         event.preventDefault();
376         var $pma_drop_handler = $('.pma_drop_handler');
377         $pma_drop_handler.clearQueue().stop();
378         $pma_drop_handler.fadeOut();
379         $pma_drop_handler.html(PMA_messages.dropImportDropFiles);
380     },
381     /**
382      * Called when upload has finished
383      *
384      * @param string, unique hash for a certain upload
385      * @param bool, true if upload was aborted
386      * @param bool, status of sql upload, as sent by server
387      *
388      * @return void
389      */
390     _importFinished: function (hash, aborted, status) {
391         $('.pma_sql_import_status div li[data-hash="' + hash + '"]')
392             .children('progress').hide();
393         var icon = 'icon ic_s_success';
394         // -- provide link to view upload status
395         if (!aborted) {
396             if (status) {
397                 $('.pma_sql_import_status div li[data-hash="' + hash +
398                    '"] span.filesize span.pma_drop_file_status')
399                     .html('<span>' + PMA_messages.dropImportMessageSuccess + '</a>');
400             } else {
401                 $('.pma_sql_import_status div li[data-hash="' + hash +
402                    '"] span.filesize span.pma_drop_file_status')
403                     .html('<span class="underline">' + PMA_messages.dropImportMessageFailed +
404                    '</a>');
405                 icon = 'icon ic_s_error';
406             }
407         } else {
408             icon = 'icon ic_s_notice';
409         }
410         $('.pma_sql_import_status div li[data-hash="' + hash +
411             '"] span.filesize span.pma_drop_file_status')
412             .attr('task', 'info');
414         // Set icon
415         $('.pma_sql_import_status div li[data-hash="' + hash + '"]')
416             .prepend('<img src="./themes/dot.gif" title="finished" class="' +
417             icon + '"> ');
419         // Decrease liveUploadCount by one
420         $('.pma_import_count').html(--PMA_DROP_IMPORT.liveUploadCount);
421         if (!PMA_DROP_IMPORT.liveUploadCount) {
422             $('.pma_sql_import_status h2 .close').fadeIn();
423         }
424     },
425     /**
426      * Triggered when dragged objects are dropped to UI
427      * From this function, the AJAX Upload operation is initiated
428      *
429      * @param event object
430      *
431      * @return void
432      */
433     _drop: function (event) {
434         // We don't want to prevent users from using
435         // browser's default drag-drop feature on some page(s)
436         if ($('.noDragDrop').length !== 0) {
437             return;
438         }
440         var dbname = PMA_commonParams.get('db');
441         var server = PMA_commonParams.get('server');
443         // if no database is selected -- no
444         if (dbname !== '') {
445             var files = event.originalEvent.dataTransfer.files;
446             if (!files || files.length === 0) {
447                 // No files actually transferred
448                 $('.pma_drop_handler').fadeOut();
449                 event.stopPropagation();
450                 event.preventDefault();
451                 return;
452             }
453             $('.pma_sql_import_status').slideDown();
454             for (var i = 0; i < files.length; i++) {
455                 var ext  = (PMA_DROP_IMPORT._getExtension(files[i].name));
456                 var hash = AJAX.hash(++PMA_DROP_IMPORT.uploadCount);
458                 var $pma_sql_import_status_div = $('.pma_sql_import_status div');
459                 $pma_sql_import_status_div.append('<li data-hash="' + hash + '">' +
460                     ((ext !== '') ? '' : '<img src="./themes/dot.gif" title="invalid format" class="icon ic_s_notice"> ') +
461                     escapeHtml(files[i].name) + '<span class="filesize" data-filename="' +
462                     escapeHtml(files[i].name) + '">' + (files[i].size / 1024).toFixed(2) +
463                     ' kb</span></li>');
465                 // scroll the UI to bottom
466                 $pma_sql_import_status_div.scrollTop(
467                     $pma_sql_import_status_div.scrollTop() + 50
468                 );  // 50 hardcoded for now
470                 if (ext !== '') {
471                     // Increment liveUploadCount by one
472                     $('.pma_import_count').html(++PMA_DROP_IMPORT.liveUploadCount);
473                     $('.pma_sql_import_status h2 .close').fadeOut();
475                     $('.pma_sql_import_status div li[data-hash="' + hash + '"]')
476                         .append('<br><progress max="100" value="2"></progress>');
478                     // uploading
479                     var fd = new FormData();
480                     fd.append('import_file', files[i]);
481                     fd.append('noplugin', Math.random().toString(36).substring(2, 12));
482                     fd.append('db', dbname);
483                     fd.append('server', server);
484                     fd.append('token', PMA_commonParams.get('token'));
485                     fd.append('import_type', 'database');
486                     // todo: method to find the value below
487                     fd.append('MAX_FILE_SIZE', '4194304');
488                     // todo: method to find the value below
489                     fd.append('charset_of_file','utf-8');
490                     // todo: method to find the value below
491                     fd.append('allow_interrupt', 'yes');
492                     fd.append('skip_queries', '0');
493                     fd.append('format',ext);
494                     fd.append('sql_compatibility','NONE');
495                     fd.append('sql_no_auto_value_on_zero','something');
496                     fd.append('ajax_request','true');
497                     fd.append('hash', hash);
499                     // init uploading
500                     PMA_DROP_IMPORT._sendFileToServer(fd, hash);
501                 } else if (!PMA_DROP_IMPORT.liveUploadCount) {
502                     $('.pma_sql_import_status h2 .close').fadeIn();
503                 }
504             }
505         }
506         $('.pma_drop_handler').fadeOut();
507         event.stopPropagation();
508         event.preventDefault();
509     }
513  * Called when some user drags, dragover, leave
514  *       a file to the PMA UI
515  * @param object Event data
516  * @return void
517  */
518 $(document).on('dragenter', PMA_DROP_IMPORT._dragenter);
519 $(document).on('dragover', PMA_DROP_IMPORT._dragover);
520 $(document).on('dragleave', '.pma_drop_handler', PMA_DROP_IMPORT._dragleave);
522 // when file is dropped to PMA UI
523 $(document).on('drop', 'body', PMA_DROP_IMPORT._drop);
525 // minimizing-maximising the sql ajax upload status
526 $(document).on('click', '.pma_sql_import_status h2 .minimize', function () {
527     if ($(this).attr('toggle') === 'off') {
528         $('.pma_sql_import_status div').css('height','270px');
529         $(this).attr('toggle','on');
530         $(this).html('-');  // to minimize
531     } else {
532         $('.pma_sql_import_status div').css('height','0px');
533         $(this).attr('toggle','off');
534         $(this).html('+');  // to maximise
535     }
538 // closing sql ajax upload status
539 $(document).on('click', '.pma_sql_import_status h2 .close', function () {
540     $('.pma_sql_import_status').fadeOut(function () {
541         $('.pma_sql_import_status div').html('');
542         PMA_DROP_IMPORT.importStatus = [];  // clear the message array
543     });
546 // Closing the import result box
547 $(document).on('click', '.pma_drop_result h2 .close', function () {
548     $(this).parent('h2').parent('div').remove();