@ahoo-wang/fetcher-react 3.5.5 → 3.5.8
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 +140 -13
- package/README.zh-CN.md +140 -13
- package/dist/cosec/RouteGuard.d.ts +49 -0
- package/dist/cosec/RouteGuard.d.ts.map +1 -0
- package/dist/cosec/SecurityContext.d.ts +47 -14
- package/dist/cosec/SecurityContext.d.ts.map +1 -1
- package/dist/cosec/index.d.ts +1 -0
- package/dist/cosec/index.d.ts.map +1 -1
- package/dist/cosec/useSecurity.d.ts +59 -7
- package/dist/cosec/useSecurity.d.ts.map +1 -1
- package/dist/index.es.js +458 -426
- package/dist/index.es.js.map +1 -1
- package/dist/index.umd.js +1 -1
- package/dist/index.umd.js.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -47,20 +47,24 @@ robust data fetching capabilities.
|
|
|
47
47
|
- [useImmerKeyStorage](#useimmerkeystorage-hook)
|
|
48
48
|
- [Event Hooks](#event-hooks)
|
|
49
49
|
- [useEventSubscription](#useeventsubscription-hook)
|
|
50
|
+
- [CoSec Security Hooks](#cosec-security-hooks)
|
|
51
|
+
- [useSecurity](#usesecurity-hook)
|
|
52
|
+
- [SecurityProvider](#securityprovider)
|
|
53
|
+
- [useSecurityContext](#usesecuritycontext-hook)
|
|
50
54
|
- [Wow Query Hooks](#wow-query-hooks)
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
55
|
+
- [Basic Query Hooks](#basic-query-hooks)
|
|
56
|
+
- [useListQuery](#uselistquery-hook)
|
|
57
|
+
- [usePagedQuery](#usepagedquery-hook)
|
|
58
|
+
- [useSingleQuery](#usesinglequery-hook)
|
|
59
|
+
- [useCountQuery](#usecountquery-hook)
|
|
60
|
+
- [Fetcher Query Hooks](#fetcher-query-hooks)
|
|
61
|
+
- [useFetcherListQuery](#usefetcherlistquery-hook)
|
|
62
|
+
- [useFetcherPagedQuery](#usefetcherpagedquery-hook)
|
|
63
|
+
- [useFetcherSingleQuery](#usefetchersinglequery-hook)
|
|
64
|
+
- [useFetcherCountQuery](#usefetchercountquery-hook)
|
|
65
|
+
- [Stream Query Hooks](#stream-query-hooks)
|
|
66
|
+
- [useListStreamQuery](#useliststreamquery-hook)
|
|
67
|
+
- [useFetcherListStreamQuery](#usefetcherliststreamquery-hook)
|
|
64
68
|
- [Best Practices](#best-practices)
|
|
65
69
|
- [API Reference](#api-reference)
|
|
66
70
|
- [License](#license)
|
|
@@ -711,6 +715,129 @@ Key features:
|
|
|
711
715
|
- **Error Handling**: Logs warnings for failed subscription attempts
|
|
712
716
|
- **Event Bus Integration**: Works seamlessly with `@ahoo-wang/fetcher-eventbus` TypedEventBus instances
|
|
713
717
|
|
|
718
|
+
### CoSec Security Hooks
|
|
719
|
+
|
|
720
|
+
🛡️ **Enterprise Security Integration** - Powerful React hooks for managing authentication state with CoSec tokens, providing seamless integration with enterprise security systems and automatic token lifecycle management.
|
|
721
|
+
|
|
722
|
+
#### useSecurity Hook
|
|
723
|
+
|
|
724
|
+
The `useSecurity` hook provides reactive access to authentication state and operations using CoSec tokens. It integrates with TokenStorage to persist tokens and updates state reactively when tokens change.
|
|
725
|
+
|
|
726
|
+
```typescript jsx
|
|
727
|
+
import { useSecurity } from '@ahoo-wang/fetcher-react/cosec';
|
|
728
|
+
import { tokenStorage } from './tokenStorage';
|
|
729
|
+
import { useNavigate } from 'react-router-dom';
|
|
730
|
+
|
|
731
|
+
function App() {
|
|
732
|
+
const navigate = useNavigate();
|
|
733
|
+
|
|
734
|
+
const { currentUser, authenticated, signIn, signOut } = useSecurity(tokenStorage, {
|
|
735
|
+
onSignIn: () => {
|
|
736
|
+
// Redirect to dashboard after successful login
|
|
737
|
+
navigate('/dashboard');
|
|
738
|
+
},
|
|
739
|
+
onSignOut: () => {
|
|
740
|
+
// Redirect to login page after logout
|
|
741
|
+
navigate('/login');
|
|
742
|
+
}
|
|
743
|
+
});
|
|
744
|
+
|
|
745
|
+
const handleSignIn = async () => {
|
|
746
|
+
// Direct token
|
|
747
|
+
await signIn(compositeToken);
|
|
748
|
+
|
|
749
|
+
// Or async function
|
|
750
|
+
await signIn(async () => {
|
|
751
|
+
const response = await fetch('/api/auth/login', {
|
|
752
|
+
method: 'POST',
|
|
753
|
+
body: JSON.stringify({ username, password })
|
|
754
|
+
});
|
|
755
|
+
return response.json();
|
|
756
|
+
});
|
|
757
|
+
};
|
|
758
|
+
|
|
759
|
+
if (!authenticated) {
|
|
760
|
+
return <button onClick={handleSignIn}>Sign In</button>;
|
|
761
|
+
}
|
|
762
|
+
|
|
763
|
+
return (
|
|
764
|
+
<div>
|
|
765
|
+
<p>Welcome, {currentUser.sub}!</p>
|
|
766
|
+
<button onClick={signOut}>Sign Out</button>
|
|
767
|
+
</div>
|
|
768
|
+
);
|
|
769
|
+
}
|
|
770
|
+
```
|
|
771
|
+
|
|
772
|
+
**Key Features:**
|
|
773
|
+
|
|
774
|
+
- **Reactive Authentication State**: Automatically updates when tokens change
|
|
775
|
+
- **Flexible Sign-in Methods**: Supports both direct tokens and async token providers
|
|
776
|
+
- **Lifecycle Callbacks**: Configurable callbacks for sign-in and sign-out events
|
|
777
|
+
- **Type Safety**: Full TypeScript support with CoSec JWT payload types
|
|
778
|
+
- **Token Persistence**: Integrates with TokenStorage for cross-session persistence
|
|
779
|
+
|
|
780
|
+
#### SecurityProvider
|
|
781
|
+
|
|
782
|
+
The `SecurityProvider` component wraps your application to provide authentication context through React context. It internally uses the `useSecurity` hook and makes authentication state available to all child components via the `useSecurityContext` hook.
|
|
783
|
+
|
|
784
|
+
```tsx
|
|
785
|
+
import { SecurityProvider } from '@ahoo-wang/fetcher-react';
|
|
786
|
+
import { tokenStorage } from './tokenStorage';
|
|
787
|
+
import { useNavigate } from 'react-router-dom';
|
|
788
|
+
|
|
789
|
+
function App() {
|
|
790
|
+
const navigate = useNavigate();
|
|
791
|
+
|
|
792
|
+
return (
|
|
793
|
+
<SecurityProvider
|
|
794
|
+
tokenStorage={tokenStorage}
|
|
795
|
+
onSignIn={() => navigate('/dashboard')}
|
|
796
|
+
onSignOut={() => navigate('/login')}
|
|
797
|
+
>
|
|
798
|
+
<MyApp />
|
|
799
|
+
</SecurityProvider>
|
|
800
|
+
);
|
|
801
|
+
}
|
|
802
|
+
```
|
|
803
|
+
|
|
804
|
+
**Configuration Options:**
|
|
805
|
+
|
|
806
|
+
- `tokenStorage`: TokenStorage instance for managing authentication tokens
|
|
807
|
+
- `onSignIn`: Callback function invoked when sign in is successful
|
|
808
|
+
- `onSignOut`: Callback function invoked when sign out occurs
|
|
809
|
+
- `children`: Child components that will have access to security context
|
|
810
|
+
|
|
811
|
+
#### useSecurityContext Hook
|
|
812
|
+
|
|
813
|
+
The `useSecurityContext` hook provides access to authentication state and methods within components wrapped by `SecurityProvider`. It offers the same interface as `useSecurity` but through React context.
|
|
814
|
+
|
|
815
|
+
```tsx
|
|
816
|
+
import { useSecurityContext } from '@ahoo-wang/fetcher-react';
|
|
817
|
+
|
|
818
|
+
function UserProfile() {
|
|
819
|
+
const { currentUser, authenticated, signOut } = useSecurityContext();
|
|
820
|
+
|
|
821
|
+
if (!authenticated) {
|
|
822
|
+
return <div>Please sign in</div>;
|
|
823
|
+
}
|
|
824
|
+
|
|
825
|
+
return (
|
|
826
|
+
<div>
|
|
827
|
+
<p>Welcome, {currentUser.sub}!</p>
|
|
828
|
+
<button onClick={signOut}>Sign Out</button>
|
|
829
|
+
</div>
|
|
830
|
+
);
|
|
831
|
+
}
|
|
832
|
+
```
|
|
833
|
+
|
|
834
|
+
**Context Benefits:**
|
|
835
|
+
|
|
836
|
+
- **Prop Drilling Elimination**: Access authentication state without passing props
|
|
837
|
+
- **Component Isolation**: Components can access auth state regardless of component tree depth
|
|
838
|
+
- **Centralized State**: Single source of truth for authentication across the application
|
|
839
|
+
- **Automatic Re-rendering**: Components automatically re-render when authentication state changes
|
|
840
|
+
|
|
714
841
|
### Storage Hooks
|
|
715
842
|
|
|
716
843
|
#### useKeyStorage Hook
|
package/README.zh-CN.md
CHANGED
|
@@ -45,20 +45,24 @@
|
|
|
45
45
|
- [useImmerKeyStorage](#useimmerkeystorage-hook)
|
|
46
46
|
- [事件 Hooks](#事件-hooks)
|
|
47
47
|
- [useEventSubscription](#useeventsubscription-hook)
|
|
48
|
+
- [CoSec 安全 Hooks](#cosec-安全-hooks)
|
|
49
|
+
- [useSecurity](#usesecurity-hook)
|
|
50
|
+
- [SecurityProvider](#securityprovider)
|
|
51
|
+
- [useSecurityContext](#usesecuritycontext-hook)
|
|
48
52
|
- [Wow 查询 Hooks](#wow-查询-hooks)
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
53
|
+
- [基础查询 Hooks](#基础查询-hooks)
|
|
54
|
+
- [useListQuery](#uselistquery-hook)
|
|
55
|
+
- [usePagedQuery](#usepagedquery-hook)
|
|
56
|
+
- [useSingleQuery](#usesinglequery-hook)
|
|
57
|
+
- [useCountQuery](#usecountquery-hook)
|
|
58
|
+
- [获取查询 Hooks](#获取查询-hooks)
|
|
59
|
+
- [useFetcherListQuery](#usefetcherlistquery-hook)
|
|
60
|
+
- [useFetcherPagedQuery](#usefetcherpagedquery-hook)
|
|
61
|
+
- [useFetcherSingleQuery](#usefetchersinglequery-hook)
|
|
62
|
+
- [useFetcherCountQuery](#usefetchercountquery-hook)
|
|
63
|
+
- [流查询 Hooks](#流查询-hooks)
|
|
64
|
+
- [useListStreamQuery](#useliststreamquery-hook)
|
|
65
|
+
- [useFetcherListStreamQuery](#usefetcherliststreamquery-hook)
|
|
62
66
|
- [最佳实践](#最佳实践)
|
|
63
67
|
- [API 参考](#api-参考)
|
|
64
68
|
- [许可证](#许可证)
|
|
@@ -1615,6 +1619,129 @@ function MyComponent() {
|
|
|
1615
1619
|
- **错误处理**: 对失败的订阅尝试记录警告
|
|
1616
1620
|
- **事件总线集成**: 与 `@ahoo-wang/fetcher-eventbus` TypedEventBus 实例无缝配合
|
|
1617
1621
|
|
|
1622
|
+
### CoSec 安全 Hooks
|
|
1623
|
+
|
|
1624
|
+
🛡️ **企业安全集成** - 强大的 React hooks,用于使用 CoSec 令牌管理认证状态,提供与企业安全系统的无缝集成和自动令牌生命周期管理。
|
|
1625
|
+
|
|
1626
|
+
#### useSecurity Hook
|
|
1627
|
+
|
|
1628
|
+
`useSecurity` hook 使用 CoSec 令牌提供对认证状态和操作的响应式访问。它与 TokenStorage 集成以持久化令牌,并在令牌更改时响应式更新状态。
|
|
1629
|
+
|
|
1630
|
+
```typescript jsx
|
|
1631
|
+
import { useSecurity } from '@ahoo-wang/fetcher-react/cosec';
|
|
1632
|
+
import { tokenStorage } from './tokenStorage';
|
|
1633
|
+
import { useNavigate } from 'react-router-dom';
|
|
1634
|
+
|
|
1635
|
+
function App() {
|
|
1636
|
+
const navigate = useNavigate();
|
|
1637
|
+
|
|
1638
|
+
const { currentUser, authenticated, signIn, signOut } = useSecurity(tokenStorage, {
|
|
1639
|
+
onSignIn: () => {
|
|
1640
|
+
// 登录成功后重定向到仪表板
|
|
1641
|
+
navigate('/dashboard');
|
|
1642
|
+
},
|
|
1643
|
+
onSignOut: () => {
|
|
1644
|
+
// 登出后重定向到登录页面
|
|
1645
|
+
navigate('/login');
|
|
1646
|
+
}
|
|
1647
|
+
});
|
|
1648
|
+
|
|
1649
|
+
const handleSignIn = async () => {
|
|
1650
|
+
// 直接令牌
|
|
1651
|
+
await signIn(compositeToken);
|
|
1652
|
+
|
|
1653
|
+
// 或异步函数
|
|
1654
|
+
await signIn(async () => {
|
|
1655
|
+
const response = await fetch('/api/auth/login', {
|
|
1656
|
+
method: 'POST',
|
|
1657
|
+
body: JSON.stringify({ username, password })
|
|
1658
|
+
});
|
|
1659
|
+
return response.json();
|
|
1660
|
+
});
|
|
1661
|
+
};
|
|
1662
|
+
|
|
1663
|
+
if (!authenticated) {
|
|
1664
|
+
return <button onClick={handleSignIn}>登录</button>;
|
|
1665
|
+
}
|
|
1666
|
+
|
|
1667
|
+
return (
|
|
1668
|
+
<div>
|
|
1669
|
+
<p>欢迎, {currentUser.sub}!</p>
|
|
1670
|
+
<button onClick={signOut}>登出</button>
|
|
1671
|
+
</div>
|
|
1672
|
+
);
|
|
1673
|
+
}
|
|
1674
|
+
```
|
|
1675
|
+
|
|
1676
|
+
**关键特性:**
|
|
1677
|
+
|
|
1678
|
+
- **响应式认证状态**: 当令牌更改时自动更新
|
|
1679
|
+
- **灵活的登录方法**: 支持直接令牌和异步令牌提供者
|
|
1680
|
+
- **生命周期回调**: 可配置的登录和登出事件回调
|
|
1681
|
+
- **类型安全**: 完全支持 TypeScript,具有 CoSec JWT 负载类型
|
|
1682
|
+
- **令牌持久化**: 与 TokenStorage 集成以实现跨会话持久化
|
|
1683
|
+
|
|
1684
|
+
#### SecurityProvider
|
|
1685
|
+
|
|
1686
|
+
`SecurityProvider` 组件包装您的应用程序以通过 React 上下文提供认证上下文。它在内部使用 `useSecurity` hook,并通过 `useSecurityContext` hook 使认证状态可用于所有子组件。
|
|
1687
|
+
|
|
1688
|
+
```tsx
|
|
1689
|
+
import { SecurityProvider } from '@ahoo-wang/fetcher-react';
|
|
1690
|
+
import { tokenStorage } from './tokenStorage';
|
|
1691
|
+
import { useNavigate } from 'react-router-dom';
|
|
1692
|
+
|
|
1693
|
+
function App() {
|
|
1694
|
+
const navigate = useNavigate();
|
|
1695
|
+
|
|
1696
|
+
return (
|
|
1697
|
+
<SecurityProvider
|
|
1698
|
+
tokenStorage={tokenStorage}
|
|
1699
|
+
onSignIn={() => navigate('/dashboard')}
|
|
1700
|
+
onSignOut={() => navigate('/login')}
|
|
1701
|
+
>
|
|
1702
|
+
<MyApp />
|
|
1703
|
+
</SecurityProvider>
|
|
1704
|
+
);
|
|
1705
|
+
}
|
|
1706
|
+
```
|
|
1707
|
+
|
|
1708
|
+
**配置选项:**
|
|
1709
|
+
|
|
1710
|
+
- `tokenStorage`: 用于管理认证令牌的 TokenStorage 实例
|
|
1711
|
+
- `onSignIn`: 登录成功时调用的回调函数
|
|
1712
|
+
- `onSignOut`: 登出时调用的回调函数
|
|
1713
|
+
- `children`: 将有权访问安全上下文的子组件
|
|
1714
|
+
|
|
1715
|
+
#### useSecurityContext Hook
|
|
1716
|
+
|
|
1717
|
+
`useSecurityContext` hook 在被 `SecurityProvider` 包装的组件中提供对认证状态和方法的访问。它通过 React 上下文提供与 `useSecurity` 相同的接口。
|
|
1718
|
+
|
|
1719
|
+
```tsx
|
|
1720
|
+
import { useSecurityContext } from '@ahoo-wang/fetcher-react';
|
|
1721
|
+
|
|
1722
|
+
function UserProfile() {
|
|
1723
|
+
const { currentUser, authenticated, signOut } = useSecurityContext();
|
|
1724
|
+
|
|
1725
|
+
if (!authenticated) {
|
|
1726
|
+
return <div>请登录</div>;
|
|
1727
|
+
}
|
|
1728
|
+
|
|
1729
|
+
return (
|
|
1730
|
+
<div>
|
|
1731
|
+
<p>欢迎, {currentUser.sub}!</p>
|
|
1732
|
+
<button onClick={signOut}>登出</button>
|
|
1733
|
+
</div>
|
|
1734
|
+
);
|
|
1735
|
+
}
|
|
1736
|
+
```
|
|
1737
|
+
|
|
1738
|
+
**上下文优势:**
|
|
1739
|
+
|
|
1740
|
+
- **消除属性钻取**: 无需传递属性即可访问认证状态
|
|
1741
|
+
- **组件隔离**: 无论组件树深度如何,组件都可以访问认证状态
|
|
1742
|
+
- **集中式状态**: 应用程序中认证的单一真实来源
|
|
1743
|
+
- **自动重新渲染**: 当认证状态更改时,组件自动重新渲染
|
|
1744
|
+
|
|
1618
1745
|
### 存储 Hooks
|
|
1619
1746
|
|
|
1620
1747
|
#### useKeyStorage
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
/**
|
|
3
|
+
* Props for the RouteGuard component.
|
|
4
|
+
*/
|
|
5
|
+
export interface RouteGuardProps {
|
|
6
|
+
/**
|
|
7
|
+
* The content to render when the user is authenticated.
|
|
8
|
+
*/
|
|
9
|
+
children: ReactNode;
|
|
10
|
+
/**
|
|
11
|
+
* The fallback content to render when the user is not authenticated.
|
|
12
|
+
* If not provided, nothing will be rendered.
|
|
13
|
+
*/
|
|
14
|
+
fallback?: ReactNode;
|
|
15
|
+
/**
|
|
16
|
+
* Optional redirect function to call when user is not authenticated.
|
|
17
|
+
* This can be used to programmatically navigate to a login page.
|
|
18
|
+
*/
|
|
19
|
+
onUnauthorized?: () => void;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Route guard component that conditionally renders content based on authentication status.
|
|
23
|
+
*
|
|
24
|
+
* This component uses the SecurityContext to check if the user is authenticated.
|
|
25
|
+
* If authenticated, it renders the children. If not authenticated, it renders the fallback
|
|
26
|
+
* content (if provided) and optionally calls the onUnauthorized callback.
|
|
27
|
+
*
|
|
28
|
+
* @param children - The protected content to render when authenticated.
|
|
29
|
+
* @param fallback - Optional fallback content to render when not authenticated.
|
|
30
|
+
* @param onUnauthorized - Optional callback to execute when user is not authenticated.
|
|
31
|
+
* @returns The children if authenticated, fallback if provided, or null otherwise.
|
|
32
|
+
* @example
|
|
33
|
+
* ```tsx
|
|
34
|
+
* import { RouteGuard } from '@ahoo-wang/fetcher-react';
|
|
35
|
+
*
|
|
36
|
+
* function ProtectedPage() {
|
|
37
|
+
* return (
|
|
38
|
+
* <RouteGuard
|
|
39
|
+
* fallback={<div>Please log in to access this page.</div>}
|
|
40
|
+
* onUnauthorized={() => navigate('/login')}
|
|
41
|
+
* >
|
|
42
|
+
* <div>Protected content</div>
|
|
43
|
+
* </RouteGuard>
|
|
44
|
+
* );
|
|
45
|
+
* }
|
|
46
|
+
* ```
|
|
47
|
+
*/
|
|
48
|
+
export declare function RouteGuard({ children, fallback, onUnauthorized, }: RouteGuardProps): string | number | bigint | boolean | Iterable<ReactNode> | Promise<string | number | bigint | boolean | import('react').ReactPortal | import('react').ReactElement<unknown, string | import('react').JSXElementConstructor<any>> | Iterable<ReactNode> | null | undefined> | import("react/jsx-runtime").JSX.Element | null | undefined;
|
|
49
|
+
//# sourceMappingURL=RouteGuard.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"RouteGuard.d.ts","sourceRoot":"","sources":["../../src/cosec/RouteGuard.tsx"],"names":[],"mappings":"AAaA,OAAO,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAGlC;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B;;OAEG;IACH,QAAQ,EAAE,SAAS,CAAC;IAEpB;;;OAGG;IACH,QAAQ,CAAC,EAAE,SAAS,CAAC;IAErB;;;OAGG;IACH,cAAc,CAAC,EAAE,MAAM,IAAI,CAAC;CAC7B;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;GA0BG;AACH,wBAAgB,UAAU,CAAC,EACzB,QAAQ,EACR,QAAQ,EACR,cAAc,GACf,EAAE,eAAe,2UAcjB"}
|
|
@@ -1,55 +1,88 @@
|
|
|
1
|
-
import { UseSecurityReturn } from './useSecurity';
|
|
1
|
+
import { UseSecurityOptions, UseSecurityReturn } from './useSecurity';
|
|
2
2
|
import { ReactNode } from 'react';
|
|
3
3
|
import { TokenStorage } from '@ahoo-wang/fetcher-cosec';
|
|
4
4
|
/**
|
|
5
|
-
* Type alias for the security context value,
|
|
6
|
-
*
|
|
5
|
+
* Type alias for the security context value, representing the authentication state and methods.
|
|
6
|
+
* This is equivalent to the return type of the useSecurity hook, providing reactive access to:
|
|
7
|
+
* - Current authenticated user information (JWT payload)
|
|
8
|
+
* - Authentication status (boolean flag)
|
|
9
|
+
* - Sign-in method for authenticating users
|
|
10
|
+
* - Sign-out method for clearing authentication
|
|
11
|
+
*
|
|
12
|
+
* Used internally by the SecurityContext to type the context value.
|
|
7
13
|
*/
|
|
8
14
|
export type SecurityContext = UseSecurityReturn;
|
|
9
15
|
/**
|
|
10
16
|
* React context for managing authentication state across the component tree.
|
|
11
|
-
* This context
|
|
12
|
-
* without prop drilling.
|
|
17
|
+
* This context enables sharing of authentication state and methods between components
|
|
18
|
+
* without prop drilling. Components can access authentication data and methods through
|
|
19
|
+
* the useSecurityContext hook when wrapped by the SecurityProvider.
|
|
20
|
+
*
|
|
21
|
+
* The context value is undefined by default, requiring components to be wrapped by
|
|
22
|
+
* SecurityProvider to access authentication functionality.
|
|
13
23
|
*/
|
|
14
24
|
export declare const SecurityContext: import('react').Context<UseSecurityReturn | undefined>;
|
|
15
25
|
/**
|
|
16
|
-
*
|
|
26
|
+
* Configuration options for the SecurityProvider component.
|
|
27
|
+
* Extends UseSecurityOptions to include provider-specific settings like token storage and children.
|
|
17
28
|
*/
|
|
18
|
-
export interface SecurityContextOptions {
|
|
29
|
+
export interface SecurityContextOptions extends UseSecurityOptions {
|
|
19
30
|
/**
|
|
20
31
|
* The token storage instance used to manage authentication tokens.
|
|
21
|
-
* This should be a valid TokenStorage implementation that handles token persistence
|
|
32
|
+
* This should be a valid TokenStorage implementation that handles token persistence,
|
|
33
|
+
* retrieval, and lifecycle management across different storage backends (localStorage,
|
|
34
|
+
* sessionStorage, memory, etc.).
|
|
22
35
|
*/
|
|
23
36
|
tokenStorage: TokenStorage;
|
|
24
37
|
/**
|
|
25
38
|
* The child components that will have access to the security context.
|
|
39
|
+
* These components can use the useSecurityContext hook to access authentication state and methods.
|
|
26
40
|
*/
|
|
27
41
|
children: ReactNode;
|
|
28
42
|
}
|
|
29
43
|
/**
|
|
30
44
|
* Provider component that supplies authentication state and methods to its child components.
|
|
31
45
|
* This component wraps the application or a portion of it to provide access to authentication
|
|
32
|
-
* functionality through the useSecurityContext hook.
|
|
46
|
+
* functionality through the useSecurityContext hook. It internally uses the useSecurity hook
|
|
47
|
+
* to manage authentication state and makes it available via React context.
|
|
33
48
|
*
|
|
34
49
|
* @param tokenStorage - The token storage instance for managing authentication tokens.
|
|
50
|
+
* This should be a valid TokenStorage implementation that handles
|
|
51
|
+
* token persistence, retrieval, and lifecycle management across different
|
|
52
|
+
* storage backends (localStorage, sessionStorage, memory, etc.).
|
|
35
53
|
* @param children - The child components that will have access to the security context.
|
|
54
|
+
* These components can use the useSecurityContext hook to access authentication
|
|
55
|
+
* state and methods without prop drilling.
|
|
56
|
+
* @param useSecurityOptions - Optional configuration object containing lifecycle callbacks
|
|
57
|
+
* for sign-in and sign-out events. Extends UseSecurityOptions interface.
|
|
58
|
+
* @param useSecurityOptions.onSignIn - Callback function invoked when sign in is successful.
|
|
59
|
+
* @param useSecurityOptions.onSignOut - Callback function invoked when sign out occurs.
|
|
36
60
|
* @returns A React element that provides the security context to its children.
|
|
37
|
-
*
|
|
61
|
+
* The context value includes currentUser, authenticated status, signIn, and signOut methods.
|
|
62
|
+
* @throws {Error} May throw errors if tokenStorage operations fail during initialization,
|
|
63
|
+
* such as invalid tokens or storage access issues (implementation dependent).
|
|
38
64
|
* @example
|
|
39
65
|
* ```tsx
|
|
40
|
-
* import { SecurityProvider } from '@ahoo-wang/fetcher-react
|
|
66
|
+
* import { SecurityProvider } from '@ahoo-wang/fetcher-react';
|
|
41
67
|
* import { tokenStorage } from './tokenStorage';
|
|
68
|
+
* import { useNavigate } from 'react-router-dom';
|
|
42
69
|
*
|
|
43
70
|
* function App() {
|
|
71
|
+
* const navigate = useNavigate();
|
|
72
|
+
*
|
|
44
73
|
* return (
|
|
45
|
-
* <SecurityProvider
|
|
74
|
+
* <SecurityProvider
|
|
75
|
+
* tokenStorage={tokenStorage}
|
|
76
|
+
* onSignIn={() => navigate('/dashboard')}
|
|
77
|
+
* onSignOut={() => navigate('/login')}
|
|
78
|
+
* >
|
|
46
79
|
* <MyApp />
|
|
47
80
|
* </SecurityProvider>
|
|
48
81
|
* );
|
|
49
82
|
* }
|
|
50
83
|
* ```
|
|
51
84
|
*/
|
|
52
|
-
export declare function SecurityProvider({ tokenStorage, children, }: SecurityContextOptions): import("react/jsx-runtime").JSX.Element;
|
|
85
|
+
export declare function SecurityProvider({ tokenStorage, children, ...useSecurityOptions }: SecurityContextOptions): import("react/jsx-runtime").JSX.Element;
|
|
53
86
|
/**
|
|
54
87
|
* Hook to access the security context within components wrapped by SecurityProvider.
|
|
55
88
|
* This hook provides reactive access to authentication state and methods throughout the component tree.
|
|
@@ -58,7 +91,7 @@ export declare function SecurityProvider({ tokenStorage, children, }: SecurityCo
|
|
|
58
91
|
* @throws {Error} Throws an error if used outside of a SecurityProvider component.
|
|
59
92
|
* @example
|
|
60
93
|
* ```tsx
|
|
61
|
-
* import { useSecurityContext } from '@ahoo-wang/fetcher-react
|
|
94
|
+
* import { useSecurityContext } from '@ahoo-wang/fetcher-react';
|
|
62
95
|
*
|
|
63
96
|
* function UserProfile() {
|
|
64
97
|
* const { currentUser, authenticated, signOut } = useSecurityContext();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"SecurityContext.d.ts","sourceRoot":"","sources":["../../src/cosec/SecurityContext.tsx"],"names":[],"mappings":"AAaA,OAAO,
|
|
1
|
+
{"version":3,"file":"SecurityContext.d.ts","sourceRoot":"","sources":["../../src/cosec/SecurityContext.tsx"],"names":[],"mappings":"AAaA,OAAO,EAEL,kBAAkB,EAClB,iBAAiB,EAClB,MAAM,eAAe,CAAC;AACvB,OAAO,EAAiB,SAAS,EAAc,MAAM,OAAO,CAAC;AAC7D,OAAO,EAAE,YAAY,EAAE,MAAM,0BAA0B,CAAC;AAExD;;;;;;;;;GASG;AACH,MAAM,MAAM,eAAe,GAAG,iBAAiB,CAAC;AAEhD;;;;;;;;GAQG;AACH,eAAO,MAAM,eAAe,wDAE3B,CAAC;AAEF;;;GAGG;AACH,MAAM,WAAW,sBAAuB,SAAQ,kBAAkB;IAChE;;;;;OAKG;IACH,YAAY,EAAE,YAAY,CAAC;IAE3B;;;OAGG;IACH,QAAQ,EAAE,SAAS,CAAC;CACrB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAyCG;AACH,wBAAgB,gBAAgB,CAAC,EAC/B,YAAY,EACZ,QAAQ,EACR,GAAG,kBAAkB,EACtB,EAAE,sBAAsB,2CAOxB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AACH,wBAAgB,kBAAkB,IAAI,eAAe,CAQpD"}
|
package/dist/cosec/index.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/cosec/index.ts"],"names":[],"mappings":"AAaA,cAAc,mBAAmB,CAAC;AAClC,cAAc,eAAe,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/cosec/index.ts"],"names":[],"mappings":"AAaA,cAAc,mBAAmB,CAAC;AAClC,cAAc,eAAe,CAAC;AAC9B,cAAc,cAAc,CAAC"}
|
|
@@ -1,11 +1,31 @@
|
|
|
1
1
|
import { TokenStorage, CompositeToken, CoSecJwtPayload } from '@ahoo-wang/fetcher-cosec';
|
|
2
|
+
/**
|
|
3
|
+
* Type representing a composite token provider.
|
|
4
|
+
* Can be either a direct composite token or a function that returns a promise of a composite token.
|
|
5
|
+
*/
|
|
6
|
+
type CompositeTokenProvider = CompositeToken | (() => Promise<CompositeToken>);
|
|
2
7
|
export declare const ANONYMOUS_USER: CoSecJwtPayload;
|
|
8
|
+
/**
|
|
9
|
+
* Options for configuring the useSecurity hook.
|
|
10
|
+
*/
|
|
11
|
+
export interface UseSecurityOptions {
|
|
12
|
+
/**
|
|
13
|
+
* Callback function invoked when sign in is successful.
|
|
14
|
+
* This is called after the token has been successfully stored.
|
|
15
|
+
*/
|
|
16
|
+
onSignIn?: () => void;
|
|
17
|
+
/**
|
|
18
|
+
* Callback function invoked when sign out occurs.
|
|
19
|
+
* This is called after the token has been removed.
|
|
20
|
+
*/
|
|
21
|
+
onSignOut?: () => void;
|
|
22
|
+
}
|
|
3
23
|
/**
|
|
4
24
|
* Return type for the useSecurity hook.
|
|
5
25
|
*/
|
|
6
26
|
export interface UseSecurityReturn {
|
|
7
27
|
/**
|
|
8
|
-
* The current authenticated user's JWT payload, or
|
|
28
|
+
* The current authenticated user's JWT payload, or ANONYMOUS_USER if not authenticated.
|
|
9
29
|
* Contains user information extracted from the access token.
|
|
10
30
|
*/
|
|
11
31
|
currentUser: CoSecJwtPayload;
|
|
@@ -15,10 +35,12 @@ export interface UseSecurityReturn {
|
|
|
15
35
|
*/
|
|
16
36
|
authenticated: boolean;
|
|
17
37
|
/**
|
|
18
|
-
* Function to sign in with a composite token.
|
|
19
|
-
* @param
|
|
38
|
+
* Function to sign in with a composite token or a function that returns a promise of composite token.
|
|
39
|
+
* @param compositeTokenProvider - Either a composite token containing access and refresh tokens,
|
|
40
|
+
* or a function that returns a promise resolving to a composite token.
|
|
41
|
+
* @returns A promise that resolves when the sign-in operation is complete.
|
|
20
42
|
*/
|
|
21
|
-
signIn: (
|
|
43
|
+
signIn: (compositeTokenProvider: CompositeTokenProvider) => Promise<void>;
|
|
22
44
|
/**
|
|
23
45
|
* Function to sign out the current user.
|
|
24
46
|
*/
|
|
@@ -34,6 +56,9 @@ export interface UseSecurityReturn {
|
|
|
34
56
|
* @param tokenStorage - The token storage instance used to manage authentication tokens.
|
|
35
57
|
* This should be a valid TokenStorage implementation that handles
|
|
36
58
|
* token persistence and retrieval.
|
|
59
|
+
* @param options - Optional configuration object containing lifecycle callbacks.
|
|
60
|
+
* @param options.onSignIn - Callback function invoked when sign in is successful.
|
|
61
|
+
* @param options.onSignOut - Callback function invoked when sign out occurs.
|
|
37
62
|
* @returns An object containing:
|
|
38
63
|
* - currentUser: The current authenticated user's JWT payload, or null if not authenticated.
|
|
39
64
|
* - authenticated: Boolean indicating whether the user is currently authenticated.
|
|
@@ -45,12 +70,38 @@ export interface UseSecurityReturn {
|
|
|
45
70
|
* ```typescript
|
|
46
71
|
* import { useSecurity } from '@ahoo-wang/fetcher-react/cosec';
|
|
47
72
|
* import { tokenStorage } from './tokenStorage';
|
|
73
|
+
* import { useNavigate } from 'react-router-dom';
|
|
48
74
|
*
|
|
49
75
|
* function App() {
|
|
50
|
-
* const
|
|
76
|
+
* const navigate = useNavigate();
|
|
77
|
+
*
|
|
78
|
+
* const { currentUser, authenticated, signIn, signOut } = useSecurity(tokenStorage, {
|
|
79
|
+
* onSignIn: () => {
|
|
80
|
+
* // Redirect to dashboard after successful login
|
|
81
|
+
* navigate('/dashboard');
|
|
82
|
+
* },
|
|
83
|
+
* onSignOut: () => {
|
|
84
|
+
* // Redirect to login page after logout
|
|
85
|
+
* navigate('/login');
|
|
86
|
+
* }
|
|
87
|
+
* });
|
|
88
|
+
*
|
|
89
|
+
* const handleSignIn = async () => {
|
|
90
|
+
* // Direct token
|
|
91
|
+
* await signIn(compositeToken);
|
|
92
|
+
*
|
|
93
|
+
* // Or async function
|
|
94
|
+
* await signIn(async () => {
|
|
95
|
+
* const response = await fetch('/api/auth/login', {
|
|
96
|
+
* method: 'POST',
|
|
97
|
+
* body: JSON.stringify({ username, password })
|
|
98
|
+
* });
|
|
99
|
+
* return response.json();
|
|
100
|
+
* });
|
|
101
|
+
* };
|
|
51
102
|
*
|
|
52
103
|
* if (!authenticated) {
|
|
53
|
-
* return <button onClick={
|
|
104
|
+
* return <button onClick={handleSignIn}>Sign In</button>;
|
|
54
105
|
* }
|
|
55
106
|
*
|
|
56
107
|
* return (
|
|
@@ -62,5 +113,6 @@ export interface UseSecurityReturn {
|
|
|
62
113
|
* }
|
|
63
114
|
* ```
|
|
64
115
|
*/
|
|
65
|
-
export declare function useSecurity(tokenStorage: TokenStorage): UseSecurityReturn;
|
|
116
|
+
export declare function useSecurity(tokenStorage: TokenStorage, options?: UseSecurityOptions): UseSecurityReturn;
|
|
117
|
+
export {};
|
|
66
118
|
//# sourceMappingURL=useSecurity.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"useSecurity.d.ts","sourceRoot":"","sources":["../../src/cosec/useSecurity.ts"],"names":[],"mappings":"AAeA,OAAO,EACL,YAAY,EACZ,cAAc,EACd,eAAe,EAChB,MAAM,0BAA0B,CAAC;
|
|
1
|
+
{"version":3,"file":"useSecurity.d.ts","sourceRoot":"","sources":["../../src/cosec/useSecurity.ts"],"names":[],"mappings":"AAeA,OAAO,EACL,YAAY,EACZ,cAAc,EACd,eAAe,EAChB,MAAM,0BAA0B,CAAC;AAGlC;;;GAGG;AACH,KAAK,sBAAsB,GAAG,cAAc,GAAG,CAAC,MAAM,OAAO,CAAC,cAAc,CAAC,CAAC,CAAC;AAE/E,eAAO,MAAM,cAAc,EAAE,eAK5B,CAAC;AAEF;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC;;;OAGG;IACH,QAAQ,CAAC,EAAE,MAAM,IAAI,CAAC;IAEtB;;;OAGG;IACH,SAAS,CAAC,EAAE,MAAM,IAAI,CAAC;CACxB;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAChC;;;OAGG;IACH,WAAW,EAAE,eAAe,CAAC;IAE7B;;;OAGG;IACH,aAAa,EAAE,OAAO,CAAC;IAEvB;;;;;OAKG;IACH,MAAM,EAAE,CAAC,sBAAsB,EAAE,sBAAsB,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAE1E;;OAEG;IACH,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkEG;AACH,wBAAgB,WAAW,CACzB,YAAY,EAAE,YAAY,EAC1B,OAAO,GAAE,kBAAuB,GAC/B,iBAAiB,CA0BnB"}
|