@ghostly-solutions/auth 0.1.1 → 0.2.1

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 CHANGED
@@ -2,33 +2,18 @@
2
2
 
3
3
  Authentication SDK for Ghostly Solutions products.
4
4
 
5
- The SDK implements a fixed Keycloak redirect flow with Ghostly Auth API validation and typed session state.
5
+ The SDK is OAuth redirect + server-owned cookie session. Client code does not process OAuth
6
+ callback tokens and does not define auth route handlers.
6
7
 
7
- ## Highlights
8
+ ## Contract
8
9
 
9
- - Fixed API contract (no runtime endpoint configuration).
10
- - Typed core client with deterministic error codes.
11
- - Dedicated callback flow with immediate token URL cleanup.
12
- - Session state with lazy revalidation.
13
- - Cross-tab synchronization via `BroadcastChannel`.
14
- - React adapter (`AuthProvider`, `useAuth`).
15
- - React callback helpers (`AuthCallbackHandler`, `useAuthCallbackRedirect`).
16
- - React session gate (`AuthSessionGate`).
17
- - Next adapter (server and client guards).
18
- - Next Auth Kit with ready route handlers (`mock` or `proxy`) and server-session helpers.
10
+ Fixed API endpoints:
19
11
 
20
- ## Fixed API Endpoints
21
-
22
- - `GET /v1/auth/keycloak/login`
23
- - `POST /v1/auth/keycloak/validate`
24
- - `GET /v1/auth/me`
25
- - `POST /v1/auth/logout`
26
-
27
- ## Entry Points
28
-
29
- - `@ghostly-solutions/auth`
30
- - `@ghostly-solutions/auth/react`
31
- - `@ghostly-solutions/auth/next`
12
+ - `GET /oauth/authorize`
13
+ - `GET /oauth/callback/provider`
14
+ - `GET /oauth/session`
15
+ - `POST /oauth/refresh`
16
+ - `POST /oauth/logout`
32
17
 
33
18
  ## Install
34
19
 
@@ -36,92 +21,91 @@ The SDK implements a fixed Keycloak redirect flow with Ghostly Auth API validati
36
21
  npm install @ghostly-solutions/auth
37
22
  ```
38
23
 
39
- ## Development
40
-
41
- ```bash
42
- npm run lint
43
- npm run typecheck
44
- npm run test
45
- npm run build
46
- ```
47
-
48
- All CI and official workflows are npm-first.
49
-
50
- Bun is optional for local use through aliases in `bun.json`.
51
-
52
- ## Quick Start
24
+ ## Core Usage
53
25
 
54
26
  ```ts
55
27
  import { createAuthClient } from "@ghostly-solutions/auth";
56
28
 
57
- const authClient = createAuthClient();
29
+ const auth = createAuthClient();
58
30
 
59
- // Start login flow
60
- authClient.login();
31
+ await auth.init();
32
+ const session = await auth.getSession();
61
33
 
62
- // In /auth/callback route
63
- await authClient.completeCallbackRedirect();
34
+ if (!session) {
35
+ auth.login();
36
+ }
64
37
  ```
65
38
 
66
- ## Next.js "No-Glue" Integration
67
-
68
- Use the high-level Next adapter in `@ghostly-solutions/auth/next`:
69
-
70
- - `getNextServerSession()`
71
- - `requireNextServerSession()`
72
- - `createNextAuthRouteHandlers({ mode: "mock" | "proxy" })`
73
-
74
- This removes custom auth boilerplate from application code and keeps app-level integration thin.
75
-
76
- ## Callback Page Helper
39
+ ## React Usage
77
40
 
78
41
  ```tsx
79
- import { AuthCallbackHandler } from "@ghostly-solutions/auth/react";
42
+ import { AuthProvider, AuthSessionGate } from "@ghostly-solutions/auth/react";
80
43
 
