From 10376da701491d6234da33da72b5360c7f935ad3 Mon Sep 17 00:00:00 2001 From: Antoine Jeanselme <67123340+ajeanselme@users.noreply.github.com> Date: Sat, 18 Apr 2026 08:55:33 +0200 Subject: [PATCH] Add ssh key generation button on sftp repository creation page --- .../repository-forms/sftp-repository-form.tsx | 34 +++++++++++++++++++ 1 file changed, 34 insertions(+) diff --git a/app/client/modules/repositories/components/repository-forms/sftp-repository-form.tsx b/app/client/modules/repositories/components/repository-forms/sftp-repository-form.tsx index e5825d00..20301600 100644 --- a/app/client/modules/repositories/components/repository-forms/sftp-repository-form.tsx +++ b/app/client/modules/repositories/components/repository-forms/sftp-repository-form.tsx @@ -1,4 +1,5 @@ import { useWatch, type UseFormReturn } from "react-hook-form"; +import { useState } from "react"; import { FormControl, FormDescription, @@ -11,6 +12,8 @@ import { Input } from "../../../../components/ui/input"; import { Textarea } from "../../../../components/ui/textarea"; import { Switch } from "../../../../components/ui/switch"; import type { RepositoryFormValues } from "../create-repository-form"; +import { Button } from "~/client/components/ui/button"; +import { generatePrivateKeyPem } from "~/utils/ssh"; type Props = { form: UseFormReturn; @@ -18,6 +21,26 @@ type Props = { export const SftpRepositoryForm = ({ form }: Props) => { const skipHostKeyCheck = useWatch({ control: form.control, name: "skipHostKeyCheck" }); + const [isGeneratingKey, setIsGeneratingKey] = useState(false); + const [keyGenerationError, setKeyGenerationError] = useState(null); + + const handleGenerateKey = async () => { + setIsGeneratingKey(true); + setKeyGenerationError(null); + + try { + const privateKey = await generatePrivateKeyPem(); + form.setValue("privateKey", privateKey, { + shouldDirty: true, + shouldTouch: true, + shouldValidate: true, + }); + } catch { + setKeyGenerationError("Could not generate SSH key in this browser."); + } finally { + setIsGeneratingKey(false); + } + }; return ( <> @@ -96,6 +119,17 @@ export const SftpRepositoryForm = ({ form }: Props) => { Paste the contents of your SSH private key. + + The key is generated privately in your browser. Don't forget to save it! + {keyGenerationError && {keyGenerationError}} )} />