[ Index ] |
PHP Cross Reference of Unnamed Project |
[Summary view] [Print] [Text view]
1 /* 2 YUI 3.17.2 (build 9c3c78e) 3 Copyright 2014 Yahoo! Inc. All rights reserved. 4 Licensed under the BSD License. 5 http://yuilibrary.com/license/ 6 */ 7 8 YUI.add('uploader-queue', function (Y, NAME) { 9 10 /** 11 * The class manages a queue of files that should be uploaded to the server. 12 * It initializes the required number of uploads, tracks them as they progress, 13 * and automatically advances to the next upload when a preceding one has completed. 14 * @module uploader-queue 15 */ 16 17 18 19 /** 20 * This class manages a queue of files to be uploaded to the server. 21 * @class Uploader.Queue 22 * @extends Base 23 * @constructor 24 */ 25 var UploaderQueue = function() { 26 this.queuedFiles = []; 27 this.uploadRetries = {}; 28 this.numberOfUploads = 0; 29 this.currentUploadedByteValues = {}; 30 this.currentFiles = {}; 31 this.totalBytesUploaded = 0; 32 this.totalBytes = 0; 33 34 UploaderQueue.superclass.constructor.apply(this, arguments); 35 }; 36 37 38 Y.extend(UploaderQueue, Y.Base, { 39 40 /** 41 * Stored value of the current queue state 42 * @property _currentState 43 * @type {String} 44 * @protected 45 * @default UploaderQueue.STOPPED 46 */ 47 _currentState: UploaderQueue.STOPPED, 48 49 /** 50 * Construction logic executed during UploaderQueue instantiation. 51 * 52 * @method initializer 53 * @protected 54 */ 55 initializer : function () {}, 56 57 /** 58 * Handles and retransmits upload start event. 59 * 60 * @method _uploadStartHandler 61 * @param event The event dispatched during the upload process. 62 * @private 63 */ 64 _uploadStartHandler : function (event) { 65 var updatedEvent = event; 66 updatedEvent.file = event.target; 67 updatedEvent.originEvent = event; 68 69 this.fire("uploadstart", updatedEvent); 70 }, 71 72 /** 73 * Handles and retransmits upload error event. 74 * 75 * @method _uploadErrorHandler 76 * @param event The event dispatched during the upload process. 77 * @private 78 */ 79 _uploadErrorHandler : function (event) { 80 var errorAction = this.get("errorAction"), 81 updatedEvent = event, 82 fileid, 83 retries; 84 85 updatedEvent.file = event.target; 86 updatedEvent.originEvent = event; 87 88 this.numberOfUploads-=1; 89 delete this.currentFiles[event.target.get("id")]; 90 this._detachFileEvents(event.target); 91 92 event.target.cancelUpload(); 93 94 if (errorAction === UploaderQueue.STOP) { 95 this.pauseUpload(); 96 } 97 98 else if (errorAction === UploaderQueue.RESTART_ASAP) { 99 fileid = event.target.get("id"); 100 retries = this.uploadRetries[fileid] || 0; 101 102 if (retries < this.get("retryCount")) { 103 this.uploadRetries[fileid] = retries + 1; 104 this.addToQueueTop(event.target); 105 } 106 this._startNextFile(); 107 } 108 else if (errorAction === UploaderQueue.RESTART_AFTER) { 109 fileid = event.target.get("id"); 110 retries = this.uploadRetries[fileid] || 0; 111 112 if (retries < this.get("retryCount")) { 113 this.uploadRetries[fileid] = retries + 1; 114 this.addToQueueBottom(event.target); 115 } 116 this._startNextFile(); 117 } 118 119 this.fire("uploaderror", updatedEvent); 120 }, 121 122 /** 123 * Launches the upload of the next file in the queue. 124 * 125 * @method _startNextFile 126 * @private 127 */ 128 _startNextFile : function () { 129 if (this.queuedFiles.length > 0) { 130 var currentFile = this.queuedFiles.shift(), 131 fileId = currentFile.get("id"), 132 parameters = this.get("perFileParameters"), 133 fileParameters = parameters.hasOwnProperty(fileId) ? parameters[fileId] : parameters; 134 135 this.currentUploadedByteValues[fileId] = 0; 136 137 currentFile.on("uploadstart", this._uploadStartHandler, this); 138 currentFile.on("uploadprogress", this._uploadProgressHandler, this); 139 currentFile.on("uploadcomplete", this._uploadCompleteHandler, this); 140 currentFile.on("uploaderror", this._uploadErrorHandler, this); 141 currentFile.on("uploadcancel", this._uploadCancelHandler, this); 142 143 currentFile.set("xhrHeaders", this.get("uploadHeaders")); 144 currentFile.set("xhrWithCredentials", this.get("withCredentials")); 145 146 currentFile.startUpload(this.get("uploadURL"), fileParameters, this.get("fileFieldName")); 147 148 this._registerUpload(currentFile); 149 } 150 }, 151 152 /** 153 * Register a new upload process. 154 * 155 * @method _registerUpload 156 * @private 157 */ 158 _registerUpload : function (file) { 159 this.numberOfUploads += 1; 160 this.currentFiles[file.get("id")] = file; 161 }, 162 163 /** 164 * Unregisters a new upload process. 165 * 166 * @method _unregisterUpload 167 * @private 168 */ 169 _unregisterUpload : function (file) { 170 if (this.numberOfUploads > 0) { 171 this.numberOfUploads -= 1; 172 } 173 174 delete this.currentFiles[file.get("id")]; 175 delete this.uploadRetries[file.get("id")]; 176 177 this._detachFileEvents(file); 178 }, 179 180 _detachFileEvents : function (file) { 181 file.detach("uploadstart", this._uploadStartHandler); 182 file.detach("uploadprogress", this._uploadProgressHandler); 183 file.detach("uploadcomplete", this._uploadCompleteHandler); 184 file.detach("uploaderror", this._uploadErrorHandler); 185 file.detach("uploadcancel", this._uploadCancelHandler); 186 }, 187 188 /** 189 * Handles and retransmits upload complete event. 190 * 191 * @method _uploadCompleteHandler 192 * @param event The event dispatched during the upload process. 193 * @private 194 */ 195 _uploadCompleteHandler : function (event) { 196 197 this._unregisterUpload(event.target); 198 199 this.totalBytesUploaded += event.target.get("size"); 200 delete this.currentUploadedByteValues[event.target.get("id")]; 201 202 203 if (this.queuedFiles.length > 0 && this._currentState === UploaderQueue.UPLOADING) { 204 this._startNextFile(); 205 } 206 207 var updatedEvent = event, 208 uploadedTotal = this.totalBytesUploaded, 209 percentLoaded = Math.min(100, Math.round(10000*uploadedTotal/this.totalBytes) / 100); 210 211 updatedEvent.file = event.target; 212 updatedEvent.originEvent = event; 213 214 Y.each(this.currentUploadedByteValues, function (value) { 215 uploadedTotal += value; 216 }); 217 218 this.fire("totaluploadprogress", { 219 bytesLoaded: uploadedTotal, 220 bytesTotal: this.totalBytes, 221 percentLoaded: percentLoaded 222 }); 223 224 this.fire("uploadcomplete", updatedEvent); 225 226 if (this.queuedFiles.length === 0 && this.numberOfUploads <= 0) { 227 this.fire("alluploadscomplete"); 228 this._currentState = UploaderQueue.STOPPED; 229 } 230 }, 231 232 /** 233 * Handles and retransmits upload cancel event. 234 * 235 * @method _uploadCancelHandler 236 * @param event The event dispatched during the upload process. 237 * @private 238 */ 239 _uploadCancelHandler : function (event) { 240 241 var updatedEvent = event; 242 updatedEvent.originEvent = event; 243 updatedEvent.file = event.target; 244 245 this.fire("uploadcancel", updatedEvent); 246 }, 247 248 249 250 /** 251 * Handles and retransmits upload progress event. 252 * 253 * @method _uploadProgressHandler 254 * @param event The event dispatched during the upload process. 255 * @private 256 */ 257 _uploadProgressHandler : function (event) { 258 259 this.currentUploadedByteValues[event.target.get("id")] = event.bytesLoaded; 260 261 var updatedEvent = event, 262 uploadedTotal = this.totalBytesUploaded, 263 percentLoaded = Math.min(100, Math.round(10000*uploadedTotal/this.totalBytes) / 100); 264 265 updatedEvent.originEvent = event; 266 updatedEvent.file = event.target; 267 268 this.fire("uploadprogress", updatedEvent); 269 270 Y.each(this.currentUploadedByteValues, function (value) { 271 uploadedTotal += value; 272 }); 273 274 this.fire("totaluploadprogress", { 275 bytesLoaded: uploadedTotal, 276 bytesTotal: this.totalBytes, 277 percentLoaded: percentLoaded 278 }); 279 }, 280 281 /** 282 * Starts uploading the queued up file list. 283 * 284 * @method startUpload 285 */ 286 startUpload: function() { 287 this.queuedFiles = this.get("fileList").slice(0); 288 this.numberOfUploads = 0; 289 this.currentUploadedByteValues = {}; 290 this.currentFiles = {}; 291 this.totalBytesUploaded = 0; 292 293 this._currentState = UploaderQueue.UPLOADING; 294 295 while (this.numberOfUploads < this.get("simUploads") && this.queuedFiles.length > 0) { 296 this._startNextFile(); 297 } 298 }, 299 300 /** 301 * Pauses the upload process. The ongoing file uploads 302 * will complete after this method is called, but no 303 * new ones will be launched. 304 * 305 * @method pauseUpload 306 */ 307 pauseUpload: function () { 308 this._currentState = UploaderQueue.STOPPED; 309 }, 310 311 /** 312 * Restarts a paused upload process. 313 * 314 * @method restartUpload 315 */ 316 restartUpload: function () { 317 this._currentState = UploaderQueue.UPLOADING; 318 while (this.numberOfUploads < this.get("simUploads")) { 319 this._startNextFile(); 320 } 321 }, 322 323 /** 324 * If a particular file is stuck in an ongoing upload without 325 * any progress events, this method allows to force its reupload 326 * by cancelling its upload and immediately relaunching it. 327 * 328 * @method forceReupload 329 * @param file {File} The file to force reupload on. 330 */ 331 forceReupload : function (file) { 332 var id = file.get("id"); 333 if (this.currentFiles.hasOwnProperty(id)) { 334 file.cancelUpload(); 335 this._unregisterUpload(file); 336 this.addToQueueTop(file); 337 this._startNextFile(); 338 } 339 }, 340 341 /** 342 * Add a new file to the top of the queue (the upload will be 343 * launched as soon as the current number of uploading files 344 * drops below the maximum permissible value). 345 * 346 * @method addToQueueTop 347 * @param file {File} The file to add to the top of the queue. 348 */ 349 addToQueueTop: function (file) { 350 this.queuedFiles.unshift(file); 351 }, 352 353 /** 354 * Add a new file to the bottom of the queue (the upload will be 355 * launched after all the other queued files are uploaded.) 356 * 357 * @method addToQueueBottom 358 * @param file {File} The file to add to the bottom of the queue. 359 */ 360 addToQueueBottom: function (file) { 361 this.queuedFiles.push(file); 362 }, 363 364 /** 365 * Cancels a specific file's upload. If no argument is passed, 366 * all ongoing uploads are cancelled and the upload process is 367 * stopped. 368 * 369 * @method cancelUpload 370 * @param file {File} An optional parameter - the file whose upload 371 * should be cancelled. 372 */ 373 cancelUpload: function (file) { 374 var id, 375 i, 376 fid; 377 378 if (file) { 379 id = file.get("id"); 380 381 if (this.currentFiles[id]) { 382 this.currentFiles[id].cancelUpload(); 383 this._unregisterUpload(this.currentFiles[id]); 384 if (this._currentState === UploaderQueue.UPLOADING) { 385 this._startNextFile(); 386 } 387 } 388 else { 389 for (i = 0, len = this.queuedFiles.length; i < len; i++) { 390 if (this.queuedFiles[i].get("id") === id) { 391 this.queuedFiles.splice(i, 1); 392 break; 393 } 394 } 395 } 396 } 397 else { 398 for (fid in this.currentFiles) { 399 this.currentFiles[fid].cancelUpload(); 400 this._unregisterUpload(this.currentFiles[fid]); 401 } 402 403 this.currentUploadedByteValues = {}; 404 this.currentFiles = {}; 405 this.totalBytesUploaded = 0; 406 this.fire("alluploadscancelled"); 407 this._currentState = UploaderQueue.STOPPED; 408 } 409 } 410 }, { 411 /** 412 * Static constant for the value of the `errorAction` attribute: 413 * prescribes the queue to continue uploading files in case of 414 * an error. 415 * @property CONTINUE 416 * @readOnly 417 * @type {String} 418 * @static 419 */ 420 CONTINUE: "continue", 421 422 /** 423 * Static constant for the value of the `errorAction` attribute: 424 * prescribes the queue to stop uploading files in case of 425 * an error. 426 * @property STOP 427 * @readOnly 428 * @type {String} 429 * @static 430 */ 431 STOP: "stop", 432 433 /** 434 * Static constant for the value of the `errorAction` attribute: 435 * prescribes the queue to restart a file upload immediately in case of 436 * an error. 437 * @property RESTART_ASAP 438 * @readOnly 439 * @type {String} 440 * @static 441 */ 442 RESTART_ASAP: "restartasap", 443 444 /** 445 * Static constant for the value of the `errorAction` attribute: 446 * prescribes the queue to restart an errored out file upload after 447 * other files have finished uploading. 448 * @property RESTART_AFTER 449 * @readOnly 450 * @type {String} 451 * @static 452 */ 453 RESTART_AFTER: "restartafter", 454 455 /** 456 * Static constant for the value of the `_currentState` property: 457 * implies that the queue is currently not uploading files. 458 * @property STOPPED 459 * @readOnly 460 * @type {String} 461 * @static 462 */ 463 STOPPED: "stopped", 464 465 /** 466 * Static constant for the value of the `_currentState` property: 467 * implies that the queue is currently uploading files. 468 * @property UPLOADING 469 * @readOnly 470 * @type {String} 471 * @static 472 */ 473 UPLOADING: "uploading", 474 475 /** 476 * The identity of the class. 477 * 478 * @property NAME 479 * @type String 480 * @default 'uploaderqueue' 481 * @readOnly 482 * @protected 483 * @static 484 */ 485 NAME: 'uploaderqueue', 486 487 /** 488 * Static property used to define the default attribute configuration of 489 * the class. 490 * 491 * @property ATTRS 492 * @type {Object} 493 * @protected 494 * @static 495 */ 496 ATTRS: { 497 498 /** 499 * Maximum number of simultaneous uploads; must be in the 500 * range between 1 and 5. The value of `2` is default. It 501 * is recommended that this value does not exceed 3. 502 * @attribute simUploads 503 * @type Number 504 * @default 2 505 */ 506 simUploads: { 507 value: 2, 508 validator: function (val) { 509 return (val >= 1 && val <= 5); 510 } 511 }, 512 513 /** 514 * The action to take in case of error. The valid values for this attribute are: 515 * `Y.Uploader.Queue.CONTINUE` (the upload process should continue on other files, 516 * ignoring the error), `Y.Uploader.Queue.STOP` (the upload process 517 * should stop completely), `Y.Uploader.Queue.RESTART_ASAP` (the upload 518 * should restart immediately on the errored out file and continue as planned), or 519 * Y.Uploader.Queue.RESTART_AFTER (the upload of the errored out file should restart 520 * after all other files have uploaded) 521 * @attribute errorAction 522 * @type String 523 * @default Y.Uploader.Queue.CONTINUE 524 */ 525 errorAction: { 526 value: "continue", 527 validator: function (val) { 528 return ( 529 val === UploaderQueue.CONTINUE || 530 val === UploaderQueue.STOP || 531 val === UploaderQueue.RESTART_ASAP || 532 val === UploaderQueue.RESTART_AFTER 533 ); 534 } 535 }, 536 537 /** 538 * The total number of bytes that has been uploaded. 539 * @attribute bytesUploaded 540 * @type Number 541 */ 542 bytesUploaded: { 543 readOnly: true, 544 value: 0 545 }, 546 547 /** 548 * The total number of bytes in the queue. 549 * @attribute bytesTotal 550 * @type Number 551 */ 552 bytesTotal: { 553 readOnly: true, 554 value: 0 555 }, 556 557 /** 558 * The queue file list. This file list should only be modified 559 * before the upload has been started; modifying it after starting 560 * the upload has no effect, and `addToQueueTop` or `addToQueueBottom` methods 561 * should be used instead. 562 * @attribute fileList 563 * @type Array 564 */ 565 fileList: { 566 value: [], 567 lazyAdd: false, 568 setter: function (val) { 569 var newValue = val; 570 Y.Array.each(newValue, function (value) { 571 this.totalBytes += value.get("size"); 572 }, this); 573 574 return val; 575 } 576 }, 577 578 /** 579 * A String specifying what should be the POST field name for the file 580 * content in the upload request. 581 * 582 * @attribute fileFieldName 583 * @type {String} 584 * @default Filedata 585 */ 586 fileFieldName: { 587 value: "Filedata" 588 }, 589 590 /** 591 * The URL to POST the file upload requests to. 592 * 593 * @attribute uploadURL 594 * @type {String} 595 * @default "" 596 */ 597 uploadURL: { 598 value: "" 599 }, 600 601 /** 602 * Additional HTTP headers that should be included 603 * in the upload request. Due to Flash Player security 604 * restrictions, this attribute is only honored in the 605 * HTML5 Uploader. 606 * 607 * @attribute uploadHeaders 608 * @type {Object} 609 * @default {} 610 */ 611 uploadHeaders: { 612 value: {} 613 }, 614 615 /** 616 * A Boolean that specifies whether the file should be 617 * uploaded with the appropriate user credentials for the 618 * domain. Due to Flash Player security restrictions, this 619 * attribute is only honored in the HTML5 Uploader. 620 * 621 * @attribute withCredentials 622 * @type {Boolean} 623 * @default true 624 */ 625 withCredentials: { 626 value: true 627 }, 628 629 630 /** 631 * An object, keyed by `fileId`, containing sets of key-value pairs 632 * that should be passed as POST variables along with each corresponding 633 * file. 634 * 635 * @attribute perFileParameters 636 * @type {Object} 637 * @default {} 638 */ 639 perFileParameters: { 640 value: {} 641 }, 642 643 /** 644 * The number of times to try re-uploading a file that failed to upload before 645 * cancelling its upload. 646 * 647 * @attribute retryCount 648 * @type {Number} 649 * @default 3 650 */ 651 retryCount: { 652 value: 3 653 } 654 655 } 656 }); 657 658 659 Y.namespace('Uploader'); 660 Y.Uploader.Queue = UploaderQueue; 661 662 663 }, '3.17.2', {"requires": ["base"]});
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
Generated: Thu Aug 11 10:00:09 2016 | Cross-referenced by PHPXref 0.7.1 |