TutorLoom
The learning platform for companies, colleges and training institutes. Free and open source, with an Enterprise edition.
翻译准备中
尚未检测到更新。GitHub 发布版本后会显示在这里。
个人 GitHub 账号下公开仓库的所有者可以登录并验证所有权,自行管理介绍,无需管理员批准。
登录并生成验证文件,在 30 分钟内将其提交到此仓库的默认分支。其他分支或分叉仓库中的文件无效。然后在下方检查文件,即可无需管理员批准直接管理项目。请保留文件以维持管理权限。
如需登录,将前往登录页面。登录后请回到此处,再次点击所选的验证按钮。
在项目文件夹中运行 /nomorevibe verify,即可验证所有权并自行管理介绍。
一分钟完成验证制作者的介绍仅有上面的一句话。 更多详情请阅读仓库 README。 仓库 README ↗
正在加载完整 README。
查看完整 README ↗The "coming soon" waitlist page for Polyngual, the consumer language brand built on Voxeo's technology. It is a standalone Next.js app, kept separate from the Voxeo repo and Vercel project (see the brief).
| Route | What it is |
|---|---|
/ | Redirects to /es |
/es | Landing page in Spanish (default, x-default in hreflang) |
/en | Landing page in English. Copy lives in src/content/en.ts, same shape as es.ts; a new language is a new dictionary plus an entry in src/content/index.ts |
/toefl-practice, /toeic-practice, /ielts-practice, /cambridge-practice and /es/preparacion-{toefl,toeic,ielts,cambridge} | Standalone exam landing pages (not in the navigation; linked from footers and the sitemap, with hreflang between each pair). Registry in src/lib/exams.ts, copy in src/content/exams/ |
/privacidad, /en/privacy | Privacy policy (Spanish path fixed by the brief; /es/privacy redirects to it) |
/baja | Unsubscribe and delete my data (linked from every email; ?l=en shows it in English) |
/api/diagnostico?key=WAITLIST_SECRET | Private setup check: which settings are present, Resend domain status, GoHighLevel access; &to= sends a test email |
POST /api/waitlist | Signup: validates the email, requires consent, saves to Resend, copies to GoHighLevel, sends the confirmation email in the page's language |
POST /api/baja | Signed unsubscribe link and mail clients' one-click unsubscribe (RFC 8058) |
/examen, /examen/*, /api/examen/*, /examen-static/* | The TOEFL / TOEIC exam-prep product and its beta (/examen/beta). Not in this repo: forwarded to the exam app (repo exitohire-ai) by rewrites in next.config.ts; EXAM_APP_ORIGIN sets where (default https://exitohire-ai.vercel.app) |
npm install
cp .env.example .env.local # optional: without RESEND_API_KEY signups are only logged
npm run dev # http://localhost:3000/es
npm test && npm run typecheck && npm run build
Resend stores the waitlist (as contacts in one segment) and sends the confirmation email.
polyngual.app and add the DNS records it shows (SPF, DKIM and the MX record for bounces) where the domain is managed. Wait for "Verified".Polyngual waitlist. Put its ID in RESEND_SEGMENT_ID.signup_order (number), and country, signup_date, utm_source, utm_medium, utm_campaign, utm_content, utm_term, referrer, landing (all string).polyngual-waitlist with full access (it must manage contacts, not only send), and put it in RESEND_API_KEY.WAITLIST_FROM_EMAIL to [email protected] (an address on the verified domain), WAITLIST_REPLY_TO to the inbox you read ([email protected]), and WAITLIST_SECRET to a long random string (openssl rand -base64 32).How signups behave:
x-vercel-ip-country header. Source comes from first-touch UTM parameters, the referrer and the landing URL.Each new signup is also copied into the Polyngual sub-account of GoHighLevel, so the list can be filtered and used in workflows there. Resend still sends the confirmation email.
GHL_TOKEN.GHL_LOCATION_ID.signup_order (number) to see each person's place in line.What lands in GoHighLevel: email, country, source ("Polyngual waitlist (instagram)") and tags: polyngual-waitlist on everyone, polyngual-fundador for the first 200, and fuente:… / campana:… from the UTM parameters. Tags need no setup and can trigger workflows. If GoHighLevel is down or misconfigured, the signup still succeeds (it's already in Resend) and the error is logged in Vercel. The unsubscribe link deletes the contact from GoHighLevel too.
src/content/exams/ rendered by src/components/exam/ExamPage.tsx. English pages live under src/app/(en) (their own lang="en" layout); Spanish ones are src/app/[locale]/[slug].NEXT_PUBLIC_MOCK_TEST_URL with ?exam=, lang= and UTM parameters (plus variant= from the IELTS and Cambridge pickers). Unset, it goes to the waitlist form in the page's language (/en#lista or /es#lista), which stores the same parameters in the signup's landing URL.mock_test_cta event (exam, lang, placement, variant) to Vercel Analytics.ExamPage.tsx; it renders only outside production. Do not fill it with invented testimonials or figures.Vercel Web Analytics, which sets no cookies, always runs. Turn it on in the Vercel project (Analytics tab).
Google Tag Manager runs Polyngual's container GTM-P2QHWHJ6 (built in; NEXT_PUBLIC_GTM_ID overrides it, off disables it). Google Analytics 4 is configured as a tag inside that container, so NEXT_PUBLIC_GA4_ID stays empty unless you want gtag.js directly. They set cookies, so they load only after the visitor accepts the cookie notice (src/components/GoogleTags.tsx); a small "Cookies" button reopens it. The <noscript> iframe from GTM's install snippet is left out on purpose: it would set cookies for visitors who never saw the notice. The waitlist_signup and mock_test_cta events go to Vercel always and to the GTM/GA4 dataLayer after consent (src/lib/analytics.ts), ready to mark as conversions.
Page views work on every plan. The waitlist_signup custom event needs a Vercel Pro plan; the source of every signup is stored in Resend either way.
Nothing public should link Polyngual to Voxeo or to its founder: no founder name in emails or on the site, no "powered by Voxeo", and the sender is the Polyngual team. Keep it that way in new copy.
src/app/globals.css: Midnight and Paper carry the page; Lagoon, Cobalt and Marigold are accents.next/font, with Latin and Latin Extended subsets.prefers-reduced-motion, and the hero demo pauses when it is off screen or the tab is hidden.public/og.png is the share image (1200×630). src/app/icon.png and apple-icon.png are made from the logo icon.Import this repo as a new Vercel project (framework preset Next.js, root directory left as is), add the environment variables above, and point polyngual.app at it.