@sansavision/yousaid-react 0.0.0-stage → 0.2.0
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 +13 -0
- package/LICENSE +6 -0
- package/README.md +105 -2
- package/dist/context.d.ts +7 -0
- package/dist/context.d.ts.map +1 -0
- package/dist/context.js +15 -0
- package/dist/index.d.ts +107 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +441 -0
- package/dist/proof-prompt.d.ts +57 -0
- package/dist/proof-prompt.d.ts.map +1 -0
- package/dist/proof-prompt.js +106 -0
- package/dist/proof.d.ts +113 -0
- package/dist/proof.d.ts.map +1 -0
- package/dist/proof.js +383 -0
- package/dist/rooms.d.ts +158 -0
- package/dist/rooms.d.ts.map +1 -0
- package/dist/rooms.js +442 -0
- package/package.json +48 -4
package/CHANGELOG.md
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to `@sansavision/yousaid-react` are recorded here. The project
|
|
4
|
+
follows semantic versioning for the stable surface listed in README.md.
|
|
5
|
+
|
|
6
|
+
## 0.2.0
|
|
7
|
+
|
|
8
|
+
First npm release.
|
|
9
|
+
|
|
10
|
+
- Ships compiled ES2022 JavaScript (`jsx: react-jsx`) with TypeScript declarations and declaration maps.
|
|
11
|
+
- Depends on `@sansavision/yousaid` `^0.2.0`; peer dependency `react >= 19`.
|
|
12
|
+
- Stable: `YouSaidProvider`, `useYouSaid`, `YouSaidLauncher`, `Inbox`, `useInbox` and `LifecycleReceipt`.
|
|
13
|
+
- Experimental (tagged `@experimental`): Rooms components and hooks, agents, approvals, moderation, Proof widgets, `ProofPrompt` and proof hooks, map helpers.
|
package/LICENSE
ADDED
package/README.md
CHANGED
|
@@ -1,3 +1,106 @@
|
|
|
1
|
-
#
|
|
1
|
+
# @sansavision/yousaid-react
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
React components and hooks for YouSaid: a feedback launcher, the end user's live
|
|
4
|
+
inbox of replies, and lifecycle receipts. Requires React 19 or later.
|
|
5
|
+
|
|
6
|
+
```sh
|
|
7
|
+
npm install @sansavision/yousaid-react @sansavision/yousaid-server
|
|
8
|
+
```
|
|
9
|
+
|
|
10
|
+
`@sansavision/yousaid` (the framework-free client) is installed with it.
|
|
11
|
+
`@sansavision/yousaid-server` runs on your server only and signs the end user's
|
|
12
|
+
identity.
|
|
13
|
+
|
|
14
|
+
## 1. Mint an identity token on your server
|
|
15
|
+
|
|
16
|
+
```ts
|
|
17
|
+
import { createYouSaidIdentityToken } from "@sansavision/yousaid-server";
|
|
18
|
+
|
|
19
|
+
export async function GET(request: Request) {
|
|
20
|
+
const user = await currentUser(request);
|
|
21
|
+
const token = await createYouSaidIdentityToken(
|
|
22
|
+
{ sub: user.id, org_id: "org_...", product_id: "prd_...", email: user.email },
|
|
23
|
+
process.env.YOUSAID_SIGNING_SECRET!,
|
|
24
|
+
{ keyId: process.env.YOUSAID_KEY_ID! },
|
|
25
|
+
);
|
|
26
|
+
return new Response(token, { headers: { "cache-control": "no-store" } });
|
|
27
|
+
}
|
|
28
|
+
```
|
|
29
|
+
|
|
30
|
+
## 2. Wrap your app in the provider
|
|
31
|
+
|
|
32
|
+
```tsx
|
|
33
|
+
"use client";
|
|
34
|
+
import { YouSaidProvider, YouSaidLauncher, Inbox } from "@sansavision/yousaid-react";
|
|
35
|
+
|
|
36
|
+
// A function, not a string: every write consumes the token's nonce.
|
|
37
|
+
const getToken = () => fetch("/api/yousaid-token").then((response) => response.text());
|
|
38
|
+
|
|
39
|
+
export function Feedback() {
|
|
40
|
+
return (
|
|
41
|
+
<YouSaidProvider token={getToken}>
|
|
42
|
+
<YouSaidLauncher label="Talk to us" appVersion="4.2.0" />
|
|
43
|
+
<Inbox title="Replies" />
|
|
44
|
+
</YouSaidProvider>
|
|
45
|
+
);
|
|
46
|
+
}
|
|
47
|
+
```
|
|
48
|
+
|
|
49
|
+
`YouSaidProvider` takes the same options as `YouSaidClient` (`token`, `endpoint`,
|
|
50
|
+
`fetch`). Keep the `token` function stable (define it outside the component or
|
|
51
|
+
wrap it in `useCallback`) so the client is not recreated on every render.
|
|
52
|
+
|
|
53
|
+
## Components and hooks
|
|
54
|
+
|
|
55
|
+
| Export | What it does |
|
|
56
|
+
| --- | --- |
|
|
57
|
+
| `YouSaidProvider` | Creates one `YouSaidClient` for the tree. |
|
|
58
|
+
| `useYouSaid()` | Returns that client, for example to call `sendSignal` or `confirmRelease` from your own UI. Throws outside the provider. |
|
|
59
|
+
| `YouSaidLauncher` | A floating "Talk to us" button and form: message kind, attachments and an opt-in diagnostics checkbox. Props: `label`, `defaultView`, `appVersion`, `featureFlags`, `breadcrumbs`, `verifyInstall` (default true). |
|
|
60
|
+
| `Inbox` | The signed-in end user's replies, live over Server-Sent Events, with unread counts and mark-read. Props: `title`, `emptyMessage`, `onOpen(item)`. |
|
|
61
|
+
| `useInbox({ live, limit })` | The same data headless: `{ items, unread, loading, connected, error, refresh, markRead }`. |
|
|
62
|
+
| `LifecycleReceipt` | A `role="status"` receipt that tells the user where their report is. Props: `title`, `state`. |
|
|
63
|
+
|
|
64
|
+
```tsx
|
|
65
|
+
import { LifecycleReceipt, useInbox, useYouSaid } from "@sansavision/yousaid-react";
|
|
66
|
+
|
|
67
|
+
function ReleaseQuestion({ releaseId }: { releaseId: string }) {
|
|
68
|
+
const client = useYouSaid();
|
|
69
|
+
return <button onClick={() => void client.confirmRelease(releaseId, "resolved")}>It works now</button>;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
function UnreadBadge() {
|
|
73
|
+
const { unread } = useInbox({ live: true });
|
|
74
|
+
return unread ? <span aria-label={`${unread} unread replies`}>{unread}</span> : null;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
<LifecycleReceipt title="Report received" state="The team is looking at it." />;
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
Send AppHelm context with a signal through `useYouSaid().sendSignal({ ..., context: { apphelm: { workspaceId, externalUserId } } })`.
|
|
81
|
+
See the `@sansavision/yousaid` README for the field rules.
|
|
82
|
+
|
|
83
|
+
## Server rendering
|
|
84
|
+
|
|
85
|
+
Every component renders on the server without touching `window`; the network work
|
|
86
|
+
starts in effects after hydration. The modules carry `"use client"`.
|
|
87
|
+
|
|
88
|
+
## Stability
|
|
89
|
+
|
|
90
|
+
Version 0.2.0 marks these exports as **stable** under semantic versioning:
|
|
91
|
+
`YouSaidProvider`, `useYouSaid`, `YouSaidLauncher`, `Inbox`, `useInbox` and
|
|
92
|
+
`LifecycleReceipt`.
|
|
93
|
+
|
|
94
|
+
Everything else is **experimental** and tagged `@experimental` in the type
|
|
95
|
+
declarations: `YouSaidRooms` and every Rooms component and hook, agent and
|
|
96
|
+
approval cards, moderation, the Proof widgets (`ProofWall`, `ProofCarousel`,
|
|
97
|
+
`ProofCard`, `ProofBadge`, `ProofMap`, `ProofMarquee`, `ProofVideoBubble`,
|
|
98
|
+
`ProofLogoStrip`), `ProofPrompt` and the proof hooks, and the map helpers.
|
|
99
|
+
Experimental APIs can change in any minor release.
|
|
100
|
+
|
|
101
|
+
## Licence
|
|
102
|
+
|
|
103
|
+
`UNLICENSED`. All rights reserved, Sansa Group AB. Licence terms are pending
|
|
104
|
+
owner and legal review; see LICENSE.
|
|
105
|
+
|
|
106
|
+
Documentation: https://yousaid.dev/docs/sdk
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { type ReactNode } from "react";
|
|
2
|
+
import { YouSaidClient, type YouSaidClientOptions } from "@sansavision/yousaid";
|
|
3
|
+
export declare function YouSaidProvider({ children, ...options }: YouSaidClientOptions & {
|
|
4
|
+
children: ReactNode;
|
|
5
|
+
}): import("react").JSX.Element;
|
|
6
|
+
export declare function useYouSaid(): YouSaidClient;
|
|
7
|
+
//# sourceMappingURL=context.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"context.d.ts","sourceRoot":"","sources":["../src/context.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAiB,KAAK,SAAS,EAAuB,MAAM,OAAO,CAAC;AAC3E,OAAO,EAAE,aAAa,EAAE,KAAK,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;AAIhF,wBAAgB,eAAe,CAAC,EAC9B,QAAQ,EACR,GAAG,OAAO,EACX,EAAE,oBAAoB,GAAG;IAAE,QAAQ,EAAE,SAAS,CAAA;CAAE,+BAQhD;AAED,wBAAgB,UAAU,IAAI,aAAa,CAK1C"}
|
package/dist/context.js
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
+
import { createContext, useContext, useMemo } from "react";
|
|
4
|
+
import { YouSaidClient } from "@sansavision/yousaid";
|
|
5
|
+
const YouSaidContext = createContext(null);
|
|
6
|
+
export function YouSaidProvider({ children, ...options }) {
|
|
7
|
+
const client = useMemo(() => new YouSaidClient(options), [options.endpoint, options.fetch, options.token]);
|
|
8
|
+
return (_jsx(YouSaidContext.Provider, { value: client, children: children }));
|
|
9
|
+
}
|
|
10
|
+
export function useYouSaid() {
|
|
11
|
+
const client = useContext(YouSaidContext);
|
|
12
|
+
if (!client)
|
|
13
|
+
throw new Error("useYouSaid must be used inside YouSaidProvider.");
|
|
14
|
+
return client;
|
|
15
|
+
}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
import { type ReactNode } from "react";
|
|
2
|
+
import { type DiagnosticsCapsule, type InboxItem, type RoomDetail, type RoomSummary } from "@sansavision/yousaid";
|
|
3
|
+
export { YouSaidProvider, useYouSaid } from "./context.js";
|
|
4
|
+
export { AgentMentionMenu, canvasEntries, DEFAULT_CANVAS_LABELS, DEFAULT_MENTION_AGENTS, filterAgents, mentionMenuKey, RequestHumanButton, RoomCanvas, roomAgentStyles, useAgentRun, usePendingApprovals, useRequestHuman, useRoomCanvas, useRoomEvents, useRoomMembers, type CanvasEntry, type MentionAgent, } from "./rooms.js";
|
|
5
|
+
export declare function YouSaidLauncher({ label, defaultView, appVersion, featureFlags, breadcrumbs, verifyInstall, }: {
|
|
6
|
+
label?: string;
|
|
7
|
+
defaultView?: "feedback" | "rooms";
|
|
8
|
+
/** Included in the diagnostic capsule only when the user opts in. */
|
|
9
|
+
appVersion?: string;
|
|
10
|
+
featureFlags?: string[];
|
|
11
|
+
breadcrumbs?: DiagnosticsCapsule["breadcrumbs"];
|
|
12
|
+
/** Report SDK installation health once per page load (used by onboarding). */
|
|
13
|
+
verifyInstall?: boolean;
|
|
14
|
+
}): import("react").JSX.Element;
|
|
15
|
+
/**
|
|
16
|
+
* Live in-app inbox for the signed-in end user: loads the latest items, keeps
|
|
17
|
+
* a Server-Sent Events stream open (with backoff reconnects), and marks items read.
|
|
18
|
+
*/
|
|
19
|
+
export declare function useInbox(options?: {
|
|
20
|
+
live?: boolean;
|
|
21
|
+
limit?: number;
|
|
22
|
+
}): {
|
|
23
|
+
items: InboxItem[];
|
|
24
|
+
unread: number;
|
|
25
|
+
loading: boolean;
|
|
26
|
+
connected: boolean;
|
|
27
|
+
error: string;
|
|
28
|
+
refresh: () => Promise<void>;
|
|
29
|
+
markRead: (ids?: string[]) => Promise<void>;
|
|
30
|
+
};
|
|
31
|
+
export declare function Inbox({ title, emptyMessage, onOpen }: {
|
|
32
|
+
title?: string;
|
|
33
|
+
emptyMessage?: string;
|
|
34
|
+
onOpen?: (item: InboxItem) => void;
|
|
35
|
+
}): import("react").JSX.Element;
|
|
36
|
+
/** @experimental */
|
|
37
|
+
export declare function useRooms(): {
|
|
38
|
+
rooms: RoomSummary[];
|
|
39
|
+
loading: boolean;
|
|
40
|
+
error: string;
|
|
41
|
+
refresh: () => Promise<void>;
|
|
42
|
+
};
|
|
43
|
+
/** @experimental */
|
|
44
|
+
export declare function useRoom(roomId: string | null): {
|
|
45
|
+
room: RoomDetail | null;
|
|
46
|
+
loading: boolean;
|
|
47
|
+
error: string;
|
|
48
|
+
refresh: () => Promise<void>;
|
|
49
|
+
};
|
|
50
|
+
/** @experimental */
|
|
51
|
+
export declare function useRoomComposer(roomId: string | null, onSent?: () => void | Promise<void>): {
|
|
52
|
+
send: (body: string) => Promise<boolean>;
|
|
53
|
+
pending: boolean;
|
|
54
|
+
error: string;
|
|
55
|
+
};
|
|
56
|
+
/** @experimental */
|
|
57
|
+
export declare function YouSaidRooms({ embedded, initialRoomId, onSolveSession, }: {
|
|
58
|
+
embedded?: boolean;
|
|
59
|
+
initialRoomId?: string | null;
|
|
60
|
+
onSolveSession?: (session: {
|
|
61
|
+
authToken: string;
|
|
62
|
+
mode: "audio" | "video" | "screen_share";
|
|
63
|
+
}) => void;
|
|
64
|
+
}): import("react").JSX.Element;
|
|
65
|
+
/** @experimental */
|
|
66
|
+
export declare function RoomsList({ rooms, selectedId, onSelect, }: {
|
|
67
|
+
rooms: RoomSummary[];
|
|
68
|
+
selectedId?: string | null;
|
|
69
|
+
onSelect: (roomId: string) => void;
|
|
70
|
+
}): import("react").JSX.Element;
|
|
71
|
+
/** @experimental */
|
|
72
|
+
export declare function RoomView({ detail, onRefresh, onSolveSession, }: {
|
|
73
|
+
detail: RoomDetail;
|
|
74
|
+
onRefresh: () => void | Promise<void>;
|
|
75
|
+
onSolveSession?: (session: {
|
|
76
|
+
authToken: string;
|
|
77
|
+
mode: "audio" | "video" | "screen_share";
|
|
78
|
+
}) => void;
|
|
79
|
+
}): import("react").JSX.Element;
|
|
80
|
+
/** @experimental */
|
|
81
|
+
export declare function RoomComposer({ roomId, onSent, }: {
|
|
82
|
+
roomId: string;
|
|
83
|
+
onSent?: () => void | Promise<void>;
|
|
84
|
+
}): import("react").JSX.Element;
|
|
85
|
+
/** @experimental */
|
|
86
|
+
export declare function AgentActionCard({ state, children, }: {
|
|
87
|
+
state: "drafted" | "approval_needed" | "completed";
|
|
88
|
+
children: ReactNode;
|
|
89
|
+
}): import("react").JSX.Element;
|
|
90
|
+
/** @experimental */
|
|
91
|
+
export declare function ApprovalCard({ summary, onApprove, onReject, }: {
|
|
92
|
+
summary: string;
|
|
93
|
+
onApprove: () => void;
|
|
94
|
+
onReject: () => void;
|
|
95
|
+
}): import("react").JSX.Element;
|
|
96
|
+
export declare function LifecycleReceipt({ title, state, }: {
|
|
97
|
+
title: string;
|
|
98
|
+
state: string;
|
|
99
|
+
}): import("react").JSX.Element;
|
|
100
|
+
export * from "./proof.js";
|
|
101
|
+
export { ProofPromptView, useProofPrompt, type ProofPromptOptions, type ProofPromptProps, type ProofPromptState } from "./proof-prompt.js";
|
|
102
|
+
/**
|
|
103
|
+
* Native in-app Proof prompt using the provider's signed identity. See ProofPromptView for props.
|
|
104
|
+
* @experimental
|
|
105
|
+
*/
|
|
106
|
+
export declare function ProofPrompt(props: Omit<import("./proof-prompt.js").ProofPromptProps, "client">): import("react").JSX.Element;
|
|
107
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.tsx"],"names":[],"mappings":"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"}
|