@smarthivelabs-devs/auth-expo 0.1.0 → 1.0.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/README.md +472 -0
- package/package.json +3 -3
package/README.md
ADDED
|
@@ -0,0 +1,472 @@
|
|
|
1
|
+
# @smarthivelabs-devs/auth-expo
|
|
2
|
+
|
|
3
|
+
SmartHive Auth for React Native and Expo. Provides a provider, hooks, and components with SecureStore-backed token storage and deep-link OAuth support.
|
|
4
|
+
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
## Installation
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npx expo install @smarthivelabs-devs/auth-expo @smarthivelabs-devs/auth-sdk expo-auth-session expo-secure-store
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
Or with npm/pnpm (non-Expo managed workflow):
|
|
14
|
+
|
|
15
|
+
```bash
|
|
16
|
+
npm install @smarthivelabs-devs/auth-expo @smarthivelabs-devs/auth-sdk expo-auth-session expo-secure-store
|
|
17
|
+
pnpm add @smarthivelabs-devs/auth-expo @smarthivelabs-devs/auth-sdk expo-auth-session expo-secure-store
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
> **Peer dependencies required:** `expo-auth-session>=5`, `expo-secure-store>=12`, `react>=18`, `react-native>=0.73`
|
|
21
|
+
|
|
22
|
+
---
|
|
23
|
+
|
|
24
|
+
## Prerequisites
|
|
25
|
+
|
|
26
|
+
1. A SmartHive Auth project — grab `projectId`, `publishableKey`, and `baseUrl` from your dashboard.
|
|
27
|
+
2. A registered deep link scheme for your Expo app (see below).
|
|
28
|
+
|
|
29
|
+
---
|
|
30
|
+
|
|
31
|
+
## Deep Link Setup
|
|
32
|
+
|
|
33
|
+
SmartHive Auth uses OAuth 2.0 + PKCE. After login, the server redirects back to your app via a deep link (e.g. `myapp://auth/callback`). You must register a custom scheme in `app.json`:
|
|
34
|
+
|
|
35
|
+
```json
|
|
36
|
+
// app.json
|
|
37
|
+
{
|
|
38
|
+
"expo": {
|
|
39
|
+
"scheme": "myapp",
|
|
40
|
+
"android": {
|
|
41
|
+
"intentFilters": [
|
|
42
|
+
{
|
|
43
|
+
"action": "VIEW",
|
|
44
|
+
"autoVerify": true,
|
|
45
|
+
"data": [{ "scheme": "myapp" }],
|
|
46
|
+
"category": ["BROWSABLE", "DEFAULT"]
|
|
47
|
+
}
|
|
48
|
+
]
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
```
|
|
53
|
+
|
|
54
|
+
Rebuild your native app after this change:
|
|
55
|
+
|
|
56
|
+
```bash
|
|
57
|
+
npx expo prebuild
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
---
|
|
61
|
+
|
|
62
|
+
## Setup
|
|
63
|
+
|
|
64
|
+
Wrap your root component with `SmartHiveProvider`. Use `buildRedirectUri` to construct the deep link URI from your scheme.
|
|
65
|
+
|
|
66
|
+
```tsx
|
|
67
|
+
// App.tsx
|
|
68
|
+
import { SmartHiveProvider, buildRedirectUri } from "@smarthivelabs-devs/auth-expo";
|
|
69
|
+
|
|
70
|
+
const REDIRECT_URI = buildRedirectUri("myapp"); // → "myapp://auth/callback"
|
|
71
|
+
|
|
72
|
+
export default function App() {
|
|
73
|
+
return (
|
|
74
|
+
<SmartHiveProvider
|
|
75
|
+
projectId={process.env.EXPO_PUBLIC_AUTH_PROJECT_ID!}
|
|
76
|
+
publishableKey={process.env.EXPO_PUBLIC_AUTH_PUBLISHABLE_KEY!}
|
|
77
|
+
baseUrl={process.env.EXPO_PUBLIC_AUTH_BASE_URL!}
|
|
78
|
+
redirectUri={REDIRECT_URI}
|
|
79
|
+
>
|
|
80
|
+
<RootNavigator />
|
|
81
|
+
</SmartHiveProvider>
|
|
82
|
+
);
|
|
83
|
+
}
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
### `buildRedirectUri(scheme, path?)`
|
|
87
|
+
|
|
88
|
+
Helper that constructs a deep link URI:
|
|
89
|
+
|
|
90
|
+
```ts
|
|
91
|
+
buildRedirectUri("myapp") // → "myapp://auth/callback"
|
|
92
|
+
buildRedirectUri("myapp", "auth/done") // → "myapp://auth/done"
|
|
93
|
+
```
|
|
94
|
+
|
|
95
|
+
---
|
|
96
|
+
|
|
97
|
+
## Provider Props
|
|
98
|
+
|
|
99
|
+
| Prop | Type | Required | Description |
|
|
100
|
+
|---|---|---|---|
|
|
101
|
+
| `projectId` | `string` | Yes | Your SmartHive project ID |
|
|
102
|
+
| `publishableKey` | `string` | Yes | Your publishable key |
|
|
103
|
+
| `baseUrl` | `string` | Yes | URL of your SmartHive Auth service |
|
|
104
|
+
| `redirectUri` | `string` | Yes | Deep link callback URI (e.g. `myapp://auth/callback`) |
|
|
105
|
+
| `authDomain` | `string` | No | Custom branded auth domain |
|
|
106
|
+
| `children` | `ReactNode` | Yes | Your app tree |
|
|
107
|
+
|
|
108
|
+
---
|
|
109
|
+
|
|
110
|
+
## How OAuth Works in Expo
|
|
111
|
+
|
|
112
|
+
1. User taps **Sign in** → `login()` is called
|
|
113
|
+
2. The SDK builds the OAuth URL with PKCE, saves the verifier in SecureStore, and opens the URL in the system browser via `Linking.openURL()`
|
|
114
|
+
3. The user logs in via the browser
|
|
115
|
+
4. The server redirects to `myapp://auth/callback?code=...&state=...`
|
|
116
|
+
5. `Linking` fires a `url` event — `SmartHiveProvider` handles it automatically, exchanges the code for tokens, and updates the session state
|
|
117
|
+
|
|
118
|
+
No manual callback handling is needed — the provider sets up the `Linking` event listener internally.
|
|
119
|
+
|
|
120
|
+
---
|
|
121
|
+
|
|
122
|
+
## Hooks
|
|
123
|
+
|
|
124
|
+
### `useAuth()`
|
|
125
|
+
|
|
126
|
+
Returns the full auth context.
|
|
127
|
+
|
|
128
|
+
```tsx
|
|
129
|
+
import { useAuth } from "@smarthivelabs-devs/auth-expo";
|
|
130
|
+
|
|
131
|
+
function HomeScreen() {
|
|
132
|
+
const {
|
|
133
|
+
session, // AuthSession | null
|
|
134
|
+
isLoaded, // true once initial SecureStore read is done
|
|
135
|
+
isSignedIn, // boolean
|
|
136
|
+
login, // (options?) => Promise<void>
|
|
137
|
+
logout, // () => Promise<void>
|
|
138
|
+
refreshSession, // () => Promise<void>
|
|
139
|
+
authFetch, // authenticated fetch wrapper
|
|
140
|
+
} = useAuth();
|
|
141
|
+
|
|
142
|
+
if (!isLoaded) return <ActivityIndicator />;
|
|
143
|
+
|
|
144
|
+
return isSignedIn ? (
|
|
145
|
+
<Button title="Sign out" onPress={logout} />
|
|
146
|
+
) : (
|
|
147
|
+
<Button title="Sign in" onPress={() => login()} />
|
|
148
|
+
);
|
|
149
|
+
}
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
---
|
|
153
|
+
|
|
154
|
+
### `useSession()`
|
|
155
|
+
|
|
156
|
+
Returns the current `AuthSession` or `null`.
|
|
157
|
+
|
|
158
|
+
```tsx
|
|
159
|
+
import { useSession } from "@smarthivelabs-devs/auth-expo";
|
|
160
|
+
|
|
161
|
+
function TokenScreen() {
|
|
162
|
+
const session = useSession();
|
|
163
|
+
if (!session) return <Text>Not signed in</Text>;
|
|
164
|
+
return <Text selectable>{session.accessToken}</Text>;
|
|
165
|
+
}
|
|
166
|
+
```
|
|
167
|
+
|
|
168
|
+
---
|
|
169
|
+
|
|
170
|
+
### `useUser()`
|
|
171
|
+
|
|
172
|
+
Returns the user object from the session, or `null`.
|
|
173
|
+
|
|
174
|
+
```tsx
|
|
175
|
+
import { useUser } from "@smarthivelabs-devs/auth-expo";
|
|
176
|
+
|
|
177
|
+
function ProfileScreen() {
|
|
178
|
+
const user = useUser();
|
|
179
|
+
if (!user) return null;
|
|
180
|
+
return <Text>Welcome, {(user as any).email}</Text>;
|
|
181
|
+
}
|
|
182
|
+
```
|
|
183
|
+
|
|
184
|
+
---
|
|
185
|
+
|
|
186
|
+
### `useIsLoaded()`
|
|
187
|
+
|
|
188
|
+
Returns `true` once the initial SecureStore session check is done. Prevents a flash of the signed-out state on app startup.
|
|
189
|
+
|
|
190
|
+
```tsx
|
|
191
|
+
import { useIsLoaded } from "@smarthivelabs-devs/auth-expo";
|
|
192
|
+
|
|
193
|
+
function RootNavigator() {
|
|
194
|
+
const isLoaded = useIsLoaded();
|
|
195
|
+
if (!isLoaded) return <SplashScreen />;
|
|
196
|
+
return <AppNavigator />;
|
|
197
|
+
}
|
|
198
|
+
```
|
|
199
|
+
|
|
200
|
+
---
|
|
201
|
+
|
|
202
|
+
### `useIsSignedIn()`
|
|
203
|
+
|
|
204
|
+
Returns `true` (signed in), `false` (signed out), or `null` (still loading).
|
|
205
|
+
|
|
206
|
+
```tsx
|
|
207
|
+
import { useIsSignedIn } from "@smarthivelabs-devs/auth-expo";
|
|
208
|
+
|
|
209
|
+
function AuthGate({ children }: { children: React.ReactNode }) {
|
|
210
|
+
const isSignedIn = useIsSignedIn();
|
|
211
|
+
const router = useRouter();
|
|
212
|
+
|
|
213
|
+
useEffect(() => {
|
|
214
|
+
if (isSignedIn === false) router.replace("/login");
|
|
215
|
+
}, [isSignedIn]);
|
|
216
|
+
|
|
217
|
+
if (isSignedIn === null) return <ActivityIndicator />;
|
|
218
|
+
if (!isSignedIn) return null;
|
|
219
|
+
return <>{children}</>;
|
|
220
|
+
}
|
|
221
|
+
```
|
|
222
|
+
|
|
223
|
+
---
|
|
224
|
+
|
|
225
|
+
### `useAuthFetch()`
|
|
226
|
+
|
|
227
|
+
Returns an authenticated `fetch` function. Automatically injects the Bearer token on every request — tokens are refreshed transparently.
|
|
228
|
+
|
|
229
|
+
```tsx
|
|
230
|
+
import { useAuthFetch } from "@smarthivelabs-devs/auth-expo";
|
|
231
|
+
|
|
232
|
+
function DataScreen() {
|
|
233
|
+
const authFetch = useAuthFetch();
|
|
234
|
+
const [data, setData] = useState(null);
|
|
235
|
+
|
|
236
|
+
async function load() {
|
|
237
|
+
const res = await authFetch("https://api.myapp.com/protected");
|
|
238
|
+
setData(await res.json());
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
return (
|
|
242
|
+
<View>
|
|
243
|
+
<Button title="Load data" onPress={load} />
|
|
244
|
+
{data && <Text>{JSON.stringify(data)}</Text>}
|
|
245
|
+
</View>
|
|
246
|
+
);
|
|
247
|
+
}
|
|
248
|
+
```
|
|
249
|
+
|
|
250
|
+
---
|
|
251
|
+
|
|
252
|
+
### `useAuthorizationHeader()`
|
|
253
|
+
|
|
254
|
+
Returns a function that resolves to `{ authorization: "Bearer <token>" }`. Useful for passing to SDKs or GraphQL clients.
|
|
255
|
+
|
|
256
|
+
```tsx
|
|
257
|
+
import { useAuthorizationHeader } from "@smarthivelabs-devs/auth-expo";
|
|
258
|
+
|
|
259
|
+
function ApolloSetup() {
|
|
260
|
+
const getAuthorizationHeader = useAuthorizationHeader();
|
|
261
|
+
|
|
262
|
+
const authLink = new ApolloLink(async (operation, forward) => {
|
|
263
|
+
const headers = await getAuthorizationHeader();
|
|
264
|
+
operation.setContext({ headers });
|
|
265
|
+
return forward(operation);
|
|
266
|
+
});
|
|
267
|
+
|
|
268
|
+
// ...
|
|
269
|
+
}
|
|
270
|
+
```
|
|
271
|
+
|
|
272
|
+
---
|
|
273
|
+
|
|
274
|
+
## Render Helpers
|
|
275
|
+
|
|
276
|
+
### `<SignedIn>`
|
|
277
|
+
|
|
278
|
+
Renders children only when auth has loaded **and** a session exists.
|
|
279
|
+
|
|
280
|
+
```tsx
|
|
281
|
+
import { SignedIn } from "@smarthivelabs-devs/auth-expo";
|
|
282
|
+
|
|
283
|
+
<SignedIn>
|
|
284
|
+
<UserDashboard />
|
|
285
|
+
</SignedIn>
|
|
286
|
+
```
|
|
287
|
+
|
|
288
|
+
### `<SignedOut>`
|
|
289
|
+
|
|
290
|
+
Renders children only when auth has loaded **and** there is no session.
|
|
291
|
+
|
|
292
|
+
```tsx
|
|
293
|
+
import { SignedOut } from "@smarthivelabs-devs/auth-expo";
|
|
294
|
+
|
|
295
|
+
<SignedOut>
|
|
296
|
+
<LandingScreen />
|
|
297
|
+
</SignedOut>
|
|
298
|
+
```
|
|
299
|
+
|
|
300
|
+
### `<AuthLoading>`
|
|
301
|
+
|
|
302
|
+
Renders children while the initial session check is running.
|
|
303
|
+
|
|
304
|
+
```tsx
|
|
305
|
+
import { AuthLoading } from "@smarthivelabs-devs/auth-expo";
|
|
306
|
+
|
|
307
|
+
<AuthLoading>
|
|
308
|
+
<ActivityIndicator size="large" />
|
|
309
|
+
</AuthLoading>
|
|
310
|
+
```
|
|
311
|
+
|
|
312
|
+
---
|
|
313
|
+
|
|
314
|
+
## Expo Router Integration
|
|
315
|
+
|
|
316
|
+
```
|
|
317
|
+
app/
|
|
318
|
+
├── _layout.tsx ← SmartHiveProvider here
|
|
319
|
+
├── index.tsx ← SignedIn / SignedOut
|
|
320
|
+
├── login.tsx ← login screen
|
|
321
|
+
└── (protected)/
|
|
322
|
+
└── dashboard.tsx ← authenticated screen
|
|
323
|
+
```
|
|
324
|
+
|
|
325
|
+
```tsx
|
|
326
|
+
// app/_layout.tsx
|
|
327
|
+
import { Stack } from "expo-router";
|
|
328
|
+
import { SmartHiveProvider, buildRedirectUri } from "@smarthivelabs-devs/auth-expo";
|
|
329
|
+
|
|
330
|
+
export default function Layout() {
|
|
331
|
+
return (
|
|
332
|
+
<SmartHiveProvider
|
|
333
|
+
projectId={process.env.EXPO_PUBLIC_AUTH_PROJECT_ID!}
|
|
334
|
+
publishableKey={process.env.EXPO_PUBLIC_AUTH_PUBLISHABLE_KEY!}
|
|
335
|
+
baseUrl={process.env.EXPO_PUBLIC_AUTH_BASE_URL!}
|
|
336
|
+
redirectUri={buildRedirectUri("myapp")}
|
|
337
|
+
>
|
|
338
|
+
<Stack />
|
|
339
|
+
</SmartHiveProvider>
|
|
340
|
+
);
|
|
341
|
+
}
|
|
342
|
+
```
|
|
343
|
+
|
|
344
|
+
```tsx
|
|
345
|
+
// app/index.tsx
|
|
346
|
+
import { SignedIn, SignedOut, AuthLoading } from "@smarthivelabs-devs/auth-expo";
|
|
347
|
+
import { Redirect } from "expo-router";
|
|
348
|
+
import { ActivityIndicator } from "react-native";
|
|
349
|
+
|
|
350
|
+
export default function Index() {
|
|
351
|
+
return (
|
|
352
|
+
<>
|
|
353
|
+
<AuthLoading><ActivityIndicator /></AuthLoading>
|
|
354
|
+
<SignedIn><Redirect href="/dashboard" /></SignedIn>
|
|
355
|
+
<SignedOut><Redirect href="/login" /></SignedOut>
|
|
356
|
+
</>
|
|
357
|
+
);
|
|
358
|
+
}
|
|
359
|
+
```
|
|
360
|
+
|
|
361
|
+
```tsx
|
|
362
|
+
// app/login.tsx
|
|
363
|
+
import { useAuth } from "@smarthivelabs-devs/auth-expo";
|
|
364
|
+
import { Button, View } from "react-native";
|
|
365
|
+
|
|
366
|
+
export default function LoginScreen() {
|
|
367
|
+
const { login } = useAuth();
|
|
368
|
+
return (
|
|
369
|
+
<View style={{ flex: 1, justifyContent: "center", alignItems: "center" }}>
|
|
370
|
+
<Button title="Sign in with SmartHive" onPress={() => login()} />
|
|
371
|
+
</View>
|
|
372
|
+
);
|
|
373
|
+
}
|
|
374
|
+
```
|
|
375
|
+
|
|
376
|
+
```tsx
|
|
377
|
+
// app/(protected)/dashboard.tsx
|
|
378
|
+
import { useAuth, SignedIn } from "@smarthivelabs-devs/auth-expo";
|
|
379
|
+
import { Button, Text, View } from "react-native";
|
|
380
|
+
|
|
381
|
+
export default function Dashboard() {
|
|
382
|
+
const { logout, authFetch } = useAuth();
|
|
383
|
+
|
|
384
|
+
return (
|
|
385
|
+
<SignedIn>
|
|
386
|
+
<View>
|
|
387
|
+
<Text>Dashboard</Text>
|
|
388
|
+
<Button title="Sign out" onPress={logout} />
|
|
389
|
+
</View>
|
|
390
|
+
</SignedIn>
|
|
391
|
+
);
|
|
392
|
+
}
|
|
393
|
+
```
|
|
394
|
+
|
|
395
|
+
---
|
|
396
|
+
|
|
397
|
+
## Low-level: `initExpoAuth`
|
|
398
|
+
|
|
399
|
+
If you need the client directly without the provider (advanced use), use `initExpoAuth`:
|
|
400
|
+
|
|
401
|
+
```ts
|
|
402
|
+
import { initExpoAuth, buildRedirectUri } from "@smarthivelabs-devs/auth-expo";
|
|
403
|
+
|
|
404
|
+
const client = initExpoAuth({
|
|
405
|
+
projectId: "proj_abc123",
|
|
406
|
+
publishableKey: "pk_live_abc123",
|
|
407
|
+
baseUrl: "https://auth.myapp.com",
|
|
408
|
+
redirectUri: buildRedirectUri("myapp"),
|
|
409
|
+
});
|
|
410
|
+
|
|
411
|
+
await client.initialize();
|
|
412
|
+
|
|
413
|
+
// The client behaves the same as SmartHiveAuthClient from auth-sdk,
|
|
414
|
+
// but uses SecureStore and Linking instead of localStorage + location.assign
|
|
415
|
+
```
|
|
416
|
+
|
|
417
|
+
---
|
|
418
|
+
|
|
419
|
+
## Environment Variables
|
|
420
|
+
|
|
421
|
+
With Expo's built-in env support (SDK 49+):
|
|
422
|
+
|
|
423
|
+
```bash
|
|
424
|
+
# .env
|
|
425
|
+
EXPO_PUBLIC_AUTH_PROJECT_ID=proj_abc123
|
|
426
|
+
EXPO_PUBLIC_AUTH_PUBLISHABLE_KEY=pk_live_abc123
|
|
427
|
+
EXPO_PUBLIC_AUTH_BASE_URL=https://auth.myapp.com
|
|
428
|
+
```
|
|
429
|
+
|
|
430
|
+
> Variables prefixed `EXPO_PUBLIC_` are embedded in the app bundle at build time.
|
|
431
|
+
|
|
432
|
+
---
|
|
433
|
+
|
|
434
|
+
## Token Storage
|
|
435
|
+
|
|
436
|
+
Tokens are stored in `expo-secure-store`, which uses:
|
|
437
|
+
- **iOS**: Keychain Services
|
|
438
|
+
- **Android**: Keystore System (Android Keystore-backed AES encryption)
|
|
439
|
+
|
|
440
|
+
PKCE verifier and state are also stored in SecureStore during the login flow and deleted after the code exchange.
|
|
441
|
+
|
|
442
|
+
---
|
|
443
|
+
|
|
444
|
+
## TypeScript Types
|
|
445
|
+
|
|
446
|
+
```ts
|
|
447
|
+
import type {
|
|
448
|
+
SmartHiveExpoConfig,
|
|
449
|
+
SmartHiveProviderProps,
|
|
450
|
+
} from "@smarthivelabs-devs/auth-expo";
|
|
451
|
+
|
|
452
|
+
import type {
|
|
453
|
+
AuthSession,
|
|
454
|
+
SmartHiveAuthClient,
|
|
455
|
+
} from "@smarthivelabs-devs/auth-sdk";
|
|
456
|
+
```
|
|
457
|
+
|
|
458
|
+
---
|
|
459
|
+
|
|
460
|
+
## Related Packages
|
|
461
|
+
|
|
462
|
+
| Package | Use case |
|
|
463
|
+
|---|---|
|
|
464
|
+
| [`@smarthivelabs-devs/auth-sdk`](https://www.npmjs.com/package/@smarthivelabs-devs/auth-sdk) | Core SDK — framework-agnostic |
|
|
465
|
+
| [`@smarthivelabs-devs/auth-react`](https://www.npmjs.com/package/@smarthivelabs-devs/auth-react) | React web apps |
|
|
466
|
+
| [`@smarthivelabs-devs/auth-server`](https://www.npmjs.com/package/@smarthivelabs-devs/auth-server) | Express / Next.js server-side JWT verification |
|
|
467
|
+
|
|
468
|
+
---
|
|
469
|
+
|
|
470
|
+
## License
|
|
471
|
+
|
|
472
|
+
MIT © SmartHive Labs
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@smarthivelabs-devs/auth-expo",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "1.0.0",
|
|
4
4
|
"description": "SmartHive Auth provider, hooks, and SecureStore integration for React Native / Expo",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": {
|
|
@@ -25,7 +25,7 @@
|
|
|
25
25
|
"LICENSE"
|
|
26
26
|
],
|
|
27
27
|
"peerDependencies": {
|
|
28
|
-
"@smarthivelabs-devs/auth-sdk": "^
|
|
28
|
+
"@smarthivelabs-devs/auth-sdk": "^1.0.0",
|
|
29
29
|
"expo-auth-session": ">=5",
|
|
30
30
|
"expo-secure-store": ">=12",
|
|
31
31
|
"react": ">=18",
|
|
@@ -36,7 +36,7 @@
|
|
|
36
36
|
"@types/react-native": "^0.73.0",
|
|
37
37
|
"tsup": "^8.3.0",
|
|
38
38
|
"typescript": "^5.7.3",
|
|
39
|
-
"@smarthivelabs-devs/auth-sdk": "^
|
|
39
|
+
"@smarthivelabs-devs/auth-sdk": "^1.0.0"
|
|
40
40
|
},
|
|
41
41
|
"scripts": {
|
|
42
42
|
"build": "tsup",
|