@ckeditor/ckeditor5-upload 0.0.0-nightly-20240603.0 → 0.0.0-nightly-20240604.0
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.
- package/README.md +0 -6
- package/dist/index.js +235 -314
- package/dist/index.js.map +1 -1
- package/dist/types/adapters/base64uploadadapter.d.ts +1 -1
- package/dist/types/filereader.d.ts +1 -1
- package/dist/types/filerepository.d.ts +1 -1
- package/package.json +3 -3
- package/src/adapters/base64uploadadapter.d.ts +1 -1
- package/src/adapters/base64uploadadapter.js +1 -1
- package/src/filereader.d.ts +1 -1
- package/src/filereader.js +1 -1
- package/src/filerepository.d.ts +1 -1
- package/src/filerepository.js +3 -6
package/dist/index.js
CHANGED
|
@@ -3,49 +3,27 @@
|
|
|
3
3
|
* For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
|
|
4
4
|
*/
|
|
5
5
|
import { Plugin, PendingActions } from '@ckeditor/ckeditor5-core/dist/index.js';
|
|
6
|
-
import { ObservableMixin,
|
|
6
|
+
import { ObservableMixin, CKEditorError, uid, logWarning, Collection } from '@ckeditor/ckeditor5-utils/dist/index.js';
|
|
7
7
|
|
|
8
|
-
|
|
9
|
-
* Wrapper over the native `FileReader`.
|
|
10
|
-
*/ class FileReader extends /* #__PURE__ */ ObservableMixin() {
|
|
11
|
-
total;
|
|
12
|
-
/**
|
|
13
|
-
* Instance of native FileReader.
|
|
14
|
-
*/ _reader;
|
|
15
|
-
/**
|
|
16
|
-
* Holds the data of an already loaded file. The file must be first loaded
|
|
17
|
-
* by using {@link module:upload/filereader~FileReader#read `read()`}.
|
|
18
|
-
*/ _data;
|
|
19
|
-
/**
|
|
20
|
-
* Creates an instance of the FileReader.
|
|
21
|
-
*/ constructor(){
|
|
22
|
-
super();
|
|
23
|
-
const reader = new window.FileReader();
|
|
24
|
-
this._reader = reader;
|
|
25
|
-
this._data = undefined;
|
|
26
|
-
this.set('loaded', 0);
|
|
27
|
-
reader.onprogress = (evt)=>{
|
|
28
|
-
this.loaded = evt.loaded;
|
|
29
|
-
};
|
|
30
|
-
}
|
|
8
|
+
class FileReader extends ObservableMixin() {
|
|
31
9
|
/**
|
|
32
|
-
|
|
33
|
-
|
|
10
|
+
* Returns error that occurred during file reading.
|
|
11
|
+
*/ get error() {
|
|
34
12
|
return this._reader.error;
|
|
35
13
|
}
|
|
36
14
|
/**
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
15
|
+
* Holds the data of an already loaded file. The file must be first loaded
|
|
16
|
+
* by using {@link module:upload/filereader~FileReader#read `read()`}.
|
|
17
|
+
*/ get data() {
|
|
40
18
|
return this._data;
|
|
41
19
|
}
|
|
42
20
|
/**
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
21
|
+
* Reads the provided file.
|
|
22
|
+
*
|
|
23
|
+
* @param file Native File object.
|
|
24
|
+
* @returns Returns a promise that will be resolved with file's content.
|
|
25
|
+
* The promise will be rejected in case of an error or when the reading process is aborted.
|
|
26
|
+
*/ read(file) {
|
|
49
27
|
const reader = this._reader;
|
|
50
28
|
this.total = file.size;
|
|
51
29
|
return new Promise((resolve, reject)=>{
|
|
@@ -64,49 +42,40 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
64
42
|
});
|
|
65
43
|
}
|
|
66
44
|
/**
|
|
67
|
-
|
|
68
|
-
|
|
45
|
+
* Aborts file reader.
|
|
46
|
+
*/ abort() {
|
|
69
47
|
this._reader.abort();
|
|
70
48
|
}
|
|
49
|
+
/**
|
|
50
|
+
* Creates an instance of the FileReader.
|
|
51
|
+
*/ constructor(){
|
|
52
|
+
super();
|
|
53
|
+
const reader = new window.FileReader();
|
|
54
|
+
this._reader = reader;
|
|
55
|
+
this._data = undefined;
|
|
56
|
+
this.set('loaded', 0);
|
|
57
|
+
reader.onprogress = (evt)=>{
|
|
58
|
+
this.loaded = evt.loaded;
|
|
59
|
+
};
|
|
60
|
+
}
|
|
71
61
|
}
|
|
72
62
|
|
|
73
|
-
|
|
74
|
-
* File repository plugin. A central point for managing file upload.
|
|
75
|
-
*
|
|
76
|
-
* To use it, first you need an upload adapter. Upload adapter's job is to handle communication with the server
|
|
77
|
-
* (sending the file and handling server's response). You can use one of the existing plugins introducing upload adapters
|
|
78
|
-
* (e.g. {@link module:easy-image/cloudservicesuploadadapter~CloudServicesUploadAdapter} or
|
|
79
|
-
* {@link module:adapter-ckfinder/uploadadapter~CKFinderUploadAdapter}) or write your own one – see
|
|
80
|
-
* the {@glink framework/deep-dive/upload-adapter Custom image upload adapter deep-dive} guide.
|
|
81
|
-
*
|
|
82
|
-
* Then, you can use {@link module:upload/filerepository~FileRepository#createLoader `createLoader()`} and the returned
|
|
83
|
-
* {@link module:upload/filerepository~FileLoader} instance to load and upload files.
|
|
84
|
-
*/ class FileRepository extends Plugin {
|
|
85
|
-
/**
|
|
86
|
-
* Collection of loaders associated with this repository.
|
|
87
|
-
*/ loaders = new Collection();
|
|
88
|
-
/**
|
|
89
|
-
* Loaders mappings used to retrieve loaders references.
|
|
90
|
-
*/ _loadersMap = new Map();
|
|
63
|
+
class FileRepository extends Plugin {
|
|
91
64
|
/**
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
*/ _pendingAction = null;
|
|
95
|
-
/**
|
|
96
|
-
* @inheritDoc
|
|
97
|
-
*/ static get pluginName() {
|
|
65
|
+
* @inheritDoc
|
|
66
|
+
*/ static get pluginName() {
|
|
98
67
|
return 'FileRepository';
|
|
99
68
|
}
|
|
100
69
|
/**
|
|
101
|
-
|
|
102
|
-
|
|
70
|
+
* @inheritDoc
|
|
71
|
+
*/ static get requires() {
|
|
103
72
|
return [
|
|
104
73
|
PendingActions
|
|
105
74
|
];
|
|
106
75
|
}
|
|
107
76
|
/**
|
|
108
|
-
|
|
109
|
-
|
|
77
|
+
* @inheritDoc
|
|
78
|
+
*/ init() {
|
|
110
79
|
// Keeps upload in a sync with pending actions.
|
|
111
80
|
this.loaders.on('change', ()=>this._updatePendingAction());
|
|
112
81
|
this.set('uploaded', 0);
|
|
@@ -116,48 +85,45 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
116
85
|
});
|
|
117
86
|
}
|
|
118
87
|
/**
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
88
|
+
* Returns the loader associated with specified file or promise.
|
|
89
|
+
*
|
|
90
|
+
* To get loader by id use `fileRepository.loaders.get( id )`.
|
|
91
|
+
*
|
|
92
|
+
* @param fileOrPromise Native file or promise handle.
|
|
93
|
+
*/ getLoader(fileOrPromise) {
|
|
125
94
|
return this._loadersMap.get(fileOrPromise) || null;
|
|
126
95
|
}
|
|
127
96
|
/**
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
97
|
+
* Creates a loader instance for the given file.
|
|
98
|
+
*
|
|
99
|
+
* Requires {@link #createUploadAdapter} factory to be defined.
|
|
100
|
+
*
|
|
101
|
+
* @param fileOrPromise Native File object or native Promise object which resolves to a File.
|
|
102
|
+
*/ createLoader(fileOrPromise) {
|
|
134
103
|
if (!this.createUploadAdapter) {
|
|
135
104
|
/**
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
*
|
|
159
|
-
* @error filerepository-no-upload-adapter
|
|
160
|
-
*/ logWarning('filerepository-no-upload-adapter');
|
|
105
|
+
* You need to enable an upload adapter in order to be able to upload files.
|
|
106
|
+
*
|
|
107
|
+
* This warning shows up when {@link module:upload/filerepository~FileRepository} is being used
|
|
108
|
+
* without {@link module:upload/filerepository~FileRepository#createUploadAdapter defining an upload adapter}.
|
|
109
|
+
*
|
|
110
|
+
* **If you see this warning when using one of the {@glink installation/getting-started/predefined-builds
|
|
111
|
+
* CKEditor 5 Builds}**
|
|
112
|
+
* it means that you did not configure any of the upload adapters available by default in those builds.
|
|
113
|
+
*
|
|
114
|
+
* See the {@glink features/images/image-upload/image-upload comprehensive "Image upload overview"} to learn which upload
|
|
115
|
+
* adapters are available in the builds and how to configure them.
|
|
116
|
+
*
|
|
117
|
+
* **If you see this warning when using a custom build** there is a chance that you enabled
|
|
118
|
+
* a feature like {@link module:image/imageupload~ImageUpload},
|
|
119
|
+
* or {@link module:image/imageupload/imageuploadui~ImageUploadUI} but you did not enable any upload adapter.
|
|
120
|
+
* You can choose one of the existing upload adapters listed in the
|
|
121
|
+
* {@glink features/images/image-upload/image-upload "Image upload overview"}.
|
|
122
|
+
*
|
|
123
|
+
* You can also implement your {@glink framework/deep-dive/upload-adapter own image upload adapter}.
|
|
124
|
+
*
|
|
125
|
+
* @error filerepository-no-upload-adapter
|
|
126
|
+
*/ logWarning('filerepository-no-upload-adapter');
|
|
161
127
|
return null;
|
|
162
128
|
}
|
|
163
129
|
const loader = new FileLoader(Promise.resolve(fileOrPromise), this.createUploadAdapter);
|
|
@@ -191,10 +157,10 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
191
157
|
return loader;
|
|
192
158
|
}
|
|
193
159
|
/**
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
160
|
+
* Destroys the given loader.
|
|
161
|
+
*
|
|
162
|
+
* @param fileOrPromiseOrLoader File or Promise associated with that loader or loader itself.
|
|
163
|
+
*/ destroyLoader(fileOrPromiseOrLoader) {
|
|
198
164
|
const loader = fileOrPromiseOrLoader instanceof FileLoader ? fileOrPromiseOrLoader : this.getLoader(fileOrPromiseOrLoader);
|
|
199
165
|
loader._destroy();
|
|
200
166
|
this.loaders.remove(loader);
|
|
@@ -205,8 +171,8 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
205
171
|
});
|
|
206
172
|
}
|
|
207
173
|
/**
|
|
208
|
-
|
|
209
|
-
|
|
174
|
+
* Registers or deregisters pending action bound with upload progress.
|
|
175
|
+
*/ _updatePendingAction() {
|
|
210
176
|
const pendingActions = this.editor.plugins.get(PendingActions);
|
|
211
177
|
if (this.loaders.length) {
|
|
212
178
|
if (!this._pendingAction) {
|
|
@@ -220,48 +186,28 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
220
186
|
this._pendingAction = null;
|
|
221
187
|
}
|
|
222
188
|
}
|
|
189
|
+
constructor(){
|
|
190
|
+
super(...arguments);
|
|
191
|
+
/**
|
|
192
|
+
* Collection of loaders associated with this repository.
|
|
193
|
+
*/ this.loaders = new Collection();
|
|
194
|
+
/**
|
|
195
|
+
* Loaders mappings used to retrieve loaders references.
|
|
196
|
+
*/ this._loadersMap = new Map();
|
|
197
|
+
/**
|
|
198
|
+
* Reference to a pending action registered in a {@link module:core/pendingactions~PendingActions} plugin
|
|
199
|
+
* while upload is in progress. When there is no upload then value is `null`.
|
|
200
|
+
*/ this._pendingAction = null;
|
|
201
|
+
}
|
|
223
202
|
}
|
|
224
203
|
/**
|
|
225
204
|
* File loader class.
|
|
226
205
|
*
|
|
227
206
|
* It is used to control the process of reading the file and uploading it using the specified upload adapter.
|
|
228
|
-
*/ class FileLoader extends
|
|
229
|
-
/**
|
|
230
|
-
* Unique id of FileLoader instance.
|
|
231
|
-
*
|
|
232
|
-
* @readonly
|
|
233
|
-
*/ id;
|
|
234
|
-
/**
|
|
235
|
-
* Additional wrapper over the initial file promise passed to this loader.
|
|
236
|
-
*/ _filePromiseWrapper;
|
|
237
|
-
/**
|
|
238
|
-
* Adapter instance associated with this file loader.
|
|
239
|
-
*/ _adapter;
|
|
240
|
-
/**
|
|
241
|
-
* FileReader used by FileLoader.
|
|
242
|
-
*/ _reader;
|
|
243
|
-
/**
|
|
244
|
-
* Creates a new instance of `FileLoader`.
|
|
245
|
-
*
|
|
246
|
-
* @param filePromise A promise which resolves to a file instance.
|
|
247
|
-
* @param uploadAdapterCreator The function which returns {@link module:upload/filerepository~UploadAdapter} instance.
|
|
248
|
-
*/ constructor(filePromise, uploadAdapterCreator){
|
|
249
|
-
super();
|
|
250
|
-
this.id = uid();
|
|
251
|
-
this._filePromiseWrapper = this._createFilePromiseWrapper(filePromise);
|
|
252
|
-
this._adapter = uploadAdapterCreator(this);
|
|
253
|
-
this._reader = new FileReader();
|
|
254
|
-
this.set('status', 'idle');
|
|
255
|
-
this.set('uploaded', 0);
|
|
256
|
-
this.set('uploadTotal', null);
|
|
257
|
-
this.bind('uploadedPercent').to(this, 'uploaded', this, 'uploadTotal', (uploaded, total)=>{
|
|
258
|
-
return total ? uploaded / total * 100 : 0;
|
|
259
|
-
});
|
|
260
|
-
this.set('uploadResponse', null);
|
|
261
|
-
}
|
|
207
|
+
*/ class FileLoader extends ObservableMixin() {
|
|
262
208
|
/**
|
|
263
|
-
|
|
264
|
-
|
|
209
|
+
* A `Promise` which resolves to a `File` instance associated with this file loader.
|
|
210
|
+
*/ get file() {
|
|
265
211
|
if (!this._filePromiseWrapper) {
|
|
266
212
|
// Loader was destroyed, return promise which resolves to null.
|
|
267
213
|
return Promise.resolve(null);
|
|
@@ -278,40 +224,40 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
278
224
|
}
|
|
279
225
|
}
|
|
280
226
|
/**
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
227
|
+
* Returns the file data. To read its data, you need for first load the file
|
|
228
|
+
* by using the {@link module:upload/filerepository~FileLoader#read `read()`} method.
|
|
229
|
+
*/ get data() {
|
|
284
230
|
return this._reader.data;
|
|
285
231
|
}
|
|
286
232
|
/**
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
233
|
+
* Reads file using {@link module:upload/filereader~FileReader}.
|
|
234
|
+
*
|
|
235
|
+
* Throws {@link module:utils/ckeditorerror~CKEditorError CKEditorError} `filerepository-read-wrong-status` when status
|
|
236
|
+
* is different than `idle`.
|
|
237
|
+
*
|
|
238
|
+
* Example usage:
|
|
239
|
+
*
|
|
240
|
+
* ```ts
|
|
241
|
+
* fileLoader.read()
|
|
242
|
+
* .then( data => { ... } )
|
|
243
|
+
* .catch( err => {
|
|
244
|
+
* if ( err === 'aborted' ) {
|
|
245
|
+
* console.log( 'Reading aborted.' );
|
|
246
|
+
* } else {
|
|
247
|
+
* console.log( 'Reading error.', err );
|
|
248
|
+
* }
|
|
249
|
+
* } );
|
|
250
|
+
* ```
|
|
251
|
+
*
|
|
252
|
+
* @returns Returns promise that will be resolved with read data. Promise will be rejected if error
|
|
253
|
+
* occurs or if read process is aborted.
|
|
254
|
+
*/ read() {
|
|
309
255
|
if (this.status != 'idle') {
|
|
310
256
|
/**
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
257
|
+
* You cannot call read if the status is different than idle.
|
|
258
|
+
*
|
|
259
|
+
* @error filerepository-read-wrong-status
|
|
260
|
+
*/ throw new CKEditorError('filerepository-read-wrong-status', this);
|
|
315
261
|
}
|
|
316
262
|
this.status = 'reading';
|
|
317
263
|
return this.file.then((file)=>this._reader.read(file)).then((data)=>{
|
|
@@ -332,33 +278,33 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
332
278
|
});
|
|
333
279
|
}
|
|
334
280
|
/**
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
281
|
+
* Reads file using the provided {@link module:upload/filerepository~UploadAdapter}.
|
|
282
|
+
*
|
|
283
|
+
* Throws {@link module:utils/ckeditorerror~CKEditorError CKEditorError} `filerepository-upload-wrong-status` when status
|
|
284
|
+
* is different than `idle`.
|
|
285
|
+
* Example usage:
|
|
286
|
+
*
|
|
287
|
+
* ```ts
|
|
288
|
+
* fileLoader.upload()
|
|
289
|
+
* .then( data => { ... } )
|
|
290
|
+
* .catch( e => {
|
|
291
|
+
* if ( e === 'aborted' ) {
|
|
292
|
+
* console.log( 'Uploading aborted.' );
|
|
293
|
+
* } else {
|
|
294
|
+
* console.log( 'Uploading error.', e );
|
|
295
|
+
* }
|
|
296
|
+
* } );
|
|
297
|
+
* ```
|
|
298
|
+
*
|
|
299
|
+
* @returns Returns promise that will be resolved with response data. Promise will be rejected if error
|
|
300
|
+
* occurs or if read process is aborted.
|
|
301
|
+
*/ upload() {
|
|
356
302
|
if (this.status != 'idle') {
|
|
357
303
|
/**
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
304
|
+
* You cannot call upload if the status is different than idle.
|
|
305
|
+
*
|
|
306
|
+
* @error filerepository-upload-wrong-status
|
|
307
|
+
*/ throw new CKEditorError('filerepository-upload-wrong-status', this);
|
|
362
308
|
}
|
|
363
309
|
this.status = 'uploading';
|
|
364
310
|
return this.file.then(()=>this._adapter.upload()).then((data)=>{
|
|
@@ -374,8 +320,8 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
374
320
|
});
|
|
375
321
|
}
|
|
376
322
|
/**
|
|
377
|
-
|
|
378
|
-
|
|
323
|
+
* Aborts loading process.
|
|
324
|
+
*/ abort() {
|
|
379
325
|
const status = this.status;
|
|
380
326
|
this.status = 'aborted';
|
|
381
327
|
if (!this._filePromiseWrapper.isFulfilled) {
|
|
@@ -392,21 +338,21 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
392
338
|
this._destroy();
|
|
393
339
|
}
|
|
394
340
|
/**
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
341
|
+
* Performs cleanup.
|
|
342
|
+
*
|
|
343
|
+
* @internal
|
|
344
|
+
*/ _destroy() {
|
|
399
345
|
this._filePromiseWrapper = undefined;
|
|
400
346
|
this._reader = undefined;
|
|
401
347
|
this._adapter = undefined;
|
|
402
348
|
this.uploadResponse = undefined;
|
|
403
349
|
}
|
|
404
350
|
/**
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
351
|
+
* Wraps a given file promise into another promise giving additional
|
|
352
|
+
* control (resolving, rejecting, checking if fulfilled) over it.
|
|
353
|
+
*
|
|
354
|
+
* @param filePromise The initial file promise to be wrapped.
|
|
355
|
+
*/ _createFilePromiseWrapper(filePromise) {
|
|
410
356
|
const wrapper = {};
|
|
411
357
|
wrapper.promise = new Promise((resolve, reject)=>{
|
|
412
358
|
wrapper.rejecter = reject;
|
|
@@ -421,33 +367,43 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
421
367
|
});
|
|
422
368
|
return wrapper;
|
|
423
369
|
}
|
|
370
|
+
/**
|
|
371
|
+
* Creates a new instance of `FileLoader`.
|
|
372
|
+
*
|
|
373
|
+
* @param filePromise A promise which resolves to a file instance.
|
|
374
|
+
* @param uploadAdapterCreator The function which returns {@link module:upload/filerepository~UploadAdapter} instance.
|
|
375
|
+
*/ constructor(filePromise, uploadAdapterCreator){
|
|
376
|
+
super();
|
|
377
|
+
this.id = uid();
|
|
378
|
+
this._filePromiseWrapper = this._createFilePromiseWrapper(filePromise);
|
|
379
|
+
this._adapter = uploadAdapterCreator(this);
|
|
380
|
+
this._reader = new FileReader();
|
|
381
|
+
this.set('status', 'idle');
|
|
382
|
+
this.set('uploaded', 0);
|
|
383
|
+
this.set('uploadTotal', null);
|
|
384
|
+
this.bind('uploadedPercent').to(this, 'uploaded', this, 'uploadTotal', (uploaded, total)=>{
|
|
385
|
+
return total ? uploaded / total * 100 : 0;
|
|
386
|
+
});
|
|
387
|
+
this.set('uploadResponse', null);
|
|
388
|
+
}
|
|
424
389
|
}
|
|
425
390
|
|
|
426
|
-
|
|
427
|
-
* A plugin that converts images inserted into the editor into [Base64 strings](https://en.wikipedia.org/wiki/Base64)
|
|
428
|
-
* in the {@glink getting-started/setup/getting-and-setting-data editor output}.
|
|
429
|
-
*
|
|
430
|
-
* This kind of image upload does not require server processing – images are stored with the rest of the text and
|
|
431
|
-
* displayed by the web browser without additional requests.
|
|
432
|
-
*
|
|
433
|
-
* Check out the {@glink features/images/image-upload/image-upload comprehensive "Image upload overview"} to learn about
|
|
434
|
-
* other ways to upload images into CKEditor 5.
|
|
435
|
-
*/ class Base64UploadAdapter extends Plugin {
|
|
391
|
+
class Base64UploadAdapter extends Plugin {
|
|
436
392
|
/**
|
|
437
|
-
|
|
438
|
-
|
|
393
|
+
* @inheritDoc
|
|
394
|
+
*/ static get requires() {
|
|
439
395
|
return [
|
|
440
396
|
FileRepository
|
|
441
397
|
];
|
|
442
398
|
}
|
|
443
399
|
/**
|
|
444
|
-
|
|
445
|
-
|
|
400
|
+
* @inheritDoc
|
|
401
|
+
*/ static get pluginName() {
|
|
446
402
|
return 'Base64UploadAdapter';
|
|
447
403
|
}
|
|
448
404
|
/**
|
|
449
|
-
|
|
450
|
-
|
|
405
|
+
* @inheritDoc
|
|
406
|
+
*/ init() {
|
|
451
407
|
this.editor.plugins.get(FileRepository).createUploadAdapter = (loader)=>new Adapter$1(loader);
|
|
452
408
|
}
|
|
453
409
|
}
|
|
@@ -455,19 +411,10 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
455
411
|
* The upload adapter that converts images inserted into the editor into Base64 strings.
|
|
456
412
|
*/ let Adapter$1 = class Adapter {
|
|
457
413
|
/**
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
* Creates a new adapter instance.
|
|
463
|
-
*/ constructor(loader){
|
|
464
|
-
this.loader = loader;
|
|
465
|
-
}
|
|
466
|
-
/**
|
|
467
|
-
* Starts the upload process.
|
|
468
|
-
*
|
|
469
|
-
* @see module:upload/filerepository~UploadAdapter#upload
|
|
470
|
-
*/ upload() {
|
|
414
|
+
* Starts the upload process.
|
|
415
|
+
*
|
|
416
|
+
* @see module:upload/filerepository~UploadAdapter#upload
|
|
417
|
+
*/ upload() {
|
|
471
418
|
return new Promise((resolve, reject)=>{
|
|
472
419
|
const reader = this.reader = new window.FileReader();
|
|
473
420
|
reader.addEventListener('load', ()=>{
|
|
@@ -487,66 +434,47 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
487
434
|
});
|
|
488
435
|
}
|
|
489
436
|
/**
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
437
|
+
* Aborts the upload process.
|
|
438
|
+
*
|
|
439
|
+
* @see module:upload/filerepository~UploadAdapter#abort
|
|
440
|
+
*/ abort() {
|
|
494
441
|
this.reader.abort();
|
|
495
442
|
}
|
|
443
|
+
/**
|
|
444
|
+
* Creates a new adapter instance.
|
|
445
|
+
*/ constructor(loader){
|
|
446
|
+
this.loader = loader;
|
|
447
|
+
}
|
|
496
448
|
};
|
|
497
449
|
|
|
498
|
-
|
|
499
|
-
* The Simple upload adapter allows uploading images to an application running on your server using
|
|
500
|
-
* the [`XMLHttpRequest`](https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest) API with a
|
|
501
|
-
* minimal {@link module:upload/uploadconfig~SimpleUploadConfig editor configuration}.
|
|
502
|
-
*
|
|
503
|
-
* ```ts
|
|
504
|
-
* ClassicEditor
|
|
505
|
-
* .create( document.querySelector( '#editor' ), {
|
|
506
|
-
* simpleUpload: {
|
|
507
|
-
* uploadUrl: 'http://example.com',
|
|
508
|
-
* headers: {
|
|
509
|
-
* ...
|
|
510
|
-
* }
|
|
511
|
-
* }
|
|
512
|
-
* } )
|
|
513
|
-
* .then( ... )
|
|
514
|
-
* .catch( ... );
|
|
515
|
-
* ```
|
|
516
|
-
*
|
|
517
|
-
* See the {@glink features/images/image-upload/simple-upload-adapter "Simple upload adapter"} guide to learn how to
|
|
518
|
-
* learn more about the feature (configuration, server–side requirements, etc.).
|
|
519
|
-
*
|
|
520
|
-
* Check out the {@glink features/images/image-upload/image-upload comprehensive "Image upload overview"} to learn about
|
|
521
|
-
* other ways to upload images into CKEditor 5.
|
|
522
|
-
*/ class SimpleUploadAdapter extends Plugin {
|
|
450
|
+
class SimpleUploadAdapter extends Plugin {
|
|
523
451
|
/**
|
|
524
|
-
|
|
525
|
-
|
|
452
|
+
* @inheritDoc
|
|
453
|
+
*/ static get requires() {
|
|
526
454
|
return [
|
|
527
455
|
FileRepository
|
|
528
456
|
];
|
|
529
457
|
}
|
|
530
458
|
/**
|
|
531
|
-
|
|
532
|
-
|
|
459
|
+
* @inheritDoc
|
|
460
|
+
*/ static get pluginName() {
|
|
533
461
|
return 'SimpleUploadAdapter';
|
|
534
462
|
}
|
|
535
463
|
/**
|
|
536
|
-
|
|
537
|
-
|
|
464
|
+
* @inheritDoc
|
|
465
|
+
*/ init() {
|
|
538
466
|
const options = this.editor.config.get('simpleUpload');
|
|
539
467
|
if (!options) {
|
|
540
468
|
return;
|
|
541
469
|
}
|
|
542
470
|
if (!options.uploadUrl) {
|
|
543
471
|
/**
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
|
|
472
|
+
* The {@link module:upload/uploadconfig~SimpleUploadConfig#uploadUrl `config.simpleUpload.uploadUrl`}
|
|
473
|
+
* configuration required by the {@link module:upload/adapters/simpleuploadadapter~SimpleUploadAdapter `SimpleUploadAdapter`}
|
|
474
|
+
* is missing. Make sure the correct URL is specified for the image upload to work properly.
|
|
475
|
+
*
|
|
476
|
+
* @error simple-upload-adapter-missing-uploadurl
|
|
477
|
+
*/ logWarning('simple-upload-adapter-missing-uploadurl');
|
|
550
478
|
return;
|
|
551
479
|
}
|
|
552
480
|
this.editor.plugins.get(FileRepository).createUploadAdapter = (loader)=>{
|
|
@@ -558,23 +486,10 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
558
486
|
* Upload adapter.
|
|
559
487
|
*/ class Adapter {
|
|
560
488
|
/**
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
*/ options;
|
|
566
|
-
xhr;
|
|
567
|
-
/**
|
|
568
|
-
* Creates a new adapter instance.
|
|
569
|
-
*/ constructor(loader, options){
|
|
570
|
-
this.loader = loader;
|
|
571
|
-
this.options = options;
|
|
572
|
-
}
|
|
573
|
-
/**
|
|
574
|
-
* Starts the upload process.
|
|
575
|
-
*
|
|
576
|
-
* @see module:upload/filerepository~UploadAdapter#upload
|
|
577
|
-
*/ upload() {
|
|
489
|
+
* Starts the upload process.
|
|
490
|
+
*
|
|
491
|
+
* @see module:upload/filerepository~UploadAdapter#upload
|
|
492
|
+
*/ upload() {
|
|
578
493
|
return this.loader.file.then((file)=>new Promise((resolve, reject)=>{
|
|
579
494
|
this._initRequest();
|
|
580
495
|
this._initListeners(resolve, reject, file);
|
|
@@ -582,30 +497,30 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
582
497
|
}));
|
|
583
498
|
}
|
|
584
499
|
/**
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
500
|
+
* Aborts the upload process.
|
|
501
|
+
*
|
|
502
|
+
* @see module:upload/filerepository~UploadAdapter#abort
|
|
503
|
+
*/ abort() {
|
|
589
504
|
if (this.xhr) {
|
|
590
505
|
this.xhr.abort();
|
|
591
506
|
}
|
|
592
507
|
}
|
|
593
508
|
/**
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
509
|
+
* Initializes the `XMLHttpRequest` object using the URL specified as
|
|
510
|
+
* {@link module:upload/uploadconfig~SimpleUploadConfig#uploadUrl `simpleUpload.uploadUrl`} in the editor's
|
|
511
|
+
* configuration.
|
|
512
|
+
*/ _initRequest() {
|
|
598
513
|
const xhr = this.xhr = new XMLHttpRequest();
|
|
599
514
|
xhr.open('POST', this.options.uploadUrl, true);
|
|
600
515
|
xhr.responseType = 'json';
|
|
601
516
|
}
|
|
602
517
|
/**
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
518
|
+
* Initializes XMLHttpRequest listeners
|
|
519
|
+
*
|
|
520
|
+
* @param resolve Callback function to be called when the request is successful.
|
|
521
|
+
* @param reject Callback function to be called when the request cannot be completed.
|
|
522
|
+
* @param file Native File object.
|
|
523
|
+
*/ _initListeners(resolve, reject, file) {
|
|
609
524
|
const xhr = this.xhr;
|
|
610
525
|
const loader = this.loader;
|
|
611
526
|
const genericErrorText = `Couldn't upload file: ${file.name}.`;
|
|
@@ -637,10 +552,10 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
637
552
|
}
|
|
638
553
|
}
|
|
639
554
|
/**
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
555
|
+
* Prepares the data and sends the request.
|
|
556
|
+
*
|
|
557
|
+
* @param file File instance to be uploaded.
|
|
558
|
+
*/ _sendRequest(file) {
|
|
644
559
|
// Set headers if specified.
|
|
645
560
|
const headers = this.options.headers || {};
|
|
646
561
|
// Use the withCredentials flag if specified.
|
|
@@ -655,6 +570,12 @@ import { ObservableMixin, Collection, logWarning, uid, CKEditorError } from '@ck
|
|
|
655
570
|
// Send the request.
|
|
656
571
|
this.xhr.send(data);
|
|
657
572
|
}
|
|
573
|
+
/**
|
|
574
|
+
* Creates a new adapter instance.
|
|
575
|
+
*/ constructor(loader, options){
|
|
576
|
+
this.loader = loader;
|
|
577
|
+
this.options = options;
|
|
578
|
+
}
|
|
658
579
|
}
|
|
659
580
|
|
|
660
581
|
export { Base64UploadAdapter, FileRepository, SimpleUploadAdapter };
|