1 | "use strict";
|
2 | var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
3 | function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
4 | return new (P || (P = Promise))(function (resolve, reject) {
|
5 | function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
6 | function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
7 | function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
8 | step((generator = generator.apply(thisArg, _arguments || [])).next());
|
9 | });
|
10 | };
|
11 | var __importDefault = (this && this.__importDefault) || function (mod) {
|
12 | return (mod && mod.__esModule) ? mod : { "default": mod };
|
13 | };
|
14 | var __importStar = (this && this.__importStar) || function (mod) {
|
15 | if (mod && mod.__esModule) return mod;
|
16 | var result = {};
|
17 | if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k];
|
18 | result["default"] = mod;
|
19 | return result;
|
20 | };
|
21 | Object.defineProperty(exports, "__esModule", { value: true });
|
22 |
|
23 | require("dotenv").config();
|
24 | const debug_1 = __importDefault(require("debug"));
|
25 | const fast_xml_parser_1 = __importDefault(require("fast-xml-parser"));
|
26 | const node_fetch_1 = require("node-fetch");
|
27 | const path_1 = __importStar(require("path"));
|
28 | const environment_1 = __importDefault(require("./environment"));
|
29 | const environmentVcapServices_1 = __importDefault(require("./environmentVcapServices"));
|
30 | const error_1 = __importDefault(require("./error"));
|
31 | exports.ClientError = error_1.default;
|
32 | const fakeServer_1 = __importDefault(require("./fakeServer"));
|
33 | exports.FakeServer = fakeServer_1.default;
|
34 | const file_1 = __importDefault(require("./file"));
|
35 | exports.File = file_1.default;
|
36 | const fileSystemElement_1 = __importDefault(require("./fileSystemElement"));
|
37 | exports.FileSystemElement = fileSystemElement_1.default;
|
38 | const folder_1 = __importDefault(require("./folder"));
|
39 | exports.Folder = folder_1.default;
|
40 | const httpClient_1 = require("./httpClient");
|
41 | const requestResponseLogEntry_1 = __importDefault(require("./requestResponseLogEntry"));
|
42 | exports.RequestResponseLogEntry = requestResponseLogEntry_1.default;
|
43 | const server_1 = __importDefault(require("./server"));
|
44 | exports.Server = server_1.default;
|
45 | const share_1 = __importStar(require("./share"));
|
46 | exports.SharePermission = share_1.SharePermission;
|
47 | const tag_1 = __importDefault(require("./tag"));
|
48 | exports.Tag = tag_1.default;
|
49 | const debug = debug_1.default("NCClient");
|
50 |
|
51 |
|
52 |
|
53 | class Client {
|
54 | |
55 |
|
56 |
|
57 |
|
58 |
|
59 |
|
60 |
|
61 |
|
62 |
|
63 |
|
64 |
|
65 |
|
66 |
|
67 |
|
68 |
|
69 |
|
70 |
|
71 |
|
72 | constructor(server) {
|
73 | this.logRequestResponse = false;
|
74 | debug("constructor");
|
75 | this.nextcloudOrigin = "";
|
76 | this.nextcloudAuthHeader = "";
|
77 | this.nextcloudRequestToken = "";
|
78 | this.webDAVUrl = "";
|
79 |
|
80 |
|
81 | if (!server) {
|
82 | try {
|
83 | const env = new environmentVcapServices_1.default("nextcloud");
|
84 | server = env.getServer();
|
85 | }
|
86 | catch (e) {
|
87 | const env = new environment_1.default();
|
88 | server = env.getServer();
|
89 | }
|
90 | }
|
91 | if (server instanceof server_1.default) {
|
92 | this.proxy = server.proxy;
|
93 | debug("constructor: webdav url %s", server.url);
|
94 | if (server.url.indexOf(Client.webDavUrlPath) === -1) {
|
95 |
|
96 | throw new error_1.default(`The provided nextcloud url "${server.url}" does not comply to the nextcloud url standard, "${Client.webDavUrlPath}" is missing`, "ERR_INVALID_NEXTCLOUD_WEBDAV_URL");
|
97 | }
|
98 | this.nextcloudOrigin = server.url.substr(0, server.url.indexOf(Client.webDavUrlPath));
|
99 | debug("constructor: nextcloud url %s", this.nextcloudOrigin);
|
100 | this.nextcloudAuthHeader = "Basic " + Buffer.from(server.basicAuth.username + ":" + server.basicAuth.password).toString("base64");
|
101 | this.nextcloudRequestToken = "";
|
102 | if (server.url.slice(-1) === "/") {
|
103 | this.webDAVUrl = server.url.slice(0, -1);
|
104 | }
|
105 | else {
|
106 | this.webDAVUrl = server.url;
|
107 | }
|
108 | this.logRequestResponse = server.logRequestResponse;
|
109 | const options = {
|
110 | authorizationHeader: this.nextcloudAuthHeader,
|
111 | logRequestResponse: this.logRequestResponse,
|
112 | origin: this.nextcloudOrigin,
|
113 | proxy: this.proxy,
|
114 | };
|
115 | this.httpClient = new httpClient_1.HttpClient(options);
|
116 | }
|
117 | if (server instanceof fakeServer_1.default) {
|
118 | this.fakeServer = server;
|
119 | this.webDAVUrl = "https://fake.server" + Client.webDavUrlPath;
|
120 | }
|
121 | }
|
122 | |
123 |
|
124 |
|
125 | getQuota() {
|
126 | return __awaiter(this, void 0, void 0, function* () {
|
127 | debug("getQuota");
|
128 | const requestInit = {
|
129 | method: "PROPFIND",
|
130 | };
|
131 | const response = yield this.getHttpResponse(this.webDAVUrl + "/", requestInit, [207], { description: "Client get quota" });
|
132 | const properties = yield this.getPropertiesFromWebDAVMultistatusResponse(response, Client.webDavUrlPath + "/");
|
133 | let quota = null;
|
134 | for (const prop of properties) {
|
135 | if (prop["quota-available-bytes"]) {
|
136 | quota = {
|
137 | available: "unlimited",
|
138 | used: prop["quota-used-bytes"],
|
139 | };
|
140 | if (prop["quota-available-bytes"] > 0) {
|
141 | quota.available = prop["quota-available-bytes"];
|
142 | }
|
143 | }
|
144 | }
|
145 | if (!quota) {
|
146 | debug("Error, quota not available: %s ", JSON.stringify(properties, null, 4));
|
147 | throw new error_1.default(`Error, quota not available`, "ERR_QUOTA_NOT_AVAILABLE");
|
148 | }
|
149 | debug("getQuota = %O", quota);
|
150 | return quota;
|
151 | });
|
152 | }
|
153 |
|
154 |
|
155 |
|
156 | |
157 |
|
158 |
|
159 |
|
160 |
|
161 |
|
162 | createTag(tagName) {
|
163 | return __awaiter(this, void 0, void 0, function* () {
|
164 | debug("createTag");
|
165 | let tag;
|
166 |
|
167 | tag = yield this.getTagByName(tagName);
|
168 | if (tag) {
|
169 | return tag;
|
170 | }
|
171 |
|
172 | const requestInit = {
|
173 | body: `{ "name": "${tagName}", "userVisible": true, "userAssignable": true, "canAssign": true }`,
|
174 | headers: new node_fetch_1.Headers({ "Content-Type": "application/json" }),
|
175 | method: "POST",
|
176 | };
|
177 | const response = yield this.getHttpResponse(this.nextcloudOrigin + "/remote.php/dav/systemtags/", requestInit, [201], { description: "Tag create" });
|
178 | const tagString = response.headers.get("Content-Location");
|
179 | debug("createTag new tagId %s, tagName %s", tagString, tagName);
|
180 | if (tagString === "" || tagString === null) {
|
181 | throw new error_1.default(`Error, tag with name '${tagName}' could not be created`, "ERR_TAG_CREATE_FAILED");
|
182 | }
|
183 |
|
184 | const tagId = this.getTagIdFromHref(tagString);
|
185 | tag = new tag_1.default(this, tagId, tagName, true, true, true);
|
186 | return tag;
|
187 | });
|
188 | }
|
189 | |
190 |
|
191 |
|
192 |
|
193 |
|
194 | getTagByName(tagName) {
|
195 | return __awaiter(this, void 0, void 0, function* () {
|
196 | debug("getTag");
|
197 | const tags = yield this.getTags();
|
198 | for (const tag of tags) {
|
199 | if (tag.name === tagName) {
|
200 | return tag;
|
201 | }
|
202 | }
|
203 | return null;
|
204 | });
|
205 | }
|
206 | |
207 |
|
208 |
|
209 |
|
210 |
|
211 | getTagById(tagId) {
|
212 | return __awaiter(this, void 0, void 0, function* () {
|
213 | debug("getTagById");
|
214 | const tags = yield this.getTags();
|
215 | for (const tag of tags) {
|
216 | if (tag.id === tagId) {
|
217 | return tag;
|
218 | }
|
219 | }
|
220 | return null;
|
221 | });
|
222 | }
|
223 | |
224 |
|
225 |
|
226 |
|
227 |
|
228 | deleteTag(tagId) {
|
229 | return __awaiter(this, void 0, void 0, function* () {
|
230 | debug("deleteTag tagId: $s", tagId);
|
231 | const requestInit = {
|
232 | method: "DELETE",
|
233 | };
|
234 | const response = yield this.getHttpResponse(`${this.nextcloudOrigin}/remote.php/dav/systemtags/${tagId}`, requestInit, [204, 404], { description: "Tag delete" });
|
235 | });
|
236 | }
|
237 | |
238 |
|
239 |
|
240 |
|
241 | deleteAllTags() {
|
242 | return __awaiter(this, void 0, void 0, function* () {
|
243 | debug("deleteAllTags");
|
244 | const tags = yield this.getTags();
|
245 | for (const tag of tags) {
|
246 |
|
247 | yield tag.delete();
|
248 | }
|
249 | });
|
250 | }
|
251 | |
252 |
|
253 |
|
254 |
|
255 | getTags() {
|
256 | return __awaiter(this, void 0, void 0, function* () {
|
257 | debug("getTags PROPFIND %s", this.nextcloudOrigin + "/remote.php/dav/systemtags/");
|
258 | const requestInit = {
|
259 | body: `<?xml version="1.0"?>
|
260 | <d:propfind xmlns:d="DAV:" xmlns:oc="http://owncloud.org/ns">
|
261 | <d:prop>
|
262 | <oc:id />
|
263 | <oc:display-name />
|
264 | <oc:user-visible />
|
265 | <oc:user-assignable />
|
266 | <oc:can-assign />
|
267 | </d:prop>
|
268 | </d:propfind>`,
|
269 | method: "PROPFIND",
|
270 | };
|
271 | const relUrl = `/remote.php/dav/systemtags/`;
|
272 | const response = yield this.getHttpResponse(this.nextcloudOrigin + relUrl, requestInit, [207], { description: "Tags get" });
|
273 | const properties = yield this.getPropertiesFromWebDAVMultistatusResponse(response, relUrl + "/*");
|
274 | const tags = [];
|
275 | for (const prop of properties) {
|
276 | tags.push(new tag_1.default(this, this.getTagIdFromHref(prop._href), prop["display-name"], prop["user-visible"], prop["user-assignable"], prop["can-assign"]));
|
277 | }
|
278 | return tags;
|
279 | });
|
280 | }
|
281 | |
282 |
|
283 |
|
284 |
|
285 | getTagsOfFile(fileId) {
|
286 | return __awaiter(this, void 0, void 0, function* () {
|
287 | debug("getTagsOfFile");
|
288 | const requestInit = {
|
289 | body: `<?xml version="1.0"?>
|
290 | <d:propfind xmlns:d="DAV:" xmlns:oc="http://owncloud.org/ns">
|
291 | <d:prop>
|
292 | <oc:id />
|
293 | <oc:display-name />
|
294 | <oc:user-visible />
|
295 | <oc:user-assignable />
|
296 | <oc:can-assign />
|
297 | </d:prop>
|
298 | </d:propfind>`,
|
299 | method: "PROPFIND",
|
300 | };
|
301 | const relUrl = `/remote.php/dav/systemtags-relations/files/${fileId}`;
|
302 | const response = yield this.getHttpResponse(`${this.nextcloudOrigin}${relUrl}`, requestInit, [207], { description: "File get tags" });
|
303 | const properties = yield this.getPropertiesFromWebDAVMultistatusResponse(response, relUrl + "/*");
|
304 | const tagMap = new Map();
|
305 | for (const prop of properties) {
|
306 | tagMap.set(prop["display-name"], prop.id);
|
307 | }
|
308 | debug("tags of file %O", tagMap);
|
309 | return tagMap;
|
310 | });
|
311 | }
|
312 | |
313 |
|
314 |
|
315 |
|
316 |
|
317 | removeTagOfFile(fileId, tagId) {
|
318 | return __awaiter(this, void 0, void 0, function* () {
|
319 | debug("removeTagOfFile tagId: $s fileId:", tagId, fileId);
|
320 | const requestInit = {
|
321 | method: "DELETE",
|
322 | };
|
323 | const response = yield this.getHttpResponse(`${this.nextcloudOrigin}/remote.php/dav/systemtags-relations/files/${fileId}/${tagId}`, requestInit, [204, 404], { description: "File remove tag" });
|
324 | return;
|
325 | });
|
326 | }
|
327 | |
328 |
|
329 |
|
330 |
|
331 | getFileId(fileUrl) {
|
332 | return __awaiter(this, void 0, void 0, function* () {
|
333 | debug("getFileId");
|
334 | const requestInit = {
|
335 | body: `
|
336 | <d:propfind xmlns:d="DAV:" xmlns:oc="http://owncloud.org/ns" xmlns:nc="http://nextcloud.org/ns">
|
337 | <d:prop>
|
338 | <oc:fileid />
|
339 | </d:prop>
|
340 | </d:propfind>`,
|
341 | method: "PROPFIND",
|
342 | };
|
343 | const response = yield this.getHttpResponse(fileUrl, requestInit, [207], { description: "File get id" });
|
344 | const properties = yield this.getPropertiesFromWebDAVMultistatusResponse(response, "");
|
345 | for (const prop of properties) {
|
346 | if (prop.fileid) {
|
347 | return prop.fileid;
|
348 | }
|
349 | }
|
350 | debug("getFileId no file id found for %s", fileUrl);
|
351 | return -1;
|
352 | });
|
353 | }
|
354 | getFolderContents(folderName) {
|
355 | return __awaiter(this, void 0, void 0, function* () {
|
356 | debug("getFolderContents");
|
357 | const requestInit = {
|
358 | body: `<?xml version="1.0"?>
|
359 | <d:propfind xmlns:d="DAV:" xmlns:oc="http://owncloud.org/ns" xmlns:nc="http://nextcloud.org/ns" xmlns:ocs="http://open-collaboration-services.org/ns">
|
360 | <d:prop>
|
361 | <d:getlastmodified />
|
362 | <d:getetag />
|
363 | <d:getcontenttype />
|
364 | <d:resourcetype />
|
365 | <oc:fileid />
|
366 | <oc:permissions />
|
367 | <oc:size />
|
368 | <d:getcontentlength />
|
369 | <nc:has-preview />
|
370 | <nc:mount-type />
|
371 | <nc:is-encrypted />
|
372 | <ocs:share-permissions />
|
373 | <oc:tags />
|
374 | <oc:favorite />
|
375 | <oc:comments-unread />
|
376 | <oc:owner-id />
|
377 | <oc:owner-display-name />
|
378 | <oc:share-types />
|
379 | </d:prop>
|
380 | </d:propfind>`,
|
381 | method: "PROPFIND",
|
382 | };
|
383 | const url = `${this.webDAVUrl}${folderName}`;
|
384 | const response = yield this.getHttpResponse(url, requestInit, [207], { description: "Folder get contents" });
|
385 | const properties = yield this.getPropertiesFromWebDAVMultistatusResponse(response, "");
|
386 | const folderContents = [];
|
387 |
|
388 | for (const prop of properties) {
|
389 | let fileName = decodeURI(prop._href.substr(prop._href.indexOf(Client.webDavUrlPath) + 18));
|
390 | if (fileName.endsWith("/")) {
|
391 | fileName = fileName.slice(0, -1);
|
392 | }
|
393 | if ((url + "/").endsWith(prop._href)) {
|
394 | continue;
|
395 | }
|
396 | const folderContentsEntry = {};
|
397 | folderContentsEntry.lastmod = prop.getlastmodified;
|
398 | folderContentsEntry.fileid = prop.fileid;
|
399 | folderContentsEntry.basename = fileName.split("/").reverse()[0];
|
400 | folderContentsEntry.filename = fileName;
|
401 | if (prop.getcontenttype) {
|
402 | folderContentsEntry.mime = prop.getcontenttype;
|
403 | folderContentsEntry.size = prop.getcontentlength;
|
404 | folderContentsEntry.type = "file";
|
405 | }
|
406 | else {
|
407 | folderContentsEntry.type = "directory";
|
408 | }
|
409 | folderContents.push(folderContentsEntry);
|
410 | }
|
411 |
|
412 | return folderContents;
|
413 | });
|
414 | }
|
415 | |
416 |
|
417 |
|
418 |
|
419 |
|
420 | createFolder(folderName) {
|
421 | return __awaiter(this, void 0, void 0, function* () {
|
422 | folderName = this.sanitizeFolderName(folderName);
|
423 | debug("createFolder: folderName=%s", folderName);
|
424 | const parts1 = folderName.split("/");
|
425 | for (const p of parts1) {
|
426 | if ((p) === "." || p === "..") {
|
427 | throw new error_1.default(`Error creating folder, folder name "${folderName}" invalid`, "ERR_CREATE_FOLDER_INVALID_FOLDER_NAME");
|
428 | }
|
429 | }
|
430 | let folder;
|
431 | folder = yield this.getFolder(folderName);
|
432 | if (folder) {
|
433 | debug("createFolder: folder already available %O", folder.name);
|
434 | return folder;
|
435 | }
|
436 | else {
|
437 |
|
438 | try {
|
439 | debug("createFolder: folder = %s", folderName);
|
440 | yield this.createFolderInternal(folderName);
|
441 | }
|
442 | catch (e) {
|
443 |
|
444 | const parts = folderName.split("/");
|
445 | parts.shift();
|
446 | let folderPath = "";
|
447 | debug("createFolder: parts = %O", parts);
|
448 | for (const part of parts) {
|
449 | debug("createFolder: part = %O", part);
|
450 | folderPath += "/" + part;
|
451 | folder = yield this.getFolder(folderPath);
|
452 | if (folder === null) {
|
453 | debug("createFolder: folder not available");
|
454 |
|
455 | debug("createFolder: folder = %s", folderPath);
|
456 | yield this.createFolderInternal(folderPath);
|
457 | }
|
458 | else {
|
459 | debug("createFolder: folder already available %s", folderPath);
|
460 | }
|
461 | }
|
462 | }
|
463 | }
|
464 | folder = yield this.getFolder(folderName);
|
465 | if (folder) {
|
466 | debug("createFolder: new folder %O", folder.name);
|
467 | return folder;
|
468 | }
|
469 | else {
|
470 | throw new error_1.default(`Error creating folder, folder name "${folderName}"
|
471 | `, "ERR_CREATE_FOLDER_FAILED");
|
472 | }
|
473 | });
|
474 | }
|
475 | |
476 |
|
477 |
|
478 |
|
479 | deleteFile(fileName) {
|
480 | return __awaiter(this, void 0, void 0, function* () {
|
481 | const url = this.webDAVUrl + fileName;
|
482 | debug("deleteFile %s", url);
|
483 | const requestInit = {
|
484 | method: "DELETE",
|
485 | };
|
486 | try {
|
487 | yield this.getHttpResponse(url, requestInit, [204], { description: "File delete" });
|
488 | }
|
489 | catch (err) {
|
490 | debug("Error in deleteFile %s %s %s", err.message, requestInit.method, url);
|
491 | throw err;
|
492 | }
|
493 | });
|
494 | }
|
495 | |
496 |
|
497 |
|
498 |
|
499 | deleteFolder(folderName) {
|
500 | return __awaiter(this, void 0, void 0, function* () {
|
501 | folderName = this.sanitizeFolderName(folderName);
|
502 | debug("deleteFolder:");
|
503 | const folder = yield this.getFolder(folderName);
|
504 | if (folder) {
|
505 | yield this.deleteFile(folderName);
|
506 | }
|
507 | });
|
508 | }
|
509 | |
510 |
|
511 |
|
512 |
|
513 |
|
514 | getFolder(folderName) {
|
515 | return __awaiter(this, void 0, void 0, function* () {
|
516 | folderName = this.sanitizeFolderName(folderName);
|
517 | debug("getFolder %s", folderName);
|
518 |
|
519 | if (folderName === "/" || folderName === "") {
|
520 | return new folder_1.default(this, "/", "", "");
|
521 | }
|
522 | try {
|
523 | const stat = yield this.stat(folderName);
|
524 | debug(": SUCCESS!!");
|
525 | if (stat.type !== "file") {
|
526 | return new folder_1.default(this, stat.filename.replace(/\\/g, "/"), stat.basename, stat.lastmod, stat.fileid);
|
527 | }
|
528 | else {
|
529 | debug("getFolder: found object is file not a folder");
|
530 | return null;
|
531 | }
|
532 | }
|
533 | catch (e) {
|
534 | debug("getFolder: exception occurred calling stat %O", e.message);
|
535 | return null;
|
536 | }
|
537 | });
|
538 | }
|
539 | |
540 |
|
541 |
|
542 |
|
543 |
|
544 | getSubFolders(folderName) {
|
545 | return __awaiter(this, void 0, void 0, function* () {
|
546 | debug("getSubFolders: folder %s", folderName);
|
547 | const folders = [];
|
548 | folderName = this.sanitizeFolderName(folderName);
|
549 | const folderElements = yield this.Contents(folderName, true);
|
550 | for (const folderElement of folderElements) {
|
551 | debug("getSubFolders: adding subfolders %s", folderElement.filename);
|
552 | folders.push(new folder_1.default(this, folderElement.filename.replace(/\\/g, "/"), folderElement.basename, folderElement.lastmod, folderElement.fileid));
|
553 | }
|
554 | return folders;
|
555 | });
|
556 | }
|
557 | |
558 |
|
559 |
|
560 |
|
561 |
|
562 | getFiles(folderName) {
|
563 | return __awaiter(this, void 0, void 0, function* () {
|
564 | debug("getFiles: folder %s", folderName);
|
565 | const files = [];
|
566 | folderName = this.sanitizeFolderName(folderName);
|
567 | const fileElements = yield this.Contents(folderName, false);
|
568 | for (const folderElement of fileElements) {
|
569 | debug("getFiles: adding file %s", folderElement.filename);
|
570 |
|
571 | files.push(new file_1.default(this, folderElement.filename.replace(/\\/g, "/"), folderElement.basename, folderElement.lastmod, folderElement.size, folderElement.mime, folderElement.fileid));
|
572 | }
|
573 | return files;
|
574 | });
|
575 | }
|
576 | |
577 |
|
578 |
|
579 |
|
580 |
|
581 | createFile(fileName, data) {
|
582 | return __awaiter(this, void 0, void 0, function* () {
|
583 | if (fileName.startsWith("./")) {
|
584 | fileName = fileName.replace("./", "/");
|
585 | }
|
586 | const baseName = path_1.default.basename(fileName);
|
587 | const folderName = path_1.default.dirname(fileName);
|
588 | debug("createFile folder name %s base name %s", folderName, baseName);
|
589 |
|
590 | yield this.createFolder(folderName);
|
591 | yield this.putFileContents(fileName, data);
|
592 | let file;
|
593 | file = yield this.getFile(fileName);
|
594 | if (!file) {
|
595 | throw new error_1.default(`Error creating file, file name "${fileName}"`, "ERR_CREATE_FILE_FAILED");
|
596 | }
|
597 | return file;
|
598 | });
|
599 | }
|
600 | |
601 |
|
602 |
|
603 |
|
604 | getFile(fileName) {
|
605 | return __awaiter(this, void 0, void 0, function* () {
|
606 | debug("getFile fileName = %s", fileName);
|
607 | try {
|
608 | const stat = yield this.stat(fileName);
|
609 | debug(": SUCCESS!!");
|
610 | if (stat.type === "file") {
|
611 | return new file_1.default(this, stat.filename.replace(/\\/g, "/"), stat.basename, stat.lastmod, stat.size, stat.mime || "", stat.fileid || -1);
|
612 | }
|
613 | else {
|
614 | debug("getFile: found object is a folder not a file");
|
615 | return null;
|
616 | }
|
617 | }
|
618 | catch (e) {
|
619 | debug("getFile: exception occurred calling stat %O", e.message);
|
620 | return null;
|
621 | }
|
622 | });
|
623 | }
|
624 | |
625 |
|
626 |
|
627 |
|
628 |
|
629 | moveFile(sourceFileName, targetFileName) {
|
630 | return __awaiter(this, void 0, void 0, function* () {
|
631 | const url = this.webDAVUrl + sourceFileName;
|
632 | const destinationUrl = this.webDAVUrl + targetFileName;
|
633 | debug("moveFile from '%s' to '%s'", url, destinationUrl);
|
634 | const requestInit = {
|
635 | headers: new node_fetch_1.Headers({ Destination: destinationUrl }),
|
636 | method: "MOVE",
|
637 | };
|
638 | try {
|
639 | yield this.getHttpResponse(url, requestInit, [201], { description: "File move" });
|
640 | }
|
641 | catch (err) {
|
642 | debug("Error in move file %s %s source: %s destination: %s", err.message, requestInit.method, url, destinationUrl);
|
643 | throw new error_1.default("Error: moving file failed: source=" + sourceFileName + " target=" + targetFileName + " - " + err.message, "ERR_FILE_MOVE_FAILED");
|
644 | }
|
645 | const targetFile = yield this.getFile(targetFileName);
|
646 | if (!targetFile) {
|
647 | throw new error_1.default("Error: moving file failed: source=" + sourceFileName + " target=" + targetFileName, "ERR_FILE_MOVE_FAILED");
|
648 | }
|
649 | return targetFile;
|
650 | });
|
651 | }
|
652 | |
653 |
|
654 |
|
655 |
|
656 |
|
657 | moveFolder(sourceFolderName, tarName) {
|
658 | return __awaiter(this, void 0, void 0, function* () {
|
659 | const url = this.webDAVUrl + sourceFolderName;
|
660 | const destinationUrl = this.webDAVUrl + tarName;
|
661 | debug("moveFolder from '%s' to '%s'", url, destinationUrl);
|
662 | const requestInit = {
|
663 | headers: new node_fetch_1.Headers({ Destination: destinationUrl }),
|
664 | method: "MOVE",
|
665 | };
|
666 | try {
|
667 | yield this.getHttpResponse(url, requestInit, [201], { description: "Folder move" });
|
668 | }
|
669 | catch (err) {
|
670 | debug("Error in move folder %s %s source: %s destination: %s", err.message, requestInit.method, url, destinationUrl);
|
671 | throw new error_1.default("Error: moving folder failed: source=" + sourceFolderName + " target=" + tarName + " - " + err.message, "ERR_FOLDER_MOVE_FAILED");
|
672 | }
|
673 | const tar = yield this.getFolder(tarName);
|
674 | if (!tar) {
|
675 | throw new error_1.default("Error: moving folder failed: source=" + sourceFolderName + " target=" + tarName, "ERR_FOLDER_MOVE_FAILED");
|
676 | }
|
677 | return tar;
|
678 | });
|
679 | }
|
680 | |
681 |
|
682 |
|
683 |
|
684 |
|
685 | getContent(fileName) {
|
686 | return __awaiter(this, void 0, void 0, function* () {
|
687 | const url = this.webDAVUrl + fileName;
|
688 | debug("getContent GET %s", url);
|
689 | const requestInit = {
|
690 | method: "GET",
|
691 | };
|
692 | let response;
|
693 | try {
|
694 | response = yield this.getHttpResponse(url, requestInit, [200], { description: "File get content" });
|
695 | }
|
696 | catch (err) {
|
697 | debug("Error getContent %s - error %s", url, err.message);
|
698 | throw err;
|
699 | }
|
700 | return Buffer.from(yield response.buffer());
|
701 | });
|
702 | }
|
703 | |
704 |
|
705 |
|
706 |
|
707 |
|
708 | getLink(fileName) {
|
709 | debug("getLink of %s", fileName);
|
710 | return this.webDAVUrl + fileName;
|
711 | }
|
712 | |
713 |
|
714 |
|
715 |
|
716 | getUILink(fileId) {
|
717 | debug("getUILink of %s", fileId);
|
718 | return `${this.nextcloudOrigin}/apps/files/?fileid=${fileId}`;
|
719 | }
|
720 | |
721 |
|
722 |
|
723 |
|
724 |
|
725 |
|
726 |
|
727 |
|
728 |
|
729 | addTagToFile(fileId, tagName) {
|
730 | return __awaiter(this, void 0, void 0, function* () {
|
731 | debug("addTagToFile file:%s tag:%s", fileId, tagName);
|
732 | const tag = yield this.createTag(tagName);
|
733 | if (!tag.canAssign) {
|
734 | throw new error_1.default(`Error: No permission to assign tag "${tagName}" to file. Tag is not assignable`, "ERR_TAG_NOT_ASSIGNABLE");
|
735 | }
|
736 | const addTagBody = {
|
737 | canAssign: tag.canAssign,
|
738 | id: tag.id,
|
739 | name: tag.name,
|
740 | userAssignable: tag.assignable,
|
741 | userVisible: tag.visible,
|
742 | };
|
743 | const requestInit = {
|
744 | body: JSON.stringify(addTagBody, null, 4),
|
745 | headers: new node_fetch_1.Headers({ "Content-Type": "application/json" }),
|
746 | method: "PUT",
|
747 | };
|
748 | yield this.getHttpResponse(`${this.nextcloudOrigin}/remote.php/dav/systemtags-relations/files/${fileId}/${tag.id}`, requestInit, [201, 409], { description: "File add tag" });
|
749 | });
|
750 | }
|
751 |
|
752 |
|
753 |
|
754 | |
755 |
|
756 |
|
757 |
|
758 |
|
759 |
|
760 |
|
761 |
|
762 |
|
763 |
|
764 |
|
765 |
|
766 |
|
767 |
|
768 |
|
769 |
|
770 |
|
771 |
|
772 |
|
773 |
|
774 |
|
775 |
|
776 |
|
777 |
|
778 |
|
779 |
|
780 |
|
781 |
|
782 |
|
783 |
|
784 |
|
785 |
|
786 |
|
787 |
|
788 |
|
789 | |
790 |
|
791 |
|
792 |
|
793 |
|
794 | addCommentToFile(fileId, comment) {
|
795 | return __awaiter(this, void 0, void 0, function* () {
|
796 | debug("addCommentToFile file:%s comment:%s", fileId, comment);
|
797 | const addCommentBody = {
|
798 | actorType: "users",
|
799 | message: comment,
|
800 | objectType: "files",
|
801 | verb: "comment",
|
802 | };
|
803 | const requestInit = {
|
804 | body: JSON.stringify(addCommentBody, null, 4),
|
805 | headers: new node_fetch_1.Headers({ "Content-Type": "application/json" }),
|
806 | method: "POST",
|
807 | };
|
808 | yield this.getHttpResponse(`${this.nextcloudOrigin}/remote.php/dav/comments/files/${fileId}`, requestInit, [201], { description: "File add comment" });
|
809 | });
|
810 | }
|
811 | |
812 |
|
813 |
|
814 |
|
815 |
|
816 |
|
817 |
|
818 |
|
819 | getFileComments(fileId, top, skip) {
|
820 | return __awaiter(this, void 0, void 0, function* () {
|
821 | debug("getFileComments fileId:%s", fileId);
|
822 | if (!top) {
|
823 | top = 30;
|
824 | }
|
825 | if (!skip) {
|
826 | skip = 0;
|
827 | }
|
828 | const requestInit = {
|
829 | body: `<?xml version="1.0" encoding="utf-8" ?>
|
830 | <oc:filter-comments xmlns:D="DAV:" xmlns:oc="http://owncloud.org/ns">
|
831 | <oc:limit>${top}</oc:limit>
|
832 | <oc:offset>${skip}</oc:offset>
|
833 | </oc:filter-comments>`,
|
834 | method: "REPORT",
|
835 | };
|
836 | const response = yield this.getHttpResponse(`${this.nextcloudOrigin}/remote.php/dav/comments/files/${fileId}`, requestInit, [207], { description: "File get comments" });
|
837 | const properties = yield this.getPropertiesFromWebDAVMultistatusResponse(response, "");
|
838 | const comments = [];
|
839 | for (const prop of properties) {
|
840 | comments.push(prop.message);
|
841 | }
|
842 | return comments;
|
843 | });
|
844 | }
|
845 | |
846 |
|
847 |
|
848 | getSystemInfo() {
|
849 | return __awaiter(this, void 0, void 0, function* () {
|
850 | const requestInit = {
|
851 | headers: new node_fetch_1.Headers({ "ocs-apirequest": "true" }),
|
852 | method: "GET",
|
853 | };
|
854 | const response = yield this.getHttpResponse(this.nextcloudOrigin + "/ocs/v2.php/apps/serverinfo/api/v1/info?format=json", requestInit, [200], { description: "SystemInfo get" });
|
855 | const rawResult = yield response.json();
|
856 |
|
857 | let version;
|
858 | if (rawResult.ocs &&
|
859 | rawResult.ocs.data &&
|
860 | rawResult.ocs.data.nextcloud &&
|
861 | rawResult.ocs.data.nextcloud.system &&
|
862 | rawResult.ocs.data.nextcloud.system.version) {
|
863 | version = rawResult.ocs.data.nextcloud.system.version;
|
864 | }
|
865 | else {
|
866 | throw new error_1.default("Fatal Error: nextcloud system version missing", "ERR_SYSTEM_INFO_MISSING_DATA");
|
867 | }
|
868 | const result = {
|
869 | nextcloud: {
|
870 | system: {
|
871 | version,
|
872 | },
|
873 | },
|
874 | nextcloudClient: {
|
875 | version: require("../package.json").version,
|
876 | },
|
877 | };
|
878 | return result;
|
879 | });
|
880 | }
|
881 |
|
882 |
|
883 |
|
884 | |
885 |
|
886 |
|
887 | getUserIDs() {
|
888 | return __awaiter(this, void 0, void 0, function* () {
|
889 | const requestInit = {
|
890 | headers: new node_fetch_1.Headers({ "OCS-APIRequest": "true", "Accept": "application/json" }),
|
891 | method: "GET",
|
892 | };
|
893 | const response = yield this.getHttpResponse(
|
894 |
|
895 | this.nextcloudOrigin + "/ocs/v1.php/cloud/users", requestInit, [200], { description: "Users get" });
|
896 | const rawResult = yield response.json();
|
897 | let users = [];
|
898 | if (rawResult.ocs &&
|
899 | rawResult.ocs.data &&
|
900 | rawResult.ocs.data.users) {
|
901 | users = rawResult.ocs.data.users;
|
902 | }
|
903 | return users;
|
904 | });
|
905 | }
|
906 | createUser(options) {
|
907 | return __awaiter(this, void 0, void 0, function* () {
|
908 | const requestInit = {
|
909 | body: JSON.stringify(options, null, 4),
|
910 | headers: new node_fetch_1.Headers({
|
911 | "Content-Type": "application/x-www-form-urlencoded",
|
912 | "OCS-APIRequest": "true",
|
913 | }),
|
914 | method: "POST",
|
915 | };
|
916 | debug("request body: ", requestInit.body);
|
917 | const response = yield this.getHttpResponse(this.nextcloudOrigin + "/ocs/v1.php/cloud/users", requestInit, [200], { description: "User create" });
|
918 | const rawResult = yield response.json();
|
919 | debug(rawResult);
|
920 | });
|
921 | }
|
922 |
|
923 |
|
924 |
|
925 |
|
926 | |
927 |
|
928 |
|
929 | createShare(options) {
|
930 | return __awaiter(this, void 0, void 0, function* () {
|
931 | const shareRequest = share_1.default.createShareRequestBody(options);
|
932 | debug(shareRequest);
|
933 | const headers = {
|
934 | "Accept": "application/json",
|
935 | "Content-Type": "application/json;charset=UTF-8",
|
936 | "OCS-APIRequest": "true",
|
937 | };
|
938 | const requestInit = {
|
939 | body: shareRequest,
|
940 | headers: new node_fetch_1.Headers(headers),
|
941 | method: "POST",
|
942 | };
|
943 | const url = this.nextcloudOrigin + "/ocs/v2.php/apps/files_sharing/api/v1/shares";
|
944 |
|
945 | const response = yield this.getHttpResponse(url, requestInit, [200], { description: "Share create" });
|
946 | const rawResult = yield response.json();
|
947 | debug(rawResult);
|
948 | return share_1.default.getShare(this, rawResult.ocs.data.id);
|
949 | |
950 |
|
951 |
|
952 |
|
953 |
|
954 |
|
955 |
|
956 | });
|
957 | }
|
958 | |
959 |
|
960 |
|
961 | updateShare(shareId, body) {
|
962 | return __awaiter(this, void 0, void 0, function* () {
|
963 | debug("updateShare body ", body);
|
964 | const headers = {
|
965 | "Accept": "application/json",
|
966 | "Content-Type": "application/json;charset=UTF-8",
|
967 | "OCS-APIRequest": "true",
|
968 | };
|
969 | const requestInit = {
|
970 | body: JSON.stringify(body, null, 4),
|
971 | headers: new node_fetch_1.Headers(headers),
|
972 | method: "PUT",
|
973 | };
|
974 | const url = this.nextcloudOrigin + "/ocs/v2.php/apps/files_sharing/api/v1/shares/" + shareId;
|
975 | yield this.getHttpResponse(url, requestInit, [200], { description: "Share update" });
|
976 | });
|
977 | }
|
978 | |
979 |
|
980 |
|
981 |
|
982 | getShare(shareId) {
|
983 | return __awaiter(this, void 0, void 0, function* () {
|
984 | const headers = {
|
985 | "Accept": "application/json",
|
986 | "OCS-APIRequest": "true",
|
987 | };
|
988 | const requestInit = {
|
989 | headers: new node_fetch_1.Headers(headers),
|
990 | method: "GET",
|
991 | };
|
992 | const url = this.nextcloudOrigin + "/ocs/v2.php/apps/files_sharing/api/v1/shares/" + shareId;
|
993 | const response = yield this.getHttpResponse(url, requestInit, [200], { description: "Share get" });
|
994 | const rawResult = yield response.json();
|
995 | return rawResult;
|
996 | |
997 |
|
998 |
|
999 |
|
1000 |
|
1001 |
|
1002 |
|
1003 |
|
1004 |
|
1005 | });
|
1006 | }
|
1007 | |
1008 |
|
1009 |
|
1010 |
|
1011 | deleteShare(shareId) {
|
1012 | return __awaiter(this, void 0, void 0, function* () {
|
1013 | const headers = {
|
1014 | "Accept": "application/json",
|
1015 | "OCS-APIRequest": "true",
|
1016 | };
|
1017 | const requestInit = {
|
1018 | headers: new node_fetch_1.Headers(headers),
|
1019 | method: "DELETE",
|
1020 | };
|
1021 | const url = this.nextcloudOrigin + "/ocs/v2.php/apps/files_sharing/api/v1/shares/" + shareId;
|
1022 | const response = yield this.getHttpResponse(url, requestInit, [200], { description: "Share delete" });
|
1023 | });
|
1024 | }
|
1025 |
|
1026 |
|
1027 |
|
1028 | |
1029 |
|
1030 |
|
1031 |
|
1032 |
|
1033 |
|
1034 |
|
1035 |
|
1036 |
|
1037 |
|
1038 | getPropertiesFromWebDAVMultistatusResponse(response, href) {
|
1039 | return __awaiter(this, void 0, void 0, function* () {
|
1040 | const responseContentType = response.headers.get("Content-Type");
|
1041 | if (!responseContentType) {
|
1042 | throw new error_1.default("Response content type expected", "ERR_RESPONSE_WITHOUT_CONTENT_TYPE_HEADER");
|
1043 | }
|
1044 | if (responseContentType.indexOf("application/xml") === -1) {
|
1045 | throw new error_1.default("XML response content type expected", "ERR_XML_RESPONSE_CONTENT_TYPE_EXPECTED");
|
1046 | }
|
1047 | const xmlBody = yield response.text();
|
1048 | if (fast_xml_parser_1.default.validate(xmlBody) !== true) {
|
1049 | throw new error_1.default(`The response is not valid XML: ${xmlBody}`, "ERR_RESPONSE_NOT_INVALID_XML");
|
1050 | }
|
1051 | const options = {
|
1052 | ignoreNameSpace: true,
|
1053 | };
|
1054 | const body = fast_xml_parser_1.default.parse(xmlBody, options);
|
1055 |
|
1056 | if (!body.multistatus || !body.multistatus.response) {
|
1057 | throw new error_1.default(`The response is is not a WebDAV multistatus response`, "ERR_RESPONSE_NO_MULTISTATUS_XML");
|
1058 | }
|
1059 |
|
1060 | if (body.multistatus.response.href || body.multistatus.response.propstat) {
|
1061 | body.multistatus.response = new Array(body.multistatus.response);
|
1062 | }
|
1063 | |
1064 |
|
1065 |
|
1066 |
|
1067 |
|
1068 | const responseProperties = [];
|
1069 | for (const res of body.multistatus.response) {
|
1070 | if (!res.href) {
|
1071 | throw new error_1.default(`The mulitstatus response must have a href`, "ERR_RESPONSE_MISSING_HREF_MULTISTATUS");
|
1072 | }
|
1073 | if (!res.propstat) {
|
1074 | throw new error_1.default(`The mulitstatus response must have a "propstat" container`, "ERR_RESPONSE_MISSING_PROPSTAT");
|
1075 | }
|
1076 | let propStats = res.propstat;
|
1077 |
|
1078 | if (res.propstat.status || res.propstat.prop) {
|
1079 | propStats = [res.propstat];
|
1080 | }
|
1081 | for (const propStat of propStats) {
|
1082 | if (!propStat.status) {
|
1083 | throw new error_1.default(`The propstat must have a "status"`, "ERR_RESPONSE_MISSING_PROPSTAT_STATUS");
|
1084 | }
|
1085 | if (propStat.status === "HTTP/1.1 200 OK") {
|
1086 | if (!propStat.prop) {
|
1087 | throw new error_1.default(`The propstat must have a "prop"`, "ERR_RESPONSE_MISSING_PROPSTAT_PROP");
|
1088 | }
|
1089 | const property = propStat.prop;
|
1090 | property._href = res.href;
|
1091 | responseProperties.push(property);
|
1092 | }
|
1093 | }
|
1094 |
|
1095 | }
|
1096 | return responseProperties;
|
1097 | });
|
1098 | }
|
1099 | |
1100 |
|
1101 |
|
1102 |
|
1103 |
|
1104 |
|
1105 | |
1106 |
|
1107 |
|
1108 |
|
1109 |
|
1110 |
|
1111 |
|
1112 |
|
1113 |
|
1114 |
|
1115 |
|
1116 |
|
1117 |
|
1118 |
|
1119 |
|
1120 |
|
1121 |
|
1122 |
|
1123 |
|
1124 |
|
1125 | getHttpResponse(url, requestInit, expectedHttpStatusCode, context) {
|
1126 | return __awaiter(this, void 0, void 0, function* () {
|
1127 | if (!requestInit.headers) {
|
1128 | requestInit.headers = new node_fetch_1.Headers();
|
1129 | }
|
1130 |
|
1131 | if (this.fakeServer) {
|
1132 | return yield this.fakeServer.getFakeHttpResponse(url, requestInit, expectedHttpStatusCode, context);
|
1133 | }
|
1134 | else {
|
1135 | return yield this.httpClient.getHttpResponse(url, requestInit, expectedHttpStatusCode, context);
|
1136 | }
|
1137 | });
|
1138 | }
|
1139 | |
1140 |
|
1141 |
|
1142 |
|
1143 |
|
1144 |
|
1145 | Contents(folderName, folderIndicator) {
|
1146 | return __awaiter(this, void 0, void 0, function* () {
|
1147 | debug("Contents: folder %s", folderName);
|
1148 | const folders = [];
|
1149 | folderName = this.sanitizeFolderName(folderName);
|
1150 | const resultArray = [];
|
1151 | if (folderIndicator === true) {
|
1152 | debug("Contents: get folders");
|
1153 | }
|
1154 | else {
|
1155 | debug("Contents: get files");
|
1156 | }
|
1157 | try {
|
1158 | const folderContentsArray = yield this.getFolderContents(folderName);
|
1159 |
|
1160 |
|
1161 |
|
1162 | yield this.getFolderContents(folderName);
|
1163 | for (const folderElement of folderContentsArray) {
|
1164 | if (folderElement.type === "directory") {
|
1165 |
|
1166 | resultArray.push(folderElement);
|
1167 |
|
1168 | }
|
1169 | else {
|
1170 |
|
1171 | debug("Contents folder element file %O ", folderElement);
|
1172 | resultArray.push(folderElement);
|
1173 |
|
1174 | }
|
1175 | }
|
1176 | }
|
1177 | catch (e) {
|
1178 | debug("Contents: exception occurred %s", e.message);
|
1179 | }
|
1180 | return resultArray;
|
1181 | });
|
1182 | }
|
1183 | sanitizeFolderName(folderName) {
|
1184 | if (folderName[0] !== "/") {
|
1185 | folderName = "/" + folderName;
|
1186 | }
|
1187 |
|
1188 | folderName = folderName.replace(/\/+$/, "");
|
1189 | if (folderName === "") {
|
1190 | folderName = "/";
|
1191 | }
|
1192 | return folderName;
|
1193 | }
|
1194 | getTagIdFromHref(href) {
|
1195 | return parseInt(href.split("/")[href.split("/").length - 1], 10);
|
1196 | }
|
1197 | createFolderInternal(folderName) {
|
1198 | return __awaiter(this, void 0, void 0, function* () {
|
1199 | const url = this.webDAVUrl + folderName;
|
1200 | debug("createFolderInternal %s", url);
|
1201 | const requestInit = {
|
1202 | method: "MKCOL",
|
1203 | };
|
1204 | try {
|
1205 | yield this.getHttpResponse(url, requestInit, [201], { description: "Folder create" });
|
1206 | }
|
1207 | catch (err) {
|
1208 | debug("Error in createFolderInternal %s %s %s %s", err.message, requestInit.method, url);
|
1209 | throw err;
|
1210 | }
|
1211 | });
|
1212 | }
|
1213 | stat(fileName) {
|
1214 | return __awaiter(this, void 0, void 0, function* () {
|
1215 | const url = this.webDAVUrl + fileName;
|
1216 | debug("stat %s", url);
|
1217 | const requestInit = {
|
1218 | body: `<?xml version="1.0"?>
|
1219 | <d:propfind xmlns:d="DAV:" xmlns:oc="http://owncloud.org/ns" xmlns:nc="http://nextcloud.org/ns">
|
1220 | <d:prop>
|
1221 | <d:getlastmodified />
|
1222 | <d:getetag />
|
1223 | <d:getcontenttype />
|
1224 | <d:resourcetype />
|
1225 | <oc:fileid />
|
1226 | <oc:permissions />
|
1227 | <oc:size />
|
1228 | <d:getcontentlength />
|
1229 | <nc:has-preview />
|
1230 | <oc:favorite />
|
1231 | <oc:comments-unread />
|
1232 | <oc:owner-display-name />
|
1233 | <oc:share-types />
|
1234 | </d:prop>
|
1235 | </d:propfind>`,
|
1236 | headers: new node_fetch_1.Headers({ Depth: "0" }),
|
1237 | method: "PROPFIND",
|
1238 | };
|
1239 | let response;
|
1240 | try {
|
1241 | response = yield this.getHttpResponse(url, requestInit, [207], { description: "File/Folder get details" });
|
1242 | }
|
1243 | catch (err) {
|
1244 | debug("Error in stat %s %s %s %s", err.message, requestInit.method, url);
|
1245 | throw err;
|
1246 | }
|
1247 | const properties = yield this.getPropertiesFromWebDAVMultistatusResponse(response, "");
|
1248 | let resultStat = null;
|
1249 | for (const prop of properties) {
|
1250 | resultStat = {
|
1251 | basename: path_1.basename(fileName),
|
1252 | fileid: prop.fileid,
|
1253 | filename: fileName,
|
1254 | lastmod: prop.getlastmodified,
|
1255 | type: "file",
|
1256 | };
|
1257 | if (prop.getcontentlength) {
|
1258 | resultStat.size = prop.getcontentlength;
|
1259 | }
|
1260 | else {
|
1261 | resultStat.type = "directory";
|
1262 | }
|
1263 | if (prop.getcontenttype) {
|
1264 | resultStat.mime = prop.getcontenttype;
|
1265 | }
|
1266 | }
|
1267 | if (!resultStat) {
|
1268 | debug("Error: response %s", JSON.stringify(properties, null, 4));
|
1269 | throw new error_1.default("Error getting status information from : " + url, "ERR_STAT");
|
1270 | }
|
1271 | return resultStat;
|
1272 | });
|
1273 | }
|
1274 | putFileContents(fileName, data) {
|
1275 | return __awaiter(this, void 0, void 0, function* () {
|
1276 | const url = this.webDAVUrl + fileName;
|
1277 | debug("putFileContents %s", url);
|
1278 | const requestInit = {
|
1279 | body: data,
|
1280 | method: "PUT",
|
1281 | };
|
1282 | let response;
|
1283 | response = yield this.getHttpResponse(url, requestInit, [201, 204], { description: "File save content" });
|
1284 | return response;
|
1285 | });
|
1286 | }
|
1287 | }
|
1288 | exports.default = Client;
|
1289 | exports.Client = Client;
|
1290 | Client.webDavUrlPath = "/remote.php/webdav";
|