@project-ajax/sdk 0.0.35 → 0.0.37
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/dist/builder.d.ts +13 -1
- package/dist/builder.d.ts.map +1 -1
- package/dist/builder.js +15 -0
- package/dist/capabilities/sync.d.ts +6 -1
- package/dist/capabilities/sync.d.ts.map +1 -1
- package/dist/cli/api/client.d.ts +27 -1
- package/dist/cli/api/client.d.ts.map +1 -1
- package/dist/cli/api/client.js +33 -2
- package/dist/cli/commands/auth.impl.d.ts.map +1 -1
- package/dist/cli/commands/auth.impl.js +2 -27
- package/dist/cli/commands/connect.d.ts +2 -0
- package/dist/cli/commands/connect.d.ts.map +1 -0
- package/dist/cli/commands/connect.impl.d.ts +6 -0
- package/dist/cli/commands/connect.impl.d.ts.map +1 -0
- package/dist/cli/commands/connect.impl.js +116 -0
- package/dist/cli/commands/connect.js +78 -0
- package/dist/cli/commands/secrets.impl.d.ts.map +1 -1
- package/dist/cli/commands/secrets.impl.js +6 -0
- package/dist/cli/routes.d.ts.map +1 -1
- package/dist/cli/routes.js +2 -0
- package/dist/cli/utils/openNotionUrl.d.ts +3 -0
- package/dist/cli/utils/openNotionUrl.d.ts.map +1 -0
- package/dist/cli/utils/openNotionUrl.js +33 -0
- package/dist/icon-names.d.ts +6 -0
- package/dist/icon-names.d.ts.map +1 -0
- package/dist/icon-names.js +0 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -0
- package/dist/schema.d.ts +7 -1
- package/dist/schema.d.ts.map +1 -1
- package/dist/types.d.ts +31 -1
- package/dist/types.d.ts.map +1 -1
- package/package.json +1 -1
- package/src/builder.ts +29 -1
- package/src/capabilities/sync.ts +6 -1
- package/src/cli/api/client.ts +60 -1
- package/src/cli/commands/auth.impl.ts +2 -38
- package/src/cli/commands/connect.impl.ts +149 -0
- package/src/cli/commands/connect.ts +80 -0
- package/src/cli/commands/secrets.impl.ts +6 -0
- package/src/cli/routes.ts +2 -0
- package/src/cli/utils/openNotionUrl.ts +40 -0
- package/src/icon-names.ts +890 -0
- package/src/index.ts +2 -0
- package/src/schema.ts +7 -0
- package/src/types.ts +47 -0
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,gCAAgC,CAAC;AAC9D,OAAO,EAAE,IAAI,EAAE,MAAM,wBAAwB,CAAC;AAC9C,OAAO,EAAE,IAAI,EAAE,MAAM,wBAAwB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AACrD,OAAO,EAAE,YAAY,EAAE,MAAM,gCAAgC,CAAC;AAC9D,OAAO,EAAE,IAAI,EAAE,MAAM,wBAAwB,CAAC;AAC9C,OAAO,EAAE,IAAI,EAAE,MAAM,wBAAwB,CAAC;AAC9C,YAAY,EAAE,IAAI,EAAE,YAAY,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -1,7 +1,10 @@
|
|
|
1
|
+
import { emojiIcon, notionIcon } from "./builder.js";
|
|
1
2
|
import { slashCommand } from "./capabilities/slashCommand.js";
|
|
2
3
|
import { sync } from "./capabilities/sync.js";
|
|
3
4
|
import { tool } from "./capabilities/tool.js";
|
|
4
5
|
export {
|
|
6
|
+
emojiIcon,
|
|
7
|
+
notionIcon,
|
|
5
8
|
slashCommand,
|
|
6
9
|
sync,
|
|
7
10
|
tool
|
package/dist/schema.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { DateFormat, NumberFormat, SelectOption, StatusGroup } from "./types.js";
|
|
1
|
+
import type { DateFormat, Icon, NumberFormat, SelectOption, StatusGroup } from "./types.js";
|
|
2
2
|
/**
|
|
3
3
|
* Supported property types for sync schemas.
|
|
4
4
|
*/
|
|
@@ -44,6 +44,12 @@ export type PropertyConfiguration = {
|
|
|
44
44
|
};
|
|
45
45
|
export type Schema<PK extends string> = {
|
|
46
46
|
dataSourceTitle: string;
|
|
47
|
+
/**
|
|
48
|
+
* Optional icon to use as the icon for the database page.
|
|
49
|
+
* If not provided, defaults to 📋.
|
|
50
|
+
* Use the `icon()` builder to create an icon value.
|
|
51
|
+
*/
|
|
52
|
+
databaseIcon?: Icon;
|
|
47
53
|
properties: PropertySchema<PK>;
|
|
48
54
|
};
|
|
49
55
|
/**
|
package/dist/schema.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"schema.d.ts","sourceRoot":"","sources":["../src/schema.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACX,UAAU,EACV,YAAY,EACZ,YAAY,EACZ,WAAW,EACX,MAAM,YAAY,CAAC;AAEpB;;GAEG;AACH,MAAM,MAAM,YAAY,GACrB,OAAO,GACP,WAAW,GACX,KAAK,GACL,OAAO,GACP,cAAc,GACd,UAAU,GACV,MAAM,GACN,QAAQ,GACR,MAAM,GACN,QAAQ,GACR,cAAc,GACd,QAAQ,CAAC;AAEZ;;GAEG;AACH,MAAM,MAAM,kBAAkB,GAAG;IAChC,IAAI,EAAE,YAAY,CAAC;CACnB,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,qBAAqB,GAC9B;IAAE,IAAI,EAAE,OAAO,CAAA;CAAE,GACjB;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAChB;IAAE,IAAI,EAAE,KAAK,CAAA;CAAE,GACf;IAAE,IAAI,EAAE,OAAO,CAAA;CAAE,GACjB;IAAE,IAAI,EAAE,cAAc,CAAA;CAAE,GACxB;IAAE,IAAI,EAAE,UAAU,CAAA;CAAE,GACpB;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAChB;IACA,IAAI,EAAE,QAAQ,CAAC;IACf,MAAM,CAAC,EAAE,YAAY,CAAC;CACrB,GACD;IACA,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,CAAC,EAAE,UAAU,CAAC;CACxB,GACD;IACA,IAAI,EAAE,QAAQ,CAAC;IACf,OAAO,EAAE,YAAY,EAAE,CAAC;CACvB,GACD;IACA,IAAI,EAAE,cAAc,CAAC;IACrB,OAAO,EAAE,YAAY,EAAE,CAAC;CACvB,GACD;IACA,IAAI,EAAE,QAAQ,CAAC;IACf,MAAM,EAAE,WAAW,EAAE,CAAC;CACrB,CAAC;AAEL,MAAM,MAAM,MAAM,CAAC,EAAE,SAAS,MAAM,IAAI;IACvC,eAAe,EAAE,MAAM,CAAC;IACxB,UAAU,EAAE,cAAc,CAAC,EAAE,CAAC,CAAC;CAC/B,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,cAAc,CAAC,EAAE,SAAS,MAAM,IAAI;KAC9C,UAAU,IAAI,EAAE,GAAG,qBAAqB;CACzC,GAAG;IACH,CAAC,YAAY,EAAE,MAAM,GAAG,qBAAqB,CAAC;CAC9C,CAAC;AAEF;;GAEG;AACH,wBAAgB,KAAK,IAAI,qBAAqB,CAE7C;AAED;;GAEG;AACH,wBAAgB,QAAQ,IAAI,qBAAqB,CAEhD;AAED;;GAEG;AACH,wBAAgB,GAAG,IAAI,qBAAqB,CAE3C;AAED;;GAEG;AACH,wBAAgB,KAAK,IAAI,qBAAqB,CAE7C;AAED;;GAEG;AACH,wBAAgB,WAAW,IAAI,qBAAqB,CAEnD;AAED;;GAEG;AACH,wBAAgB,QAAQ,IAAI,qBAAqB,CAEhD;AAED;;GAEG;AACH,wBAAgB,IAAI,IAAI,qBAAqB,CAE5C;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,MAAM,CAAC,EAAE,YAAY,GAAG,qBAAqB,CAEnE;AAED;;GAEG;AACH,wBAAgB,IAAI,CAAC,WAAW,CAAC,EAAE,UAAU,GAAG,qBAAqB,CAEpE;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,OAAO,EAAE,YAAY,EAAE,GAAG,qBAAqB,CAErE;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,OAAO,EAAE,YAAY,EAAE,GAAG,qBAAqB,CAE1E;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,MAAM,EAAE;IAC9B,MAAM,EAAE,WAAW,EAAE,CAAC;CACtB,GAAG,qBAAqB,CAExB"}
|
|
1
|
+
{"version":3,"file":"schema.d.ts","sourceRoot":"","sources":["../src/schema.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACX,UAAU,EACV,IAAI,EACJ,YAAY,EACZ,YAAY,EACZ,WAAW,EACX,MAAM,YAAY,CAAC;AAEpB;;GAEG;AACH,MAAM,MAAM,YAAY,GACrB,OAAO,GACP,WAAW,GACX,KAAK,GACL,OAAO,GACP,cAAc,GACd,UAAU,GACV,MAAM,GACN,QAAQ,GACR,MAAM,GACN,QAAQ,GACR,cAAc,GACd,QAAQ,CAAC;AAEZ;;GAEG;AACH,MAAM,MAAM,kBAAkB,GAAG;IAChC,IAAI,EAAE,YAAY,CAAC;CACnB,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,qBAAqB,GAC9B;IAAE,IAAI,EAAE,OAAO,CAAA;CAAE,GACjB;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAChB;IAAE,IAAI,EAAE,KAAK,CAAA;CAAE,GACf;IAAE,IAAI,EAAE,OAAO,CAAA;CAAE,GACjB;IAAE,IAAI,EAAE,cAAc,CAAA;CAAE,GACxB;IAAE,IAAI,EAAE,UAAU,CAAA;CAAE,GACpB;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAChB;IACA,IAAI,EAAE,QAAQ,CAAC;IACf,MAAM,CAAC,EAAE,YAAY,CAAC;CACrB,GACD;IACA,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,CAAC,EAAE,UAAU,CAAC;CACxB,GACD;IACA,IAAI,EAAE,QAAQ,CAAC;IACf,OAAO,EAAE,YAAY,EAAE,CAAC;CACvB,GACD;IACA,IAAI,EAAE,cAAc,CAAC;IACrB,OAAO,EAAE,YAAY,EAAE,CAAC;CACvB,GACD;IACA,IAAI,EAAE,QAAQ,CAAC;IACf,MAAM,EAAE,WAAW,EAAE,CAAC;CACrB,CAAC;AAEL,MAAM,MAAM,MAAM,CAAC,EAAE,SAAS,MAAM,IAAI;IACvC,eAAe,EAAE,MAAM,CAAC;IACxB;;;;OAIG;IACH,YAAY,CAAC,EAAE,IAAI,CAAC;IACpB,UAAU,EAAE,cAAc,CAAC,EAAE,CAAC,CAAC;CAC/B,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,cAAc,CAAC,EAAE,SAAS,MAAM,IAAI;KAC9C,UAAU,IAAI,EAAE,GAAG,qBAAqB;CACzC,GAAG;IACH,CAAC,YAAY,EAAE,MAAM,GAAG,qBAAqB,CAAC;CAC9C,CAAC;AAEF;;GAEG;AACH,wBAAgB,KAAK,IAAI,qBAAqB,CAE7C;AAED;;GAEG;AACH,wBAAgB,QAAQ,IAAI,qBAAqB,CAEhD;AAED;;GAEG;AACH,wBAAgB,GAAG,IAAI,qBAAqB,CAE3C;AAED;;GAEG;AACH,wBAAgB,KAAK,IAAI,qBAAqB,CAE7C;AAED;;GAEG;AACH,wBAAgB,WAAW,IAAI,qBAAqB,CAEnD;AAED;;GAEG;AACH,wBAAgB,QAAQ,IAAI,qBAAqB,CAEhD;AAED;;GAEG;AACH,wBAAgB,IAAI,IAAI,qBAAqB,CAE5C;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,MAAM,CAAC,EAAE,YAAY,GAAG,qBAAqB,CAEnE;AAED;;GAEG;AACH,wBAAgB,IAAI,CAAC,WAAW,CAAC,EAAE,UAAU,GAAG,qBAAqB,CAEpE;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,OAAO,EAAE,YAAY,EAAE,GAAG,qBAAqB,CAErE;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,OAAO,EAAE,YAAY,EAAE,GAAG,qBAAqB,CAE1E;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,MAAM,EAAE;IAC9B,MAAM,EAAE,WAAW,EAAE,CAAC;CACtB,GAAG,qBAAqB,CAExB"}
|
package/dist/types.d.ts
CHANGED
|
@@ -76,5 +76,35 @@ export type NumberFormat = "number" | "number_with_commas" | "percent" | "dollar
|
|
|
76
76
|
* Date format types
|
|
77
77
|
*/
|
|
78
78
|
export type DateFormat = "relative" | "MM/DD/YYYY" | "DD/MM/YYYY" | "YYYY/MM/DD" | "ll" | "MMM d";
|
|
79
|
-
|
|
79
|
+
import type { NoticonName } from "./icon-names.js";
|
|
80
|
+
/**
|
|
81
|
+
* Icon representing an emoji
|
|
82
|
+
*/
|
|
83
|
+
export interface EmojiIcon {
|
|
84
|
+
type: "emoji";
|
|
85
|
+
value: string;
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Valid colors for Notion icons
|
|
89
|
+
*/
|
|
90
|
+
export type NoticonColor = "gray" | "lightgray" | "brown" | "yellow" | "orange" | "green" | "blue" | "purple" | "pink" | "red";
|
|
91
|
+
/**
|
|
92
|
+
* Icon representing a Notion built-in icon
|
|
93
|
+
*/
|
|
94
|
+
export interface NoticonIcon {
|
|
95
|
+
type: "notion";
|
|
96
|
+
/**
|
|
97
|
+
* The name of the Notion icon (e.g., "checkmark", "pizza", "rocket")
|
|
98
|
+
*/
|
|
99
|
+
icon: NoticonName;
|
|
100
|
+
/**
|
|
101
|
+
* The color variant of the icon
|
|
102
|
+
*/
|
|
103
|
+
color: NoticonColor;
|
|
104
|
+
}
|
|
105
|
+
/**
|
|
106
|
+
* All possible icon types
|
|
107
|
+
*/
|
|
108
|
+
export type Icon = EmojiIcon | NoticonIcon;
|
|
109
|
+
export type { NoticonName } from "./icon-names.js";
|
|
80
110
|
//# sourceMappingURL=types.d.ts.map
|
package/dist/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,KAAK,SAAS,GAAG,CAAC,MAAM,EAAE,GAAG,OAAO,EAAE,CAAC,CAAC;AAExC;;GAEG;AACH,MAAM,MAAM,SAAS,GAAG,KAAK,CAAC,SAAS,CAAC,CAAC;AAEzC;;GAEG;AACH,MAAM,MAAM,WAAW,GACpB,SAAS,GACT,MAAM,GACN,OAAO,GACP,QAAQ,GACR,QAAQ,GACR,OAAO,GACP,MAAM,GACN,QAAQ,GACR,MAAM,GACN,KAAK,CAAC;AAET;;GAEG;AACH,MAAM,WAAW,YAAY;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,WAAW,CAAC;CACpB;AAED;;GAEG;AACH,MAAM,MAAM,eAAe,GAAG,OAAO,GAAG,aAAa,GAAG,UAAU,CAAC;AAEnE;;GAEG;AACH,MAAM,WAAW,WAAW;IAC3B,IAAI,EAAE,eAAe,CAAC;IACtB,OAAO,EAAE,YAAY,EAAE,CAAC;CACxB;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,WAAW,cAAc;IAC9B,IAAI,EAAE,UAAU,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,WAAW,SAAS;IACzB,IAAI,EAAE,WAAW,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;CACjB;AAED;;GAEG;AACH,MAAM,WAAW,aAAa;IAC7B,IAAI,EAAE,eAAe,CAAC;IACtB,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,MAAM,SAAS,GAAG,UAAU,GAAG,cAAc,GAAG,SAAS,GAAG,aAAa,CAAC;AAEhF;;GAEG;AACH,MAAM,MAAM,YAAY,GACrB,QAAQ,GACR,oBAAoB,GACpB,SAAS,GACT,QAAQ,GACR,MAAM,GACN,OAAO,GACP,KAAK,GACL,OAAO,GACP,KAAK,GACL,MAAM,CAAC;AAEV;;GAEG;AACH,MAAM,MAAM,UAAU,GACnB,UAAU,GACV,YAAY,GACZ,YAAY,GACZ,YAAY,GACZ,IAAI,GACJ,OAAO,CAAC"}
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,KAAK,SAAS,GAAG,CAAC,MAAM,EAAE,GAAG,OAAO,EAAE,CAAC,CAAC;AAExC;;GAEG;AACH,MAAM,MAAM,SAAS,GAAG,KAAK,CAAC,SAAS,CAAC,CAAC;AAEzC;;GAEG;AACH,MAAM,MAAM,WAAW,GACpB,SAAS,GACT,MAAM,GACN,OAAO,GACP,QAAQ,GACR,QAAQ,GACR,OAAO,GACP,MAAM,GACN,QAAQ,GACR,MAAM,GACN,KAAK,CAAC;AAET;;GAEG;AACH,MAAM,WAAW,YAAY;IAC5B,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,WAAW,CAAC;CACpB;AAED;;GAEG;AACH,MAAM,MAAM,eAAe,GAAG,OAAO,GAAG,aAAa,GAAG,UAAU,CAAC;AAEnE;;GAEG;AACH,MAAM,WAAW,WAAW;IAC3B,IAAI,EAAE,eAAe,CAAC;IACtB,OAAO,EAAE,YAAY,EAAE,CAAC;CACxB;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,WAAW,cAAc;IAC9B,IAAI,EAAE,UAAU,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,WAAW,SAAS;IACzB,IAAI,EAAE,WAAW,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;CACjB;AAED;;GAEG;AACH,MAAM,WAAW,aAAa;IAC7B,IAAI,EAAE,eAAe,CAAC;IACtB,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;CACnB;AAED;;GAEG;AACH,MAAM,MAAM,SAAS,GAAG,UAAU,GAAG,cAAc,GAAG,SAAS,GAAG,aAAa,CAAC;AAEhF;;GAEG;AACH,MAAM,MAAM,YAAY,GACrB,QAAQ,GACR,oBAAoB,GACpB,SAAS,GACT,QAAQ,GACR,MAAM,GACN,OAAO,GACP,KAAK,GACL,OAAO,GACP,KAAK,GACL,MAAM,CAAC;AAEV;;GAEG;AACH,MAAM,MAAM,UAAU,GACnB,UAAU,GACV,YAAY,GACZ,YAAY,GACZ,YAAY,GACZ,IAAI,GACJ,OAAO,CAAC;AAEX,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAC;AAEnD;;GAEG;AACH,MAAM,WAAW,SAAS;IACzB,IAAI,EAAE,OAAO,CAAC;IACd,KAAK,EAAE,MAAM,CAAC;CACd;AAED;;GAEG;AACH,MAAM,MAAM,YAAY,GACrB,MAAM,GACN,WAAW,GACX,OAAO,GACP,QAAQ,GACR,QAAQ,GACR,OAAO,GACP,MAAM,GACN,QAAQ,GACR,MAAM,GACN,KAAK,CAAC;AAET;;GAEG;AACH,MAAM,WAAW,WAAW;IAC3B,IAAI,EAAE,QAAQ,CAAC;IACf;;OAEG;IACH,IAAI,EAAE,WAAW,CAAC;IAClB;;OAEG;IACH,KAAK,EAAE,YAAY,CAAC;CACpB;AAED;;GAEG;AACH,MAAM,MAAM,IAAI,GAAG,SAAS,GAAG,WAAW,CAAC;AAE3C,YAAY,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAC"}
|
package/package.json
CHANGED
package/src/builder.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { NoticonName } from "./icon-names.js";
|
|
2
|
+
import type { DateValue, Icon, NoticonColor, TextValue } from "./types.js";
|
|
2
3
|
|
|
3
4
|
/**
|
|
4
5
|
* Creates a rich text value.
|
|
@@ -213,3 +214,30 @@ function formatTime(date: Date): string {
|
|
|
213
214
|
const minutes = String(date.getMinutes()).padStart(2, "0");
|
|
214
215
|
return `${hours}:${minutes}`;
|
|
215
216
|
}
|
|
217
|
+
|
|
218
|
+
/**
|
|
219
|
+
* Creates an emoji icon.
|
|
220
|
+
* @param emoji - An emoji string (e.g., "🎯", "✨", "🚀")
|
|
221
|
+
*/
|
|
222
|
+
export function emojiIcon(emoji: string): Icon {
|
|
223
|
+
return {
|
|
224
|
+
type: "emoji",
|
|
225
|
+
value: emoji,
|
|
226
|
+
};
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
/**
|
|
230
|
+
* Creates a Notion icon with a specific color.
|
|
231
|
+
* @param icon - The name of the Notion icon (e.g., "checkmark", "pizza", "rocket")
|
|
232
|
+
* @param color - The color variant (defaults to "gray")
|
|
233
|
+
*/
|
|
234
|
+
export function notionIcon(
|
|
235
|
+
icon: NoticonName,
|
|
236
|
+
color: NoticonColor = "gray",
|
|
237
|
+
): Icon {
|
|
238
|
+
return {
|
|
239
|
+
type: "notion",
|
|
240
|
+
icon,
|
|
241
|
+
color,
|
|
242
|
+
};
|
|
243
|
+
}
|
package/src/capabilities/sync.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { ExecutionError } from "../error.js";
|
|
2
2
|
import type { PropertySchema, Schema } from "../schema.js";
|
|
3
|
-
import type { TextValue } from "../types.js";
|
|
3
|
+
import type { Icon, TextValue } from "../types.js";
|
|
4
4
|
|
|
5
5
|
/**
|
|
6
6
|
* An object representing a third-party record to be synced.
|
|
@@ -8,6 +8,11 @@ import type { TextValue } from "../types.js";
|
|
|
8
8
|
export type SyncedObject<PK extends string, S extends PropertySchema<PK>> = {
|
|
9
9
|
key: string;
|
|
10
10
|
properties: { [Property in keyof S]: TextValue };
|
|
11
|
+
/**
|
|
12
|
+
* Optional icon to use as the icon for this row's page.
|
|
13
|
+
* Use the `icon()` builder to create an icon value.
|
|
14
|
+
*/
|
|
15
|
+
icon?: Icon;
|
|
11
16
|
};
|
|
12
17
|
|
|
13
18
|
/**
|
package/src/cli/api/client.ts
CHANGED
|
@@ -330,7 +330,10 @@ export class ApiClient {
|
|
|
330
330
|
/**
|
|
331
331
|
* List all secrets for a worker (keys only, not values)
|
|
332
332
|
*/
|
|
333
|
-
async listSecrets(
|
|
333
|
+
async listSecrets(
|
|
334
|
+
workerId: string,
|
|
335
|
+
options?: { secretKinds?: Array<"keyValue" | "oauth"> },
|
|
336
|
+
): Promise<
|
|
334
337
|
Result<
|
|
335
338
|
{
|
|
336
339
|
secrets: Array<{
|
|
@@ -338,6 +341,7 @@ export class ApiClient {
|
|
|
338
341
|
workerId: string;
|
|
339
342
|
key: string;
|
|
340
343
|
createdAt: string;
|
|
344
|
+
kind: "keyValue" | "oauth";
|
|
341
345
|
}>;
|
|
342
346
|
},
|
|
343
347
|
ApiError
|
|
@@ -347,6 +351,61 @@ export class ApiClient {
|
|
|
347
351
|
method: "POST",
|
|
348
352
|
body: {
|
|
349
353
|
workerId,
|
|
354
|
+
secretKinds: options?.secretKinds,
|
|
355
|
+
},
|
|
356
|
+
});
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
async listOauthProviders(): Promise<
|
|
360
|
+
Result<
|
|
361
|
+
{
|
|
362
|
+
providers: Array<{
|
|
363
|
+
key: string;
|
|
364
|
+
displayName: string;
|
|
365
|
+
}>;
|
|
366
|
+
},
|
|
367
|
+
ApiError
|
|
368
|
+
>
|
|
369
|
+
> {
|
|
370
|
+
return this.fetch("/workersListOauthProviders", {
|
|
371
|
+
method: "POST",
|
|
372
|
+
body: {},
|
|
373
|
+
});
|
|
374
|
+
}
|
|
375
|
+
|
|
376
|
+
/**
|
|
377
|
+
* Start the OAuth flow for a provider
|
|
378
|
+
*/
|
|
379
|
+
async startOauth(args: { workerId: string; provider: string }): Promise<
|
|
380
|
+
Result<
|
|
381
|
+
{
|
|
382
|
+
authorizationUrl: string;
|
|
383
|
+
state: string;
|
|
384
|
+
},
|
|
385
|
+
ApiError
|
|
386
|
+
>
|
|
387
|
+
> {
|
|
388
|
+
return this.fetch("/workersStartOauth", {
|
|
389
|
+
method: "POST",
|
|
390
|
+
body: {
|
|
391
|
+
workerId: args.workerId,
|
|
392
|
+
provider: args.provider,
|
|
393
|
+
},
|
|
394
|
+
});
|
|
395
|
+
}
|
|
396
|
+
|
|
397
|
+
/**
|
|
398
|
+
* Remove an OAuth connection for a worker
|
|
399
|
+
*/
|
|
400
|
+
async deleteOauthConnection(args: {
|
|
401
|
+
workerId: string;
|
|
402
|
+
provider: string;
|
|
403
|
+
}): Promise<Result<Record<string, never>, ApiError>> {
|
|
404
|
+
return this.fetch("/workersDeleteOauthConnection", {
|
|
405
|
+
method: "POST",
|
|
406
|
+
body: {
|
|
407
|
+
workerId: args.workerId,
|
|
408
|
+
provider: args.provider,
|
|
350
409
|
},
|
|
351
410
|
});
|
|
352
411
|
}
|
|
@@ -1,49 +1,13 @@
|
|
|
1
|
-
import { exec } from "node:child_process";
|
|
2
|
-
import { existsSync } from "node:fs";
|
|
3
1
|
import { baseUrl } from "../api/client.js";
|
|
4
2
|
import type { Environment } from "../config.js";
|
|
5
3
|
import { buildHandler, type HandlerContext } from "../handler.js";
|
|
4
|
+
import { openNotionUrl } from "../utils/openNotionUrl.js";
|
|
6
5
|
|
|
7
6
|
interface LoginFlags {
|
|
8
7
|
env?: Environment;
|
|
9
8
|
"base-url"?: string;
|
|
10
9
|
}
|
|
11
10
|
|
|
12
|
-
/**
|
|
13
|
-
* Open a URL in the user's default browser or Notion app (if app available)
|
|
14
|
-
*/
|
|
15
|
-
async function openUrl(env: Environment, url: string): Promise<void> {
|
|
16
|
-
const platform = process.platform;
|
|
17
|
-
|
|
18
|
-
try {
|
|
19
|
-
if (platform === "darwin") {
|
|
20
|
-
// Check if we should try to open Notion app on macOS
|
|
21
|
-
let notionAppName: string | null = null;
|
|
22
|
-
|
|
23
|
-
if (env === "prod" && existsSync("/Applications/Notion.app")) {
|
|
24
|
-
notionAppName = "Notion";
|
|
25
|
-
} else if (env === "dev" && existsSync("/Applications/Notion Dev.app")) {
|
|
26
|
-
notionAppName = "Notion Dev";
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
if (notionAppName) {
|
|
30
|
-
// Open the app first, then the URL (which will open in the app)
|
|
31
|
-
exec(`open -a "${notionAppName}" "${url}"`);
|
|
32
|
-
} else {
|
|
33
|
-
// Fall back to opening in default browser
|
|
34
|
-
exec(`open "${url}"`);
|
|
35
|
-
}
|
|
36
|
-
} else if (platform === "win32") {
|
|
37
|
-
exec(`start "" "${url}"`);
|
|
38
|
-
} else {
|
|
39
|
-
// Linux and other Unix-like systems
|
|
40
|
-
exec(`xdg-open "${url}"`);
|
|
41
|
-
}
|
|
42
|
-
} catch (error) {
|
|
43
|
-
throw new Error(`Failed to open browser: ${error}`);
|
|
44
|
-
}
|
|
45
|
-
}
|
|
46
|
-
|
|
47
11
|
export const login = buildHandler(async function (
|
|
48
12
|
this: HandlerContext,
|
|
49
13
|
flags: LoginFlags,
|
|
@@ -67,7 +31,7 @@ export const login = buildHandler(async function (
|
|
|
67
31
|
this.writer.writeErr("\tnpx workers auth login <token>");
|
|
68
32
|
|
|
69
33
|
try {
|
|
70
|
-
await
|
|
34
|
+
await openNotionUrl(environment, url);
|
|
71
35
|
} catch (_error) {
|
|
72
36
|
this.writer.writeErr(
|
|
73
37
|
`Failed to open browser automatically. Please visit:\n ${url}`,
|
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
import type { ApiError } from "../api/client.js";
|
|
2
|
+
import { Result } from "../api/result.js";
|
|
3
|
+
import type { FormatFlags, GlobalFlags } from "../flags.js";
|
|
4
|
+
import { type AuthedContext, buildAuthedHandler } from "../handler.js";
|
|
5
|
+
import { openNotionUrl } from "../utils/openNotionUrl.js";
|
|
6
|
+
|
|
7
|
+
export const listProviders = buildAuthedHandler(async function (
|
|
8
|
+
flags: FormatFlags,
|
|
9
|
+
) {
|
|
10
|
+
this.process.stderr.write("Fetching providers...");
|
|
11
|
+
const providersResult = await this.apiClient.listOauthProviders();
|
|
12
|
+
|
|
13
|
+
if (Result.isFail(providersResult)) {
|
|
14
|
+
this.process.stderr.write("ERROR\n\n");
|
|
15
|
+
reportApiError(this, providersResult.error, "list providers");
|
|
16
|
+
} else {
|
|
17
|
+
this.process.stderr.write("OK\n\n");
|
|
18
|
+
const providers = providersResult.value.providers;
|
|
19
|
+
if (providers.length === 0) {
|
|
20
|
+
this.writer.writeErr("No OAuth providers are currently available.");
|
|
21
|
+
return;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
this.writer.writeTableOut({
|
|
25
|
+
headers: ["Provider", "Description"],
|
|
26
|
+
rows: providers.map((provider) => [provider.key, provider.displayName]),
|
|
27
|
+
plain: flags.plain,
|
|
28
|
+
});
|
|
29
|
+
}
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
export const addConnection = buildAuthedHandler(async function (
|
|
33
|
+
_flags: GlobalFlags,
|
|
34
|
+
provider: string,
|
|
35
|
+
) {
|
|
36
|
+
const workerId = requireWorkerId(this);
|
|
37
|
+
|
|
38
|
+
this.process.stderr.write(
|
|
39
|
+
`Starting OAuth flow with provider "${provider}"...`,
|
|
40
|
+
);
|
|
41
|
+
const startResult = await this.apiClient.startOauth({ workerId, provider });
|
|
42
|
+
|
|
43
|
+
if (Result.isFail(startResult)) {
|
|
44
|
+
this.process.stderr.write("ERROR\n\n");
|
|
45
|
+
reportApiError(this, startResult.error, "start OAuth flow");
|
|
46
|
+
return;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
this.process.stderr.write("OK\n\n");
|
|
50
|
+
|
|
51
|
+
const { authorizationUrl } = startResult.value;
|
|
52
|
+
|
|
53
|
+
this.writer.writeErr("Opening your browser to continue the OAuth flow...");
|
|
54
|
+
try {
|
|
55
|
+
await openNotionUrl(this.config.environment ?? "prod", authorizationUrl);
|
|
56
|
+
} catch (error) {
|
|
57
|
+
this.writer.writeErr(
|
|
58
|
+
`Unable to open the browser automatically (${String(
|
|
59
|
+
error,
|
|
60
|
+
)}). Please open the link below manually.`,
|
|
61
|
+
);
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
this.writer.writeErr("");
|
|
65
|
+
this.writer.writeErr("If the browser did not open, visit:");
|
|
66
|
+
this.writer.writeErr(` ${authorizationUrl}`);
|
|
67
|
+
this.writer.writeErr("");
|
|
68
|
+
this.writer.writeErr(
|
|
69
|
+
"After completing the flow in your browser, return to the CLI.",
|
|
70
|
+
);
|
|
71
|
+
});
|
|
72
|
+
|
|
73
|
+
export const listConnections = buildAuthedHandler(async function (
|
|
74
|
+
flags: FormatFlags,
|
|
75
|
+
) {
|
|
76
|
+
const workerId = requireWorkerId(this);
|
|
77
|
+
|
|
78
|
+
this.process.stderr.write("Fetching OAuth connections...");
|
|
79
|
+
const secretsResult = await this.apiClient.listSecrets(workerId, {
|
|
80
|
+
secretKinds: ["oauth"],
|
|
81
|
+
});
|
|
82
|
+
|
|
83
|
+
if (Result.isFail(secretsResult)) {
|
|
84
|
+
this.process.stderr.write("ERROR\n\n");
|
|
85
|
+
reportApiError(this, secretsResult.error, "list OAuth connections");
|
|
86
|
+
return;
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
this.process.stderr.write("OK\n\n");
|
|
90
|
+
|
|
91
|
+
const secrets = secretsResult.value.secrets;
|
|
92
|
+
|
|
93
|
+
if (secrets.length === 0) {
|
|
94
|
+
this.writer.writeErr("No OAuth connections found for this worker.");
|
|
95
|
+
return;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
this.writer.writeTableOut({
|
|
99
|
+
headers: ["Env Var", "Created At"],
|
|
100
|
+
rows: secrets.map((secret) => [
|
|
101
|
+
`process.env.${secret.key}`,
|
|
102
|
+
secret.createdAt,
|
|
103
|
+
]),
|
|
104
|
+
plain: flags.plain,
|
|
105
|
+
});
|
|
106
|
+
});
|
|
107
|
+
|
|
108
|
+
export const removeConnection = buildAuthedHandler(async function (
|
|
109
|
+
_flags: GlobalFlags,
|
|
110
|
+
provider: string,
|
|
111
|
+
) {
|
|
112
|
+
const workerId = requireWorkerId(this);
|
|
113
|
+
|
|
114
|
+
this.process.stderr.write(
|
|
115
|
+
`Removing OAuth connection for provider "${provider}"...`,
|
|
116
|
+
);
|
|
117
|
+
const result = await this.apiClient.deleteOauthConnection({
|
|
118
|
+
workerId,
|
|
119
|
+
provider,
|
|
120
|
+
});
|
|
121
|
+
|
|
122
|
+
if (Result.isFail(result)) {
|
|
123
|
+
this.process.stderr.write("ERROR\n\n");
|
|
124
|
+
reportApiError(this, result.error, "remove connection");
|
|
125
|
+
return;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
this.process.stderr.write("OK\n");
|
|
129
|
+
});
|
|
130
|
+
|
|
131
|
+
function requireWorkerId(context: AuthedContext): string {
|
|
132
|
+
const workerId = context.config.workerId;
|
|
133
|
+
if (!workerId) {
|
|
134
|
+
throw new Error(
|
|
135
|
+
"No worker configured. Run 'workers deploy' first to create a worker.",
|
|
136
|
+
);
|
|
137
|
+
}
|
|
138
|
+
return workerId;
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
function reportApiError(
|
|
142
|
+
context: AuthedContext,
|
|
143
|
+
error: ApiError,
|
|
144
|
+
action: string,
|
|
145
|
+
): never {
|
|
146
|
+
context.writer.writeErr(`✗ Failed to ${action}`);
|
|
147
|
+
context.writer.writeErr(`✗ ${error.message}`);
|
|
148
|
+
throw new Error(error.message);
|
|
149
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import { buildCommand, buildRouteMap } from "@stricli/core";
|
|
2
|
+
|
|
3
|
+
import { formatFlags, globalFlags } from "../flags.js";
|
|
4
|
+
|
|
5
|
+
export const connectCommands = buildRouteMap({
|
|
6
|
+
docs: {
|
|
7
|
+
brief: "Manage OAuth connections for your worker",
|
|
8
|
+
},
|
|
9
|
+
routes: {
|
|
10
|
+
providers: buildCommand({
|
|
11
|
+
docs: {
|
|
12
|
+
brief: "List available OAuth providers",
|
|
13
|
+
},
|
|
14
|
+
parameters: {
|
|
15
|
+
flags: {
|
|
16
|
+
...globalFlags,
|
|
17
|
+
...formatFlags,
|
|
18
|
+
},
|
|
19
|
+
},
|
|
20
|
+
loader: () => import("./connect.impl.js").then((m) => m.listProviders),
|
|
21
|
+
}),
|
|
22
|
+
|
|
23
|
+
add: buildCommand({
|
|
24
|
+
docs: {
|
|
25
|
+
brief: "Start an OAuth flow for a provider",
|
|
26
|
+
},
|
|
27
|
+
parameters: {
|
|
28
|
+
positional: {
|
|
29
|
+
kind: "tuple",
|
|
30
|
+
parameters: [
|
|
31
|
+
{
|
|
32
|
+
brief: "Provider name (see `providers` command)",
|
|
33
|
+
parse: String,
|
|
34
|
+
placeholder: "provider",
|
|
35
|
+
},
|
|
36
|
+
],
|
|
37
|
+
},
|
|
38
|
+
flags: {
|
|
39
|
+
...globalFlags,
|
|
40
|
+
},
|
|
41
|
+
},
|
|
42
|
+
loader: () => import("./connect.impl.js").then((m) => m.addConnection),
|
|
43
|
+
}),
|
|
44
|
+
|
|
45
|
+
list: buildCommand({
|
|
46
|
+
docs: {
|
|
47
|
+
brief: "List active OAuth connections",
|
|
48
|
+
},
|
|
49
|
+
parameters: {
|
|
50
|
+
flags: {
|
|
51
|
+
...globalFlags,
|
|
52
|
+
...formatFlags,
|
|
53
|
+
},
|
|
54
|
+
},
|
|
55
|
+
loader: () => import("./connect.impl.js").then((m) => m.listConnections),
|
|
56
|
+
}),
|
|
57
|
+
|
|
58
|
+
rm: buildCommand({
|
|
59
|
+
docs: {
|
|
60
|
+
brief: "Remove an OAuth connection",
|
|
61
|
+
},
|
|
62
|
+
parameters: {
|
|
63
|
+
positional: {
|
|
64
|
+
kind: "tuple",
|
|
65
|
+
parameters: [
|
|
66
|
+
{
|
|
67
|
+
brief: "Provider name to remove",
|
|
68
|
+
parse: String,
|
|
69
|
+
placeholder: "provider",
|
|
70
|
+
},
|
|
71
|
+
],
|
|
72
|
+
},
|
|
73
|
+
flags: {
|
|
74
|
+
...globalFlags,
|
|
75
|
+
},
|
|
76
|
+
},
|
|
77
|
+
loader: () => import("./connect.impl.js").then((m) => m.removeConnection),
|
|
78
|
+
}),
|
|
79
|
+
},
|
|
80
|
+
});
|
|
@@ -52,12 +52,18 @@ export const listSecrets = buildAuthedHandler(async function (
|
|
|
52
52
|
const data = Result.unwrap(result);
|
|
53
53
|
if (data.secrets.length === 0) {
|
|
54
54
|
this.writer.writeErr("No secrets for this worker.");
|
|
55
|
+
this.writer.writeErr(
|
|
56
|
+
"To list OAuth connect secrets, use `npx workers connect list`",
|
|
57
|
+
);
|
|
55
58
|
} else {
|
|
56
59
|
this.writer.writeTableOut({
|
|
57
60
|
headers: ["Key", "Created At"],
|
|
58
61
|
rows: data.secrets.map((secret) => [secret.key, secret.createdAt]),
|
|
59
62
|
plain: flags.plain,
|
|
60
63
|
});
|
|
64
|
+
this.writer.writeErr(
|
|
65
|
+
"To list OAuth connect secrets, use `npx workers connect list`",
|
|
66
|
+
);
|
|
61
67
|
}
|
|
62
68
|
} else {
|
|
63
69
|
this.process.stderr.write("ERROR\n\n");
|
package/src/cli/routes.ts
CHANGED
|
@@ -3,6 +3,7 @@ import packageJson from "../../package.json" with { type: "json" };
|
|
|
3
3
|
import { authCommands } from "./commands/auth.js";
|
|
4
4
|
import { bundleCommands } from "./commands/bundle.js";
|
|
5
5
|
import { capabilitiesCommands } from "./commands/capabilities.js";
|
|
6
|
+
import { connectCommands } from "./commands/connect.js";
|
|
6
7
|
import deploy from "./commands/deploy.js";
|
|
7
8
|
import exec from "./commands/exec.js";
|
|
8
9
|
import { runsCommands } from "./commands/runs.js";
|
|
@@ -18,6 +19,7 @@ const routes = buildRouteMap({
|
|
|
18
19
|
capabilities: capabilitiesCommands,
|
|
19
20
|
deploy: deploy,
|
|
20
21
|
exec: exec,
|
|
22
|
+
connect: connectCommands,
|
|
21
23
|
runs: runsCommands,
|
|
22
24
|
secrets: secretsCommands,
|
|
23
25
|
bundle: bundleCommands,
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { exec } from "node:child_process";
|
|
2
|
+
import { existsSync } from "node:fs";
|
|
3
|
+
|
|
4
|
+
import type { Environment } from "../config.js";
|
|
5
|
+
|
|
6
|
+
export async function openNotionUrl(
|
|
7
|
+
env: Environment,
|
|
8
|
+
url: string,
|
|
9
|
+
): Promise<void> {
|
|
10
|
+
const platform = process.platform;
|
|
11
|
+
|
|
12
|
+
try {
|
|
13
|
+
if (platform === "darwin") {
|
|
14
|
+
const appName = preferredNotionApp(env);
|
|
15
|
+
if (appName) {
|
|
16
|
+
exec(`open -a "${appName}" "${url}"`);
|
|
17
|
+
} else {
|
|
18
|
+
exec(`open "${url}"`);
|
|
19
|
+
}
|
|
20
|
+
} else if (platform === "win32") {
|
|
21
|
+
exec(`start "" "${url}"`);
|
|
22
|
+
} else {
|
|
23
|
+
exec(`xdg-open "${url}"`);
|
|
24
|
+
}
|
|
25
|
+
} catch (error) {
|
|
26
|
+
throw new Error(`Failed to open browser: ${error}`);
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
function preferredNotionApp(env: Environment): string | null {
|
|
31
|
+
if (env === "prod" && existsSync("/Applications/Notion.app")) {
|
|
32
|
+
return "Notion";
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
if (env === "dev" && existsSync("/Applications/Notion Dev.app")) {
|
|
36
|
+
return "Notion Dev";
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
return null;
|
|
40
|
+
}
|