@cosmoops/connect-sdk 0.23.0 → 0.24.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/CHANGELOG.md +61 -0
- package/dist/cjs/client/components/confirm-dialog.js +14 -6
- package/dist/cjs/server/client.js +1 -1
- package/dist/cjs/server/handler.js +12 -2
- package/dist/cjs/server/resources/integrations.js +7 -5
- package/dist/esm/client/components/confirm-dialog.js +15 -7
- package/dist/esm/server/client.js +1 -1
- package/dist/esm/server/handler.js +12 -2
- package/dist/esm/server/resources/integrations.js +7 -5
- package/dist/types/client/components/confirm-dialog.d.ts +21 -6
- package/dist/types/server/client.d.ts +1 -1
- package/dist/types/server/index.d.ts +1 -1
- package/dist/types/server/resources/integrations.d.ts +20 -4
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,67 @@
|
|
|
3
3
|
`@cosmoops/connect-sdk` follows semver, with the 0.x convention that **minor
|
|
4
4
|
versions may carry breaking changes** and patch versions never do.
|
|
5
5
|
|
|
6
|
+
## 0.24.1
|
|
7
|
+
|
|
8
|
+
### Fixed
|
|
9
|
+
|
|
10
|
+
- **`<ConnectConfirmDialog />` never opened.** Its trigger was wrapped in
|
|
11
|
+
`Modal.Trigger`, which renders a `div role="button"` inside React Aria's
|
|
12
|
+
`Pressable` and depends on a plain `onClick` bubbling up to it. A React Aria
|
|
13
|
+
button nested inside - which every real trigger is, including HeroUI's
|
|
14
|
+
`<Button>` - calls `e.stopPropagation()` in its own `usePress` click
|
|
15
|
+
handler, so the click never arrived. Nothing threw and nothing warned; the
|
|
16
|
+
press was simply eaten, and every confirmation in every app built on this
|
|
17
|
+
SDK was inert. Twelve of them across the two reference apps: each delete
|
|
18
|
+
confirmation in the CRM, and each in the club app.
|
|
19
|
+
|
|
20
|
+
The trigger is now a direct child of the `Modal` root, which is React Aria's
|
|
21
|
+
`DialogTrigger`. Its `PressResponder` picks the trigger up directly, so
|
|
22
|
+
there is no nested pressable and no propagation to lose.
|
|
23
|
+
|
|
24
|
+
No call site changes. The prop's contract is now stated the right way round:
|
|
25
|
+
the trigger **must** be a pressable - a HeroUI `Button`, or anything else
|
|
26
|
+
built on React Aria's `useButton`. A non-pressable element (a bare `<span>`)
|
|
27
|
+
used to be the only thing that worked and now does not; nothing shipped
|
|
28
|
+
passes one.
|
|
29
|
+
|
|
30
|
+
## 0.24.0
|
|
31
|
+
|
|
32
|
+
### Fixed
|
|
33
|
+
|
|
34
|
+
- **`connect.integrations.initiateConnect()` could never succeed.** Connect's
|
|
35
|
+
`POST /integrations/connect` requires a `userId` - it stores it as the
|
|
36
|
+
connection's `connectedByUserId` - and the SDK sent `workspaceId`,
|
|
37
|
+
`toolkitSlug` and `returnUrl` and nothing else. Every call 400'd, including
|
|
38
|
+
the one `createConnectHandler`'s own `POST /integrations/connect` route
|
|
39
|
+
makes, so **`<ConnectIntegrationsModal />`'s Connect button was broken too**:
|
|
40
|
+
the browser reached the bridge, the bridge reached Connect, and Connect
|
|
41
|
+
refused with `Invalid input: expected string, received undefined` - a Zod
|
|
42
|
+
message that names no field, which is most of why this survived.
|
|
43
|
+
|
|
44
|
+
The conformance suite pinned the *response* shape and not the request, so
|
|
45
|
+
nothing failed the build. It now pins the request body against the
|
|
46
|
+
use-case command, and `src/conformance.test.ts` fails to compile if the
|
|
47
|
+
route grows a fourth required field.
|
|
48
|
+
|
|
49
|
+
### Changed
|
|
50
|
+
|
|
51
|
+
- **`initiateConnect` takes an input object** - `initiateConnect(workspaceId,
|
|
52
|
+
{ toolkitSlug, returnUrl, userId })`, replacing the three positional
|
|
53
|
+
strings. Breaking in name only: the old signature had no working call to
|
|
54
|
+
break. The object shape matches `execute()` on the same resource, and it is
|
|
55
|
+
what keeps `returnUrl` and `userId` from being silently transposable.
|
|
56
|
+
|
|
57
|
+
`userId` is the signed-in member starting the connection. Take it from your
|
|
58
|
+
own session, never from a form: the toolkit connection is shared by the
|
|
59
|
+
whole workspace, so this attribution is the only record of who turned it on.
|
|
60
|
+
The bridge already does this for you - it reads the session's user, and a
|
|
61
|
+
`userId` in the request body is ignored, the same way a crafted
|
|
62
|
+
`workspaceId` always was.
|
|
63
|
+
|
|
64
|
+
- **`InitiateIntegrationConnectionInput` is exported** from
|
|
65
|
+
`@cosmoops/connect-sdk/server`, beside `ExecuteIntegrationActionInput`.
|
|
66
|
+
|
|
6
67
|
## 0.23.0
|
|
7
68
|
|
|
8
69
|
### Added
|
|
@@ -19,11 +19,19 @@ const react_2 = require("@heroui/react");
|
|
|
19
19
|
* rejection is caught here rather than escaping - an error thrown out of an
|
|
20
20
|
* async transition reaches the nearest error boundary and takes the page down.
|
|
21
21
|
*
|
|
22
|
-
* The anatomy is HeroUI's: `Modal
|
|
23
|
-
* `Modal.Container` the sizing, `Modal.Dialog` the focus trap. The trigger
|
|
24
|
-
*
|
|
25
|
-
*
|
|
26
|
-
* and the dialog
|
|
22
|
+
* The anatomy is HeroUI's: the `Modal` root owns the open state,
|
|
23
|
+
* `Modal.Container` the sizing, `Modal.Dialog` the focus trap. **The trigger
|
|
24
|
+
* is a direct child of the root**, never wrapped in `Modal.Trigger`.
|
|
25
|
+
*
|
|
26
|
+
* That wrapping is what this component used to do, and it meant the dialog
|
|
27
|
+
* never opened for any caller passing a `<Button>` - which was all of them.
|
|
28
|
+
* `Modal.Trigger` renders a `div role="button"` inside React Aria's
|
|
29
|
+
* `Pressable` and relies on a plain `onClick` bubbling up to it; a React Aria
|
|
30
|
+
* button nested inside calls `e.stopPropagation()` in its own `usePress`
|
|
31
|
+
* click handler, so the click never arrives. Nothing failed loudly - the
|
|
32
|
+
* press was simply eaten. The root is `DialogTrigger`, whose `PressResponder`
|
|
33
|
+
* the trigger registers with directly, so there is no nesting and no
|
|
34
|
+
* propagation to lose.
|
|
27
35
|
*/
|
|
28
36
|
function ConnectConfirmDialog({ trigger, title, description, confirmLabel = "Confirm", cancelLabel = "Cancel", tone = "danger", onConfirm, }) {
|
|
29
37
|
const [isOpen, setIsOpen] = (0, react_1.useState)(false);
|
|
@@ -36,5 +44,5 @@ function ConnectConfirmDialog({ trigger, title, description, confirmLabel = "Con
|
|
|
36
44
|
// caller, which owns the toast and the rollback.
|
|
37
45
|
});
|
|
38
46
|
};
|
|
39
|
-
return ((0, jsx_runtime_1.jsxs)(
|
|
47
|
+
return ((0, jsx_runtime_1.jsxs)(react_2.Modal, { isOpen: isOpen, onOpenChange: setIsOpen, children: [trigger, (0, jsx_runtime_1.jsx)(react_2.Modal.Backdrop, { children: (0, jsx_runtime_1.jsx)(react_2.Modal.Container, { size: "sm", children: (0, jsx_runtime_1.jsxs)(react_2.Modal.Dialog, { children: [(0, jsx_runtime_1.jsx)(react_2.Modal.CloseTrigger, { onPress: () => setIsOpen(false) }), (0, jsx_runtime_1.jsx)(react_2.Modal.Header, { children: (0, jsx_runtime_1.jsx)(react_2.Modal.Heading, { children: title }) }), description && ((0, jsx_runtime_1.jsx)(react_2.Modal.Body, { children: (0, jsx_runtime_1.jsx)("p", { className: "text-sm text-muted", children: description }) })), (0, jsx_runtime_1.jsxs)(react_2.Modal.Footer, { children: [(0, jsx_runtime_1.jsx)(react_2.Button, { variant: "secondary", onPress: () => setIsOpen(false), children: cancelLabel }), (0, jsx_runtime_1.jsx)(react_2.Button, { variant: tone === "danger" ? "danger" : "primary", onPress: confirm, children: confirmLabel })] })] }) }) })] }));
|
|
40
48
|
}
|
|
@@ -605,8 +605,14 @@ function createConnectHandler(options) {
|
|
|
605
605
|
const { workspaceId } = await requireWorkspace(request);
|
|
606
606
|
return json({ toolkits: await client.integrations.list(workspaceId) });
|
|
607
607
|
},
|
|
608
|
+
/*
|
|
609
|
+
* `userId` comes from the session alongside `workspaceId`, never from the
|
|
610
|
+
* body - it is stored as `connectedByUserId`, so letting the browser name
|
|
611
|
+
* it would let anyone sign a workspace-shared connection with someone
|
|
612
|
+
* else's name.
|
|
613
|
+
*/
|
|
608
614
|
"POST /integrations/connect": async (request) => {
|
|
609
|
-
const { workspaceId } = await requireWorkspace(request);
|
|
615
|
+
const { workspaceId, user } = await requireWorkspace(request);
|
|
610
616
|
const body = (await request.json().catch(() => null));
|
|
611
617
|
if (!body?.toolkitSlug || !body?.returnUrl) {
|
|
612
618
|
throw new errors_js_1.ConnectError({
|
|
@@ -616,7 +622,11 @@ function createConnectHandler(options) {
|
|
|
616
622
|
endpoint: "POST /integrations/connect",
|
|
617
623
|
});
|
|
618
624
|
}
|
|
619
|
-
return json(await client.integrations.initiateConnect(workspaceId,
|
|
625
|
+
return json(await client.integrations.initiateConnect(workspaceId, {
|
|
626
|
+
toolkitSlug: body.toolkitSlug,
|
|
627
|
+
returnUrl: body.returnUrl,
|
|
628
|
+
userId: user.userId,
|
|
629
|
+
}));
|
|
620
630
|
},
|
|
621
631
|
"POST /integrations/disconnect": async (request) => {
|
|
622
632
|
const { workspaceId } = await requireWorkspace(request);
|
|
@@ -35,15 +35,17 @@ class IntegrationsResource {
|
|
|
35
35
|
* itself. Reconnecting a disconnected/failed toolkit calls this same
|
|
36
36
|
* method - there is no separate reconnect.
|
|
37
37
|
*
|
|
38
|
-
* Meant to be called on behalf of a signed-in workspace admin (this is what
|
|
39
|
-
* bridge's fixed `POST /integrations/connect` route does), not as a bare
|
|
40
|
-
* background action with no admin present to complete the OAuth screen.
|
|
38
|
+
* Meant to be called on behalf of a signed-in workspace admin (this is what
|
|
39
|
+
* the bridge's fixed `POST /integrations/connect` route does), not as a bare
|
|
40
|
+
* background action with no admin present to complete the OAuth screen. That
|
|
41
|
+
* is why `userId` is part of the input rather than inferred - see
|
|
42
|
+
* `InitiateIntegrationConnectionInput`.
|
|
41
43
|
*/
|
|
42
|
-
async initiateConnect(workspaceId,
|
|
44
|
+
async initiateConnect(workspaceId, input) {
|
|
43
45
|
return (0, http_js_1.request)(this.transport, {
|
|
44
46
|
method: "POST",
|
|
45
47
|
path: "/integrations/connect",
|
|
46
|
-
json: { workspaceId,
|
|
48
|
+
json: { workspaceId, ...input },
|
|
47
49
|
});
|
|
48
50
|
}
|
|
49
51
|
/** Idempotent - disconnecting a toolkit that was never connected, or is already disconnected, is a success. */
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import { jsx as _jsx, jsxs as _jsxs
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
3
|
import { useState } from "react";
|
|
4
4
|
import { Button, Modal } from "@heroui/react";
|
|
5
5
|
/**
|
|
@@ -16,11 +16,19 @@ import { Button, Modal } from "@heroui/react";
|
|
|
16
16
|
* rejection is caught here rather than escaping - an error thrown out of an
|
|
17
17
|
* async transition reaches the nearest error boundary and takes the page down.
|
|
18
18
|
*
|
|
19
|
-
* The anatomy is HeroUI's: `Modal
|
|
20
|
-
* `Modal.Container` the sizing, `Modal.Dialog` the focus trap. The trigger
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
* and the dialog
|
|
19
|
+
* The anatomy is HeroUI's: the `Modal` root owns the open state,
|
|
20
|
+
* `Modal.Container` the sizing, `Modal.Dialog` the focus trap. **The trigger
|
|
21
|
+
* is a direct child of the root**, never wrapped in `Modal.Trigger`.
|
|
22
|
+
*
|
|
23
|
+
* That wrapping is what this component used to do, and it meant the dialog
|
|
24
|
+
* never opened for any caller passing a `<Button>` - which was all of them.
|
|
25
|
+
* `Modal.Trigger` renders a `div role="button"` inside React Aria's
|
|
26
|
+
* `Pressable` and relies on a plain `onClick` bubbling up to it; a React Aria
|
|
27
|
+
* button nested inside calls `e.stopPropagation()` in its own `usePress`
|
|
28
|
+
* click handler, so the click never arrives. Nothing failed loudly - the
|
|
29
|
+
* press was simply eaten. The root is `DialogTrigger`, whose `PressResponder`
|
|
30
|
+
* the trigger registers with directly, so there is no nesting and no
|
|
31
|
+
* propagation to lose.
|
|
24
32
|
*/
|
|
25
33
|
export function ConnectConfirmDialog({ trigger, title, description, confirmLabel = "Confirm", cancelLabel = "Cancel", tone = "danger", onConfirm, }) {
|
|
26
34
|
const [isOpen, setIsOpen] = useState(false);
|
|
@@ -33,5 +41,5 @@ export function ConnectConfirmDialog({ trigger, title, description, confirmLabel
|
|
|
33
41
|
// caller, which owns the toast and the rollback.
|
|
34
42
|
});
|
|
35
43
|
};
|
|
36
|
-
return (_jsxs(
|
|
44
|
+
return (_jsxs(Modal, { isOpen: isOpen, onOpenChange: setIsOpen, children: [trigger, _jsx(Modal.Backdrop, { children: _jsx(Modal.Container, { size: "sm", children: _jsxs(Modal.Dialog, { children: [_jsx(Modal.CloseTrigger, { onPress: () => setIsOpen(false) }), _jsx(Modal.Header, { children: _jsx(Modal.Heading, { children: title }) }), description && (_jsx(Modal.Body, { children: _jsx("p", { className: "text-sm text-muted", children: description }) })), _jsxs(Modal.Footer, { children: [_jsx(Button, { variant: "secondary", onPress: () => setIsOpen(false), children: cancelLabel }), _jsx(Button, { variant: tone === "danger" ? "danger" : "primary", onPress: confirm, children: confirmLabel })] })] }) }) })] }));
|
|
37
45
|
}
|
|
@@ -602,8 +602,14 @@ export function createConnectHandler(options) {
|
|
|
602
602
|
const { workspaceId } = await requireWorkspace(request);
|
|
603
603
|
return json({ toolkits: await client.integrations.list(workspaceId) });
|
|
604
604
|
},
|
|
605
|
+
/*
|
|
606
|
+
* `userId` comes from the session alongside `workspaceId`, never from the
|
|
607
|
+
* body - it is stored as `connectedByUserId`, so letting the browser name
|
|
608
|
+
* it would let anyone sign a workspace-shared connection with someone
|
|
609
|
+
* else's name.
|
|
610
|
+
*/
|
|
605
611
|
"POST /integrations/connect": async (request) => {
|
|
606
|
-
const { workspaceId } = await requireWorkspace(request);
|
|
612
|
+
const { workspaceId, user } = await requireWorkspace(request);
|
|
607
613
|
const body = (await request.json().catch(() => null));
|
|
608
614
|
if (!body?.toolkitSlug || !body?.returnUrl) {
|
|
609
615
|
throw new ConnectError({
|
|
@@ -613,7 +619,11 @@ export function createConnectHandler(options) {
|
|
|
613
619
|
endpoint: "POST /integrations/connect",
|
|
614
620
|
});
|
|
615
621
|
}
|
|
616
|
-
return json(await client.integrations.initiateConnect(workspaceId,
|
|
622
|
+
return json(await client.integrations.initiateConnect(workspaceId, {
|
|
623
|
+
toolkitSlug: body.toolkitSlug,
|
|
624
|
+
returnUrl: body.returnUrl,
|
|
625
|
+
userId: user.userId,
|
|
626
|
+
}));
|
|
617
627
|
},
|
|
618
628
|
"POST /integrations/disconnect": async (request) => {
|
|
619
629
|
const { workspaceId } = await requireWorkspace(request);
|
|
@@ -32,15 +32,17 @@ export class IntegrationsResource {
|
|
|
32
32
|
* itself. Reconnecting a disconnected/failed toolkit calls this same
|
|
33
33
|
* method - there is no separate reconnect.
|
|
34
34
|
*
|
|
35
|
-
* Meant to be called on behalf of a signed-in workspace admin (this is what
|
|
36
|
-
* bridge's fixed `POST /integrations/connect` route does), not as a bare
|
|
37
|
-
* background action with no admin present to complete the OAuth screen.
|
|
35
|
+
* Meant to be called on behalf of a signed-in workspace admin (this is what
|
|
36
|
+
* the bridge's fixed `POST /integrations/connect` route does), not as a bare
|
|
37
|
+
* background action with no admin present to complete the OAuth screen. That
|
|
38
|
+
* is why `userId` is part of the input rather than inferred - see
|
|
39
|
+
* `InitiateIntegrationConnectionInput`.
|
|
38
40
|
*/
|
|
39
|
-
async initiateConnect(workspaceId,
|
|
41
|
+
async initiateConnect(workspaceId, input) {
|
|
40
42
|
return request(this.transport, {
|
|
41
43
|
method: "POST",
|
|
42
44
|
path: "/integrations/connect",
|
|
43
|
-
json: { workspaceId,
|
|
45
|
+
json: { workspaceId, ...input },
|
|
44
46
|
});
|
|
45
47
|
}
|
|
46
48
|
/** Idempotent - disconnecting a toolkit that was never connected, or is already disconnected, is a success. */
|
|
@@ -1,6 +1,13 @@
|
|
|
1
1
|
import { type ReactNode } from "react";
|
|
2
2
|
export interface ConnectConfirmDialogProps {
|
|
3
|
-
/**
|
|
3
|
+
/**
|
|
4
|
+
* The control that opens it, and it **must be a pressable** - a HeroUI
|
|
5
|
+
* `Button`, or anything else built on React Aria's `useButton`. It is
|
|
6
|
+
* rendered as a direct child of the `Modal` root, which is React Aria's
|
|
7
|
+
* `DialogTrigger`: that puts a `PressResponder` around its children and the
|
|
8
|
+
* trigger registers with it. A plain `<span>` never registers, and React
|
|
9
|
+
* Aria warns that the responder has no pressable child.
|
|
10
|
+
*/
|
|
4
11
|
trigger: ReactNode;
|
|
5
12
|
title: ReactNode;
|
|
6
13
|
/** What will happen, in the user's words. Name the thing being acted on. */
|
|
@@ -25,10 +32,18 @@ export interface ConnectConfirmDialogProps {
|
|
|
25
32
|
* rejection is caught here rather than escaping - an error thrown out of an
|
|
26
33
|
* async transition reaches the nearest error boundary and takes the page down.
|
|
27
34
|
*
|
|
28
|
-
* The anatomy is HeroUI's: `Modal
|
|
29
|
-
* `Modal.Container` the sizing, `Modal.Dialog` the focus trap. The trigger
|
|
30
|
-
*
|
|
31
|
-
*
|
|
32
|
-
* and the dialog
|
|
35
|
+
* The anatomy is HeroUI's: the `Modal` root owns the open state,
|
|
36
|
+
* `Modal.Container` the sizing, `Modal.Dialog` the focus trap. **The trigger
|
|
37
|
+
* is a direct child of the root**, never wrapped in `Modal.Trigger`.
|
|
38
|
+
*
|
|
39
|
+
* That wrapping is what this component used to do, and it meant the dialog
|
|
40
|
+
* never opened for any caller passing a `<Button>` - which was all of them.
|
|
41
|
+
* `Modal.Trigger` renders a `div role="button"` inside React Aria's
|
|
42
|
+
* `Pressable` and relies on a plain `onClick` bubbling up to it; a React Aria
|
|
43
|
+
* button nested inside calls `e.stopPropagation()` in its own `usePress`
|
|
44
|
+
* click handler, so the click never arrives. Nothing failed loudly - the
|
|
45
|
+
* press was simply eaten. The root is `DialogTrigger`, whose `PressResponder`
|
|
46
|
+
* the trigger registers with directly, so there is no nesting and no
|
|
47
|
+
* propagation to lose.
|
|
33
48
|
*/
|
|
34
49
|
export declare function ConnectConfirmDialog({ trigger, title, description, confirmLabel, cancelLabel, tone, onConfirm, }: Readonly<ConnectConfirmDialogProps>): import("react").JSX.Element;
|
|
@@ -26,7 +26,7 @@ export type { OtpResource } from "./resources/otp.js";
|
|
|
26
26
|
export type { LogsResource } from "./resources/logs.js";
|
|
27
27
|
export type { AnalyticsResource } from "./resources/analytics.js";
|
|
28
28
|
export type { SessionsResource } from "./resources/sessions.js";
|
|
29
|
-
export type { ExecuteIntegrationActionInput, IntegrationsResource } from "./resources/integrations.js";
|
|
29
|
+
export type { ExecuteIntegrationActionInput, InitiateIntegrationConnectionInput, IntegrationsResource, } from "./resources/integrations.js";
|
|
30
30
|
export type { PlatformResource } from "./resources/platform.js";
|
|
31
31
|
export type { SchedulingResource, FindSlotsInput, ListBookingsInput, CreateBookingInput, RescheduleBookingInput, } from "./resources/scheduling.js";
|
|
32
32
|
export type { ContactsResource, LookupContactInput } from "./resources/contacts.js";
|
|
@@ -1,5 +1,19 @@
|
|
|
1
1
|
import { type TransportOptions } from "../http.js";
|
|
2
2
|
import type { DisconnectIntegrationResponse, ExecuteIntegrationActionResponse, InitiateIntegrationConnectionResponse, IntegrationsListResponse } from "../../types.js";
|
|
3
|
+
export interface InitiateIntegrationConnectionInput {
|
|
4
|
+
toolkitSlug: string;
|
|
5
|
+
returnUrl: string;
|
|
6
|
+
/**
|
|
7
|
+
* The signed-in member starting the connection, recorded by Connect as
|
|
8
|
+
* `connectedByUserId`.
|
|
9
|
+
*
|
|
10
|
+
* Required, and deliberately not defaulted: the connection is *shared by
|
|
11
|
+
* the whole workspace*, so "who turned this on" is the only attribution
|
|
12
|
+
* anyone gets - and a call that cannot name a person is one where nobody
|
|
13
|
+
* is present to finish the OAuth screen either.
|
|
14
|
+
*/
|
|
15
|
+
userId: string;
|
|
16
|
+
}
|
|
3
17
|
export interface ExecuteIntegrationActionInput {
|
|
4
18
|
toolkitSlug: string;
|
|
5
19
|
actionSlug: string;
|
|
@@ -28,11 +42,13 @@ export declare class IntegrationsResource {
|
|
|
28
42
|
* itself. Reconnecting a disconnected/failed toolkit calls this same
|
|
29
43
|
* method - there is no separate reconnect.
|
|
30
44
|
*
|
|
31
|
-
* Meant to be called on behalf of a signed-in workspace admin (this is what
|
|
32
|
-
* bridge's fixed `POST /integrations/connect` route does), not as a bare
|
|
33
|
-
* background action with no admin present to complete the OAuth screen.
|
|
45
|
+
* Meant to be called on behalf of a signed-in workspace admin (this is what
|
|
46
|
+
* the bridge's fixed `POST /integrations/connect` route does), not as a bare
|
|
47
|
+
* background action with no admin present to complete the OAuth screen. That
|
|
48
|
+
* is why `userId` is part of the input rather than inferred - see
|
|
49
|
+
* `InitiateIntegrationConnectionInput`.
|
|
34
50
|
*/
|
|
35
|
-
initiateConnect(workspaceId: string,
|
|
51
|
+
initiateConnect(workspaceId: string, input: InitiateIntegrationConnectionInput): Promise<InitiateIntegrationConnectionResponse>;
|
|
36
52
|
/** Idempotent - disconnecting a toolkit that was never connected, or is already disconnected, is a success. */
|
|
37
53
|
disconnect(workspaceId: string, toolkitSlug: string): Promise<DisconnectIntegrationResponse>;
|
|
38
54
|
/** Calls a Composio action against this workspace's connected account for the named toolkit. */
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cosmoops/connect-sdk",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.24.1",
|
|
4
4
|
"description": "Official server-side SDK for the CosmoOps Connect platform API - Login with Connect, entitlements, billing and metering.",
|
|
5
5
|
"license": "SEE LICENSE IN LICENSE",
|
|
6
6
|
"type": "commonjs",
|