From 5642c48285c296aa3b77760ed5d1431ccdb0f2f3 Mon Sep 17 00:00:00 2001 From: =?utf8?q?Daniel=20Kuty=C5=82a?= Date: Fri, 26 Mar 2021 13:54:21 +0100 Subject: [PATCH] 17337: Added more tests to cover edge cases MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit Arvados-DCO-1.1-Signed-off-by: Daniel Kutyła --- cypress/integration/collection.spec.js | 1 + src/common/webdav.ts | 6 ++++-- src/common/xml.ts | 12 ++++++++---- .../collection-service-files-response.test.ts | 13 +++++++++++++ .../collection-service-files-response.ts | 8 +++----- 5 files changed, 29 insertions(+), 11 deletions(-) diff --git a/cypress/integration/collection.spec.js b/cypress/integration/collection.spec.js index 3041acf5..7764a8eb 100644 --- a/cypress/integration/collection.spec.js +++ b/cypress/integration/collection.spec.js @@ -206,6 +206,7 @@ describe('Collection panel tests', function () { 'some%22file.pdf', 'some%20file.pdf', "G%C3%BCnter's%20file.pdf", + 'table%&?*2', 'bar' // make sure we can go back to the original name as a last step ]; eachPair(names, (from, to) => { diff --git a/src/common/webdav.ts b/src/common/webdav.ts index 8d071fa6..0b77f8c3 100644 --- a/src/common/webdav.ts +++ b/src/common/webdav.ts @@ -2,7 +2,7 @@ // // SPDX-License-Identifier: AGPL-3.0 -import { customEncodeURI, encodeHash } from "./url"; +import { customEncodeURI } from "./url"; export class WebDAV { @@ -80,7 +80,9 @@ export class WebDAV { : ''}${customEncodeURI(config.url)}`); if (config.headers && config.headers.Destination) { - config.headers.Destination = encodeHash(config.headers.Destination); + const regexp = /(http[s]?:\/\/)?([^\/\s]+\/)(.*)/; + const match = decodeURIComponent(config.headers.Destination).match(regexp) || {}; + config.headers.Destination = `${match[1]}${match[2]}${customEncodeURI(match[3])}`; } const headers = { ...this.defaults.headers, ...config.headers }; diff --git a/src/common/xml.ts b/src/common/xml.ts index 751a327c..e7db3aca 100644 --- a/src/common/xml.ts +++ b/src/common/xml.ts @@ -2,13 +2,17 @@ // // SPDX-License-Identifier: AGPL-3.0 -export const getTagValue = (document: Document | Element, tagName: string, defaultValue: string) => { +import { customDecodeURI } from "./url"; + +export const getTagValue = (document: Document | Element, tagName: string, defaultValue: string, skipDecoding: boolean = false) => { const [el] = Array.from(document.getElementsByTagName(tagName)); const URI = el ? htmlDecode(el.innerHTML) : defaultValue; - try { - return decodeURI(URI); - } catch(e) {} + if (!skipDecoding) { + try { + return customDecodeURI(URI); + } catch(e) {} + } return URI; }; diff --git a/src/services/collection-service/collection-service-files-response.test.ts b/src/services/collection-service/collection-service-files-response.test.ts index ad75f572..17a1f388 100644 --- a/src/services/collection-service/collection-service-files-response.test.ts +++ b/src/services/collection-service/collection-service-files-response.test.ts @@ -20,6 +20,19 @@ describe('collection-service-files-response', () => { // then expect(result).toEqual([{ id: "zzzzz-xxxxx-vvvvvvvvvvvvvvv/2", name: "2", path: "", size: 1582976, type: "file", url: "/c=zzzzz-xxxxx-vvvvvvvvvvvvvvv/2" }, { id: "zzzzz-xxxxx-vvvvvvvvvvvvvvv/table 1 2 3", name: "table 1 2 3", path: "", size: 133352, type: "file", url: "/c=zzzzz-xxxxx-vvvvvvvvvvvvvvv/table 1 2 3" }]); }); + + it('should extract ecoded data and do not encode already encoded props', () => { + // given + const xmlString = '/c=zzzzz-xxxxx-vvvvvvvvvvvvvvv/Fri, 26 Mar 2021 11:45:50 GMTHTTP/1.1 200 OK/c=zzzzz-xxxxx-vvvvvvvvvvvvvvv/table%25&%3F%2A23Fri, 26 Mar 2021 11:45:50 GMT"166fe1e1a403fb683"text/plain; charset=utf-8table%&?*2HTTP/1.1 200 OK'; + const parser = new DOMParser(); + const xmlDoc = parser.parseFromString(xmlString, "text/xml"); + + // when + const result = extractFilesData(xmlDoc); + + // then + expect(result).toEqual([{ id: "zzzzz-xxxxx-vvvvvvvvvvvvvvv/table%&?*2", name: "table%&?*2", path: "", size: 3, type: "file", url: "/c=zzzzz-xxxxx-vvvvvvvvvvvvvvv/table%&?*2" }]); + }); }); describe('getFileFullPath', () => { diff --git a/src/services/collection-service/collection-service-files-response.ts b/src/services/collection-service/collection-service-files-response.ts index 9583b7a4..1be99457 100644 --- a/src/services/collection-service/collection-service-files-response.ts +++ b/src/services/collection-service/collection-service-files-response.ts @@ -5,7 +5,6 @@ import { CollectionDirectory, CollectionFile, CollectionFileType, createCollectionDirectory, createCollectionFile } from "../../models/collection-file"; import { getTagValue } from "~/common/xml"; import { getNodeChildren, Tree, mapTree } from '~/models/tree'; -import { customDecodeURI } from "~/common/url"; export const sortFilesTree = (tree: Tree) => { return mapTree(node => { @@ -26,10 +25,9 @@ export const extractFilesData = (document: Document) => { .from(document.getElementsByTagName('D:response')) .slice(1) // omit first element which is collection itself .map(element => { - const name = getTagValue(element, 'D:displayname', ''); - const size = parseInt(getTagValue(element, 'D:getcontentlength', '0'), 10); - const href = getTagValue(element, 'D:href', ''); - const url = customDecodeURI(href); + const name = getTagValue(element, 'D:displayname', '', true); // skip decoding as value should be already decoded + const size = parseInt(getTagValue(element, 'D:getcontentlength', '0', true), 10); + const url = getTagValue(element, 'D:href', ''); const nameSuffix = name; const collectionUuidMatch = collectionUrlPrefix.exec(url); const collectionUuid = collectionUuidMatch ? collectionUuidMatch.pop() : ''; -- 2.30.2