UI: Add support for usernames with @ symbol

This commit is contained in:
Max Berger
2026-04-25 21:21:10 +02:00
parent 146d4b4a9a
commit f1af26a798
8 changed files with 67 additions and 36 deletions

View File

@@ -170,7 +170,7 @@ export class Share {
* @param {function(Array<Share>, ?string):void} callback
*/
export function reload_sharing_list(user, password, collection, callback) {
let body = collection ? { PathMapped: collection.href } : {};
let body = collection ? { PathMapped: decodeURIComponent(collection.href) } : {};
return call_sharing_api(
user,
password,
@@ -241,7 +241,7 @@ export function add_share_by_token(
password,
"token/create",
{
PathMapped: share.PathMapped,
PathMapped: decodeURIComponent(share.PathMapped),
Permissions: share.Permissions,
Enabled: share.EnabledByOwner,
Hidden: share.HiddenByOwner,
@@ -280,13 +280,13 @@ export function add_share_by_map(
password,
"map/create",
{
PathMapped: share.PathMapped,
PathMapped: decodeURIComponent(share.PathMapped),
Permissions: share.Permissions,
Enabled: share.EnabledByOwner,
Hidden: share.HiddenByOwner,
Properties: share.Properties,
User: share.User,
PathOrToken: share.PathOrToken,
PathOrToken: decodeURIComponent(share.PathOrToken),
Conversion: share.Conversion,
},
function (response) {
@@ -320,7 +320,7 @@ export function delete_share_by_token(
user,
password,
"token/delete",
{ PathOrToken: share.PathOrToken },
{ PathOrToken: decodeURIComponent(share.PathOrToken) },
function (response) {
let json_response = JSON.parse(response);
if (json_response["Status"] !== "success") {
@@ -352,7 +352,7 @@ export function delete_share_by_map(
user,
password,
"map/delete",
{ PathOrToken: share.PathOrToken },
{ PathOrToken: decodeURIComponent(share.PathOrToken) },
function (response) {
let json_response = JSON.parse(response);
if (json_response["Status"] !== "success") {
@@ -384,7 +384,7 @@ export function update_share_by_token(
password,
"token/update",
{
PathOrToken: share.PathOrToken,
PathOrToken: decodeURIComponent(share.PathOrToken),
Permissions: share.Permissions,
Enabled: share.EnabledByOwner,
Hidden: share.HiddenByOwner,
@@ -423,8 +423,8 @@ export function update_share_by_map(
password,
"map/update",
{
PathOrToken: share.PathOrToken,
PathMapped: share.PathMapped,
PathOrToken: decodeURIComponent(share.PathOrToken),
PathMapped: decodeURIComponent(share.PathMapped),
User: share.User,
Permissions: share.Permissions,
Enabled: share.EnabledByOwner,
@@ -466,7 +466,7 @@ export function update_incoming_share(
password,
share.ShareType + "/update",
{
PathOrToken: share.PathOrToken,
PathOrToken: decodeURIComponent(share.PathOrToken),
Enabled: share.EnabledByUser,
Hidden: share.HiddenByUser,
},

View File

@@ -202,7 +202,7 @@ export class CollectionsScene {
let transformed_from = get_element(node, "[data-name=transformed-from]");
let share = (shares || []).find(
s => (s.ShareType === "map") &&
(s.PathOrToken || "").replace(/\/+$/, "") === (collection.href || "").replace(/\/+$/, ""));
decodeURIComponent(s.PathOrToken || "").replace(/\/+$/, "") === decodeURIComponent(collection.href || "").replace(/\/+$/, ""));
if (share) {
if (share.Owner !== this._user) {
share_info.classList.remove("hidden");

View File

@@ -46,7 +46,7 @@ export class CreateEditShareScene {
this._shareType = shareType;
this._share = share;
this._edit = !!share;
this._pathMapped = collection.href;
this._pathMapped = decodeURIComponent(collection.href);
this._html_scene = get_element_by_id("createeditsharescene");
this._title = get_element(this._html_scene, "[data-name=title]");

View File

@@ -97,10 +97,10 @@ export class IncomingSharingScene {
});
this._nodes = [];
let prefix = "/" + this._user + "/";
let prefix = "/" + decodeURIComponent(this._user) + "/";
let filtered_shares = shares.filter(
share => (share.ShareType === "map")
&& share.PathOrToken.startsWith(prefix));
&& decodeURIComponent(share.PathOrToken).startsWith(prefix));
if (filtered_shares.length === 0) {
this._table.classList.add("hidden");

View File

@@ -226,9 +226,13 @@ function add_share_rows(user, password, collection, shares, errorHandler) {
shares.forEach(function (share) {
let pathortoken = share["PathOrToken"] || "";
let pathmapped = share["PathMapped"] || "";
let decodedHref = decodeURIComponent(collection.href).replace(/\/+$/, "") + "/";
let decodedPathMapped = decodeURIComponent(pathmapped).replace(/\/+$/, "") + "/";
let decodedPathOrToken = decodeURIComponent(pathortoken).replace(/\/+$/, "") + "/";
if (
collection.href.includes(pathmapped) ||
collection.href.includes(pathortoken)
decodedHref.includes(decodedPathMapped) ||
decodedHref.includes(decodedPathOrToken)
) {
if (share["ShareType"] === "token") {
add_share_row_node(user, password, collection, share, token_template, "share", delete_share_by_token, errorHandler);

View File

@@ -58,7 +58,7 @@ export function random_hex(length) {
export function cleanHREFinput(href_form) {
let currentTxtVal = href_form.value.trim().toLowerCase();
//Clean the HREF to remove not permitted chars
currentTxtVal = currentTxtVal.replace(/(?![0-9a-z\-\_\.])./g, '');
currentTxtVal = currentTxtVal.replace(/(?![0-9a-z\-\_\.\@])./g, '');
//Clean the HREF to remove leading . (would result in hidden directory)
currentTxtVal = currentTxtVal.replace(/^\./, '');
href_form.value = currentTxtVal;