npm package: @rakilabs/klynt-sso-sdk
Description: Klynt SSO SDK for frontend applications
Author: Raki Labs
Latest version: 0.4.7

# Klynt SSO SDK

A TypeScript SDK for integrating with the Klynt SSO authentication system. Supports React, Vue, and vanilla JavaScript/TypeScript applications.

## Features

- 🔐 **Multi-tenant SSO authentication**
- ⚛️ **React hooks and components**
- 🖖 **Vue composables and components**
- 🔄 **Automatic token refresh**
- 🛡️ **Permission and feature checking**
- 🌐 **Cross-domain session management**
- 📱 **SSR/hydration safe**
- 🎯 **TypeScript support**

## Installation

```bash
npm install @rakilabs/klynt-sso-sdk
# or
yarn add @rakilabs/klynt-sso-sdk
```

## Quick Start

### React

```typescript
import { KlyntSSO } from '@rakilabs/klynt-sso-sdk';
import { SSOProvider, useKlyntSSO } from '@rakilabs/klynt-sso-sdk/react';

// 1. Wrap your app with SSOProvider
function App() {
  return (
    <SSOProvider config={{ authDomain: 'https://auth.klynt.dev' }}>
      <Dashboard />
    </SSOProvider>
  );
}

// 2. Use SSO in components
function Dashboard() {
  const { isAuthenticated, user, login, logout } = useKlyntSSO();

  if (!isAuthenticated) {
    return <button onClick={() => login({ username: 'user', password: 'pass' })}>Login</button>;
  }

  return (
    <div>
      <h1>Welcome, {user?.username}!</h1>
      <button onClick={logout}>Logout</button>
    </div>
  );
}
```

### Vue

```typescript
import { KlyntSSO } from '@rakilabs/klynt-sso-sdk';
import { provideSSO, useKlyntSSO } from '@rakilabs/klynt-sso-sdk/vue';

// 1. Setup in your main app
const app = createApp(App);
app.use(provideSSO, { authDomain: 'https://auth.klynt.dev' });

// 2. Use in components
export default defineComponent({
  setup() {
    const { isAuthenticated, user, login, logout } = useKlyntSSO();
    
    return {
      isAuthenticated,
      user,
      login,
      logout
    };
  }
});
```

### Vanilla JavaScript/TypeScript

```typescript
import { KlyntSSO } from '@rakilabs/klynt-sso-sdk';

const sso = new KlyntSSO({
  authDomain: 'https://auth.klynt.dev',
  currentTenant: 'main'
});

// Check authentication
const isAuth = await sso.isAuthenticated();

// Login
if (!isAuth) {
  await sso.login({ username: 'user', password: 'password' });
}

// Get user info
const user = await sso.getCurrentUser();

// Check permissions
const canEdit = await sso.hasPermission('edit:documents');
```

## Configuration

```typescript
interface SSOConfig {
  authDomain: string;              // SSO authentication domain
  currentTenant?: string;          // Current tenant ID (auto-detected)
  tokenRefreshThreshold?: number;  // Token refresh threshold in seconds (default: 300)
  autoRedirect?: boolean;          // Auto-redirect to login (default: true)
  debug?: boolean;                 // Enable debug logging (default: false)
}
```

## React API

### SSOProvider

```typescript
interface SSOProviderProps {
  config?: Partial<SSOConfig>;
  children: React.ReactNode;
  onAuthStateChange?: (isAuthenticated: boolean, user: SSOUser | null) => void;
}
```

### Hooks

- `useKlyntSSO()` - Main SSO context
- `useCurrentUser()` - Get current user
- `useIsAuthenticated()` - Authentication status
- `usePermission(permission, tenantId?)` - Check permission
- `useFeature(feature, tenantId?)` - Check feature access
- `useTenants()` - Available tenants

### Components

```typescript
// Protected Route
<ProtectedRoute permission="admin" fallback={<AccessDenied />}>
  <AdminPanel />
</ProtectedRoute>

// Higher-order component
const ProtectedAdmin = withAuth(AdminComponent, { permission: 'admin' });
```

## Vue API

### Plugin Installation

```typescript
app.use(KlyntSSOPlugin, {
  authDomain: 'https://auth.klynt.dev'
});
```

### Composables

- `useKlyntSSO()` - Main SSO composable
- `useCurrentUser()` - Get current user
- `useIsAuthenticated()` - Authentication status
- `usePermission(permission, tenantId?)` - Check permission
- `useFeature(feature, tenantId?)` - Check feature access
- `useTenants()` - Available tenants

## Core API

### KlyntSSO Class

```typescript
class KlyntSSO {
  // Authentication
  async isAuthenticated(): Promise<boolean>
  async getCurrentUser(): Promise<SSOUser | null>
  async login(credentials: LoginCredentials): Promise<LoginResponse>
  async logout(): Promise<void>

  // Permissions
  async hasPermission(permission: string, tenantId?: string): Promise<boolean>
  async hasFeature(feature: string, tenantId?: string): Promise<boolean>
  async hasAnyPermission(permissions: string[], tenantId?: string): Promise<boolean>
  async hasAllPermissions(permissions: string[], tenantId?: string): Promise<boolean>

  // Tenants
  async getAvailableTenants(): Promise<TenantInfo[]>
  async switchTenant(tenantId: string): Promise<void>
  async getTenantAccess(tenantId?: string): Promise<TenantAccess | null>

  // API calls with automatic token handling
  async apiCall(endpoint: string, options?: RequestInit): Promise<Response>
}
```

## Migration from v0.2.x

Version 0.3.0 introduces separate entry points to prevent React runtime loading issues:

```typescript
// Before v0.3.0
import { KlyntSSO, SSOProvider, useKlyntSSO } from '@rakilabs/klynt-sso-sdk';

// After v0.3.0  
import { KlyntSSO } from '@rakilabs/klynt-sso-sdk'; // Core classes/types
import { SSOProvider, useKlyntSSO } from '@rakilabs/klynt-sso-sdk/react'; // React components
```

## Error Handling

```typescript
import { SSOAuthError } from '@rakilabs/klynt-sso-sdk';

try {
  await sso.login(credentials);
} catch (error) {
  if (error instanceof SSOAuthError) {
    console.log('Auth error:', error.code, error.message);
  }
}
```

## Development Setup

For development against local Klynt server:

```typescript
const sso = new KlyntSSO({
  authDomain: 'http://localhost:8080', // Local development
  debug: true
});
```

## License

MIT

## Support

- GitHub Issues: https://github.com/nexra/klynt-core/issues
- Documentation: https://docs.klynt.dev/sso-sdk