Skip to content

Commit

Permalink
Merge branch 'master' into fix-error-response
Browse files Browse the repository at this point in the history
  • Loading branch information
perry-mitchell authored May 17, 2021
2 parents 5daa571 + 0b61a93 commit 0397544
Show file tree
Hide file tree
Showing 34 changed files with 1,179 additions and 3,952 deletions.
2 changes: 1 addition & 1 deletion .prettierrc
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
{
"printWidth": 120,
"printWidth": 100,
"tabWidth": 4
}
4,509 changes: 762 additions & 3,747 deletions package-lock.json

Large diffs are not rendered by default.

17 changes: 8 additions & 9 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,11 @@
"build:node": "tsc",
"build:web": "webpack --mode production --config webpack.config.js && tsc --emitDeclarationOnly --outDir dist/web/",
"clean": "rimraf dist web",
"format": "prettier --write '{source,test}/**/*.js'",
"format": "prettier --write '{source,test}/**/*.{js,ts}'",
"prepare:publish:web": "cp -r ./dist/web ./web && mv ./web/webdav.js ./web/index.js",
"prepublishOnly": "run-s build prepare:publish:web",
"test": "run-s test:node test:web test:format",
"test:format": "prettier-check '{source,test}/**/*.js'",
"test:format": "prettier-check '{source,test}/**/*.{js,ts}'",
"test:node": "npm run build:node && nyc mocha -r test/index.node.js \"test/node/**/*.spec.js\"",
"test:node:watch": "nodemon --exec 'npm run test:node' --ignore 'dist/'",
"test:web": "concurrently --success 'first' --kill-others 'npm run test:web:karma' 'npm run test:web:server'",
Expand All @@ -37,7 +37,7 @@
"sync"
],
"lint-staged": {
"{source,test}/**/*.js": [
"{source,test}/**/*.{js,ts}": [
"prettier --write"
]
},
Expand Down Expand Up @@ -67,10 +67,10 @@
"url-parse": "^1.5.1"
},
"devDependencies": {
"@babel/core": "^7.14.0",
"@babel/preset-env": "^7.14.1",
"@babel/core": "^7.14.2",
"@babel/preset-env": "^7.14.2",
"@babel/preset-typescript": "^7.13.0",
"@types/node": "^15.0.2",
"@types/node": "^15.3.0",
"@types/url-parse": "^1.4.3",
"babel-loader": "^8.2.2",
"babel-plugin-transform-async-to-promises": "^0.8.15",
Expand All @@ -82,7 +82,6 @@
"directory-exists": "^2.0.1",
"exists-file": "^3.0.2",
"husky": "^4.3.8",
"jsdoc-to-markdown": "^7.0.1",
"karma": "^6.3.2",
"karma-chai": "^0.1.0",
"karma-chrome-launcher": "^3.1.0",
Expand All @@ -105,7 +104,7 @@
"typescript": "^4.2.4",
"wait-on": "^5.3.0",
"webdav-server": "^2.6.2",
"webpack": "^4.46.0",
"webpack-cli": "^3.3.12"
"webpack": "^5.37.0",
"webpack-cli": "^4.7.0"
}
}
13 changes: 8 additions & 5 deletions source/auth/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,13 @@ export function setupAuth(
context.headers.Authorization = generateTokenAuthHeader(oauthToken);
break;
default:
throw new Layerr({
info: {
code: ErrorCode.InvalidAuthType
}
}, `Invalid auth type: ${context.authType}`);
throw new Layerr(
{
info: {
code: ErrorCode.InvalidAuthType
}
},
`Invalid auth type: ${context.authType}`
);
}
}
5 changes: 4 additions & 1 deletion source/compat/arrayBuffer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,5 +3,8 @@ const { toString: objToString } = Object.prototype;

