Fix Apps UI: replace 'Managed' label with actual app name and unify app icons (#19897)

## Summary

- The Data Model table was labeling core Twenty objects (e.g. Person,
Company) as **Managed** even though they are part of the standard
application. This PR teaches the frontend to resolve an `applicationId`
back to its real application name (`Standard`, `Custom`, or any
installed app), and removes the misleading **Managed** label entirely.
- Introduces a single, consistent way to render an "app badge" across
the settings UI:
- new `Avatar` variant `type="app"` (rounded 4px corners + 1px
deterministic border derived from `placeholderColorSeed`)
- new `AppChip` component (icon + name) backed by a new
`useApplicationChipData` hook
- new `useApplicationsByIdMap` hook + `CurrentApplicationContext` so the
chip can render **This app** when shown inside the matching app's detail
page
- Reuses these primitives on:
- the application detail page header (`SettingsApplicationDetailTitle`)
  - the Installed / My apps tables (`SettingsApplicationTableRow`)
  - the NPM packages list (`SettingsApplicationsDeveloperTab`)
- Backend: exposes a minimal `installedApplications { id name
universalIdentifier }` field on `Workspace` (resolved from the workspace
cache, soft-deleted entries filtered out) so the frontend can resolve
`applicationId` -> name without N+1 fetches.
- Cleanup: deletes `getItemTagInfo` and inlines its tiny
responsibilities into the components that need them, matching the
`RecordChip` pattern.
This commit is contained in:
Charles Bochet
2026-04-21 00:44:14 +02:00
committed by GitHub
parent 9a963ddeca
commit 96fc98e710
42 changed files with 564 additions and 290 deletions
@@ -1,56 +0,0 @@
import { isDefined } from 'twenty-shared/utils';
export type ItemTagInfo =
| StandardItemTagInfo
| CustomItemTagInfo
| RemoteItemTagInfo
| ManagedItemTagInfo;
type StandardItemTagInfo = {
labelText: 'Standard';
labelColor: 'blue';
};
type CustomItemTagInfo = {
labelText: 'Custom';
labelColor: 'orange';
};
type RemoteItemTagInfo = {
labelText: 'Remote';
labelColor: 'green';
};
type ManagedItemTagInfo = {
labelText: 'Managed';
labelColor: 'sky';
};
export const getItemTagInfo = ({
item: { isCustom, isRemote, applicationId },
workspaceCustomApplicationId,
}: {
item: {
isCustom?: boolean;
isRemote?: boolean;
applicationId?: string | null;
};
workspaceCustomApplicationId?: string;
}): ItemTagInfo => {
if (
isDefined(applicationId) &&
applicationId !== workspaceCustomApplicationId
) {
return { labelText: 'Managed', labelColor: 'sky' };
}
if (isCustom!!) {
return { labelText: 'Custom', labelColor: 'orange' };
}
if (isRemote!!) {
return { labelText: 'Remote', labelColor: 'green' };
}
return { labelText: 'Standard', labelColor: 'blue' };
};