Compare commits

...

1 Commits

Author SHA1 Message Date
Dhruwang
9c63f663b5 basic setup 2025-03-03 15:13:48 +05:30
8 changed files with 67 additions and 7 deletions

View File

@@ -0,0 +1,40 @@
"use server";
import { CRON_SECRET } from "@formbricks/lib/constants";
import { getTelemetryId } from "@formbricks/lib/telemetry";
// Send admin account information to n8n webhook
export const notifyAdminCreation = async (email: string): Promise<void> => {
try {
if (process.env.NODE_ENV !== "production") {
return;
}
// Get the instance ID (using telemetry ID function which hashes CRON_SECRET)
const instanceId = getTelemetryId();
// Send data to n8n webhook
const response = await fetch(
"https://n8n.formbricks.com/webhook-test/6a107551-e368-425f-81e7-05e680cf21e8",
{
method: "POST",
headers: {
"Content-Type": "application/json",
"x-api-key": CRON_SECRET,
},
body: JSON.stringify({
email,
instanceId,
timestamp: new Date().toISOString(),
}),
}
);
if (!response.ok) {
console.error(`Failed to notify admin creation: ${response.statusText}`);
}
} catch (error) {
// Don't throw errors - just log them to avoid disrupting the signup flow
console.error("Error notifying admin creation:", error);
// We're intentionally not throwing here to prevent signup flow disruption
}
};

View File

@@ -1,6 +1,7 @@
"use server";
import { actionClient } from "@/lib/utils/action-client";
import { notifyAdminCreation } from "@/modules/auth/lib/admin-notification";
import { createUser, updateUser } from "@/modules/auth/lib/user";
import { deleteInvite, getInvite } from "@/modules/auth/signup/lib/invite";
import { createTeamMembership } from "@/modules/auth/signup/lib/team";
@@ -10,6 +11,7 @@ import { sendInviteAcceptedEmail, sendVerificationEmail } from "@/modules/email"
import { z } from "zod";
import { hashPassword } from "@formbricks/lib/auth";
import { IS_TURNSTILE_CONFIGURED, TURNSTILE_SECRET_KEY } from "@formbricks/lib/constants";
import { getIsFreshInstance } from "@formbricks/lib/instance/service";
import { verifyInviteToken } from "@formbricks/lib/jwt";
import { createMembership } from "@formbricks/lib/membership/service";
import { createOrganization, getOrganization } from "@formbricks/lib/organization/service";
@@ -131,6 +133,19 @@ export const createUserAction = actionClient.schema(ZCreateUserAction).action(as
),
},
});
const isFreshInstance = await getIsFreshInstance();
console.log("isFreshInstance", isFreshInstance);
console.log("role", role);
// If this is a fresh setup (role is owner), notify about admin creation
if (role === "owner" && isFreshInstance) {
try {
await notifyAdminCreation(user.email);
} catch (error) {
// Log error but continue with signup
console.error("Failed to notify about admin creation:", error);
}
}
}
}

View File

