doover-js 0.4.2 → 0.4.4
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/react/index.d.ts +1 -1
- package/dist/react/useAgentChannel.d.ts +2 -1
- package/dist/react/useAgentChannel.js +2 -2
- package/dist/react/useChannelAggregate.d.ts +17 -1
- package/dist/react/useChannelAggregate.js +13 -2
- package/dist/react/useMultiAgentAggregates.d.ts +5 -6
- package/dist/react/useMultiAgentChannelMessages.d.ts +6 -6
- package/dist/react/useMultiAgentChannelMessages.js +2 -1
- package/dist/react/useSendMessage.d.ts +1 -1
- package/dist/react/useUpdateAggregate.d.ts +1 -1
- package/dist/react/useUpdateAggregate.js +2 -2
- package/dist/react/useUpdateMessage.d.ts +3 -3
- package/dist/react/useUpdateMessage.js +1 -1
- package/package.json +1 -1
package/dist/react/index.d.ts
CHANGED
|
@@ -6,7 +6,7 @@ export { useAgentConnections, agentConnectionsQueryKey, } from "./useAgentConnec
|
|
|
6
6
|
export { useChannelSubscription, } from "./useChannelSubscription";
|
|
7
7
|
export type { ChannelSubscriptionHandlers } from "./useChannelSubscription";
|
|
8
8
|
export { useChannelAggregate, channelAggregateQueryKey, } from "./useChannelAggregate";
|
|
9
|
-
export type { UseChannelAggregateResult } from "./useChannelAggregate";
|
|
9
|
+
export type { UseChannelAggregateOptions, UseChannelAggregateResult, } from "./useChannelAggregate";
|
|
10
10
|
export { useAgentChannel } from "./useAgentChannel";
|
|
11
11
|
export { useSendMessage } from "./useSendMessage";
|
|
12
12
|
export { useUpdateAggregate } from "./useUpdateAggregate";
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import type { Aggregate } from "../types/common";
|
|
2
|
+
import { type UseChannelAggregateOptions } from "./useChannelAggregate";
|
|
2
3
|
/**
|
|
3
4
|
* Convenience wrapper around `useChannelAggregate` that accepts an agent id
|
|
4
5
|
* and channel name as separate arguments — the most common shape at call
|
|
5
6
|
* sites where the identifier isn't already a `ChannelIdentifier`.
|
|
6
7
|
*/
|
|
7
|
-
export declare function useAgentChannel<TData = Aggregate["data"]>(agentId: string | undefined, channelName: string): import("./useChannelAggregate").UseChannelAggregateResult<TData>;
|
|
8
|
+
export declare function useAgentChannel<TData = Aggregate["data"]>(agentId: string | undefined, channelName: string, options?: UseChannelAggregateOptions): import("./useChannelAggregate").UseChannelAggregateResult<TData>;
|
|
@@ -7,6 +7,6 @@ const useChannelAggregate_1 = require("./useChannelAggregate");
|
|
|
7
7
|
* and channel name as separate arguments — the most common shape at call
|
|
8
8
|
* sites where the identifier isn't already a `ChannelIdentifier`.
|
|
9
9
|
*/
|
|
10
|
-
function useAgentChannel(agentId, channelName) {
|
|
11
|
-
return (0, useChannelAggregate_1.useChannelAggregate)({ agentId, channelName });
|
|
10
|
+
function useAgentChannel(agentId, channelName, options) {
|
|
11
|
+
return (0, useChannelAggregate_1.useChannelAggregate)({ agentId, channelName }, options);
|
|
12
12
|
}
|
|
@@ -19,6 +19,22 @@ export interface UseChannelAggregateResult<TData> extends Omit<UseQueryResult<Ag
|
|
|
19
19
|
/** Server timestamp (epoch seconds) of the last aggregate update. */
|
|
20
20
|
last_updated: number | null | undefined;
|
|
21
21
|
}
|
|
22
|
+
export interface UseChannelAggregateOptions {
|
|
23
|
+
/**
|
|
24
|
+
* Whether to fetch the initial aggregate over REST on mount.
|
|
25
|
+
*
|
|
26
|
+
* Defaults to `true` — the hook does a one-shot HTTP GET to seed the cache
|
|
27
|
+
* before the gateway WebSocket has connected, so the first paint isn't
|
|
28
|
+
* empty.
|
|
29
|
+
*
|
|
30
|
+
* Set to `false` for purely WS-driven consumers that don't want the REST
|
|
31
|
+
* round-trip (e.g. when the gateway's upsert-on-subscribe semantics make
|
|
32
|
+
* the REST call redundant or actively wrong, like channels that don't yet
|
|
33
|
+
* exist). The cache is then populated only by `ChannelSync` /
|
|
34
|
+
* `AggregateUpdate` events.
|
|
35
|
+
*/
|
|
36
|
+
fetchInitial?: boolean;
|
|
37
|
+
}
|
|
22
38
|
/**
|
|
23
39
|
* Fetch a channel's aggregate and keep it live via the gateway. Incoming
|
|
24
40
|
* `channelSync` and `aggregateUpdate` events patch the react-query cache
|
|
@@ -30,4 +46,4 @@ export interface UseChannelAggregateResult<TData> extends Omit<UseQueryResult<Ag
|
|
|
30
46
|
* don't have the implicit index signature that `Aggregate["data"]` carries
|
|
31
47
|
* and enforcing compatibility there just forces `as` casts at call sites.
|
|
32
48
|
*/
|
|
33
|
-
export declare function useChannelAggregate<TData = Aggregate["data"]>(identifier: ChannelIdentifier): UseChannelAggregateResult<TData>;
|
|
49
|
+
export declare function useChannelAggregate<TData = Aggregate["data"]>(identifier: ChannelIdentifier, options?: UseChannelAggregateOptions): UseChannelAggregateResult<TData>;
|
|
@@ -4,6 +4,7 @@ exports.channelAggregateQueryKey = channelAggregateQueryKey;
|
|
|
4
4
|
exports.useChannelAggregate = useChannelAggregate;
|
|
5
5
|
const react_1 = require("react");
|
|
6
6
|
const react_query_1 = require("@tanstack/react-query");
|
|
7
|
+
const errors_1 = require("../http/errors");
|
|
7
8
|
const context_1 = require("./context");
|
|
8
9
|
const useChannelSubscription_1 = require("./useChannelSubscription");
|
|
9
10
|
function channelAggregateQueryKey(agentId, channelName) {
|
|
@@ -20,11 +21,12 @@ function channelAggregateQueryKey(agentId, channelName) {
|
|
|
20
21
|
* don't have the implicit index signature that `Aggregate["data"]` carries
|
|
21
22
|
* and enforcing compatibility there just forces `as` casts at call sites.
|
|
22
23
|
*/
|
|
23
|
-
function useChannelAggregate(identifier) {
|
|
24
|
+
function useChannelAggregate(identifier, options) {
|
|
24
25
|
const client = (0, context_1.useDooverClient)();
|
|
25
26
|
const queryClient = (0, react_query_1.useQueryClient)();
|
|
26
27
|
const { agentId, channelName } = identifier;
|
|
27
28
|
const key = channelAggregateQueryKey(agentId, channelName);
|
|
29
|
+
const fetchInitial = options?.fetchInitial ?? true;
|
|
28
30
|
const onAggregate = (0, react_1.useCallback)((aggregate) => {
|
|
29
31
|
queryClient.setQueryData(key, aggregate);
|
|
30
32
|
},
|
|
@@ -34,9 +36,18 @@ function useChannelAggregate(identifier) {
|
|
|
34
36
|
(0, useChannelSubscription_1.useChannelSubscription)(identifier, { onAggregate });
|
|
35
37
|
const query = (0, react_query_1.useQuery)({
|
|
36
38
|
queryKey: key,
|
|
37
|
-
enabled: !!agentId && !!channelName,
|
|
39
|
+
enabled: fetchInitial && !!agentId && !!channelName,
|
|
38
40
|
staleTime: Infinity,
|
|
39
41
|
queryFn: () => client.viewer.getAggregate(identifier),
|
|
42
|
+
// A 404 means the aggregate doesn't exist — retrying won't change that,
|
|
43
|
+
// and the caller needs the error promptly to render an empty/"not
|
|
44
|
+
// installed" state. Fall back to the react-query default (3 retries) for
|
|
45
|
+
// every other failure.
|
|
46
|
+
retry: (failureCount, error) => {
|
|
47
|
+
if (error instanceof errors_1.DooverApiError && error.status === 404)
|
|
48
|
+
return false;
|
|
49
|
+
return failureCount < 3;
|
|
50
|
+
},
|
|
40
51
|
});
|
|
41
52
|
const aggregate = query.data;
|
|
42
53
|
const { data: _ignored, ...rest } = query;
|
|
@@ -1,16 +1,15 @@
|
|
|
1
1
|
import { type UseQueryResult } from "@tanstack/react-query";
|
|
2
|
-
import type { Aggregate } from "../types/common";
|
|
3
|
-
import type { AgentAggregate } from "../types/openapi";
|
|
2
|
+
import type { Aggregate, JSONValue, AgentAggregate } from "../types/common";
|
|
4
3
|
export declare function multiAgentAggregatesQueryKey(channelName: string, agentIds: string[]): readonly ["doover", "channel", string, "aggregates", string];
|
|
5
4
|
export interface UseMultiAgentAggregatesOptions {
|
|
6
5
|
/** If false, skip per-agent live subscriptions. Defaults true. */
|
|
7
6
|
liveUpdates?: boolean;
|
|
8
7
|
}
|
|
9
|
-
export interface UseMultiAgentAggregatesResult {
|
|
8
|
+
export interface UseMultiAgentAggregatesResult<TData> {
|
|
10
9
|
/** Keyed by `agent_id` for O(1) lookup. */
|
|
11
|
-
aggregatesByAgent: Record<string, Aggregate
|
|
10
|
+
aggregatesByAgent: Record<string, Aggregate<TData>>;
|
|
12
11
|
query: UseQueryResult<{
|
|
13
|
-
results: AgentAggregate[];
|
|
12
|
+
results: AgentAggregate<TData>[];
|
|
14
13
|
count: number;
|
|
15
14
|
}>;
|
|
16
15
|
}
|
|
@@ -19,4 +18,4 @@ export interface UseMultiAgentAggregatesResult {
|
|
|
19
18
|
* agent's slot live via its own gateway subscription. Reconciles per-agent
|
|
20
19
|
* `channelSync`/`aggregateUpdate` events into the batched query cache.
|
|
21
20
|
*/
|
|
22
|
-
export declare function useMultiAgentAggregates(channelName: string, agentIds: string[], options?: UseMultiAgentAggregatesOptions): UseMultiAgentAggregatesResult
|
|
21
|
+
export declare function useMultiAgentAggregates<TData = Record<string, JSONValue>>(channelName: string, agentIds: string[], options?: UseMultiAgentAggregatesOptions): UseMultiAgentAggregatesResult<TData>;
|
|
@@ -13,13 +13,13 @@ export interface UseMultiAgentChannelMessagesOptions {
|
|
|
13
13
|
/** Optional first-page `before` cursor (snowflake id). */
|
|
14
14
|
initialBefore?: string;
|
|
15
15
|
}
|
|
16
|
-
interface Page {
|
|
17
|
-
results: MessageStructure[];
|
|
16
|
+
interface Page<TData> {
|
|
17
|
+
results: MessageStructure<TData>[];
|
|
18
18
|
next?: string;
|
|
19
19
|
}
|
|
20
|
-
export interface UseMultiAgentChannelMessagesResult extends Omit<UseInfiniteQueryResult<InfiniteData<Page
|
|
21
|
-
messages: MessageStructure[];
|
|
22
|
-
data: InfiniteData<Page
|
|
20
|
+
export interface UseMultiAgentChannelMessagesResult<TData> extends Omit<UseInfiniteQueryResult<InfiniteData<Page<TData>>>, "data"> {
|
|
21
|
+
messages: MessageStructure<TData>[];
|
|
22
|
+
data: InfiniteData<Page<TData>> | undefined;
|
|
23
23
|
}
|
|
24
|
-
export declare function useMultiAgentChannelMessages(channelName: string, agentIds: string[], options?: UseMultiAgentChannelMessagesOptions): UseMultiAgentChannelMessagesResult
|
|
24
|
+
export declare function useMultiAgentChannelMessages<TData = unknown>(channelName: string, agentIds: string[], options?: UseMultiAgentChannelMessagesOptions): UseMultiAgentChannelMessagesResult<TData>;
|
|
25
25
|
export {};
|
|
@@ -26,12 +26,13 @@ function useMultiAgentChannelMessages(channelName, agentIds, options) {
|
|
|
26
26
|
queryClient.setQueryData(key, (current) => {
|
|
27
27
|
if (!current)
|
|
28
28
|
return current;
|
|
29
|
+
const typed = message;
|
|
29
30
|
const [firstPage, ...rest] = current.pages;
|
|
30
31
|
const firstResults = firstPage?.results ?? [];
|
|
31
32
|
return {
|
|
32
33
|
...current,
|
|
33
34
|
pages: [
|
|
34
|
-
{ ...firstPage, results: [
|
|
35
|
+
{ ...firstPage, results: [typed, ...firstResults] },
|
|
35
36
|
...rest,
|
|
36
37
|
],
|
|
37
38
|
};
|
|
@@ -6,4 +6,4 @@ import type { ChannelIdentifier } from "../types/viewer";
|
|
|
6
6
|
* to the channel and resolves with the created `MessageStructure` (including
|
|
7
7
|
* its server-assigned `id` and `timestamp`).
|
|
8
8
|
*/
|
|
9
|
-
export declare function useSendMessage(identifier: ChannelIdentifier): UseMutationResult<MessageStructure
|
|
9
|
+
export declare function useSendMessage<TData extends object = object>(identifier: ChannelIdentifier): UseMutationResult<MessageStructure<TData>, Error, TData>;
|
|
@@ -18,4 +18,4 @@ export interface UseUpdateAggregateOptions {
|
|
|
18
18
|
* aggregate into the react-query cache for its channel so consumers of
|
|
19
19
|
* `useChannelAggregate` see the change immediately.
|
|
20
20
|
*/
|
|
21
|
-
export declare function useUpdateAggregate(identifier: ChannelIdentifier, options?: UseUpdateAggregateOptions): UseMutationResult<Aggregate
|
|
21
|
+
export declare function useUpdateAggregate<TData extends object = object>(identifier: ChannelIdentifier, options?: UseUpdateAggregateOptions): UseMutationResult<Aggregate<TData>, Error, TData>;
|
|
@@ -16,9 +16,9 @@ function useUpdateAggregate(identifier, options) {
|
|
|
16
16
|
const replace = options?.replace ?? false;
|
|
17
17
|
const params = options?.params;
|
|
18
18
|
return (0, react_query_1.useMutation)({
|
|
19
|
-
mutationFn: (data) => replace
|
|
19
|
+
mutationFn: (data) => (replace
|
|
20
20
|
? client.viewer.putAggregate(identifier, data, params)
|
|
21
|
-
: client.viewer.updateAggregate(identifier, data, params),
|
|
21
|
+
: client.viewer.updateAggregate(identifier, data, params)),
|
|
22
22
|
onSuccess: (aggregate) => {
|
|
23
23
|
queryClient.setQueryData((0, useChannelAggregate_1.channelAggregateQueryKey)(identifier.agentId, identifier.channelName), aggregate);
|
|
24
24
|
},
|
|
@@ -15,9 +15,9 @@ export interface UpdateMessageCallOptions {
|
|
|
15
15
|
}
|
|
16
16
|
export interface UseUpdateMessageOptions extends UpdateMessageCallOptions {
|
|
17
17
|
}
|
|
18
|
-
export interface UpdateMessageVariables {
|
|
18
|
+
export interface UpdateMessageVariables<TBody extends MessageBody = MessageBody> {
|
|
19
19
|
messageId: string;
|
|
20
|
-
body:
|
|
20
|
+
body: TBody;
|
|
21
21
|
/**
|
|
22
22
|
* Per-call overrides. Extensible — add new knobs here without breaking
|
|
23
23
|
* the variables shape.
|
|
@@ -30,4 +30,4 @@ export interface UpdateMessageVariables {
|
|
|
30
30
|
* invocation can override `replace` / `params` via `variables.options` for
|
|
31
31
|
* mutation sites that sometimes PUT and sometimes PATCH the same channel.
|
|
32
32
|
*/
|
|
33
|
-
export declare function useUpdateMessage(identifier: ChannelIdentifier, options?: UseUpdateMessageOptions): UseMutationResult<unknown, Error, UpdateMessageVariables
|
|
33
|
+
export declare function useUpdateMessage<TBody extends MessageBody = MessageBody>(identifier: ChannelIdentifier, options?: UseUpdateMessageOptions): UseMutationResult<unknown, Error, UpdateMessageVariables<TBody>>;
|
|
@@ -14,7 +14,7 @@ function useUpdateMessage(identifier, options) {
|
|
|
14
14
|
const defaultReplace = options?.replace ?? false;
|
|
15
15
|
const defaultParams = options?.params;
|
|
16
16
|
return (0, react_query_1.useMutation)({
|
|
17
|
-
mutationFn: ({ messageId, body, options: call }) => {
|
|
17
|
+
mutationFn: ({ messageId, body, options: call, }) => {
|
|
18
18
|
if (!identifier.agentId || !identifier.channelName) {
|
|
19
19
|
throw new Error("useUpdateMessage requires both agentId and channelName on the identifier.");
|
|
20
20
|
}
|