# Introduction
- FlatFieldMetadataType validators hashmap
- Do not fail fast on validation but aggregate errors
- Implemented `enum` validation
- Plugged the new v2 dynamic call in the field metadata service v2
## What's next:
- Implem integration tests to make things run 🙃
- migrate existing settings valdiation
- Finish the create object metadata service
- Handle update input transpilation and validation
## Open question
Should we implement, not covered validation ?, adding strictness now or
never.
This will be required by the import anw
## Discovered issue with cache
Currently the cache is not accurately typed, `fieldsById` map are not
storing any relations.
Which means the current transpilation tools are hitting undefined at
runtime
In the best of the world we will refactor the cache to be storing
`FlatObjectMetadata` and `FlatFieldMetadata` so we don't even have to
transpile them for validation and so on
But it would require to refactor the loaders that returns the cache to
the front on hit as FieldMetadataEntity, so we might land on a lighter
solution to rather add a new `getExistingFlatCache` that handles the
transpilation itself
About to do that in an other PR to be discussed with Coco
- Replaced `getAuthTokensFromLoginToken` with
`getAccessTokensFromLoginToken` for clarity.
- Introduced `getWorkspaceAgnosticTokenFromEmailVerificationToken`.
- Extended mutation inputs to include `locale` and
`verifyEmailNextPath`.
- Added email verification check and sending to various handlers.
- Updated GraphQL types and hooks to reflect these changes.
Fix#13412
---------
Co-authored-by: greptile-apps[bot] <165735046+greptile-apps[bot]@users.noreply.github.com>
Co-authored-by: Félix Malfait <felix.malfait@gmail.com>
Co-authored-by: Félix Malfait <felix@twenty.com>
# Introduction
Following https://github.com/twentyhq/twenty/pull/13420
What has been done:
- `CreateFieldInput` transpilation to `FlatFieldMetadata`
- `FlatFieldMetadata` validator service
- A lof of transpilation utils from `input` to `flatObject` or
`flatField`
- Created dedicated v2 api metadata services
- Introducing `inferDeletionFromMissingObjectFieldIndex` in the builder,
to avoid diffing every object and field of the current workspace we
allow only generating create/update migration operations, usefull when
passing by the api metadata
## We still need to in another PR:
- Implement a strong unit test coverage and critical functions and
services
- Finalize flat field metadata validation exception for `options`
`defaultValue` `settings` and `relations`
- Finalize `flatObjectMetadata` validation and v2 service refactor
- Plug the new service when feature flag is enabled
resolvetwentyhq/core-team-issues#1255
- Introduced a new field isWeekStartMonday in the workspaceMember table.
- Added a function updateCalendarStartDay to update the
isWeekStartMonday value when the user toggles the corresponding field in
the settings.
The logic works for me, but I couldn’t find a way to create the column
locally in the database for the workspaceMember tables. Please let me
know if this approach looks good and how to properly create dynamic
columns that are not directly handled via migration.
https://github.com/user-attachments/assets/4eebada5-6a96-4a88-8e96-98f1501859e3
---------
Co-authored-by: Félix Malfait <felix.malfait@gmail.com>
Co-authored-by: Félix Malfait <felix@twenty.com>
# Introduction
In this PR we create basic transpilation methods and utils to handle
input to flat, entity to flat, object maps to flat. In order to
transpile everything into a common validation that will be implemented
in another PR
## FieldMetadataEntity typing
Added `never | null` to fields that should never be in order to ease
general abstracted method to pass null, as anw it's what is in the
database
## Todo
- ~~Create a feature flag~~
- Integration test for object creation through metadata api + pg col
introspection and snapshoting
resolve#13253
This PR enables the use of Google Place Autocomplete and Place Details
APIs in the backend. It allows users to automatically fill in address
fields by typing into the address1 input. The input is debounced, then
the Autocomplete API is called. Once the user selects an address, the
Place Details API is used to parse and fill in the individual address
fields.
https://github.com/user-attachments/assets/e04b8474-25b8-48f5-83d0-2074f8d5fc94
---------
Co-authored-by: Félix Malfait <felix.malfait@gmail.com>
Co-authored-by: Félix Malfait <felix@twenty.com>
Webhooks are still documented in core playground to detail Webhooks of
core objects.
We moved webhooks to metadata playground and forgot to keep computation
of WebhookForResponse
This PR adds it back
This PR adds a public feature flag for search any field.
This feature flag default value has been set to false also to avoid
breaking the frontend, we'll wait for a sync metadata in the next
release on all workspace to remove this feature flag.
- Renamed `WorkflowActionAdapter` to `ToolExecutorWorkflowAction`
- Renamed `settingPermission` table to `permissionFlag` and `setting`
column to `flag`
- Decoupled the send email logic from workflows to tools
- Add new `Tools Permission` section in FE
---------
Co-authored-by: Félix Malfait <felix.malfait@gmail.com>
Co-authored-by: Félix Malfait <felix@twenty.com>
### Summary
This PR fixes an inconsistency in the display of application versions in
the Admin Panel. Previously, the "Current version" was displayed with a
"v" prefix (e.g., `v1.1.1`), while the "Latest version" was displayed
without it (e.g., `1.1.1`).
### Problem
The inconsistency originated from two different data sources being
handled differently in the backend:
- `currentVersion` was read directly from the `APP_VERSION`
configuration variable, which includes the "v" prefix.
- `latestVersion` was fetched from the Docker Hub API, and the
`semver.coerce()` function was used to parse it, which strips the "v"
prefix.

