twenty-sdk 0.0.6 → 0.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +82 -8
- package/dist/_commonjsHelpers-DKOUU3wS.js +1 -0
- package/dist/_commonjsHelpers-DaMA6jEr.mjs +8 -0
- package/dist/application/application-config.d.ts +1 -2
- package/dist/application/field-metadata/field.decorator.d.ts +1 -2
- package/dist/application/field-metadata/relation.decorator.d.ts +1 -2
- package/dist/application/{serverless-function-config.d.ts → function-config.d.ts} +4 -5
- package/dist/application/index.d.ts +1 -1
- package/dist/application/object-metadata/object.decorator.d.ts +1 -2
- package/dist/cli/cli.d.ts +2 -0
- package/dist/cli/commands/app-add.command.d.ts +12 -0
- package/dist/cli/commands/app-dev.command.d.ts +10 -0
- package/dist/cli/commands/app-generate.command.d.ts +4 -0
- package/dist/cli/commands/app-sync.command.d.ts +7 -0
- package/dist/cli/commands/app-uninstall.command.d.ts +9 -0
- package/dist/cli/commands/app.command.d.ts +9 -0
- package/dist/cli/commands/auth.command.d.ts +9 -0
- package/dist/cli/constants/current-execution-directory.d.ts +1 -0
- package/dist/cli/services/api.service.d.ts +14 -0
- package/dist/cli/services/config.service.d.ts +14 -0
- package/dist/cli/services/generate.service.d.ts +7 -0
- package/dist/cli/types/config.types.d.ts +99 -0
- package/dist/cli/utils/convert-to-label.d.ts +1 -0
- package/dist/cli/utils/find-path-file.d.ts +1 -0
- package/dist/cli/utils/format-and-warn-ts-diagnostics.d.ts +4 -0
- package/dist/cli/utils/format-path.d.ts +1 -0
- package/dist/cli/utils/get-function-base-file.d.ts +4 -0
- package/dist/cli/utils/get-object-decorated-class.d.ts +4 -0
- package/dist/cli/utils/get-ts-program-and-diagnostics.d.ts +7 -0
- package/dist/cli/utils/jsonc-parser.d.ts +17 -0
- package/dist/cli/utils/load-env-variables.d.ts +2 -0
- package/dist/cli/utils/load-manifest.d.ts +9 -0
- package/dist/cli.cjs +242 -0
- package/dist/cli.mjs +9507 -0
- package/dist/index.cjs +51 -1
- package/dist/index.d.ts +1 -2
- package/dist/index.mjs +17588 -2
- package/package.json +54 -22
- package/dist/application.cjs +0 -20
- package/dist/application.mjs +0 -3202
package/README.md
CHANGED
|
@@ -1,6 +1,26 @@
|
|
|
1
|
-
|
|
1
|
+
<div align="center">
|
|
2
|
+
<a href="https://twenty.com">
|
|
3
|
+
<picture>
|
|
4
|
+
<img alt="Twenty logo" src="https://raw.githubusercontent.com/twentyhq/twenty/2f25922f4cd5bd61e1427c57c4f8ea224e1d552c/packages/twenty-website/public/images/core/logo.svg" height="128">
|
|
5
|
+
</picture>
|
|
6
|
+
</a>
|
|
7
|
+
<h1>Twenty SDK</h1>
|
|
2
8
|
|
|
3
|
-
|
|
9
|
+
<a href="https://www.npmjs.com/package/twenty-sdk"><img alt="NPM version" src="https://img.shields.io/npm/v/twenty-sdk.svg?style=for-the-badge&labelColor=000000"></a>
|
|
10
|
+
<a href="https://github.com/twentyhq/twenty/blob/main/LICENSE"><img alt="License" src="https://img.shields.io/npm/l/next.svg?style=for-the-badge&labelColor=000000"></a>
|
|
11
|
+
<a href="https://discord.gg/cx5n4Jzs57"><img alt="Join the community on Discord" src="https://img.shields.io/badge/Join%20the%20community-blueviolet.svg?style=for-the-badge&logo=Twenty&labelColor=000000&logoWidth=20"></a>
|
|
12
|
+
|
|
13
|
+
</div>
|
|
14
|
+
|
|
15
|
+
A CLI and SDK to develop, build, and publish applications that extend [Twenty CRM](https://twenty.com).
|
|
16
|
+
|
|
17
|
+
- Type‑safe client and workspace entity typings
|
|
18
|
+
- Built‑in CLI for auth, generate, dev sync, one‑off sync, and uninstall
|
|
19
|
+
- Works great with the scaffolder: [create-twenty-app](https://www.npmjs.com/package/create-twenty-app)
|
|
20
|
+
|
|
21
|
+
## Prerequisites
|
|
22
|
+
- Node.js 24+ (recommended) and Yarn 4
|
|
23
|
+
- A Twenty workspace and an API key. Generate one at https://app.twenty.com/settings/api-webhooks
|
|
4
24
|
|
|
5
25
|
## Installation
|
|
6
26
|
|
|
@@ -10,18 +30,72 @@ npm install twenty-sdk
|
|
|
10
30
|
yarn add twenty-sdk
|
|
11
31
|
```
|
|
12
32
|
|
|
13
|
-
##
|
|
33
|
+
## Getting started
|
|
34
|
+
You can either scaffold a new app or add the SDK to an existing one.
|
|
35
|
+
|
|
36
|
+
- Start new (recommended):
|
|
37
|
+
```bash
|
|
38
|
+
npx create-twenty-app@latest my-twenty-app
|
|
39
|
+
cd my-twenty-app
|
|
40
|
+
```
|
|
41
|
+
- Existing project: install the SDK as shown above, then use the CLI below.
|
|
42
|
+
|
|
43
|
+
## CLI quickstart
|
|
44
|
+
```bash
|
|
45
|
+
# Authenticate using your API key (CLI will prompt for it)
|
|
46
|
+
twenty auth login
|
|
47
|
+
|
|
48
|
+
# Add a new entity to your application (guided prompts)
|
|
49
|
+
twenty app add
|
|
50
|
+
|
|
51
|
+
# Generate a typed Twenty client and TypeScript definitions for your workspace entities
|
|
52
|
+
twenty app generate
|
|
53
|
+
|
|
54
|
+
# Start dev mode: automatically syncs changes to your workspace for instant testing
|
|
55
|
+
twenty app dev
|
|
56
|
+
|
|
57
|
+
# One‑time sync of local changes
|
|
58
|
+
twenty app sync
|
|
14
59
|
|
|
60
|
+
# Uninstall the application from the current workspace
|
|
61
|
+
twenty app uninstall
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
## Usage (SDK)
|
|
15
65
|
```typescript
|
|
66
|
+
// Example: import what you need from the SDK
|
|
16
67
|
import { /* your exports */ } from 'twenty-sdk';
|
|
17
68
|
```
|
|
18
69
|
|
|
19
|
-
##
|
|
70
|
+
## Publish your application
|
|
71
|
+
Applications are currently stored in [`twenty/packages/twenty-apps`](https://github.com/twentyhq/twenty/tree/main/packages/twenty-apps).
|
|
72
|
+
|
|
73
|
+
You can share your application with all Twenty users:
|
|
20
74
|
|
|
21
75
|
```bash
|
|
22
|
-
#
|
|
23
|
-
|
|
76
|
+
# pull the Twenty project
|
|
77
|
+
git clone https://github.com/twentyhq/twenty.git
|
|
78
|
+
cd twenty
|
|
79
|
+
|
|
80
|
+
# create a new branch
|
|
81
|
+
git checkout -b feature/my-awesome-app
|
|
82
|
+
```
|
|
24
83
|
|
|
25
|
-
|
|
26
|
-
|
|
84
|
+
- Copy your app folder into `twenty/packages/twenty-apps`.
|
|
85
|
+
- Commit your changes and open a pull request on https://github.com/twentyhq/twenty
|
|
86
|
+
|
|
87
|
+
```bash
|
|
88
|
+
git commit -m "Add new application"
|
|
89
|
+
git push
|
|
27
90
|
```
|
|
91
|
+
|
|
92
|
+
Our team reviews contributions for quality, security, and reusability.
|
|
93
|
+
|
|
94
|
+
## Troubleshooting
|
|
95
|
+
- Auth errors: run `twenty auth login` again and ensure the API key has the required permissions.
|
|
96
|
+
- Typings out of date: run `twenty app generate` to refresh the client and types.
|
|
97
|
+
- Not seeing changes in dev: make sure dev mode is running (`twenty app dev`).
|
|
98
|
+
|
|
99
|
+
## Contributing
|
|
100
|
+
- See our [GitHub](https://github.com/twentyhq/twenty)
|
|
101
|
+
- Join our [Discord](https://discord.gg/cx5n4Jzs57)
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";var o=typeof globalThis<"u"?globalThis:typeof window<"u"?window:typeof global<"u"?global:typeof self<"u"?self:{};function l(e){return e&&e.__esModule&&Object.prototype.hasOwnProperty.call(e,"default")?e.default:e}exports.commonjsGlobal=o;exports.getDefaultExportFromCjs=l;
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
var o = typeof globalThis < "u" ? globalThis : typeof window < "u" ? window : typeof global < "u" ? global : typeof self < "u" ? self : {};
|
|
2
|
+
function l(e) {
|
|
3
|
+
return e && e.__esModule && Object.prototype.hasOwnProperty.call(e, "default") ? e.default : e;
|
|
4
|
+
}
|
|
5
|
+
export {
|
|
6
|
+
o as c,
|
|
7
|
+
l as g
|
|
8
|
+
};
|
|
@@ -1,6 +1,5 @@
|
|
|
1
|
+
import { SyncableEntityOptions } from '../syncable-entity-options.type';
|
|
1
2
|
import { FieldMetadataType, FieldMetadataSettings, FieldMetadataOptions, FieldMetadataDefaultValue } from 'twenty-shared/types';
|
|
2
|
-
import { SyncableEntityOptions } from '@/application/syncable-entity-options.type';
|
|
3
|
-
|
|
4
3
|
type FieldOptions<T extends FieldMetadataType = Exclude<FieldMetadataType, FieldMetadataType.RELATION>> = SyncableEntityOptions & {
|
|
5
4
|
type: T;
|
|
6
5
|
label: string;
|
|
@@ -1,6 +1,5 @@
|
|
|
1
|
+
import { SyncableEntityOptions } from '../syncable-entity-options.type';
|
|
1
2
|
import { RelationOnDeleteAction, RelationType } from 'twenty-shared/types';
|
|
2
|
-
import { SyncableEntityOptions } from '@/application/syncable-entity-options.type';
|
|
3
|
-
|
|
4
3
|
interface WorkspaceRelationMinimumBaseOptions<TClass> {
|
|
5
4
|
label: string;
|
|
6
5
|
description?: string;
|
|
@@ -1,5 +1,4 @@
|
|
|
1
|
-
import { SyncableEntityOptions } from '
|
|
2
|
-
|
|
1
|
+
import { SyncableEntityOptions } from './syncable-entity-options.type';
|
|
3
2
|
type RouteTrigger = {
|
|
4
3
|
type: 'route';
|
|
5
4
|
path: string;
|
|
@@ -14,11 +13,11 @@ type DatabaseEventTrigger = {
|
|
|
14
13
|
type: 'databaseEvent';
|
|
15
14
|
eventName: string;
|
|
16
15
|
};
|
|
17
|
-
type
|
|
18
|
-
export type
|
|
16
|
+
type FunctionTrigger = SyncableEntityOptions & (RouteTrigger | CronTrigger | DatabaseEventTrigger);
|
|
17
|
+
export type FunctionConfig = SyncableEntityOptions & {
|
|
19
18
|
name?: string;
|
|
20
19
|
description?: string;
|
|
21
20
|
timeoutSeconds?: number;
|
|
22
|
-
triggers?:
|
|
21
|
+
triggers?: FunctionTrigger[];
|
|
23
22
|
};
|
|
24
23
|
export {};
|
|
@@ -5,7 +5,7 @@ export { Field } from './field-metadata/field.decorator';
|
|
|
5
5
|
export { OnDeleteAction } from './field-metadata/on-delete-action';
|
|
6
6
|
export { RelationType } from './field-metadata/relation-type';
|
|
7
7
|
export { Relation } from './field-metadata/relation.decorator';
|
|
8
|
+
export type { FunctionConfig } from './function-config';
|
|
8
9
|
export { Object } from './object-metadata/object.decorator';
|
|
9
10
|
export { STANDARD_OBJECT_UNIVERSAL_IDENTIFIERS } from './object-metadata/standard-object-ids';
|
|
10
|
-
export type { ServerlessFunctionConfig } from './serverless-function-config';
|
|
11
11
|
export type { SyncableEntityOptions } from './syncable-entity-options.type';
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export declare enum SyncableEntity {
|
|
2
|
+
AGENT = "agent",
|
|
3
|
+
OBJECT = "object",
|
|
4
|
+
FUNCTION = "function"
|
|
5
|
+
}
|
|
6
|
+
export declare const isSyncableEntity: (value: string) => value is SyncableEntity;
|
|
7
|
+
export declare class AppAddCommand {
|
|
8
|
+
execute(entityType?: SyncableEntity, path?: string): Promise<void>;
|
|
9
|
+
private getEntity;
|
|
10
|
+
private getEntityName;
|
|
11
|
+
private getObjectData;
|
|
12
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { ApiResponse } from '../types/config.types';
|
|
2
|
+
export declare class AppUninstallCommand {
|
|
3
|
+
private apiService;
|
|
4
|
+
execute({ appPath, askForConfirmation, }: {
|
|
5
|
+
appPath?: string;
|
|
6
|
+
askForConfirmation: boolean;
|
|
7
|
+
}): Promise<ApiResponse<any>>;
|
|
8
|
+
private confirmationPrompt;
|
|
9
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const CURRENT_EXECUTION_DIRECTORY: string;
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { ApiResponse, AppManifest, PackageJson } from '../types/config.types';
|
|
2
|
+
export declare class ApiService {
|
|
3
|
+
private client;
|
|
4
|
+
private configService;
|
|
5
|
+
constructor();
|
|
6
|
+
validateAuth(): Promise<boolean>;
|
|
7
|
+
syncApplication({ packageJson, yarnLock, manifest, }: {
|
|
8
|
+
packageJson: PackageJson;
|
|
9
|
+
yarnLock: string;
|
|
10
|
+
manifest: AppManifest;
|
|
11
|
+
}): Promise<ApiResponse>;
|
|
12
|
+
uninstallApplication(universalIdentifier: string): Promise<ApiResponse>;
|
|
13
|
+
getSchema(): Promise<ApiResponse<string>>;
|
|
14
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { TwentyConfig } from '../types/config.types';
|
|
2
|
+
export declare class ConfigService {
|
|
3
|
+
private readonly configPath;
|
|
4
|
+
private static activeWorkspace;
|
|
5
|
+
constructor();
|
|
6
|
+
static setActiveWorkspace(name?: string): void;
|
|
7
|
+
static getActiveWorkspace(): string;
|
|
8
|
+
private getActiveWorkspaceName;
|
|
9
|
+
private readRawConfig;
|
|
10
|
+
getConfig(): Promise<TwentyConfig>;
|
|
11
|
+
setConfig(config: Partial<TwentyConfig>): Promise<void>;
|
|
12
|
+
clearConfig(): Promise<void>;
|
|
13
|
+
private getDefaultConfig;
|
|
14
|
+
}
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
export interface TwentyConfig {
|
|
2
|
+
apiUrl: string;
|
|
3
|
+
apiKey?: string;
|
|
4
|
+
}
|
|
5
|
+
export type PackageJson = {
|
|
6
|
+
name: string;
|
|
7
|
+
license: string;
|
|
8
|
+
engines: {
|
|
9
|
+
node: string;
|
|
10
|
+
npm: string;
|
|
11
|
+
yarn: string;
|
|
12
|
+
};
|
|
13
|
+
packageManager: string;
|
|
14
|
+
version: string;
|
|
15
|
+
dependencies?: object;
|
|
16
|
+
devDependencies?: object;
|
|
17
|
+
};
|
|
18
|
+
type ApplicationVariable = {
|
|
19
|
+
universalIdentifier: string;
|
|
20
|
+
value?: string;
|
|
21
|
+
description?: string;
|
|
22
|
+
isSecret?: boolean;
|
|
23
|
+
};
|
|
24
|
+
export type Application = {
|
|
25
|
+
universalIdentifier: string;
|
|
26
|
+
displayName?: string;
|
|
27
|
+
description?: string;
|
|
28
|
+
icon?: string;
|
|
29
|
+
applicationVariables?: Record<string, ApplicationVariable>;
|
|
30
|
+
};
|
|
31
|
+
export type AppManifest = {
|
|
32
|
+
application: Application;
|
|
33
|
+
objects: ObjectManifest[];
|
|
34
|
+
serverlessFunctions: ServerlessFunctionManifest[];
|
|
35
|
+
sources: Sources;
|
|
36
|
+
};
|
|
37
|
+
export type ServerlessFunctionManifest = {
|
|
38
|
+
universalIdentifier: string;
|
|
39
|
+
name?: string;
|
|
40
|
+
description?: string;
|
|
41
|
+
timeoutSeconds?: number;
|
|
42
|
+
triggers: ServerlessFunctionTriggerManifest[];
|
|
43
|
+
handlerPath: string;
|
|
44
|
+
handlerName: string;
|
|
45
|
+
};
|
|
46
|
+
export type DatabaseEventTrigger = {
|
|
47
|
+
type: 'databaseEvent';
|
|
48
|
+
eventName: string;
|
|
49
|
+
};
|
|
50
|
+
export type CronTrigger = {
|
|
51
|
+
type: 'cron';
|
|
52
|
+
pattern: string;
|
|
53
|
+
};
|
|
54
|
+
export type RouteTrigger = {
|
|
55
|
+
type: 'route';
|
|
56
|
+
path: string;
|
|
57
|
+
httpMethod: string;
|
|
58
|
+
isAuthRequired: boolean;
|
|
59
|
+
};
|
|
60
|
+
export type ServerlessFunctionTriggerManifest = {
|
|
61
|
+
universalIdentifier: string;
|
|
62
|
+
} & (CronTrigger | DatabaseEventTrigger | RouteTrigger);
|
|
63
|
+
export type Sources = {
|
|
64
|
+
[key: string]: string | Sources;
|
|
65
|
+
};
|
|
66
|
+
export type FieldMetadata = {
|
|
67
|
+
universalIdentifier: string;
|
|
68
|
+
type: string;
|
|
69
|
+
label: string;
|
|
70
|
+
description?: string;
|
|
71
|
+
icon?: string;
|
|
72
|
+
defaultValue?: any;
|
|
73
|
+
options?: any;
|
|
74
|
+
settings?: any;
|
|
75
|
+
isNullable?: boolean;
|
|
76
|
+
isFieldUiReadOnly?: boolean;
|
|
77
|
+
};
|
|
78
|
+
export type ObjectManifest = {
|
|
79
|
+
universalIdentifier: string;
|
|
80
|
+
nameSingular: string;
|
|
81
|
+
namePlural: string;
|
|
82
|
+
labelSingular: string;
|
|
83
|
+
labelPlural: string;
|
|
84
|
+
description?: string;
|
|
85
|
+
icon?: string;
|
|
86
|
+
fields: FieldMetadata[];
|
|
87
|
+
};
|
|
88
|
+
export type SuccessfulApiResponse<T = unknown> = {
|
|
89
|
+
success: true;
|
|
90
|
+
data: T;
|
|
91
|
+
message?: string;
|
|
92
|
+
};
|
|
93
|
+
export type FailingApiResponse = {
|
|
94
|
+
success: false;
|
|
95
|
+
error?: unknown;
|
|
96
|
+
message?: string;
|
|
97
|
+
};
|
|
98
|
+
export type ApiResponse<T = unknown> = SuccessfulApiResponse<T> | FailingApiResponse;
|
|
99
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const convertToLabel: (str: string) => string;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const findPathFile: (appPath: string, fileName: string) => Promise<string>;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare const formatPath: (appPath?: string) => string | undefined;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { ParseError } from 'jsonc-parser';
|
|
2
|
+
export interface JsoncParseOptions {
|
|
3
|
+
allowTrailingComma?: boolean;
|
|
4
|
+
disallowComments?: boolean;
|
|
5
|
+
allowEmptyContent?: boolean;
|
|
6
|
+
}
|
|
7
|
+
export declare class JsoncParseError extends Error {
|
|
8
|
+
readonly parseErrors: ParseError[];
|
|
9
|
+
readonly filePath?: string | undefined;
|
|
10
|
+
constructor(message: string, parseErrors: ParseError[], filePath?: string | undefined);
|
|
11
|
+
}
|
|
12
|
+
export declare const parseJsoncString: (content: string, options?: JsoncParseOptions) => any;
|
|
13
|
+
export declare const parseTextFile: (filePath: string) => Promise<string>;
|
|
14
|
+
export declare const parseJsoncFile: (filePath: string, options?: JsoncParseOptions) => Promise<any>;
|
|
15
|
+
export declare const writeJsoncFile: (filePath: string, data: any, options?: {
|
|
16
|
+
spaces?: number;
|
|
17
|
+
}) => Promise<void>;
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { Program } from 'typescript';
|
|
2
|
+
import { AppManifest, Application, PackageJson } from '../types/config.types';
|
|
3
|
+
export declare const extractTwentyAppConfig: (program: Program) => Application;
|
|
4
|
+
export declare const loadManifest: (appPath: string) => Promise<{
|
|
5
|
+
packageJson: PackageJson;
|
|
6
|
+
yarnLock: string;
|
|
7
|
+
manifest: AppManifest;
|
|
8
|
+
shouldGenerate: boolean;
|
|
9
|
+
}>;
|