@bytexbyte/nxtlinq-ai-agent-react-native-development 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/dist/context/NxtlinqAgentContext.d.ts +13 -0
- package/dist/context/NxtlinqAgentContext.d.ts.map +1 -0
- package/dist/context/NxtlinqAgentContext.js +42 -0
- package/dist/createNxtlinqAgent.d.ts +9 -0
- package/dist/createNxtlinqAgent.d.ts.map +1 -0
- package/dist/createNxtlinqAgent.js +16 -0
- package/dist/hooks/useNxtlinqAgent.d.ts +20 -0
- package/dist/hooks/useNxtlinqAgent.d.ts.map +1 -0
- package/dist/hooks/useNxtlinqAgent.js +25 -0
- package/dist/hooks/useNxtlinqVoice.d.ts +23 -0
- package/dist/hooks/useNxtlinqVoice.d.ts.map +1 -0
- package/dist/hooks/useNxtlinqVoice.js +79 -0
- package/dist/index.d.ts +14 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +12 -0
- package/dist/ports/createAsyncStoragePort.d.ts +9 -0
- package/dist/ports/createAsyncStoragePort.d.ts.map +1 -0
- package/dist/ports/createAsyncStoragePort.js +7 -0
- package/dist/ports/createRNHttpPort.d.ts +4 -0
- package/dist/ports/createRNHttpPort.d.ts.map +1 -0
- package/dist/ports/createRNHttpPort.js +9 -0
- package/dist/ports/createRNPlatformPorts.d.ts +14 -0
- package/dist/ports/createRNPlatformPorts.d.ts.map +1 -0
- package/dist/ports/createRNPlatformPorts.js +21 -0
- package/dist/ports/createRNWebRTCPort.d.ts +81 -0
- package/dist/ports/createRNWebRTCPort.d.ts.map +1 -0
- package/dist/ports/createRNWebRTCPort.js +235 -0
- package/dist/utils/ensureRecordAudioPermission.d.ts +7 -0
- package/dist/utils/ensureRecordAudioPermission.d.ts.map +1 -0
- package/dist/utils/ensureRecordAudioPermission.js +24 -0
- package/dist/utils/fetchUriAsDataUri.d.ts +11 -0
- package/dist/utils/fetchUriAsDataUri.d.ts.map +1 -0
- package/dist/utils/fetchUriAsDataUri.js +143 -0
- package/dist/utils/iosAudioSessionReady.d.ts +27 -0
- package/dist/utils/iosAudioSessionReady.d.ts.map +1 -0
- package/dist/utils/iosAudioSessionReady.js +93 -0
- package/dist/utils/iosWebRTCAudioSession.d.ts +5 -0
- package/dist/utils/iosWebRTCAudioSession.d.ts.map +1 -0
- package/dist/utils/iosWebRTCAudioSession.js +35 -0
- package/package.json +56 -0
- package/src/context/NxtlinqAgentContext.tsx +87 -0
- package/src/createNxtlinqAgent.ts +32 -0
- package/src/hooks/useNxtlinqAgent.ts +76 -0
- package/src/hooks/useNxtlinqVoice.ts +148 -0
- package/src/index.ts +74 -0
- package/src/ports/createAsyncStoragePort.ts +16 -0
- package/src/ports/createRNHttpPort.ts +11 -0
- package/src/ports/createRNPlatformPorts.ts +37 -0
- package/src/ports/createRNWebRTCPort.ts +327 -0
- package/src/utils/ensureRecordAudioPermission.ts +28 -0
- package/src/utils/fetchUriAsDataUri.ts +166 -0
- package/src/utils/iosAudioSessionReady.ts +106 -0
- package/src/utils/iosWebRTCAudioSession.ts +39 -0
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { NxtlinqAgent, type AgentConfig } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
import React, { type ReactNode } from 'react';
|
|
3
|
+
import { type CreateNxtlinqAgentRNOptions } from '../createNxtlinqAgent';
|
|
4
|
+
export type NxtlinqAgentProviderProps = CreateNxtlinqAgentRNOptions & {
|
|
5
|
+
children: ReactNode;
|
|
6
|
+
/** Replace messages when identity fields change (e.g. new chat session). */
|
|
7
|
+
resetOnIdentityChange?: boolean;
|
|
8
|
+
};
|
|
9
|
+
export declare function NxtlinqAgentProvider({ children, resetOnIdentityChange, storage, fetchImpl, getTimezone, webrtcModule, webrtc, ...config }: NxtlinqAgentProviderProps): React.ReactElement;
|
|
10
|
+
export declare function useNxtlinqAgentContext(): NxtlinqAgent;
|
|
11
|
+
/** Re-export for apps that build the agent manually. */
|
|
12
|
+
export type { AgentConfig };
|
|
13
|
+
//# sourceMappingURL=NxtlinqAgentContext.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"NxtlinqAgentContext.d.ts","sourceRoot":"","sources":["../../src/context/NxtlinqAgentContext.tsx"],"names":[],"mappings":"AAAA,OAAO,EACL,YAAY,EACZ,KAAK,WAAW,EACjB,MAAM,8CAA8C,CAAC;AACtD,OAAO,KAAK,EAAE,EAKZ,KAAK,SAAS,EACf,MAAM,OAAO,CAAC;AACf,OAAO,EAEL,KAAK,2BAA2B,EACjC,MAAM,uBAAuB,CAAC;AAI/B,MAAM,MAAM,yBAAyB,GAAG,2BAA2B,GAAG;IACpE,QAAQ,EAAE,SAAS,CAAC;IACpB,4EAA4E;IAC5E,qBAAqB,CAAC,EAAE,OAAO,CAAC;CACjC,CAAC;AAEF,wBAAgB,oBAAoB,CAAC,EACnC,QAAQ,EACR,qBAA4B,EAC5B,OAAO,EACP,SAAS,EACT,WAAW,EACX,YAAY,EACZ,MAAM,EACN,GAAG,MAAM,EACV,EAAE,yBAAyB,GAAG,KAAK,CAAC,YAAY,CAwChD;AAED,wBAAgB,sBAAsB,IAAI,YAAY,CAQrD;AAED,wDAAwD;AACxD,YAAY,EAAE,WAAW,EAAE,CAAC"}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { createContext, useContext, useEffect, useMemo, } from 'react';
|
|
3
|
+
import { createNxtlinqAgentRN, } from '../createNxtlinqAgent';
|
|
4
|
+
const NxtlinqAgentContext = createContext(null);
|
|
5
|
+
export function NxtlinqAgentProvider({ children, resetOnIdentityChange = true, storage, fetchImpl, getTimezone, webrtcModule, webrtc, ...config }) {
|
|
6
|
+
const agent = useMemo(() => createNxtlinqAgentRN({
|
|
7
|
+
storage,
|
|
8
|
+
fetchImpl,
|
|
9
|
+
getTimezone,
|
|
10
|
+
webrtcModule,
|
|
11
|
+
webrtc,
|
|
12
|
+
...config,
|
|
13
|
+
}), [
|
|
14
|
+
config.serviceId,
|
|
15
|
+
config.apiKey,
|
|
16
|
+
config.apiSecret,
|
|
17
|
+
config.environment,
|
|
18
|
+
config.pseudoId,
|
|
19
|
+
config.externalId,
|
|
20
|
+
config.defaultModel,
|
|
21
|
+
config.voiceMode,
|
|
22
|
+
storage,
|
|
23
|
+
fetchImpl,
|
|
24
|
+
getTimezone,
|
|
25
|
+
webrtcModule,
|
|
26
|
+
webrtc,
|
|
27
|
+
]);
|
|
28
|
+
useEffect(() => {
|
|
29
|
+
if (!resetOnIdentityChange)
|
|
30
|
+
return;
|
|
31
|
+
agent.setMessages([]);
|
|
32
|
+
}, [agent, resetOnIdentityChange, config.pseudoId, config.externalId]);
|
|
33
|
+
useEffect(() => () => agent.destroy(), [agent]);
|
|
34
|
+
return (_jsx(NxtlinqAgentContext.Provider, { value: agent, children: children }));
|
|
35
|
+
}
|
|
36
|
+
export function useNxtlinqAgentContext() {
|
|
37
|
+
const agent = useContext(NxtlinqAgentContext);
|
|
38
|
+
if (!agent) {
|
|
39
|
+
throw new Error('useNxtlinqAgentContext must be used within <NxtlinqAgentProvider>');
|
|
40
|
+
}
|
|
41
|
+
return agent;
|
|
42
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { NxtlinqAgent, type AgentConfig } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
import { type CreateRNPlatformPortsOptions } from './ports/createRNPlatformPorts';
|
|
3
|
+
export type CreateNxtlinqAgentRNOptions = AgentConfig & CreateRNPlatformPortsOptions;
|
|
4
|
+
export type { RNWebRTCModule } from './ports/createRNWebRTCPort';
|
|
5
|
+
/**
|
|
6
|
+
* Create a platform-ready {@link NxtlinqAgent} for React Native custom UIs.
|
|
7
|
+
*/
|
|
8
|
+
export declare function createNxtlinqAgentRN(options: CreateNxtlinqAgentRNOptions): NxtlinqAgent;
|
|
9
|
+
//# sourceMappingURL=createNxtlinqAgent.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createNxtlinqAgent.d.ts","sourceRoot":"","sources":["../src/createNxtlinqAgent.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,YAAY,EACZ,KAAK,WAAW,EAEjB,MAAM,8CAA8C,CAAC;AACtD,OAAO,EAAyB,KAAK,4BAA4B,EAAE,MAAM,+BAA+B,CAAC;AAEzG,MAAM,MAAM,2BAA2B,GAAG,WAAW,GAAG,4BAA4B,CAAC;AAErF,YAAY,EAAE,cAAc,EAAE,MAAM,4BAA4B,CAAC;AAEjE;;GAEG;AACH,wBAAgB,oBAAoB,CAAC,OAAO,EAAE,2BAA2B,GAAG,YAAY,CAiBvF"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { NxtlinqAgent, } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
import { createRNPlatformPorts } from './ports/createRNPlatformPorts';
|
|
3
|
+
/**
|
|
4
|
+
* Create a platform-ready {@link NxtlinqAgent} for React Native custom UIs.
|
|
5
|
+
*/
|
|
6
|
+
export function createNxtlinqAgentRN(options) {
|
|
7
|
+
const { storage, fetchImpl, getTimezone, webrtcModule, webrtc, ...config } = options;
|
|
8
|
+
const ports = createRNPlatformPorts({
|
|
9
|
+
storage,
|
|
10
|
+
fetchImpl,
|
|
11
|
+
getTimezone,
|
|
12
|
+
webrtcModule,
|
|
13
|
+
webrtc,
|
|
14
|
+
});
|
|
15
|
+
return new NxtlinqAgent(config, ports);
|
|
16
|
+
}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import type { Message, NxtlinqAgentSnapshot, PostTextTtsResult, SendMessageOptions } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
import { useNxtlinqAgentContext } from '../context/NxtlinqAgentContext';
|
|
3
|
+
export type UseNxtlinqAgentResult = NxtlinqAgentSnapshot & {
|
|
4
|
+
agent: ReturnType<typeof useNxtlinqAgentContext>;
|
|
5
|
+
sendMessage: (text: string, options?: Omit<SendMessageOptions, 'text'>) => Promise<void>;
|
|
6
|
+
loadHistory: (options?: {
|
|
7
|
+
last?: number;
|
|
8
|
+
}) => Promise<void>;
|
|
9
|
+
syncVoiceTurnHistory: (options?: {
|
|
10
|
+
last?: number;
|
|
11
|
+
}) => Promise<void>;
|
|
12
|
+
setMessages: (messages: Message[]) => void;
|
|
13
|
+
postTextTts: (text: string) => Promise<PostTextTtsResult>;
|
|
14
|
+
buildTextTtsPlaybackUri: (result: PostTextTtsResult) => string;
|
|
15
|
+
};
|
|
16
|
+
/**
|
|
17
|
+
* Subscribe to {@link NxtlinqAgent} state for custom RN chat UIs.
|
|
18
|
+
*/
|
|
19
|
+
export declare function useNxtlinqAgent(): UseNxtlinqAgentResult;
|
|
20
|
+
//# sourceMappingURL=useNxtlinqAgent.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useNxtlinqAgent.d.ts","sourceRoot":"","sources":["../../src/hooks/useNxtlinqAgent.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,OAAO,EACP,oBAAoB,EACpB,iBAAiB,EACjB,kBAAkB,EACnB,MAAM,8CAA8C,CAAC;AAEtD,OAAO,EAAE,sBAAsB,EAAE,MAAM,gCAAgC,CAAC;AAExE,MAAM,MAAM,qBAAqB,GAAG,oBAAoB,GAAG;IACzD,KAAK,EAAE,UAAU,CAAC,OAAO,sBAAsB,CAAC,CAAC;IACjD,WAAW,EAAE,CACX,IAAI,EAAE,MAAM,EACZ,OAAO,CAAC,EAAE,IAAI,CAAC,kBAAkB,EAAE,MAAM,CAAC,KACvC,OAAO,CAAC,IAAI,CAAC,CAAC;IACnB,WAAW,EAAE,CAAC,OAAO,CAAC,EAAE;QAAE,IAAI,CAAC,EAAE,MAAM,CAAA;KAAE,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5D,oBAAoB,EAAE,CAAC,OAAO,CAAC,EAAE;QAAE,IAAI,CAAC,EAAE,MAAM,CAAA;KAAE,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACrE,WAAW,EAAE,CAAC,QAAQ,EAAE,OAAO,EAAE,KAAK,IAAI,CAAC;IAC3C,WAAW,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC,iBAAiB,CAAC,CAAC;IAC1D,uBAAuB,EAAE,CAAC,MAAM,EAAE,iBAAiB,KAAK,MAAM,CAAC;CAChE,CAAC;AAEF;;GAEG;AACH,wBAAgB,eAAe,IAAI,qBAAqB,CAkDvD"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { useCallback, useSyncExternalStore } from 'react';
|
|
2
|
+
import { useNxtlinqAgentContext } from '../context/NxtlinqAgentContext';
|
|
3
|
+
/**
|
|
4
|
+
* Subscribe to {@link NxtlinqAgent} state for custom RN chat UIs.
|
|
5
|
+
*/
|
|
6
|
+
export function useNxtlinqAgent() {
|
|
7
|
+
const agent = useNxtlinqAgentContext();
|
|
8
|
+
const snapshot = useSyncExternalStore((onStoreChange) => agent.subscribe(onStoreChange), () => agent.getSnapshot(), () => agent.getSnapshot());
|
|
9
|
+
const sendMessage = useCallback((text, options) => agent.sendMessage(text, options), [agent]);
|
|
10
|
+
const loadHistory = useCallback((options) => agent.loadHistory(options), [agent]);
|
|
11
|
+
const syncVoiceTurnHistory = useCallback((options) => agent.syncVoiceTurnHistory(options), [agent]);
|
|
12
|
+
const setMessages = useCallback((messages) => agent.setMessages(messages), [agent]);
|
|
13
|
+
const postTextTts = useCallback((text) => agent.postTextTts(text), [agent]);
|
|
14
|
+
const buildTextTtsPlaybackUri = useCallback((result) => agent.buildTextTtsPlaybackUri(result), [agent]);
|
|
15
|
+
return {
|
|
16
|
+
agent,
|
|
17
|
+
...snapshot,
|
|
18
|
+
sendMessage,
|
|
19
|
+
loadHistory,
|
|
20
|
+
syncVoiceTurnHistory,
|
|
21
|
+
setMessages,
|
|
22
|
+
postTextTts,
|
|
23
|
+
buildTextTtsPlaybackUri,
|
|
24
|
+
};
|
|
25
|
+
}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import type { StartVoiceSessionOptions, VoiceGreetingOptions, VoiceSession, VoiceStatus, VoiceUserInputOptions } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
export type UseNxtlinqVoiceOptions = Partial<Omit<StartVoiceSessionOptions, 'apiKey' | 'apiSecret' | 'pseudoId'>>;
|
|
3
|
+
export type UseNxtlinqVoiceResult = {
|
|
4
|
+
voiceStatus: VoiceStatus;
|
|
5
|
+
voiceSessionId: string | null;
|
|
6
|
+
isVoiceActive: boolean;
|
|
7
|
+
startVoice: (options?: UseNxtlinqVoiceOptions) => Promise<VoiceSession>;
|
|
8
|
+
stopVoice: (reason?: string) => Promise<void>;
|
|
9
|
+
muteMic: (muted: boolean) => void;
|
|
10
|
+
interrupt: () => void;
|
|
11
|
+
getRemoteAudioStream: () => MediaStream | null;
|
|
12
|
+
getOutputAudioLevel: () => number;
|
|
13
|
+
sendVoiceUserInput: (options: VoiceUserInputOptions) => void;
|
|
14
|
+
triggerVoiceGreeting: (options: VoiceGreetingOptions, greetOptions?: {
|
|
15
|
+
waitForChannel?: boolean;
|
|
16
|
+
timeoutMs?: number;
|
|
17
|
+
}) => Promise<void>;
|
|
18
|
+
};
|
|
19
|
+
/**
|
|
20
|
+
* Voice controls for custom RN UIs. Requires `webrtcModule` on {@link NxtlinqAgentProvider}.
|
|
21
|
+
*/
|
|
22
|
+
export declare function useNxtlinqVoice(): UseNxtlinqVoiceResult;
|
|
23
|
+
//# sourceMappingURL=useNxtlinqVoice.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useNxtlinqVoice.d.ts","sourceRoot":"","sources":["../../src/hooks/useNxtlinqVoice.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,wBAAwB,EACxB,oBAAoB,EACpB,YAAY,EACZ,WAAW,EACX,qBAAqB,EACtB,MAAM,8CAA8C,CAAC;AAKtD,MAAM,MAAM,sBAAsB,GAAG,OAAO,CAC1C,IAAI,CACF,wBAAwB,EACxB,QAAQ,GAAG,WAAW,GAAG,UAAU,CACpC,CACF,CAAC;AAEF,MAAM,MAAM,qBAAqB,GAAG;IAClC,WAAW,EAAE,WAAW,CAAC;IACzB,cAAc,EAAE,MAAM,GAAG,IAAI,CAAC;IAC9B,aAAa,EAAE,OAAO,CAAC;IACvB,UAAU,EAAE,CAAC,OAAO,CAAC,EAAE,sBAAsB,KAAK,OAAO,CAAC,YAAY,CAAC,CAAC;IACxE,SAAS,EAAE,CAAC,MAAM,CAAC,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAC9C,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,IAAI,CAAC;IAClC,SAAS,EAAE,MAAM,IAAI,CAAC;IACtB,oBAAoB,EAAE,MAAM,WAAW,GAAG,IAAI,CAAC;IAC/C,mBAAmB,EAAE,MAAM,MAAM,CAAC;IAClC,kBAAkB,EAAE,CAAC,OAAO,EAAE,qBAAqB,KAAK,IAAI,CAAC;IAC7D,oBAAoB,EAAE,CACpB,OAAO,EAAE,oBAAoB,EAC7B,YAAY,CAAC,EAAE;QAAE,cAAc,CAAC,EAAE,OAAO,CAAC;QAAC,SAAS,CAAC,EAAE,MAAM,CAAA;KAAE,KAC5D,OAAO,CAAC,IAAI,CAAC,CAAC;CACpB,CAAC;AAEF;;GAEG;AACH,wBAAgB,eAAe,IAAI,qBAAqB,CA6GvD"}
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
import { VoiceNotSupportedError } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
import { useCallback, useMemo, useRef, useSyncExternalStore } from 'react';
|
|
3
|
+
import { useNxtlinqAgentContext } from '../context/NxtlinqAgentContext';
|
|
4
|
+
/**
|
|
5
|
+
* Voice controls for custom RN UIs. Requires `webrtcModule` on {@link NxtlinqAgentProvider}.
|
|
6
|
+
*/
|
|
7
|
+
export function useNxtlinqVoice() {
|
|
8
|
+
const agent = useNxtlinqAgentContext();
|
|
9
|
+
const sessionRef = useRef(null);
|
|
10
|
+
const snapshot = useSyncExternalStore((onStoreChange) => agent.subscribe(onStoreChange), () => agent.getSnapshot(), () => agent.getSnapshot());
|
|
11
|
+
const refreshSessionRef = useCallback(() => {
|
|
12
|
+
sessionRef.current = agent.getVoiceSession();
|
|
13
|
+
}, [agent]);
|
|
14
|
+
const startVoice = useCallback(async (options) => {
|
|
15
|
+
try {
|
|
16
|
+
const session = await agent.startVoice(options);
|
|
17
|
+
sessionRef.current = session;
|
|
18
|
+
return session;
|
|
19
|
+
}
|
|
20
|
+
catch (err) {
|
|
21
|
+
if (err instanceof VoiceNotSupportedError) {
|
|
22
|
+
throw new Error('Voice requires react-native-webrtc — pass webrtcModule to NxtlinqAgentProvider.');
|
|
23
|
+
}
|
|
24
|
+
throw err;
|
|
25
|
+
}
|
|
26
|
+
}, [agent]);
|
|
27
|
+
const stopVoice = useCallback(async (reason) => {
|
|
28
|
+
await agent.stopVoice(reason);
|
|
29
|
+
sessionRef.current = null;
|
|
30
|
+
}, [agent]);
|
|
31
|
+
const muteMic = useCallback((muted) => {
|
|
32
|
+
refreshSessionRef();
|
|
33
|
+
sessionRef.current?.muteMic(muted);
|
|
34
|
+
}, [refreshSessionRef]);
|
|
35
|
+
const interrupt = useCallback(() => {
|
|
36
|
+
refreshSessionRef();
|
|
37
|
+
sessionRef.current?.interrupt();
|
|
38
|
+
}, [refreshSessionRef]);
|
|
39
|
+
const getRemoteAudioStream = useCallback(() => {
|
|
40
|
+
return agent.getVoiceSession()?.getRemoteAudioStream() ?? null;
|
|
41
|
+
}, [agent]);
|
|
42
|
+
const getOutputAudioLevel = useCallback(() => {
|
|
43
|
+
refreshSessionRef();
|
|
44
|
+
return sessionRef.current?.getOutputAudioLevel() ?? agent.getOutputAudioLevel();
|
|
45
|
+
}, [refreshSessionRef, agent]);
|
|
46
|
+
const sendVoiceUserInput = useCallback((options) => {
|
|
47
|
+
refreshSessionRef();
|
|
48
|
+
if (sessionRef.current) {
|
|
49
|
+
sessionRef.current.sendVoiceUserInput(options);
|
|
50
|
+
return;
|
|
51
|
+
}
|
|
52
|
+
agent.sendVoiceUserInput(options);
|
|
53
|
+
}, [refreshSessionRef, agent]);
|
|
54
|
+
const triggerVoiceGreeting = useCallback((options, greetOptions) => agent.triggerVoiceGreeting(options, greetOptions), [agent]);
|
|
55
|
+
return useMemo(() => ({
|
|
56
|
+
voiceStatus: snapshot.voiceStatus,
|
|
57
|
+
voiceSessionId: snapshot.voiceSessionId,
|
|
58
|
+
isVoiceActive: snapshot.voiceSessionId != null,
|
|
59
|
+
startVoice,
|
|
60
|
+
stopVoice,
|
|
61
|
+
muteMic,
|
|
62
|
+
interrupt,
|
|
63
|
+
getRemoteAudioStream,
|
|
64
|
+
getOutputAudioLevel,
|
|
65
|
+
sendVoiceUserInput,
|
|
66
|
+
triggerVoiceGreeting,
|
|
67
|
+
}), [
|
|
68
|
+
snapshot.voiceStatus,
|
|
69
|
+
snapshot.voiceSessionId,
|
|
70
|
+
startVoice,
|
|
71
|
+
stopVoice,
|
|
72
|
+
muteMic,
|
|
73
|
+
interrupt,
|
|
74
|
+
getRemoteAudioStream,
|
|
75
|
+
getOutputAudioLevel,
|
|
76
|
+
sendVoiceUserInput,
|
|
77
|
+
triggerVoiceGreeting,
|
|
78
|
+
]);
|
|
79
|
+
}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export { createNxtlinqAgentRN, type CreateNxtlinqAgentRNOptions, } from './createNxtlinqAgent';
|
|
2
|
+
export { NxtlinqAgentProvider, useNxtlinqAgentContext, type NxtlinqAgentProviderProps, type AgentConfig, } from './context/NxtlinqAgentContext';
|
|
3
|
+
export { useNxtlinqAgent, type UseNxtlinqAgentResult } from './hooks/useNxtlinqAgent';
|
|
4
|
+
export { useNxtlinqVoice, type UseNxtlinqVoiceResult, type UseNxtlinqVoiceOptions } from './hooks/useNxtlinqVoice';
|
|
5
|
+
export { createAsyncStoragePort, type AsyncStorageLike, } from './ports/createAsyncStoragePort';
|
|
6
|
+
export { createRNHttpPort } from './ports/createRNHttpPort';
|
|
7
|
+
export { createRNPlatformPorts, type CreateRNPlatformPortsOptions, } from './ports/createRNPlatformPorts';
|
|
8
|
+
export { createRNWebRTCPort, type RNWebRTCModule, } from './ports/createRNWebRTCPort';
|
|
9
|
+
export { fetchUriAsDataUriAttachment, uriToVoiceImageAttachment, } from './utils/fetchUriAsDataUri';
|
|
10
|
+
export { ensureRecordAudioPermission, MicrophonePermissionDeniedError, } from './utils/ensureRecordAudioPermission';
|
|
11
|
+
export { ensureIOSAudioSessionForVoiceCapture, markIOSAudioSessionReady, markIOSVoiceCaptureCompleted, notifyIOSVoiceSessionEnded, setIOSAudioSessionPrewarmHandler, waitForIOSAudioSessionReady, waitForIOSVoiceCaptureRelease, } from './utils/iosAudioSessionReady';
|
|
12
|
+
export type { Message, Attachment, AgentResponse, AgentConfig as CoreAgentConfig, SendMessageOptions, NxtlinqAgentSnapshot, ToolUse, StartVoiceSessionOptions, VoiceSession, VoiceStatus, VoiceTranscriptEvent, VoiceDoneEvent, VoiceUserInputOptions, VoiceGreetingOptions, } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
13
|
+
export { NxtlinqAgent, setApiHosts, startVoiceSessionWithPort, createBrowserWebRTCPort, VoiceNotSupportedError, mapServerHistoryToMessages, appendServerHistoryIntoMessages, STORAGE_KEYS, } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
14
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,oBAAoB,EACpB,KAAK,2BAA2B,GACjC,MAAM,sBAAsB,CAAC;AAE9B,OAAO,EACL,oBAAoB,EACpB,sBAAsB,EACtB,KAAK,yBAAyB,EAC9B,KAAK,WAAW,GACjB,MAAM,+BAA+B,CAAC;AAEvC,OAAO,EAAE,eAAe,EAAE,KAAK,qBAAqB,EAAE,MAAM,yBAAyB,CAAC;AACtF,OAAO,EAAE,eAAe,EAAE,KAAK,qBAAqB,EAAE,KAAK,sBAAsB,EAAE,MAAM,yBAAyB,CAAC;AAEnH,OAAO,EACL,sBAAsB,EACtB,KAAK,gBAAgB,GACtB,MAAM,gCAAgC,CAAC;AACxC,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAC5D,OAAO,EACL,qBAAqB,EACrB,KAAK,4BAA4B,GAClC,MAAM,+BAA+B,CAAC;AACvC,OAAO,EACL,kBAAkB,EAClB,KAAK,cAAc,GACpB,MAAM,4BAA4B,CAAC;AACpC,OAAO,EACL,2BAA2B,EAC3B,yBAAyB,GAC1B,MAAM,2BAA2B,CAAC;AACnC,OAAO,EACL,2BAA2B,EAC3B,+BAA+B,GAChC,MAAM,qCAAqC,CAAC;AAC7C,OAAO,EACL,oCAAoC,EACpC,wBAAwB,EACxB,4BAA4B,EAC5B,0BAA0B,EAC1B,gCAAgC,EAChC,2BAA2B,EAC3B,6BAA6B,GAC9B,MAAM,8BAA8B,CAAC;AAGtC,YAAY,EACV,OAAO,EACP,UAAU,EACV,aAAa,EACb,WAAW,IAAI,eAAe,EAC9B,kBAAkB,EAClB,oBAAoB,EACpB,OAAO,EACP,wBAAwB,EACxB,YAAY,EACZ,WAAW,EACX,oBAAoB,EACpB,cAAc,EACd,qBAAqB,EACrB,oBAAoB,GACrB,MAAM,8CAA8C,CAAC;AAEtD,OAAO,EACL,YAAY,EACZ,WAAW,EACX,yBAAyB,EACzB,uBAAuB,EACvB,sBAAsB,EACtB,0BAA0B,EAC1B,+BAA+B,EAC/B,YAAY,GACb,MAAM,8CAA8C,CAAC"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export { createNxtlinqAgentRN, } from './createNxtlinqAgent';
|
|
2
|
+
export { NxtlinqAgentProvider, useNxtlinqAgentContext, } from './context/NxtlinqAgentContext';
|
|
3
|
+
export { useNxtlinqAgent } from './hooks/useNxtlinqAgent';
|
|
4
|
+
export { useNxtlinqVoice } from './hooks/useNxtlinqVoice';
|
|
5
|
+
export { createAsyncStoragePort, } from './ports/createAsyncStoragePort';
|
|
6
|
+
export { createRNHttpPort } from './ports/createRNHttpPort';
|
|
7
|
+
export { createRNPlatformPorts, } from './ports/createRNPlatformPorts';
|
|
8
|
+
export { createRNWebRTCPort, } from './ports/createRNWebRTCPort';
|
|
9
|
+
export { fetchUriAsDataUriAttachment, uriToVoiceImageAttachment, } from './utils/fetchUriAsDataUri';
|
|
10
|
+
export { ensureRecordAudioPermission, MicrophonePermissionDeniedError, } from './utils/ensureRecordAudioPermission';
|
|
11
|
+
export { ensureIOSAudioSessionForVoiceCapture, markIOSAudioSessionReady, markIOSVoiceCaptureCompleted, notifyIOSVoiceSessionEnded, setIOSAudioSessionPrewarmHandler, waitForIOSAudioSessionReady, waitForIOSVoiceCaptureRelease, } from './utils/iosAudioSessionReady';
|
|
12
|
+
export { NxtlinqAgent, setApiHosts, startVoiceSessionWithPort, createBrowserWebRTCPort, VoiceNotSupportedError, mapServerHistoryToMessages, appendServerHistoryIntoMessages, STORAGE_KEYS, } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { StoragePort } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
/** Minimal AsyncStorage surface (matches @react-native-async-storage/async-storage). */
|
|
3
|
+
export type AsyncStorageLike = {
|
|
4
|
+
getItem(key: string): Promise<string | null>;
|
|
5
|
+
setItem(key: string, value: string): Promise<void>;
|
|
6
|
+
removeItem(key: string): Promise<void>;
|
|
7
|
+
};
|
|
8
|
+
export declare function createAsyncStoragePort(storage: AsyncStorageLike): StoragePort;
|
|
9
|
+
//# sourceMappingURL=createAsyncStoragePort.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createAsyncStoragePort.d.ts","sourceRoot":"","sources":["../../src/ports/createAsyncStoragePort.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,8CAA8C,CAAC;AAEhF,wFAAwF;AACxF,MAAM,MAAM,gBAAgB,GAAG;IAC7B,OAAO,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC;IAC7C,OAAO,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACnD,UAAU,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CACxC,CAAC;AAEF,wBAAgB,sBAAsB,CAAC,OAAO,EAAE,gBAAgB,GAAG,WAAW,CAM7E"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createRNHttpPort.d.ts","sourceRoot":"","sources":["../../src/ports/createRNHttpPort.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,8CAA8C,CAAC;AAE7E,+DAA+D;AAC/D,wBAAgB,gBAAgB,CAAC,SAAS,GAAE,OAAO,KAAwB,GAAG,QAAQ,CAOrF"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
/** React Native global `fetch` (same signature as browser). */
|
|
2
|
+
export function createRNHttpPort(fetchImpl = globalThis.fetch) {
|
|
3
|
+
if (!fetchImpl) {
|
|
4
|
+
throw new Error('fetch is not available — pass a fetch implementation to createRNHttpPort');
|
|
5
|
+
}
|
|
6
|
+
return {
|
|
7
|
+
fetch: (input, init) => fetchImpl(input, init),
|
|
8
|
+
};
|
|
9
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { PlatformPorts, WebRTCPort } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
import { type AsyncStorageLike } from './createAsyncStoragePort';
|
|
3
|
+
import { type RNWebRTCModule } from './createRNWebRTCPort';
|
|
4
|
+
export type CreateRNPlatformPortsOptions = {
|
|
5
|
+
storage: AsyncStorageLike;
|
|
6
|
+
fetchImpl?: typeof fetch;
|
|
7
|
+
getTimezone?: () => string;
|
|
8
|
+
/** Pass `react-native-webrtc` exports to enable voice (M2). */
|
|
9
|
+
webrtcModule?: RNWebRTCModule;
|
|
10
|
+
/** Pre-built port (overrides `webrtcModule`). */
|
|
11
|
+
webrtc?: WebRTCPort;
|
|
12
|
+
};
|
|
13
|
+
export declare function createRNPlatformPorts(options: CreateRNPlatformPortsOptions): PlatformPorts;
|
|
14
|
+
//# sourceMappingURL=createRNPlatformPorts.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createRNPlatformPorts.d.ts","sourceRoot":"","sources":["../../src/ports/createRNPlatformPorts.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,8CAA8C,CAAC;AAC9F,OAAO,EAA0B,KAAK,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAEzF,OAAO,EAAsB,KAAK,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAE/E,MAAM,MAAM,4BAA4B,GAAG;IACzC,OAAO,EAAE,gBAAgB,CAAC;IAC1B,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;IACzB,WAAW,CAAC,EAAE,MAAM,MAAM,CAAC;IAC3B,+DAA+D;IAC/D,YAAY,CAAC,EAAE,cAAc,CAAC;IAC9B,iDAAiD;IACjD,MAAM,CAAC,EAAE,UAAU,CAAC;CACrB,CAAC;AAEF,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,4BAA4B,GACpC,aAAa,CAmBf"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { createAsyncStoragePort } from './createAsyncStoragePort';
|
|
2
|
+
import { createRNHttpPort } from './createRNHttpPort';
|
|
3
|
+
import { createRNWebRTCPort } from './createRNWebRTCPort';
|
|
4
|
+
export function createRNPlatformPorts(options) {
|
|
5
|
+
const webrtc = options.webrtc
|
|
6
|
+
?? (options.webrtcModule ? createRNWebRTCPort(options.webrtcModule) : undefined);
|
|
7
|
+
return {
|
|
8
|
+
storage: createAsyncStoragePort(options.storage),
|
|
9
|
+
http: createRNHttpPort(options.fetchImpl),
|
|
10
|
+
webrtc,
|
|
11
|
+
getTimezone: options.getTimezone
|
|
12
|
+
?? (() => {
|
|
13
|
+
try {
|
|
14
|
+
return Intl.DateTimeFormat().resolvedOptions().timeZone;
|
|
15
|
+
}
|
|
16
|
+
catch {
|
|
17
|
+
return 'UTC';
|
|
18
|
+
}
|
|
19
|
+
}),
|
|
20
|
+
};
|
|
21
|
+
}
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
import type { IceServerConfig, MediaStreamLike, PeerConnectionLike, WebRTCPort } from '@bytexbyte/nxtlinq-ai-agent-core-development';
|
|
2
|
+
/** Subset of `react-native-webrtc` exports required for voice. */
|
|
3
|
+
export type RNWebRTCModule = {
|
|
4
|
+
RTCPeerConnection: new (config: {
|
|
5
|
+
iceServers: IceServerConfig[];
|
|
6
|
+
}) => RNPeerConnection;
|
|
7
|
+
mediaDevices: {
|
|
8
|
+
getUserMedia(constraints: {
|
|
9
|
+
audio: boolean;
|
|
10
|
+
video?: boolean;
|
|
11
|
+
}): Promise<RNMediaStream>;
|
|
12
|
+
};
|
|
13
|
+
};
|
|
14
|
+
type RNMediaStream = MediaStreamLike & {
|
|
15
|
+
getAudioTracks(): Array<{
|
|
16
|
+
enabled: boolean;
|
|
17
|
+
readyState?: string;
|
|
18
|
+
stop(): void;
|
|
19
|
+
}>;
|
|
20
|
+
};
|
|
21
|
+
type RNDataChannel = {
|
|
22
|
+
label?: string;
|
|
23
|
+
readyState: string;
|
|
24
|
+
onopen: (() => void) | null;
|
|
25
|
+
onmessage: ((event: {
|
|
26
|
+
data: string;
|
|
27
|
+
}) => void) | null;
|
|
28
|
+
onclose: (() => void) | null;
|
|
29
|
+
send(data: string): void;
|
|
30
|
+
close(): void;
|
|
31
|
+
addEventListener?: (type: 'open' | 'message' | 'close', listener: (event?: {
|
|
32
|
+
data?: string;
|
|
33
|
+
}) => void) => void;
|
|
34
|
+
removeEventListener?: (type: 'open' | 'message' | 'close', listener: (event?: {
|
|
35
|
+
data?: string;
|
|
36
|
+
}) => void) => void;
|
|
37
|
+
};
|
|
38
|
+
type RNPeerConnection = {
|
|
39
|
+
connectionState: string;
|
|
40
|
+
iceConnectionState: string;
|
|
41
|
+
iceGatheringState: string;
|
|
42
|
+
localDescription: {
|
|
43
|
+
sdp?: string;
|
|
44
|
+
type?: string;
|
|
45
|
+
} | null;
|
|
46
|
+
onconnectionstatechange: (() => void) | null;
|
|
47
|
+
oniceconnectionstatechange: (() => void) | null;
|
|
48
|
+
ontrack: ((event: {
|
|
49
|
+
streams: RNMediaStream[];
|
|
50
|
+
track: {
|
|
51
|
+
kind: string;
|
|
52
|
+
};
|
|
53
|
+
}) => void) | null;
|
|
54
|
+
ondatachannel: ((event: {
|
|
55
|
+
channel: RNDataChannel;
|
|
56
|
+
}) => void) | null;
|
|
57
|
+
addEventListener(type: string, listener: (...args: unknown[]) => void): void;
|
|
58
|
+
removeEventListener(type: string, listener: (...args: unknown[]) => void): void;
|
|
59
|
+
createDataChannel(label: string): RNDataChannel;
|
|
60
|
+
addTrack(track: unknown, stream: RNMediaStream): void;
|
|
61
|
+
createOffer(): Promise<{
|
|
62
|
+
sdp?: string;
|
|
63
|
+
type?: string;
|
|
64
|
+
}>;
|
|
65
|
+
setLocalDescription(desc: unknown): Promise<void>;
|
|
66
|
+
setRemoteDescription(desc: unknown): Promise<void>;
|
|
67
|
+
close(): void;
|
|
68
|
+
};
|
|
69
|
+
export type RNPeerConnectionLike = PeerConnectionLike & {
|
|
70
|
+
__nativePc: RNPeerConnection;
|
|
71
|
+
};
|
|
72
|
+
/**
|
|
73
|
+
* React Native WebRTC adapter — pass exports from `react-native-webrtc`.
|
|
74
|
+
*
|
|
75
|
+
* @example
|
|
76
|
+
* import { RTCPeerConnection, mediaDevices } from 'react-native-webrtc';
|
|
77
|
+
* const webrtc = createRNWebRTCPort({ RTCPeerConnection, mediaDevices });
|
|
78
|
+
*/
|
|
79
|
+
export declare function createRNWebRTCPort(module: RNWebRTCModule): WebRTCPort;
|
|
80
|
+
export {};
|
|
81
|
+
//# sourceMappingURL=createRNWebRTCPort.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"createRNWebRTCPort.d.ts","sourceRoot":"","sources":["../../src/ports/createRNWebRTCPort.ts"],"names":[],"mappings":"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"}
|