Install & Compatibility
Where this runs
tested against v? · npm install
Install × environment matrix
Each cell = how many times install + import succeeded across repeated harness runs. Partial = flaky.
glibc = Debian/Ubuntu slim · musl = Alpine Linux
muslnode 18–226 runs
build_error
glibcnode 18–226 runs
build_error
Code
Verified usage
Verified import paths — ran on the pinned version, not inferred.
AuthHandler
✓ import { AuthHandler } from 'libts-csrfx-auth';
✗ const { AuthHandler } = require('libts-csrfx-auth');
The library primarily uses ESM. While CommonJS might transpile, direct `require` can lead to issues with type recognition or bundling, especially in modern TypeScript projects.
AuthHandlerConfig
✓ import type { AuthHandlerConfig } from 'libts-csrfx-auth';
✗ import { AuthHandlerConfig } from 'libts-csrfx-auth';
Use `import type` for importing interfaces or types to ensure they are stripped during compilation, preventing runtime errors or unnecessary bundle size.
AuthError
✓ import { AuthError } from 'libts-csrfx-auth';
✗ import AuthError from 'libts-csrfx-auth/dist/AuthError';
Named exports are standard; avoid deep imports from internal `dist` paths which are subject to change between versions.
This quickstart demonstrates the core authentication flow: logging in, fetching a CSRF token, making a protected request, and logging out, showing how to initialize and use the `AuthHandler`.
import { AuthHandler } from 'libts-csrfx-auth';
interface MyApiCredentials {
username: string;
password: string;
}
// Simulate a backend API
const API_BASE_URL = 'http://localhost:3000';
const authHandler = new AuthHandler({
apiBaseUrl: API_BASE_URL,
loginEndpoint: '/auth/login',
logoutEndpoint: '/auth/logout',
csrfTokenEndpoint: '/auth/csrf-token',
// In a real app, use a secure, persistent storage mechanism (e.g., localStorage, secure cookies)
// For this example, we'll use a simple in-memory store.
storage: {
get: (key) => {
console.log(`[Storage] Getting ${key}`);
return localStorage.getItem(key);
},
set: (key, value) => {
console.log(`[Storage] Setting ${key}=${value}`);
localStorage.setItem(key, value);
},
remove: (key) => {
console.log(`[Storage] Removing ${key}`);
localStorage.removeItem(key);
}
},
// Custom fetch function to intercept and add tokens/cookies
fetch: async (input, init) => {
const response = await fetch(input, {
...init,
headers: {
'Content-Type': 'application/json',
// Assuming AuthHandler automatically manages Cookie and X-CSRF-Token
...(init?.headers || {})
}
});
if (!response.ok) {
console.error(`API Error: ${response.status} ${response.statusText}`);
}
return response;
}
});
async function runAuthFlow() {
const credentials: MyApiCredentials = {
username: process.env.TEST_USERNAME ?? 'testuser',
password: process.env.TEST_PASSWORD ?? 'testpass'
};
try {
console.log('--- Attempting Login ---');
await authHandler.login(credentials);
console.log('Login successful! Session should be active.');
console.log('\n--- Fetching CSRF Token ---');
const csrfToken = await authHandler.getCSRFToken();
console.log(`Received CSRF Token: ${csrfToken ? csrfToken.substring(0, 10) + '...' : 'none'}`);
console.log('\n--- Making a Protected Request (e.g., update profile) ---');
// In a real scenario, `fetch` would be wrapped by AuthHandler to inject CSRF token
const protectedResponse = await authHandler.fetch(`${API_BASE_URL}/profile`, {
method: 'POST',
body: JSON.stringify({ name: 'Jane Doe' })
});
if (protectedResponse.ok) {
console.log('Protected request successful!');
} else {
console.error('Protected request failed.');
}
console.log('\n--- Attempting Logout ---');
await authHandler.logout();
console.log('Logout successful! Session should be terminated.');
} catch (error) {
console.error('Authentication flow failed:', error);
}
}
// Note: For a real example, you'd need a mock server at http://localhost:3000
// that handles /auth/login, /auth/logout, /auth/csrf-token, and /profile.
// The server should set 'Set-Cookie' headers for session and CSRF tokens
// and validate 'X-CSRF-Token' for POST requests.
runAuthFlow();
Errors
Common errors & fixes
TypeError: AuthHandler is not a constructor
Attempting to instantiate `AuthHandler` without `new` keyword, or incorrect import (e.g., CommonJS `require` when only ESM default export is available, or vice-versa).
fixEnsure you are using `new AuthHandler(...)` and that your import statement is `import { AuthHandler } from 'libts-csrfx-auth';` for ESM environments, or ensure correct CommonJS syntax if the library supports it. Verify your build system handles TypeScript modules correctly. Error: CSRF token mismatch
The CSRF token sent with a request does not match the token expected by the server. This can be due to an expired token, an invalid token (e.g., after logout/re-login), or a server-side misconfiguration.
fixClear browser cookies and session storage, then re-authenticate. Verify the `csrfTokenEndpoint` is correctly configured and the server is consistently setting and validating CSRF tokens. Ensure no caching issues are serving stale tokens.
Failed to fetch
Generic network error indicating the client could not reach the API endpoint. This could be due to incorrect `apiBaseUrl`, server being down, CORS issues, or browser network restrictions.
fixCheck `apiBaseUrl` for typos. Verify your backend server is running and accessible from the client's origin. Inspect browser developer tools (Network tab) for specific HTTP errors (e.g., 404, 500, CORS related errors). Ensure `fetch` API is available in your environment (Node.js >=18, Bun, browser).
Property 'username' does not exist on type 'AuthHandlerConfig'.
Attempting to pass authentication credentials directly into `AuthHandlerConfig` instead of the `login` method.
fixThe `AuthHandlerConfig` is for setting up the handler itself (endpoints, storage, fetch function). User credentials like `username` and `password` should be passed to the `login` method as arguments, for example: `authHandler.login({ username: 'user', password: 'pass' });` Audit
Dependencies
No dependency data recorded yet.