@@ -6,6 +6,7 @@
"continue_with_google": "Login mit Google",
"continue_with_oidc": "Weiter mit {oidcDisplayName}",
"continue_with_openid": "Login mit OpenID",
"continue_with_saml": "Login mit SAML SSO",
"forgot-password": {
"back_to_login": "Zurück zum Login",
"email-sent": {
@@ -52,6 +53,7 @@
"new_to_formbricks": "Neu bei Formbricks?",
"use_a_backup_code": "Einen Backup-Code verwenden"
},
"saml_connection_error": "Etwas ist schiefgelaufen. Bitte überprüfe die App-Konsole für weitere Details.",
"signup": {
"captcha_failed": "reCAPTCHA fehlgeschlagen",
"have_an_account": "Hast Du ein Konto?",
@@ -1894,7 +1896,6 @@
"s": {
"check_inbox_or_spam": "Bitte überprüfe auch deinen Spam-Ordner, falls Du die E-Mail nicht in deinem Posteingang siehst.",
"completed": "Diese kostenlose und quelloffene Umfrage wurde geschlossen.",
"could_not_create_display": "Konnte Anzeige nicht erstellen",
"create_your_own": "Erstelle deine eigene",
"enter_pin": "Diese Umfrage ist geschützt. Gib unten die PIN ein",
"just_curious": "Einfach neugierig?",

View File

@@ -6,6 +6,7 @@
"continue_with_google": "Continue with Google",
"continue_with_oidc": "Continue with {oidcDisplayName}",
"continue_with_openid": "Continue with OpenID",
"continue_with_saml": "Continue with SAML SSO",
"forgot-password": {
"back_to_login": "Back to login",
"email-sent": {
@@ -52,6 +53,7 @@
"new_to_formbricks": "New to Formbricks?",
"use_a_backup_code": "Use a backup code"
},
"saml_connection_error": "Something went wrong. Please check your app console for more details.",
"signup": {
"captcha_failed": "Captcha failed",
"have_an_account": "Have an account?",
@@ -265,7 +267,7 @@
"off": "Off",
"on": "On",
"only_one_file_allowed": "Only one file is allowed",
"only_owners_managers_and_manage_access_members_can_perform_this_action": "Only owners, managers and manage access members can perform this action.",
"only_owners_managers_and_manage_access_members_can_perform_this_action": "Only owners and managers can perform this action.",
"or": "or",
"organization": "Organization",
"organization_not_found": "Organization not found",
@@ -1894,7 +1896,6 @@
"s": {
"check_inbox_or_spam": "Please also check your spam folder if you don't see the email in your inbox.",
"completed": "This free & open-source survey has been closed.",
"could_not_create_display": "Could not create display",
"create_your_own": "Create your own",
"enter_pin": "This survey is protected. Enter the PIN below",
"just_curious": "Just curious?",

View File

@@ -6,6 +6,7 @@
"continue_with_google": "Continuer avec Google",
"continue_with_oidc": "Continuer avec {oidcDisplayName}",
"continue_with_openid": "Continuer avec OpenID",
"continue_with_saml": "Continuer avec SAML SSO",
"forgot-password": {
"back_to_login": "Retour à la connexion",
"email-sent": {
@@ -52,6 +53,7 @@
"new_to_formbricks": "Nouveau sur Formbricks ?",
"use_a_backup_code": "Utiliser un code de secours"
},
"saml_connection_error": "Quelque chose s'est mal passé. Veuillez vérifier la console de votre application pour plus de détails.",
"signup": {
"captcha_failed": "Captcha échoué",
"have_an_account": "Avez-vous un compte ?",
@@ -1894,7 +1896,6 @@
"s": {
"check_inbox_or_spam": "Veuillez également vérifier votre dossier de spam si vous ne voyez pas l'e-mail dans votre boîte de réception.",
"completed": "Cette enquête gratuite et open-source a été fermée.",
"could_not_create_display": "Impossible de créer l'affichage",
"create_your_own": "Créez le vôtre",
"enter_pin": "Ce sondage est protégé. Entrez le code PIN ci-dessous",
"just_curious": "Juste curieux ?",

View File

@@ -6,6 +6,7 @@
"continue_with_google": "Continuar com o Google",
"continue_with_oidc": "Continuar com {oidcDisplayName}",
"continue_with_openid": "Continuar com OpenID",
"continue_with_saml": "Continuar com SAML SSO",
"forgot-password": {
"back_to_login": "Voltar para o login",
"email-sent": {
@@ -52,6 +53,7 @@
"new_to_formbricks": "Novo no Formbricks?",
"use_a_backup_code": "Usar um código de backup"
},
"saml_connection_error": "Algo deu errado. Por favor, verifica o console do app para mais detalhes.",
"signup": {
"captcha_failed": "reCAPTCHA falhou",
"have_an_account": "Já tem uma conta?",
@@ -1894,7 +1896,6 @@
"s": {
"check_inbox_or_spam": "Por favor, dá uma olhada na sua pasta de spam se você não encontrar o e-mail na sua caixa de entrada.",
"completed": "Essa pesquisa gratuita e de código aberto foi encerrada.",
"could_not_create_display": "Não foi possível criar a tela",
"create_your_own": "Crie o seu próprio",
"enter_pin": "Essa pesquisa está protegida. Insira o PIN abaixo",
"just_curious": "Só curioso?",

View File

@@ -6,6 +6,7 @@
"continue_with_google": "使用 Google 繼續",
"continue_with_oidc": "使用 '{'oidcDisplayName'}' 繼續",
"continue_with_openid": "使用 OpenID 繼續",
"continue_with_saml": "使用 SAML SSO 繼續",
"forgot-password": {
"back_to_login": "返回登入",
"email-sent": {
@@ -52,6 +53,7 @@
"new_to_formbricks": "初次使用 Formbricks",
"use_a_backup_code": "使用備份碼"
},
"saml_connection_error": "發生錯誤。請檢查您的 app 主控台以取得更多詳細資料。",
"signup": {
"captcha_failed": "驗證碼失敗",
"have_an_account": "已有帳戶?",
@@ -1894,7 +1896,6 @@
"s": {
"check_inbox_or_spam": "如果您的收件匣中沒有看到電子郵件,也請檢查您的垃圾郵件資料夾。",
"completed": "此免費且開源的問卷已關閉。",
"could_not_create_display": "無法建立顯示",
"create_your_own": "建立您自己的",
"enter_pin": "此問卷已受保護。請輸入下方 PIN 碼",
"just_curious": "只是好奇?",

View File

@@ -9,7 +9,7 @@ const crypto = require("crypto");
// We are using the hashed CRON_SECRET as the distinct identifier for the instance for telemetry.
// The hash cannot be traced back to the original value or the instance itself.
// This is to ensure that the telemetry data is anonymous but still unique to the instance.
const getTelemetryId = (): string => {
export const getTelemetryId = (): string => {
return crypto.createHash("sha256").update(env.CRON_SECRET).digest("hex");
};