@dora-cell/sdk-react 0.1.1-beta.26 → 0.1.1-beta.30
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/README.md +55 -293
- package/dist/index.d.mts +1 -27
- package/dist/index.d.ts +1 -27
- package/dist/index.js +156 -119
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +156 -119
- package/dist/index.mjs.map +1 -1
- package/dist/styles.css +3 -0
- package/package.json +18 -7
package/README.md
CHANGED
|
@@ -5,10 +5,9 @@ React hooks and components for the Dora Cell VoIP SDK.
|
|
|
5
5
|
## Features
|
|
6
6
|
|
|
7
7
|
✅ **React Hooks** - Easy-to-use hooks for call management
|
|
8
|
-
✅ **Context Provider** - Simple setup with DoraCellProvider
|
|
9
|
-
✅ **
|
|
10
|
-
✅ **Auto state management** - Automatic call state and connection tracking
|
|
11
|
-
✅ **React 18 & 19 compatible** - Works with latest React versions
|
|
8
|
+
✅ **Context Provider** - Simple setup with `DoraCellProvider`
|
|
9
|
+
✅ **Pre-built UI** - Includes `Dialpad` and `CallInterface` components
|
|
10
|
+
✅ **Auto state management** - Automatic call state and connection tracking
|
|
12
11
|
|
|
13
12
|
## Installation
|
|
14
13
|
|
|
@@ -22,357 +21,120 @@ pnpm add @dora-cell/sdk @dora-cell/sdk-react jssip
|
|
|
22
21
|
|
|
23
22
|
## Quick Start
|
|
24
23
|
|
|
25
|
-
### Authentication
|
|
26
|
-
|
|
27
|
-
You can authenticate using either an API Token (recommended for production) or Direct SIP Credentials (useful for testing/development).
|
|
28
|
-
|
|
29
|
-
#### Option 1: API Token (Production)
|
|
30
|
-
The SDK will fetch SIP credentials from your backend using the token.
|
|
31
|
-
```tsx
|
|
32
|
-
const config = {
|
|
33
|
-
auth: {
|
|
34
|
-
type: 'api-token',
|
|
35
|
-
apiToken: 'YOUR_API_TOKEN',
|
|
36
|
-
// apiBaseUrl: 'https://api.your-backend.com' (Optional)
|
|
37
|
-
}
|
|
38
|
-
};
|
|
39
|
-
```
|
|
40
|
-
|
|
41
|
-
#### Option 2: Extension Authentication (Plug & Play)
|
|
42
|
-
You can connect using just your extension number. The SDK handles the server configuration automatically.
|
|
43
|
-
|
|
44
|
-
```tsx
|
|
45
|
-
const config = {
|
|
46
|
-
auth: {
|
|
47
|
-
type: 'extension',
|
|
48
|
-
extension: '1000',
|
|
49
|
-
// password: '...' // Optional override (default: 1234)
|
|
50
|
-
}
|
|
51
|
-
};
|
|
52
|
-
```
|
|
53
|
-
|
|
54
24
|
### 1. Wrap your app with DoraCellProvider
|
|
55
25
|
|
|
56
26
|
```tsx
|
|
57
|
-
import { DoraCellProvider } from
|
|
27
|
+
import { DoraCellProvider } from "@dora-cell/sdk-react";
|
|
58
28
|
|
|
59
29
|
function App() {
|
|
60
30
|
return (
|
|
61
31
|
<DoraCellProvider
|
|
62
32
|
config={{
|
|
63
33
|
auth: {
|
|
64
|
-
type:
|
|
65
|
-
|
|
66
|
-
apiBaseUrl: 'https://api.usedora.com'
|
|
34
|
+
type: "extension",
|
|
35
|
+
extension: "1001",
|
|
67
36
|
},
|
|
68
|
-
debug: true
|
|
37
|
+
debug: true,
|
|
69
38
|
}}
|
|
39
|
+
autoInitialize={true}
|
|
70
40
|
>
|
|
71
|
-
<
|
|
41
|
+
<MainApp />
|
|
72
42
|
</DoraCellProvider>
|
|
73
43
|
);
|
|
74
44
|
}
|
|
75
45
|
```
|
|
76
46
|
|
|
77
|
-
### 2. Use
|
|
47
|
+
### 2. Use Hooks in your components
|
|
78
48
|
|
|
79
49
|
```tsx
|
|
80
|
-
import { useCall, useConnectionStatus } from
|
|
81
|
-
|
|
82
|
-
function
|
|
83
|
-
const {
|
|
84
|
-
|
|
85
|
-
hangup,
|
|
86
|
-
toggleMute,
|
|
87
|
-
callStatus,
|
|
88
|
-
callDuration,
|
|
89
|
-
isMuted,
|
|
90
|
-
currentCall
|
|
91
|
-
} = useCall();
|
|
92
|
-
|
|
93
|
-
const { isConnected, status } = useConnectionStatus();
|
|
94
|
-
const [number, setNumber] = useState('');
|
|
95
|
-
|
|
96
|
-
const handleCall = async () => {
|
|
97
|
-
try {
|
|
98
|
-
await call(number);
|
|
99
|
-
} catch (error) {
|
|
100
|
-
console.error('Call failed:', error);
|
|
101
|
-
}
|
|
102
|
-
};
|
|
50
|
+
import { useCall, useConnectionStatus } from "@dora-cell/sdk-react";
|
|
51
|
+
|
|
52
|
+
function CallManager() {
|
|
53
|
+
const { call, callStatus, callDuration } = useCall();
|
|
54
|
+
const { isConnected } = useConnectionStatus();
|
|
103
55
|
|
|
104
56
|
return (
|
|
105
57
|
<div>
|
|
106
|
-
<p>Status: {isConnected ?
|
|
107
|
-
|
|
108
|
-
{
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
value={number}
|
|
112
|
-
onChange={(e) => setNumber(e.target.value)}
|
|
113
|
-
placeholder="Enter phone number"
|
|
114
|
-
/>
|
|
115
|
-
<button onClick={handleCall} disabled={!isConnected}>
|
|
116
|
-
Call
|
|
117
|
-
</button>
|
|
118
|
-
</>
|
|
119
|
-
)}
|
|
120
|
-
|
|
121
|
-
{callStatus === 'ongoing' && (
|
|
122
|
-
<>
|
|
123
|
-
<p>Call with: {currentCall?.remoteNumber}</p>
|
|
124
|
-
<p>Duration: {callDuration}</p>
|
|
125
|
-
<button onClick={toggleMute}>
|
|
126
|
-
{isMuted ? 'Unmute' : 'Mute'}
|
|
127
|
-
</button>
|
|
128
|
-
<button onClick={hangup}>Hang Up</button>
|
|
129
|
-
</>
|
|
130
|
-
)}
|
|
131
|
-
|
|
132
|
-
{callStatus === 'ringing' && (
|
|
133
|
-
<p>Ringing...</p>
|
|
134
|
-
)}
|
|
58
|
+
<p>Status: {isConnected ? "Ready" : "Connecting..."}</p>
|
|
59
|
+
{callStatus === "ongoing" && <p>Talking: {callDuration}</p>}
|
|
60
|
+
<button onClick={() => call("08012345678")} disabled={!isConnected}>
|
|
61
|
+
Call Now
|
|
62
|
+
</button>
|
|
135
63
|
</div>
|
|
136
64
|
);
|
|
137
65
|
}
|
|
138
66
|
```
|
|
139
67
|
|
|
140
|
-
##
|
|
68
|
+
## UI Components
|
|
141
69
|
|
|
142
|
-
|
|
70
|
+
We provide high-level components that match the Dora Cell design language.
|
|
143
71
|
|
|
144
|
-
|
|
72
|
+
### `CallInterface`
|
|
145
73
|
|
|
146
|
-
|
|
147
|
-
<DoraCellProvider
|
|
148
|
-
config={{
|
|
149
|
-
auth: {
|
|
150
|
-
type: 'api-token',
|
|
151
|
-
apiToken: string,
|
|
152
|
-
apiBaseUrl?: string
|
|
153
|
-
},
|
|
154
|
-
turnServers?: RTCIceServer[],
|
|
155
|
-
debug?: boolean,
|
|
156
|
-
autoSelectExtension?: boolean
|
|
157
|
-
}}
|
|
158
|
-
>
|
|
159
|
-
{children}
|
|
160
|
-
</DoraCellProvider>
|
|
161
|
-
```
|
|
162
|
-
|
|
163
|
-
### useCall()
|
|
164
|
-
|
|
165
|
-
Hook for managing calls.
|
|
166
|
-
|
|
167
|
-
```typescript
|
|
168
|
-
const {
|
|
169
|
-
// Methods
|
|
170
|
-
call: (phoneNumber: string) => Promise<void>,
|
|
171
|
-
hangup: () => void,
|
|
172
|
-
answerCall: () => void,
|
|
173
|
-
toggleMute: () => void,
|
|
174
|
-
|
|
175
|
-
// State
|
|
176
|
-
callStatus: 'idle' | 'ringing' | 'ongoing',
|
|
177
|
-
callDuration: string, // Formatted as "MM:SS"
|
|
178
|
-
isMuted: boolean,
|
|
179
|
-
currentCall: Call | null,
|
|
180
|
-
error: Error | null
|
|
181
|
-
} = useCall();
|
|
182
|
-
```
|
|
183
|
-
|
|
184
|
-
**Methods:**
|
|
185
|
-
- `call(phoneNumber)` - Make an outbound call
|
|
186
|
-
- `hangup()` - End the current call
|
|
187
|
-
- `answerCall()` - Answer an incoming call
|
|
188
|
-
- `toggleMute()` - Toggle mute/unmute
|
|
189
|
-
|
|
190
|
-
**State:**
|
|
191
|
-
- `callStatus` - Current call status
|
|
192
|
-
- `callDuration` - Formatted call duration (e.g., "01:23")
|
|
193
|
-
- `isMuted` - Whether the call is muted
|
|
194
|
-
- `currentCall` - Current call object with details
|
|
195
|
-
- `error` - Any call-related errors
|
|
196
|
-
|
|
197
|
-
### useConnectionStatus()
|
|
198
|
-
|
|
199
|
-
Hook for monitoring connection status.
|
|
200
|
-
|
|
201
|
-
```typescript
|
|
202
|
-
const {
|
|
203
|
-
isConnected: boolean,
|
|
204
|
-
status: 'disconnected' | 'connecting' | 'connected' | 'error',
|
|
205
|
-
error: Error | null
|
|
206
|
-
} = useConnectionStatus();
|
|
207
|
-
```
|
|
208
|
-
|
|
209
|
-
### useDoraCell()
|
|
210
|
-
|
|
211
|
-
Access the underlying SDK instance directly.
|
|
212
|
-
|
|
213
|
-
```typescript
|
|
214
|
-
const sdk = useDoraCell();
|
|
215
|
-
|
|
216
|
-
// Use SDK methods directly
|
|
217
|
-
sdk.getExtensions();
|
|
218
|
-
sdk.on('call:incoming', (call) => {
|
|
219
|
-
console.log('Incoming call from:', call.remoteNumber);
|
|
220
|
-
});
|
|
221
|
-
```
|
|
222
|
-
|
|
223
|
-
### UI Components
|
|
224
|
-
|
|
225
|
-
The SDK includes pre-built UI components for typical call flows.
|
|
226
|
-
|
|
227
|
-
#### CallInterface
|
|
228
|
-
A complete active call modal that handles ringing, connecting, and ongoing call states.
|
|
74
|
+
A slide-over interface that handles the entire call lifecycle (Ringing, Connecting, Ongoing, Mute controls).
|
|
229
75
|
|
|
230
76
|
```tsx
|
|
231
|
-
import { CallInterface } from
|
|
77
|
+
import { CallInterface } from "@dora-cell/sdk-react";
|
|
232
78
|
|
|
233
|
-
function
|
|
79
|
+
function Dashboard() {
|
|
234
80
|
const [isOpen, setIsOpen] = useState(false);
|
|
235
81
|
|
|
236
82
|
return (
|
|
237
83
|
<>
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
onOpenChange={setIsOpen}
|
|
241
|
-
onCallEnded={() => console.log('Call ended')}
|
|
242
|
-
/>
|
|
84
|
+
{/* This should be rendered globally to handle incoming calls */}
|
|
85
|
+
<CallInterface isOpen={isOpen} onOpenChange={setIsOpen} />
|
|
243
86
|
</>
|
|
244
87
|
);
|
|
245
88
|
}
|
|
246
89
|
```
|
|
247
90
|
|
|
248
|
-
|
|
249
|
-
|
|
91
|
+
### `Dialpad`
|
|
92
|
+
|
|
93
|
+
A flexible keypad for entering numbers and initiating calls.
|
|
250
94
|
|
|
251
95
|
```tsx
|
|
252
|
-
import { Dialpad } from
|
|
96
|
+
import { Dialpad } from "@dora-cell/sdk-react";
|
|
253
97
|
|
|
254
|
-
function
|
|
98
|
+
function DialerModal() {
|
|
255
99
|
return (
|
|
256
|
-
<Dialpad
|
|
257
|
-
|
|
258
|
-
|
|
100
|
+
<Dialpad
|
|
101
|
+
showKeys={true}
|
|
102
|
+
onCallInitiated={(number) => console.log("Placing call to:", number)}
|
|
259
103
|
/>
|
|
260
104
|
);
|
|
261
105
|
}
|
|
262
106
|
```
|
|
263
107
|
|
|
264
|
-
##
|
|
265
|
-
|
|
266
|
-
### Handling Incoming Calls
|
|
267
|
-
|
|
268
|
-
```tsx
|
|
269
|
-
function IncomingCallHandler() {
|
|
270
|
-
const { currentCall, answerCall, hangup, callStatus } = useCall();
|
|
271
|
-
const sdk = useDoraCell();
|
|
272
|
-
|
|
273
|
-
useEffect(() => {
|
|
274
|
-
const handleIncoming = (call) => {
|
|
275
|
-
// Show notification or UI for incoming call
|
|
276
|
-
console.log('Incoming call from:', call.remoteNumber);
|
|
277
|
-
};
|
|
278
|
-
|
|
279
|
-
sdk.on('call:incoming', handleIncoming);
|
|
280
|
-
return () => sdk.off('call:incoming', handleIncoming);
|
|
281
|
-
}, [sdk]);
|
|
282
|
-
|
|
283
|
-
if (callStatus === 'ringing' && currentCall?.direction === 'inbound') {
|
|
284
|
-
return (
|
|
285
|
-
<div>
|
|
286
|
-
<p>Incoming call from {currentCall.remoteNumber}</p>
|
|
287
|
-
<button onClick={answerCall}>Answer</button>
|
|
288
|
-
<button onClick={hangup}>Decline</button>
|
|
289
|
-
</div>
|
|
290
|
-
);
|
|
291
|
-
}
|
|
292
|
-
|
|
293
|
-
return null;
|
|
294
|
-
}
|
|
295
|
-
```
|
|
296
|
-
|
|
297
|
-
### Custom Extension Selection
|
|
108
|
+
## API Reference
|
|
298
109
|
|
|
299
|
-
|
|
300
|
-
function CallWithExtension() {
|
|
301
|
-
const sdk = useDoraCell();
|
|
302
|
-
const [selectedExtension, setSelectedExtension] = useState('');
|
|
110
|
+
### `useCall()`
|
|
303
111
|
|
|
304
|
-
|
|
112
|
+
Returns methods and state for the active call.
|
|
305
113
|
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
114
|
+
- `call(number)`: Initiate a call.
|
|
115
|
+
- `hangup()`: End current call.
|
|
116
|
+
- `answerCall()`: Answer incoming call.
|
|
117
|
+
- `toggleMute()`: Toggle microphone.
|
|
118
|
+
- `callStatus`: `'idle' | 'connecting' | 'ringing' | 'ongoing' | 'ended'`.
|
|
119
|
+
- `callDuration`: Formatted string `"00:00"`.
|
|
120
|
+
- `isMuted`: Boolean state.
|
|
309
121
|
|
|
310
|
-
|
|
311
|
-
<div>
|
|
312
|
-
<select
|
|
313
|
-
value={selectedExtension}
|
|
314
|
-
onChange={(e) => setSelectedExtension(e.target.value)}
|
|
315
|
-
>
|
|
316
|
-
{extensions.map(ext => (
|
|
317
|
-
<option key={ext} value={ext}>{ext}</option>
|
|
318
|
-
))}
|
|
319
|
-
</select>
|
|
320
|
-
{/* Rest of your call UI */}
|
|
321
|
-
</div>
|
|
322
|
-
);
|
|
323
|
-
}
|
|
324
|
-
```
|
|
122
|
+
### `useConnectionStatus()`
|
|
325
123
|
|
|
326
|
-
|
|
124
|
+
Returns the SIP registration state.
|
|
327
125
|
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
const [number, setNumber] = useState('');
|
|
332
|
-
|
|
333
|
-
const handleCall = async () => {
|
|
334
|
-
try {
|
|
335
|
-
await call(number);
|
|
336
|
-
} catch (err) {
|
|
337
|
-
console.error('Call failed:', err);
|
|
338
|
-
// Show error to user
|
|
339
|
-
}
|
|
340
|
-
};
|
|
126
|
+
- `isConnected`: `true` when registered and ready.
|
|
127
|
+
- `connectionStatus`: `'disconnected' | 'connecting' | 'connected' | 'registered' | 'registrationFailed'`.
|
|
128
|
+
- `error`: Any connection error object.
|
|
341
129
|
|
|
342
|
-
|
|
343
|
-
<div>
|
|
344
|
-
{error && <div className="error">{error.message}</div>}
|
|
345
|
-
{/* Rest of your UI */}
|
|
346
|
-
</div>
|
|
347
|
-
);
|
|
348
|
-
}
|
|
349
|
-
```
|
|
350
|
-
|
|
351
|
-
## TypeScript Support
|
|
130
|
+
## Styling
|
|
352
131
|
|
|
353
|
-
|
|
132
|
+
The components use Tailwind CSS internally. You can import our styles in your main entry file:
|
|
354
133
|
|
|
355
|
-
```
|
|
356
|
-
import
|
|
357
|
-
import type { DoraCellConfig } from '@dora-cell/sdk-react';
|
|
134
|
+
```javascript
|
|
135
|
+
import "@dora-cell/sdk-react/dist/styles.css";
|
|
358
136
|
```
|
|
359
137
|
|
|
360
|
-
## Examples
|
|
361
|
-
|
|
362
|
-
See the `/examples` directory in the main repository for complete working examples:
|
|
363
|
-
- `react-app/` - React application with hooks
|
|
364
|
-
- `nextjs-app/` - Next.js application
|
|
365
|
-
|
|
366
|
-
## Requirements
|
|
367
|
-
|
|
368
|
-
- React 18.0.0 or higher (including React 19)
|
|
369
|
-
- @dora-cell/sdk (peer dependency)
|
|
370
|
-
- jssip (peer dependency)
|
|
371
|
-
|
|
372
138
|
## License
|
|
373
139
|
|
|
374
140
|
MIT
|
|
375
|
-
|
|
376
|
-
## Related Packages
|
|
377
|
-
|
|
378
|
-
- [@dora-cell/sdk](https://www.npmjs.com/package/@dora-cell/sdk) - Core VoIP SDK
|
package/dist/index.d.mts
CHANGED
|
@@ -3,45 +3,18 @@ import React from 'react';
|
|
|
3
3
|
import { DoraCellConfig, CallStatus, Call, ConnectionStatus, DoraCell } from '@dora-cell/sdk';
|
|
4
4
|
|
|
5
5
|
interface CallInterfaceProps {
|
|
6
|
-
/**
|
|
7
|
-
* Whether the interface is open/visible
|
|
8
|
-
*/
|
|
9
6
|
isOpen?: boolean;
|
|
10
|
-
/**
|
|
11
|
-
* Callback when visibility changes
|
|
12
|
-
*/
|
|
13
7
|
onOpenChange?: (open: boolean) => void;
|
|
14
|
-
/**
|
|
15
|
-
* Callback when call ends (useful for invalidating queries)
|
|
16
|
-
*/
|
|
17
8
|
onCallEnded?: () => void;
|
|
18
|
-
/**
|
|
19
|
-
* Custom maximize icon component
|
|
20
|
-
*/
|
|
21
9
|
maximizeIcon?: React.ReactNode;
|
|
22
|
-
/**
|
|
23
|
-
* Custom minimize icon component
|
|
24
|
-
*/
|
|
25
10
|
minimizeIcon?: React.ReactNode;
|
|
26
11
|
}
|
|
27
12
|
declare function CallInterface({ isOpen, onOpenChange, onCallEnded, maximizeIcon, minimizeIcon, }: CallInterfaceProps): react_jsx_runtime.JSX.Element | null;
|
|
28
13
|
|
|
29
14
|
interface DialpadProps {
|
|
30
|
-
/**
|
|
31
|
-
* Callback when call is initiated
|
|
32
|
-
*/
|
|
33
15
|
onCallInitiated?: (number: string) => void;
|
|
34
|
-
/**
|
|
35
|
-
* Initial number to populate
|
|
36
|
-
*/
|
|
37
16
|
initialNumber?: string;
|
|
38
|
-
/**
|
|
39
|
-
* Whether to show the dialpad keys (0-9)
|
|
40
|
-
*/
|
|
41
17
|
showKeys?: boolean;
|
|
42
|
-
/**
|
|
43
|
-
* Custom class name for the container
|
|
44
|
-
*/
|
|
45
18
|
className?: string;
|
|
46
19
|
availableExtensions?: Array<{
|
|
47
20
|
label: string;
|
|
@@ -88,6 +61,7 @@ declare function useCall(): {
|
|
|
88
61
|
callDuration: string;
|
|
89
62
|
isMuted: boolean;
|
|
90
63
|
currentCall: Call | null;
|
|
64
|
+
callError: string | undefined;
|
|
91
65
|
};
|
|
92
66
|
/**
|
|
93
67
|
* Hook for connection status
|
package/dist/index.d.ts
CHANGED
|
@@ -3,45 +3,18 @@ import React from 'react';
|
|
|
3
3
|
import { DoraCellConfig, CallStatus, Call, ConnectionStatus, DoraCell } from '@dora-cell/sdk';
|
|
4
4
|
|
|
5
5
|
interface CallInterfaceProps {
|
|
6
|
-
/**
|
|
7
|
-
* Whether the interface is open/visible
|
|
8
|
-
*/
|
|
9
6
|
isOpen?: boolean;
|
|
10
|
-
/**
|
|
11
|
-
* Callback when visibility changes
|
|
12
|
-
*/
|
|
13
7
|
onOpenChange?: (open: boolean) => void;
|
|
14
|
-
/**
|
|
15
|
-
* Callback when call ends (useful for invalidating queries)
|
|
16
|
-
*/
|
|
17
8
|
onCallEnded?: () => void;
|
|
18
|
-
/**
|
|
19
|
-
* Custom maximize icon component
|
|
20
|
-
*/
|
|
21
9
|
maximizeIcon?: React.ReactNode;
|
|
22
|
-
/**
|
|
23
|
-
* Custom minimize icon component
|
|
24
|
-
*/
|
|
25
10
|
minimizeIcon?: React.ReactNode;
|
|
26
11
|
}
|
|
27
12
|
declare function CallInterface({ isOpen, onOpenChange, onCallEnded, maximizeIcon, minimizeIcon, }: CallInterfaceProps): react_jsx_runtime.JSX.Element | null;
|
|
28
13
|
|
|
29
14
|
interface DialpadProps {
|
|
30
|
-
/**
|
|
31
|
-
* Callback when call is initiated
|
|
32
|
-
*/
|
|
33
15
|
onCallInitiated?: (number: string) => void;
|
|
34
|
-
/**
|
|
35
|
-
* Initial number to populate
|
|
36
|
-
*/
|
|
37
16
|
initialNumber?: string;
|
|
38
|
-
/**
|
|
39
|
-
* Whether to show the dialpad keys (0-9)
|
|
40
|
-
*/
|
|
41
17
|
showKeys?: boolean;
|
|
42
|
-
/**
|
|
43
|
-
* Custom class name for the container
|
|
44
|
-
*/
|
|
45
18
|
className?: string;
|
|
46
19
|
availableExtensions?: Array<{
|
|
47
20
|
label: string;
|
|
@@ -88,6 +61,7 @@ declare function useCall(): {
|
|
|
88
61
|
callDuration: string;
|
|
89
62
|
isMuted: boolean;
|
|
90
63
|
currentCall: Call | null;
|
|
64
|
+
callError: string | undefined;
|
|
91
65
|
};
|
|
92
66
|
/**
|
|
93
67
|
* Hook for connection status
|