81
- export default function AuthCallbackPage() {
44
+ export function App() {
82
45
  return (
83
- <AuthCallbackHandler
84
- processing={<div>Signing you in...</div>}
85
- renderError={() => <div>Could not complete sign in.</div>}
86
- />
46
+ <AuthProvider>
47
+ <AuthSessionGate
48
+ loading={<div>Loading...</div>}
49
+ unauthorized={({ login }) => <button onClick={() => login()}>Sign in</button>}
50
+ authorized={(session) => <div>{session.email}</div>}
51
+ />
52
+ </AuthProvider>
87
53
  );
88
54
  }
89
55
  ```
90
56
 
91
- ## Error Handling
57
+ ## Next.js Usage
92
58
 
93
59
  ```ts
94
- import { AuthSdkError } from "@ghostly-solutions/auth";
95
-
96
- try {
97
- await authClient.requireSession();
98
- } catch (error) {
99
- if (error instanceof AuthSdkError) {
100
- if (error.code === "unauthorized") {
101
- authClient.login();
102
- }
103
- }
60
+ import { requireNextServerSession } from "@ghostly-solutions/auth/next";
61
+
62
+ export async function getServerData(headers: Headers) {
63
+ const session = await requireNextServerSession({
64
+ headers,
65
+ apiOrigin: "https://api.ghostlysolutions.com",
66
+ });
67
+
68
+ return {
69
+ actorId: session.id,
70
+ };
104
71
  }
105
72
  ```
106
73
 
107
- ## Documentation
74
+ No Next route handlers are required.
108
75
 
109
- - [Docs Index](./docs/index.md)
110
- - [Overview](./docs/overview.md)
111
- - [API Reference](./docs/api-reference.md)
112
- - [Integration Guide](./docs/integration-guide.md)
113
- - [Architecture](./docs/architecture.md)
114
- - [Development and CI](./docs/development-and-ci.md)
76
+ ## Extension Usage
115
77
 
116
- ## Interactive Demo
78
+ ```ts
79
+ import { createExtensionAuthClient } from "@ghostly-solutions/auth/extension";
117
80
 
118
- Run the simulated authentication page in this repository:
81
+ const auth = createExtensionAuthClient({
82
+ apiOrigin: "https://api.ghostlysolutions.com",
83
+ launchWebAuthFlow: async ({ authorizeUrl }) => {
84
+ // chrome.identity.launchWebAuthFlow(...) wrapper
85
+ await openAuthWindow(authorizeUrl);
86
+ },
87
+ });
88
+
89
+ await auth.loginWithWebAuthFlow();
90
+ ```
91
+
92
+ ## Development
119
93
 
120
94
  ```bash
121
- npm run demo
95
+ npm run lint
96
+ npm run typecheck
97
+ npm run test
98
+ npm run build
122
99
  ```
123
100
 
124
- Then open `http://localhost:4100/` to test login, callback processing, session retrieval,
125
- and logout.
101
+ Bun is optional for local shortcuts (`bun run ...`).
126
102
 
127
- Detailed demo docs: [demo/README.md](./demo/README.md).
103
+ ## Documentation
104
+
105
+ - [Docs Index](./docs/index.md)
106
+ - [Overview](./docs/overview.md)
107
+ - [API Reference](./docs/api-reference.md)
108
+ - [Integration Guide](./docs/integration-guide.md)
109
+ - [Architecture](./docs/architecture.md)
110
+ - [Development and CI](./docs/development-and-ci.md)
111
+ - [Demo](./demo/README.md)
@@ -8,25 +8,33 @@ interface GhostlySession {
8
8
  permissions: string[];
9
9
  }
10
10
 
11
- interface ProcessCallbackResult {
12
- redirectTo: string;
13
- session: GhostlySession;
11
+ interface AuthClientOptions {
12
+ apiOrigin?: string;
13
+ application?: string;
14
+ }
15
+ interface AuthInitOptions {
16
+ forceRefresh?: boolean;
17
+ }
18
+ interface AuthInitResult {
19
+ session: GhostlySession | null;
20
+ status: "authenticated" | "unauthenticated";
14
21
  }
15
22
  interface LoginOptions {
16
23
  returnTo?: string;
24
+ application?: string;
17
25
  }
18
26
  interface SessionRequestOptions {
19
27
  forceRefresh?: boolean;
20
28
  }
21
29
  type SessionListener = (session: GhostlySession | null) => void;
22
30
  interface AuthClient {
23
- completeCallbackRedirect(): Promise<never>;
31
+ init(options?: AuthInitOptions): Promise<AuthInitResult>;
24
32
  getSession(options?: SessionRequestOptions): Promise<GhostlySession | null>;
25
33
  login(options?: LoginOptions): void;
26
34
  logout(): Promise<void>;
27
- processCallback(): Promise<ProcessCallbackResult>;
35
+ refresh(): Promise<GhostlySession | null>;
28
36
  requireSession(): Promise<GhostlySession>;
29
37
  subscribe(listener: SessionListener): () => void;
30
38
  }
31
39
 
32
- export type { AuthClient as A, GhostlySession as G, LoginOptions as L, ProcessCallbackResult as P, SessionListener as S, SessionRequestOptions as a };
40
+ export type { AuthClient as A, GhostlySession as G, LoginOptions as L, SessionListener as S, AuthClientOptions as a, AuthInitOptions as b, AuthInitResult as c, SessionRequestOptions as d };
@@ -1,7 +1,4 @@
1
1
  declare const authErrorCode: {
2
- readonly callbackMissingToken: "callback_missing_token";
3
- readonly callbackInvalidToken: "callback_invalid_token";
4
- readonly callbackValidationFailed: "callback_validation_failed";
5
2
  readonly unauthorized: "unauthorized";
6
3
  readonly networkError: "network_error";
7
4
  readonly apiError: "api_error";
@@ -0,0 +1,16 @@
1
+ import { A as AuthClient, L as LoginOptions } from './auth-client-Cdkp07ii.js';
2
+
3
+ interface LaunchWebAuthFlowPayload {
4
+ authorizeUrl: string;
5
+ }
6
+ interface ExtensionAuthClientOptions {
7
+ apiOrigin: string;
8
+ application?: string;
9
+ launchWebAuthFlow: (payload: LaunchWebAuthFlowPayload) => Promise<void>;
10
+ }
11
+ interface ExtensionAuthClient extends AuthClient {
12
+ loginWithWebAuthFlow(options?: LoginOptions): Promise<void>;
13
+ }
14
+ declare function createExtensionAuthClient(options: ExtensionAuthClientOptions): ExtensionAuthClient;
15
+
16
+ export { type ExtensionAuthClient, type ExtensionAuthClientOptions, createExtensionAuthClient };