From 9cbbade1aee3a42406141a7fdb9e56edbdb7de62 Mon Sep 17 00:00:00 2001 From: zzwt Date: Fri, 3 Dec 2021 12:56:07 +1100 Subject: feat: change link password --- client/components/LinksTable.tsx | 38 ++++++++++++++++++++++++++++++++++---- server/handlers/links.ts | 6 +++--- server/handlers/validators.ts | 7 +++++++ server/queries/link.ts | 5 +++++ 4 files changed, 49 insertions(+), 7 deletions(-) diff --git a/client/components/LinksTable.tsx b/client/components/LinksTable.tsx index f1b2a26..0759ec0 100644 --- a/client/components/LinksTable.tsx +++ b/client/components/LinksTable.tsx @@ -116,6 +116,7 @@ interface EditForm { address: string; description?: string; expire_in?: string; + password?: string; } const Row: FC = ({ index, link, setDeleteModal }) => { @@ -123,7 +124,7 @@ const Row: FC = ({ index, link, setDeleteModal }) => { const ban = useStoreActions(s => s.links.ban); const edit = useStoreActions(s => s.links.edit); const [banFormState, { checkbox }] = useFormState(); - const [editFormState, { text, label }] = useFormState( + const [editFormState, { text, label, password }] = useFormState( { target: link.target, address: link.address, @@ -132,7 +133,8 @@ const Row: FC = ({ index, link, setDeleteModal }) => { ? ms(differenceInMilliseconds(new Date(link.expire_in), new Date()), { long: true }) - : "" + : "", + password: "" }, { withIds: true } ); @@ -175,6 +177,7 @@ const Row: FC = ({ index, link, setDeleteModal }) => { } catch (err) { setEditMessage(errorMessage(err)); } + editFormState.setField("password", ""); setEditLoading(false); }; @@ -355,7 +358,7 @@ const Row: FC = ({ index, link, setDeleteModal }) => { /> - + = ({ index, link, setDeleteModal }) => { /> + + + Password + + + + + @@ -613,7 +643,7 @@ const LinksTable: FC = () => {

Recent shortened links.

- +
diff --git a/server/handlers/links.ts b/server/handlers/links.ts index a497cdd..857c857 100644 --- a/server/handlers/links.ts +++ b/server/handlers/links.ts @@ -108,8 +108,7 @@ export const create: Handler = async (req: CreateLinkReq, res) => { }; export const edit: Handler = async (req, res) => { - const { address, target, description, expire_in } = req.body; - + const { address, target, description, expire_in, password } = req.body; if (!address && !target) { throw new CustomError("Should at least update one field."); } @@ -152,7 +151,8 @@ export const edit: Handler = async (req, res) => { ...(address && { address }), ...(description && { description }), ...(target && { target }), - ...(expire_in && { expire_in }) + ...(expire_in && { expire_in }), + ...(password && { password }) } ); diff --git a/server/handlers/validators.ts b/server/handlers/validators.ts index 635401b..7b5015c 100644 --- a/server/handlers/validators.ts +++ b/server/handlers/validators.ts @@ -145,6 +145,13 @@ export const editLink = [ .withMessage("URL is not valid.") .custom(value => removeWww(URL.parse(value).host) !== env.DEFAULT_DOMAIN) .withMessage(`${env.DEFAULT_DOMAIN} URLs are not allowed.`), + body("password") + .optional({ nullable: true, checkFalsy: true }) + .custom(checkUser) + .withMessage("Only users can use this field.") + .isString() + .isLength({ min: 3, max: 64 }) + .withMessage("Password length must be between 3 and 64."), body("address") .optional({ checkFalsy: true, nullable: true }) .isString() diff --git a/server/queries/link.ts b/server/queries/link.ts index 38c9a0e..e892df8 100644 --- a/server/queries/link.ts +++ b/server/queries/link.ts @@ -180,6 +180,11 @@ export const batchRemove = async (match: Match) => { }; export const update = async (match: Partial, update: Partial) => { + if (update.password) { + const salt = await bcrypt.genSalt(12); + update.password = await bcrypt.hash(update.password, salt); + } + const links = await knex("links") .where(match) .update({ ...update, updated_at: new Date().toISOString() }, "*"); -- cgit v1.2.3