Ce sunt aplicațiile?
Aplicațiile vă permit să construiți și să gestionați personalizările Twenty sub formă de cod. În loc să configurați totul prin interfața de utilizator (UI), vă definiți modelul de date și funcțiile de logică în cod — făcând mai rapidă construirea, mentenanța și implementarea în mai multe spații de lucru. Ce puteți face astăzi:- Definiți obiecte și câmpuri personalizate sub formă de cod (model de date gestionat)
- Creați funcții de logică cu declanșatoare personalizate
- Implementați aceeași aplicație în mai multe spații de lucru
Cerințe
- Node.js 24+ și Yarn 4
- Un spațiu de lucru Twenty și o cheie API (creați una la https://app.twenty.com/settings/api-webhooks)
Începeți
Creați o aplicație nouă folosind generatorul oficial, apoi autentificați-vă și începeți să dezvoltați:Structura proiectului (generată)
Când rulaținpx create-twenty-app@latest my-twenty-app, generatorul:
- Copiază o aplicație de bază minimală în
my-twenty-app/ - Adaugă o dependență locală
twenty-sdkși configurația Yarn 4 - Creează fișiere de configurare și scripturi conectate la CLI-ul
twenty - Generează o configurație implicită a aplicației și un rol implicit pentru funcții
- package.json: Declară numele aplicației, versiunea, motoarele (Node 24+, Yarn 4) și adaugă
twenty-sdkplus un scripttwentycare deleagă către CLI-ul localtwenty. Ruleazăyarn twenty helppentru a lista toate comenzile disponibile. - .gitignore: Ignoră artefacte comune precum
node_modules,.yarn,generated/(client tipizat),dist/,build/, foldere de coverage, fișiere jurnal și fișiere.env*. - yarn.lock, .yarnrc.yml, .yarn/: Blochează și configurează lanțul de instrumente Yarn 4 folosit de proiect.
- .nvmrc: Fixează versiunea Node.js așteptată de proiect.
- eslint.config.mjs și tsconfig.json: Oferă linting și configurație TypeScript pentru fișierele TypeScript ale aplicației.
- README.md: Un README scurt în rădăcina aplicației, cu instrucțiuni de bază.
- public/: Un folder pentru stocarea resurselor publice (imagini, fonturi, fișiere statice) care vor fi servite împreună cu aplicația ta. Fișierele plasate aici sunt încărcate în timpul sincronizării și sunt accesibile la rulare.
- src/: Locul principal unde vă definiți aplicația sub formă de cod
Detectarea entităților
SDK-ul detectează entitățile analizând fișierele TypeScript pentru apeluriexport default define<Entity>({...}). Fiecare tip de entitate are o funcție ajutătoare corespunzătoare, exportată din twenty-sdk:
| Funcție ajutătoare | Tipul entității |
|---|---|
defineObject() | Definiții de obiecte personalizate |
defineLogicFunction() | Definiții de funcții de logică |
defineFrontComponent() | Definiții ale componentelor de interfață |
defineRole() | Definiții de rol |
defineField() | Extensii de câmp pentru obiectele existente |
Denumirea fișierelor este flexibilă. Detectarea entităților se bazează pe AST — SDK-ul scanează fișierele sursă pentru tiparul
export default define<Entity>({...}). Puteți organiza fișierele și folderele cum doriți. Gruparea după tipul de entitate (de exemplu, logic-functions/, roles/) este doar o convenție pentru organizarea codului, nu o cerință.yarn twenty app:generateva crea un foldergenerated/(client Twenty tipizat + tipuri pentru spațiul de lucru).yarn twenty entity:addva adăuga fișiere de definire a entităților însrc/pentru obiectele, funcțiile, componentele front-end sau rolurile personalizate.
Autentificare
The first time you runyarn twenty auth:login, you’ll be prompted for:
- URL-ul API (implicit http://localhost:3000 sau profilul spațiului de lucru curent)
- Cheie API
~/.twenty/config.json. Puteți menține mai multe profiluri și comuta între ele.
Gestionarea spațiilor de lucru
yarn twenty auth:switch, all subsequent commands will use that workspace by default. Îl puteți totuși suprascrie temporar cu --workspace <name>.
Utilizați resursele SDK (tipuri și configurare)
Biblioteca twenty-sdk oferă blocuri de bază tipizate și funcții ajutătoare pe care le utilizați în aplicația dvs. Mai jos sunt elementele cheie cu care veți interacționa cel mai des.Funcții ajutătoare
SDK-ul oferă funcții ajutătoare pentru definirea entităților aplicației. După cum este descris în Detectarea entităților, trebuie să folosițiexport default define<Entity>({...}) pentru ca entitățile să fie detectate:
| Funcție | Scop |
|---|---|
defineApplication() | Configurați metadatele aplicației (obligatoriu, una per aplicație) |
defineObject() | Definiți obiecte personalizate cu câmpuri |
defineLogicFunction() | Definiți funcții de logică cu handleri |
defineFrontComponent() | Definiți componente Front pentru interfața de utilizator personalizată |
defineRole() | Configurați permisiunile rolurilor și accesul la obiecte |
defineField() | Extindeți obiectele existente cu câmpuri suplimentare |
Definirea obiectelor
Obiectele personalizate descriu atât schema, cât și comportamentul înregistrărilor din spațiul dvs. de lucru. UtilizațidefineObject() pentru a defini obiecte cu validare încorporată:
- Folosiți
defineObject()pentru validare încorporată și suport mai bun în IDE. universalIdentifiertrebuie să fie unic și stabil între implementări.- Fiecare câmp necesită un
name, untype, unlabelși propriuluniversalIdentifierstabil. - Matricea
fieldseste opțională — puteți defini obiecte fără câmpuri personalizate. - You can scaffold new objects using
yarn twenty entity:add, which guides you through naming, fields, and relationships.
Câmpurile de bază sunt create automat. Când definiți un obiect personalizat, Twenty adaugă automat câmpuri standard precum
name, createdAt, updatedAt, createdBy, position și deletedAt. Nu trebuie să le definiți în tabloul fields — adăugați doar câmpurile personalizate proprii.Configurația aplicației (application-config.ts)
Fiecare aplicație are un singur fișierapplication-config.ts care descrie:
- Cine este aplicația: identificatori, nume de afișare și descriere.
- Cum rulează funcțiile: ce rol folosesc pentru permisiuni.
- (Opțional) variabile: perechi cheie–valoare expuse funcțiilor ca variabile de mediu.
defineApplication() pentru a defini configurația aplicației:
- Câmpurile
universalIdentifiersunt ID-uri deterministe pe care le dețineți; generați-le o singură dată și păstrați-le stabile între sincronizări. applicationVariablesdevin variabile de mediu pentru funcțiile dvs. (de exemplu,DEFAULT_RECIPIENT_NAMEeste disponibil caprocess.env.DEFAULT_RECIPIENT_NAME).defaultRoleUniversalIdentifiertrebuie să corespundă fișierului de rol (vedeți mai jos).
Roluri și permisiuni
Aplicațiile pot defini roluri care încapsulează permisiuni asupra obiectelor și acțiunilor din spațiul dvs. de lucru. CâmpuldefaultRoleUniversalIdentifier din application-config.ts desemnează rolul implicit utilizat de funcțiile de logică ale aplicației.
- Cheia API de runtime injectată ca
TWENTY_API_KEYeste derivată din acest rol implicit pentru funcții. - Clientul tipizat va fi restricționat la permisiunile acordate acelui rol.
- Respectați principiul celui mai mic privilegiu: creați un rol dedicat doar cu permisiunile de care au nevoie funcțiile, apoi referiți identificatorul său universal.
Rol implicit pentru funcții (*.role.ts)
Când generați o aplicație nouă, CLI creează și un fișier de rol implicit. FolosițidefineRole() pentru a defini roluri cu validare încorporată:
universalIdentifier al acestui rol este apoi referențiat în application-config.ts ca defaultRoleUniversalIdentifier. Cu alte cuvinte:
- *.role.ts definește ce poate face rolul implicit pentru funcții.
- application-config.ts indică acel rol, astfel încât funcțiile moștenesc permisiunile lui.
- Porniți de la rolul generat, apoi restrângeți-l progresiv urmând principiul celui mai mic privilegiu.
- Înlocuiți
objectPermissionsșifieldPermissionscu obiectele/câmpurile de care au nevoie funcțiile. permissionFlagscontrolează accesul la capabilități la nivelul platformei. Mențineți-le la minimum; adăugați doar ceea ce aveți nevoie.- Vedeți un exemplu funcțional în aplicația Hello World:
packages/twenty-apps/hello-world/src/roles/function-role.ts.
Configurația funcției de logică și punctul de intrare
Fiecare fișier de funcție foloseștedefineLogicFunction() pentru a exporta o configurație cu un handler și declanșatoare opționale.
- route: Expune funcția pe o rută și metodă HTTP sub endpoint-ul
/s/:
de ex.path: '/post-card/create',-> apel pe<APP_URL>/s/post-card/create
- cron: Rulează funcția pe un program folosind o expresie CRON.
- databaseEvent: Rulează la evenimentele ciclului de viață ale obiectelor din spațiul de lucru. Când operațiunea evenimentului este
updated, câmpurile specifice de urmărit pot fi specificate în array-ulupdatedFields. Dacă este lăsat nedefinit sau gol, orice actualizare va declanșa funcția.
de ex. person.updated
Notițe:
- Matricea
triggerseste opțională. Funcțiile fără declanșatoare pot fi folosite ca funcții utilitare apelate de alte funcții. - Puteți combina mai multe tipuri de declanșatoare într-o singură funcție.
Payload-ul declanșatorului de rută
Când un declanșator de rută apelează funcția dvs. de logică, aceasta primește un obiectRoutePayload care urmează formatul AWS HTTP API v2. Importă tipul din twenty-sdk:
RoutePayload are următoarea structură:
| Proprietate | Tip | Descriere |
|---|---|---|
headers | Record<string, string | undefined> | Anteturi HTTP (doar cele listate în forwardedRequestHeaders) |
queryStringParameters | Record<string, string | undefined> | Parametri query string (valorile multiple unite cu virgule) |
pathParameters | Record<string, string | undefined> | Parametri de cale extrași din modelul rutei (de ex., /users/:id → { id: '123' }) |
corp | object | null | Corpul cererii analizat (JSON) |
isBase64Encoded | boolean | Indică dacă corpul este codificat în base64 |
requestContext.http.method | string | Metoda HTTP (GET, POST, PUT, PATCH, DELETE) |
requestContext.http.path | string | Calea brută a cererii |
Transmiterea anteturilor HTTP
În mod implicit, anteturile HTTP din cererile de intrare nu sunt transmise funcției dvs. de logică din motive de securitate. Pentru a accesa anumite anteturi, listează-le explicit în array-ulforwardedRequestHeaders:
Numele anteturilor sunt normalizate la litere mici. Accesează-le folosind chei cu litere mici (de exemplu,
event.headers['content-type']).- Scaffolded: Run
yarn twenty entity:addand choose the option to add a new logic function. Aceasta generează un fișier inițial cu un handler și o configurație. - Manual: Creați un fișier nou
*.logic-function.tsși folosițidefineLogicFunction(), urmând același model.
Componente Front
Componentele Front vă permit să construiți componente React personalizate care sunt randate în interfața Twenty. UtilizațidefineFrontComponent() pentru a defini componente cu validare încorporată:
- Componentele Front sunt componente React care sunt randate în contexte izolate în cadrul Twenty.
- Folosiți sufixul de fișier
*.front-component.tsxpentru detectare automată. - Câmpul
componentface referire la componenta React. - Components are built and synced automatically during
yarn twenty app:dev.
- Scaffolded: Run
yarn twenty entity:addand choose the option to add a new front component. - Manual: Creați un fișier nou
*.front-component.tsxși folosițidefineFrontComponent().
Client tipizat generat
Runyarn twenty app:generate to create a local typed client in generated/ based on your workspace schema. Folosiți-l în funcțiile dvs.:
yarn twenty app:generate. Rulați din nou după ce vă modificați obiectele sau când vă integrați într-un spațiu de lucru nou.
Acreditări la runtime în funcțiile de logică
Când funcția rulează pe Twenty, platforma injectează acreditări ca variabile de mediu înainte de execuția codului:TWENTY_API_URL: URL-ul de bază al API-ului Twenty către care țintește aplicația.TWENTY_API_KEY: Cheie cu durată scurtă, limitată la rolul implicit de funcție al aplicației.
- Nu trebuie să transmiteți URL-ul sau cheia API către clientul generat. Acesta citește
TWENTY_API_URLșiTWENTY_API_KEYdin process.env la runtime. - Permisiunile cheii API sunt determinate de rolul referențiat în
application-config.tsprindefaultRoleUniversalIdentifier. Acesta este rolul implicit folosit de funcțiile de logică ale aplicației. - Aplicațiile pot defini roluri pentru a urma principiul celui mai mic privilegiu. Acordați doar permisiunile de care au nevoie funcțiile, apoi setați
defaultRoleUniversalIdentifierla identificatorul universal al acelui rol.
Exemplu Hello World
Explorați un exemplu minim, cap la cap, care demonstrează obiecte, funcții de logică, componente Front și declanșatoare multiple aici:Configurare manuală (fără generator)
Deși recomandăm utilizareacreate-twenty-app pentru cea mai bună experiență de început, puteți configura și un proiect manual. Nu instalați CLI-ul global. Instead, add twenty-sdk as a local dependency and wire a single script in your package.json:
twenty script:
yarn twenty <command>, e.g. yarn twenty app:dev, yarn twenty app:generate, yarn twenty help, etc.
Depanare
- Authentication errors: run
yarn twenty auth:loginand ensure your API key has the required permissions. - Nu se poate conecta la server: verificați URL-ul API și că serverul Twenty este accesibil.
- Types or client missing/outdated: run
yarn twenty app:generate. - Dev mode not syncing: ensure
yarn twenty app:devis running and that changes are not ignored by your environment.