### Solution
The fix addresses the root cause in the [AdminPanelService] on the
backend. The `semver.coerce()` function is now also applied to the
`currentVersion`.
This ensures that both version numbers are normalized at the data
source, providing a consistent format before being sent to the frontend.
This is a cleaner approach than manipulating the data on the client
side.
**Before:**
- Current version: `v1.1.1`
- Latest version: `1.1.1`
**After:**
- Current version: `1.1.1`
- Latest version: `1.1.1`
---------
Co-authored-by: prastoin <paul@twenty.com>
## Problem
After migrating webhooks and API keys from workspace to core level, REST
API endpoints were still creating entities in workspace schema
(`workspace_*`) instead of core schema, causing webhooks to not fire.
## Solution
- Added dedicated REST controllers for webhooks (`/rest/webhooks`) and
API keys (`/rest/apiKeys`)
- Updated dynamic controller to block workspace-gated entities from
being processed
- Fixed OpenAPI documentation to exclude these endpoints from playground
- Ensured return formats match GraphQL resolvers exactly
## Testing
✅ All endpoints tested with provided auth token - webhooks and API keys
now correctly stored in `core` schema
Implementation is very simple
Established authentication dynamic is intercepted at
getAuthTokensFromLoginToken. If 2FA is required, a pattern similar to
EmailVerification is executed. That is, getAuthTokensFromLoginToken
mutation fails with either of the following errors:
1. TWO_FACTOR_AUTHENTICATION_VERIFICATION_REQUIRED
2. TWO_FACTOR_AUTHENTICATION_PROVISION_REQUIRED
UI knows how to respond accordingly.
2FA provisioning occurs at the 2FA resolver.
2FA verification, currently only OTP, is handled by auth.resolver's
getAuthTokensFromOTP
---------
Co-authored-by: Charles Bochet <charlesBochet@users.noreply.github.com>
Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
Co-authored-by: github-actions <github-actions@twenty.com>
Co-authored-by: Jean-Baptiste Ronssin <65334819+jbronssin@users.noreply.github.com>
Co-authored-by: Lucas Bordeau <bordeau.lucas@gmail.com>
Co-authored-by: Félix Malfait <felix.malfait@gmail.com>
Co-authored-by: Félix Malfait <felix@twenty.com>
# Introduction
Following https://github.com/twentyhq/twenty/pull/13264, this PR
introduces several `fieldMetadataEntity` typing enhancement suggestions.
Mainly any nullable field metadata entity properties are now either
nullable or defined.
Or never if field is dynamically required or not depending on the field
metadata type
This enhance DevX
## Standards
- field enum ( `MULTI_SELECT`, `SELECT`, `RATING` ) will never have
`options` set to `NULL` in db
- field `RELATION` or `MORH_RELATION` won't ever have its relation
fields set to `NULL` in db
- field of any type `settings`, even if possibly defined, can still be
`NULL` in db
- field of any type `defaultValue`, even if possibly defined, can still
be `NULL` in db
It coud be interesting to guard these standards by adding dedicated pg
constraints on each field
## TypesScript type tests
added coverage for each `settings`, `defaultValue`, and `options`
depending on the current `fieldMetadata`
Honestly I don' know if this typescript assertions test file is not
overkill, but regarding metadata staticness it might be very interesting
to have this guard
## Possible improvements
- We could type as `unknown` instead of "all" on `FieldMetadataType`
inferrance
- We still need to deprecate remaining duplicated entities such as
`Index/Field/MetadataInterface` etc not a huge refactor neither urgent
# Introduction
Following https://github.com/twentyhq/twenty/pull/13310
> After this PR merge will create a new one removing the type and
replacing it to ObjectMetadataEntity.
This is it !
# Introduction
Following `FieldMetadataInterface` deprecation in
https://github.com/twentyhq/twenty/pull/13264
As for the previous PR will rename and remove all the file in a
secondary PR to avoid conflicts and over loading this one
## Improvements
Removed optional properties from the `objectMetadataEntity` model and
added utils to retrieve test data
## Notes
By touching to `ObjectMetadataDTO` I would have expected a twenty-front
codegenerated types mutation, but it does not seem to be granular enough
to null/undefined coercion
# Introduction
From the moment replaced the FieldMetadataInterface definition to:
```ts
import { FieldMetadataType } from 'twenty-shared/types';
import { FieldMetadataEntity } from 'src/engine/metadata-modules/field-metadata/field-metadata.entity';
export type FieldMetadataInterface<
T extends FieldMetadataType = FieldMetadataType,
> = FieldMetadataEntity<T>;
```
After this PR merge will create a new one removing the type and
replacing it to `FieldMetadataEntity`.
Did not renamed it here to avoid conflicts on naming + type issues fixs
within the same PR
## Field metadata entity RELATION or MORPH
Relations fields cannot be null for those field metadata entity instance
anymore, but are never for the others see
`packages/twenty-server/src/engine/metadata-modules/field-metadata/types/field-metadata-entity-test.type.ts`
( introduced TypeScript tests )
## Concerns
- TS_VECTOR is the most at risk with the `generatedType` and
`asExpression` removal from interface
## What's next
- `FielMetadataInterface` removal and rename ( see introduction )
- Depcrecating `ObjectMetadataInterface`
- Refactor `FieldMetadataEntity` optional fiels to be nullable only
- TO DIG `never` occurences on settings, defaultValue etc
- Some interfaces will be replaced by the `FlatFieldMetadata` when
deprecating the current sync and comparators tools
Fixes: https://github.com/twentyhq/twenty/issues/13110
I'm deprecating note.body and task.body to remove confusion between body
and bodyV2
What will be left but should be done later to avoid breaking changes:
- re-add a body field in the graphql API only that points to the same
bodyV2 field in SQL (need to be handled in fields and filter for note
and task)
- (wait some time)
- remove bodyV2 field
- Added a generic HTTP request tool, allowing agents and workflows to
make HTTP requests to external APIs with configurable method, headers,
and body.
- Decoupled HTTP request workflow nodes from workflow-specific types and
factories, introducing a generic tool interface.
- Updated agent system prompts to include explicit guidance for the HTTP
request tool, including when and how to use it, and how to communicate
limitations.
### Demo
https://github.com/user-attachments/assets/129bc445-a277-4a19-95ab-09f890f8f051
This PR adds the frontend logic to handle the user input of a search any
field value.
It also adds the associated feature flag, that can be modified from the
admin panel.
This PR does not add the filtering part nor the saving on view logic,
which will come in their separate PRs.
https://github.com/user-attachments/assets/6a52c090-b957-46aa-bff7-a90b51109789
## Context
Add an eventEmitter instance to twenty datasources so we can emit DB
events.
Add input and output formatting to twenty orm (formatData, formatResult)
Those 2 elements simplified existing logic when we interact with the
ORM, input will be formatted by the ORM so we can directly use
field-like structure instead of column-like. The output will be
formatted, for builder queries it will be in `result.generatedMaps`
where `result.raw` preserves the previous column-like structure.
Important change: We now have an authContext that we can pass when we
get a repository, this will be used for the different events emitted in
the ORM. We also removed the caching for repositories as it was not
scaling well and not necessary imho
Note: An upcoming PR should handle the onDelete: cascade behavior where
we send DESTROY events in cascade when there is an onDelete: CASCADE on
the FK.
---------
Co-authored-by: Charles Bochet <charles@twenty.com>
Context:
Users are complaining to see their workspace in a language they don't
know. This behavior is transient, happens on data model update and
disappear on refresh
I've check the cache for users that got the issue and did not spot any
weird language
==> I think we somehow fallback the the request header locale. I feel we
should always use the userWorkspace.locale, request locale should not be
used in BE in my opinion except for unauthenticated endpoints. I'm also
adding logs to understand the locale issue
In this PR:
rename user.workspaces into user.userWorkspaces which is more correct
improve / simplify LOCALES typing