diff --git a/src/app/api/services/chatizalo/chatizalo-service.ts b/src/app/api/services/chatizalo/chatizalo-service.ts index 54b3c78c..2829203a 100644 --- a/src/app/api/services/chatizalo/chatizalo-service.ts +++ b/src/app/api/services/chatizalo/chatizalo-service.ts @@ -1,18 +1,31 @@ -import { BOT_API_TOKEN } from 'src/config-global' -import { post, endpoints } from 'src/app/api/hooks/api-resolver' - -// ---------------------------------------------------------------------- - -export async function send2FACode(phone: string, code: number, codeMsg: string) { - const botSendMsgEndpoint = endpoints.backend_bot.sendMessage() - const botSendMsgData = { - data_token: BOT_API_TOKEN, - channel_user_id: phone, - message: codeMsg.replace('{2FA_CODE}', code.toString()) - } - console.info('botSendMsgData', botSendMsgData) - const botSendMsgResult = await post(botSendMsgEndpoint, botSendMsgData) - console.info('botSendMsgResult', botSendMsgResult) - - return true -} +import { endpoints, post } from 'src/app/api/hooks/api-resolver' +import { BOT_API_TOKEN } from 'src/config-global' + +// ---------------------------------------------------------------------- + +export async function send2FACode( + phone: string, + code: number, + codeMsg: string, + preferredLanguage: 'es' | 'pt' | 'en' +) { + const botSendMsgEndpoint = endpoints.backend_bot.sendMessage() + const codeAsString = code.toString() + const botSendMsgData = { + data_token: BOT_API_TOKEN, + channel_user_id: phone, + message_kind: 'auth', + template_key: 'login_v1', + template_params: { code: codeAsString }, + template_buttons: { 0: codeAsString }, + force_template: 'true', + preferred_language: preferredLanguage, + message: codeMsg.replace('{2FA_CODE}', codeAsString) + } + const { data_token: _redactedToken, ...botSendMsgDataSafe } = botSendMsgData + console.info('botSendMsgData', botSendMsgDataSafe) + const botSendMsgResult = await post(botSendMsgEndpoint, botSendMsgData) + console.info('botSendMsgResult', botSendMsgResult) + + return true +} diff --git a/src/app/api/v1/auth/code/route.ts b/src/app/api/v1/auth/code/route.ts index d145bd5a..8b81a67b 100644 --- a/src/app/api/v1/auth/code/route.ts +++ b/src/app/api/v1/auth/code/route.ts @@ -26,8 +26,14 @@ export async function POST(req: NextRequest) { const { phone, codeMsg, - recaptchaToken - }: { phone: string; codeMsg: string; recaptchaToken: string } = await req.json() + recaptchaToken, + preferred_language: preferredLanguageInput + }: { + phone: string + codeMsg: string + recaptchaToken: string + preferred_language?: string + } = await req.json() const ip = getIpFromRequest(req) @@ -77,6 +83,8 @@ export async function POST(req: NextRequest) { const code: number = Math.floor(Math.random() * (999999 - 100000 + 1)) + 100000 await updateUserCode(user.id, code) + const preferredLanguage = normalizePreferredLanguage(preferredLanguageInput) + // Send 2FA code to user'whatsapp let botSentCodeResult: boolean = true if (botApiWappEnabled) { @@ -86,10 +94,10 @@ export async function POST(req: NextRequest) { // which may cause it to take about 10 seconds, so this variable is used to improve that logic. // send async console.info('/auth/code, calling send2FACode ASYNC', phone, code) - send2FACode(phone, code, codeMsg) + send2FACode(phone, code, codeMsg, preferredLanguage) } else { console.info('/auth/code, calling send2FACode SYNC', phone, code) - botSentCodeResult = await send2FACode(phone, code, codeMsg) + botSentCodeResult = await send2FACode(phone, code, codeMsg, preferredLanguage) } if (!botSentCodeResult) { @@ -128,3 +136,13 @@ export async function POST(req: NextRequest) { }) } } + +function normalizePreferredLanguage(preferredLanguage?: string): 'es' | 'pt' | 'en' { + const normalized = (preferredLanguage || '').trim().toLowerCase() + + if (normalized.startsWith('es')) return 'es' + if (normalized.startsWith('pt') || normalized.startsWith('br')) return 'pt' + if (normalized.startsWith('en')) return 'en' + + return 'en' +} diff --git a/src/app/api/v1/user/[id]/code/route.ts b/src/app/api/v1/user/[id]/code/route.ts index 708d044f..4d0b409f 100644 --- a/src/app/api/v1/user/[id]/code/route.ts +++ b/src/app/api/v1/user/[id]/code/route.ts @@ -18,8 +18,11 @@ export async function POST(req: NextRequest, { params }: { params: IParams }) { const userValidationResult = await validateUserCommonsInputs(req, params.id) if (userValidationResult instanceof NextResponse) return userValidationResult - const { phone, codeMsg }: { phone: string; codeMsg: string; recaptchaToken: string } = - await req.json() + const { + phone, + codeMsg, + preferred_language: preferredLanguageInput + }: { phone: string; codeMsg: string; preferred_language?: string } = await req.json() if (!phone || !codeMsg) { return new NextResponse( @@ -59,11 +62,13 @@ export async function POST(req: NextRequest, { params }: { params: IParams }) { const code: number = Math.floor(Math.random() * (999999 - 100000 + 1)) + 100000 await updateUserCode(user.id, code) + const preferredLanguage = normalizePreferredLanguage(preferredLanguageInput) + // Send 2FA code to user'whatsapp let botSentCodeResult: boolean = true if (botApiWappEnabled) { console.info('/user/[id]/code, calling send2FACode SYNC', phone, code) - botSentCodeResult = await send2FACode(phone, code, codeMsg) + botSentCodeResult = await send2FACode(phone, code, codeMsg, preferredLanguage) if (!botSentCodeResult) { return new NextResponse( @@ -93,3 +98,13 @@ export async function POST(req: NextRequest, { params }: { params: IParams }) { }) } } + +function normalizePreferredLanguage(preferredLanguage?: string): 'es' | 'pt' | 'en' { + const normalized = (preferredLanguage || '').trim().toLowerCase() + + if (normalized.startsWith('es')) return 'es' + if (normalized.startsWith('pt') || normalized.startsWith('br')) return 'pt' + if (normalized.startsWith('en')) return 'en' + + return 'en' +} diff --git a/src/auth/context/jwt/auth-provider.tsx b/src/auth/context/jwt/auth-provider.tsx index 42d6aff9..7b6ab94d 100644 --- a/src/auth/context/jwt/auth-provider.tsx +++ b/src/auth/context/jwt/auth-provider.tsx @@ -3,6 +3,7 @@ import { useMemo, useEffect, useReducer, useCallback } from 'react' import { post, fetcher, endpoints } from 'src/app/api/hooks/api-resolver' +import { useLocales } from 'src/locales' import { setSession } from 'src/auth/context/jwt/utils' import { AuthContext } from './auth-context' @@ -69,6 +70,7 @@ type Props = { children: React.ReactNode } export function AuthProvider({ children }: Props) { const [state, dispatch] = useReducer(reducer, initialState) + const { currentLang } = useLocales() const initialize = useCallback(async () => { try { @@ -106,10 +108,15 @@ export function AuthProvider({ children }: Props) { const generate2faCodeLogin = useCallback( async (phone: string, codeMsg: string, recaptchaToken: string) => { - await post(endpoints.auth.code(), { phone, codeMsg, recaptchaToken }) + await post(endpoints.auth.code(), { + phone, + codeMsg, + recaptchaToken, + preferred_language: normalizePreferredLanguage(currentLang?.value) + }) dispatch({ type: Types.GENERATE_CODE_LOGIN, payload: { user: null } }) }, - [] + [currentLang?.value] ) const generate2faCodeEmail = useCallback( @@ -194,3 +201,13 @@ export function AuthProvider({ children }: Props) { return {children} } + +function normalizePreferredLanguage(langValue?: string): 'es' | 'pt' | 'en' { + const normalized = (langValue || '').trim().toLowerCase() + + if (normalized.startsWith('es')) return 'es' + if (normalized.startsWith('pt') || normalized.startsWith('br')) return 'pt' + if (normalized.startsWith('en')) return 'en' + + return 'en' +}