// Taken from: https://github.com/fengyuanchen/is-array-buffer/blob/master/src/index.js
export function isArrayBuffer(value: any): boolean {
return hasArrayBuffer && (value instanceof ArrayBuffer || objToString.call(value) === "[object ArrayBuffer]");
return (
hasArrayBuffer &&
(value instanceof ArrayBuffer || objToString.call(value) === "[object ArrayBuffer]")
);
}
7 changes: 6 additions & 1 deletion source/compat/buffer.ts
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
export function isBuffer(value: any): boolean {
return value != null && value.constructor != null && typeof value.constructor.isBuffer === "function" && value.constructor.isBuffer(value);
return (
value != null &&
value.constructor != null &&
typeof value.constructor.isBuffer === "function" &&
value.constructor.isBuffer(value)
);
}
36 changes: 26 additions & 10 deletions source/factory.ts
Original file line number Diff line number Diff line change
Expand Up @@ -65,21 +65,37 @@ export function createClient(remoteURL: string, options: WebDAVClientOptions = {
};
setupAuth(context, username, password, token);
return {
copyFile: (filename: string, destination: string, options?: WebDAVMethodOptions) => copyFile(context, filename, destination, options),
createDirectory: (path: string, options?: WebDAVMethodOptions) => createDirectory(context, path, options),
createReadStream: (filename: string, options?: CreateReadStreamOptions) => createReadStream(context, filename, options),
createWriteStream: (filename: string, options?: CreateWriteStreamOptions, callback?: CreateWriteStreamCallback) => createWriteStream(context, filename, options, callback),
customRequest: (path: string, requestOptions: RequestOptionsCustom) => customRequest(context, path, requestOptions),
deleteFile: (filename: string, options?: WebDAVMethodOptions) => deleteFile(context, filename, options),
copyFile: (filename: string, destination: string, options?: WebDAVMethodOptions) =>
copyFile(context, filename, destination, options),
createDirectory: (path: string, options?: WebDAVMethodOptions) =>
createDirectory(context, path, options),
createReadStream: (filename: string, options?: CreateReadStreamOptions) =>
createReadStream(context, filename, options),
createWriteStream: (
filename: string,
options?: CreateWriteStreamOptions,
callback?: CreateWriteStreamCallback
) => createWriteStream(context, filename, options, callback),
customRequest: (path: string, requestOptions: RequestOptionsCustom) =>
customRequest(context, path, requestOptions),
deleteFile: (filename: string, options?: WebDAVMethodOptions) =>
deleteFile(context, filename, options),
exists: (path: string, options?: WebDAVMethodOptions) => exists(context, path, options),
getDirectoryContents: (path: string, options?: GetDirectoryContentsOptions) => getDirectoryContents(context, path, options),
getFileContents: (filename: string, options?: GetFileContentsOptions) => getFileContents(context, filename, options),
getDirectoryContents: (path: string, options?: GetDirectoryContentsOptions) =>
getDirectoryContents(context, path, options),
getFileContents: (filename: string, options?: GetFileContentsOptions) =>
getFileContents(context, filename, options),
getFileDownloadLink: (filename: string) => getFileDownloadLink(context, filename),
getFileUploadLink: (filename: string) => getFileUploadLink(context, filename),
getHeaders: () => Object.assign({}, context.headers),
getQuota: (options?: GetQuotaOptions) => getQuota(context, options),
moveFile: (filename: string, destinationFilename: string, options?: WebDAVMethodOptions) => moveFile(context, filename, destinationFilename, options),
putFileContents: (filename: string, data: string | BufferLike | Stream.Readable, options?: PutFileContentsOptions) => putFileContents(context, filename, data, options),
moveFile: (filename: string, destinationFilename: string, options?: WebDAVMethodOptions) =>
moveFile(context, filename, destinationFilename, options),
putFileContents: (
filename: string,
data: string | BufferLike | Stream.Readable,
options?: PutFileContentsOptions
) => putFileContents(context, filename, data, options),
setHeaders: (headers: Headers) => {
context.headers = Object.assign({}, headers);
},
Expand Down
18 changes: 11 additions & 7 deletions source/operations/copyFile.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,17 @@ export async function copyFile(
destination: string,
options: WebDAVMethodOptions = {}
): Promise<void> {
const requestOptions = prepareRequestOptions({
url: joinURL(context.remoteURL, encodePath(filename)),
method: "COPY",
headers: {
Destination: joinURL(context.remoteURL, encodePath(destination))
}
}, context, options);
const requestOptions = prepareRequestOptions(
{
url: joinURL(context.remoteURL, encodePath(filename)),
method: "COPY",
headers: {
Destination: joinURL(context.remoteURL, encodePath(destination))
}
},
context,
options
);
const response = await request(requestOptions);
handleResponseCode(context, response);
}
14 changes: 9 additions & 5 deletions source/operations/createDirectory.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,14 @@ export async function createDirectory(
options: CreateDirectoryOptions = {}
): Promise<void> {
if (options.recursive === true) return createDirectoryRecursively(context, dirPath, options);
const requestOptions = prepareRequestOptions({
url: joinURL(context.remoteURL, ensureCollectionPath(encodePath(dirPath))),
method: "MKCOL"
}, context, options);
const requestOptions = prepareRequestOptions(
{
url: joinURL(context.remoteURL, ensureCollectionPath(encodePath(dirPath))),
method: "MKCOL"
},
context,
options
);
const response = await request(requestOptions);
handleResponseCode(context, response);
}
Expand Down Expand Up @@ -57,7 +61,7 @@ async function createDirectoryRecursively(
continue;
}
try {
const testStat = await getStat(context, testPath) as FileStat;
const testStat = (await getStat(context, testPath)) as FileStat;
if (testStat.type !== "directory") {
throw new Error(`Path includes a file: ${dirPath}`);
}
Expand Down
40 changes: 25 additions & 15 deletions source/operations/createStream.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,19 +43,23 @@ export function createWriteStream(
if (options.overwrite === false) {
headers["If-None-Match"] = "*";
}
const requestOptions = prepareRequestOptions({
url: joinURL(context.remoteURL, encodePath(filePath)),
method: "PUT",
headers,
data: writeStream,
maxRedirects: 0
}, context, options);
const requestOptions = prepareRequestOptions(
{
url: joinURL(context.remoteURL, encodePath(filePath)),
method: "PUT",
headers,
data: writeStream,
maxRedirects: 0
},
context,
options
);
request(requestOptions)
.then(response => handleResponseCode(context, response))
.then(response => {
// Fire callback asynchronously to avoid errors
setTimeout(() => {
callback(response)
callback(response);
}, 0);
})
.catch(err => {
Expand All @@ -77,16 +81,22 @@ async function getFileStream(
}
headers.Range = rangeHeader;
}
const requestOptions = prepareRequestOptions({
url: joinURL(context.remoteURL, encodePath(filePath)),
method: "GET",
headers,
responseType: "stream"
}, context, options);
const requestOptions = prepareRequestOptions(
{
url: joinURL(context.remoteURL, encodePath(filePath)),
method: "GET",
headers,
responseType: "stream"
},
context,
options
);
const response = await request(requestOptions);
handleResponseCode(context, response);
if (headers.Range && response.status !== 206) {
const responseError: WebDAVClientError = new Error(`Invalid response code for partial request: ${response.status}`);
const responseError: WebDAVClientError = new Error(
`Invalid response code for partial request: ${response.status}`
);
responseError.status = response.status;
throw responseError;
}
Expand Down
14 changes: 9 additions & 5 deletions source/operations/deleteFile.ts
Original file line number Diff line number Diff line change
@@ -1,18 +1,22 @@
import { joinURL } from "../tools/url";
import { encodePath } from "../tools/path";
import { request, prepareRequestOptions } from "../request";
import { handleResponseCode, } from "../response";
import { handleResponseCode } from "../response";
import { WebDAVClientContext, WebDAVMethodOptions } from "../types";

export async function deleteFile(
context: WebDAVClientContext,
filename: string,
options: WebDAVMethodOptions = {}
): Promise<void> {
const requestOptions = prepareRequestOptions({
url: joinURL(context.remoteURL, encodePath(filename)),
method: "DELETE"
}, context, options);
const requestOptions = prepareRequestOptions(
{
url: joinURL(context.remoteURL, encodePath(filename)),
method: "DELETE"
},
context,
options
);
const response = await request(requestOptions);
handleResponseCode(context, response);
}
33 changes: 23 additions & 10 deletions source/operations/directoryContents.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,15 +17,19 @@ export async function getDirectoryContents(
remotePath: string,
options: GetDirectoryContentsOptions = {}
): Promise<Array<FileStat> | ResponseDataDetailed<Array<FileStat>>> {
const requestOptions = prepareRequestOptions({
url: joinURL(context.remoteURL, encodePath(remotePath), "/"),
method: "PROPFIND",
headers: {
Accept: "text/plain",
Depth: options.deep ? "infinity" : "1"
const requestOptions = prepareRequestOptions(
{
url: joinURL(context.remoteURL, encodePath(remotePath), "/"),
method: "PROPFIND",
headers: {
Accept: "text/plain",
Depth: options.deep ? "infinity" : "1"
},
responseType: "text"
},
responseType: "text"
}, context, options);
context,
options
);
const response = await request(requestOptions);
handleResponseCode(context, response);
const davResp = await parseXML(response.data as string);
Expand All @@ -36,7 +40,12 @@ export async function getDirectoryContents(
return processResponsePayload(response, files, options.details);
}

function getDirectoryFiles(result: DAVResult, serverBasePath: string, requestPath: string, isDetailed: boolean = false): Array<FileStat> {
function getDirectoryFiles(
result: DAVResult,
serverBasePath: string,
requestPath: string,
isDetailed: boolean = false
): Array<FileStat> {
const serverBase = pathPosix.join(serverBasePath, "/");
// Extract the response items (directory contents)
const {
Expand All @@ -60,6 +69,10 @@ function getDirectoryFiles(result: DAVResult, serverBasePath: string, requestPat
return prepareFileFromProps(props, filename, isDetailed);
})
// Filter out the item pointing to the current directory (not needed)
.filter(item => item.basename && (item.type === "file" || item.filename !== requestPath.replace(/\/$/, "")))
.filter(
item =>
item.basename &&
(item.type === "file" || item.filename !== requestPath.replace(/\/$/, ""))
)
);
}
Loading

0 comments on commit 0397544

Please sign in to comment.