# @documedis-components/prescription-sign

React component for signing electronic prescriptions with HIN authentication.

## Installation

```bash
npm install @documedis-components/prescription-sign
```

## Requirements

This component requires:

- React 18.0.0 or higher
- An access token given by HCI allowing access to our components-service backend

## Quick Start

```tsx
import { PrescriptionSign } from '@documedis-components/prescription-sign/react';

function App() {
  return <PrescriptionSign environment="demo" accessToken="your-access-token" chmed="CHMED16A1..." onSuccess={(signedCHMED) => console.log('Signed:', signedCHMED)} onError={(error) => console.error('Error:', error)} />;
}
```

## API Reference

### PrescriptionSign Component

#### Props

| Parameter              | Type                                                   | Required | Description                                                                                                        |
| ---------------------- | ------------------------------------------------------ | -------- | ------------------------------------------------------------------------------------------------------------------ |
| `environment`          | `'demo' \| 'prod'`                                     | ✅       | Environment configuration for the prescription service ('demo' for testing and development, 'prod' for production) |
| `accessToken`          | `string`                                               | ✅       | Authentication token for backend service                                                                           |
| `chmed`                | `string`                                               | ✅       | Encoded CHMED prescription data                                                                                    |
| `sessionToken`         | `string`                                               | ❌       | Optional existing session token to reuse authentication state                                                      |
| `onSessionTokenUpdate` | `(token: string) => void`                              | ❌       | Callback invoked when the session token is updated                                                                 |
| `onSuccess`            | `(signedCHMED: string, generatedPdf?: string) => void` | ❌       | Callback invoked when prescription signing succeeds                                                                |
| `onError`              | `(error: DomainError) => void`                         | ❌       | Callback invoked when prescription signing fails                                                                   |
| `generatePdf`          | `boolean`                                              | ❌       | Generate PDF document alongside signed CHMED (default: false)                                                      |
| `className`            | `string`                                               | ❌       | Additional CSS classes                                                                                             |

### usePrescriptionSigning Hook

For advanced use cases, you can use the `usePrescriptionSigning` hook directly:

```tsx
import { usePrescriptionSigning } from '@documedis-components/prescription-sign/react';

function CustomSigningButton({ chmed, accessToken }) {
  const { start, interrupt, isActive, isSuccess, isError, signedCHMED } = usePrescriptionSigning({
    environment: 'demo',
    accessToken,
    onSuccess: (signedCHMED) => console.log('Signed!', signedCHMED),
    onError: (error) => console.error('Failed:', error),
  });

  if (isSuccess) {
    return <div>✅ Prescription signed</div>;
  }

  return (
    <button onClick={() => start(chmed)} disabled={isActive}>
      {isActive ? 'Signing...' : 'Sign Prescription'}
    </button>
  );
}
```

#### Hook Parameters

| Parameter              | Type                                                   | Required | Description                              |
| ---------------------- | ------------------------------------------------------ | -------- | ---------------------------------------- |
| `environment`          | `'demo' \| 'prod'`                                     | ✅       | Environment configuration                |
| `accessToken`          | `string`                                               | ✅       | Authentication token for backend service |
| `sessionToken`         | `string`                                               | ❌       | Optional existing session token          |
| `onSessionTokenUpdate` | `(token: string) => void`                              | ❌       | Callback when session token updates      |
| `onSuccess`            | `(signedCHMED: string, generatedPdf?: string) => void` | ❌       | Success callback                         |
| `onError`              | `(error: DomainError) => void`                         | ❌       | Error callback                           |

#### Hook Return Values

| Property      | Type                                             | Description                                  |
| ------------- | ------------------------------------------------ | -------------------------------------------- |
| `start`       | `(chmed: string, generatePdf?: boolean) => void` | Initiates the signing process                |
| `interrupt`   | `() => void`                                     | Terminates the signing process               |
| `isIdle`      | `boolean`                                        | True when ready to start signing             |
| `isActive`    | `boolean`                                        | True when actively processing                |
| `isError`     | `boolean`                                        | True when in error state                     |
| `isSuccess`   | `boolean`                                        | True when signing completed successfully     |
| `isSigning`   | `boolean`                                        | True during the actual signature operation   |
| `signedCHMED` | `string \| undefined`                            | The signed prescription data (after success) |

## Session Restoration

The library intelligently optimizes the signing process by checking session state first:

- **Fast Path**: When valid authentication data exists in session, the process can skip the authorization phase
- **Full Path**: When no valid session data exists, the full OAuth/SAML flow executes

## Error Handling

All errors are instances of `DomainError` with three key properties:

- `code`: Stable error code for programmatic handling
- `message`: Technical message for debugging (not for end users)
- `userMessage`: User-friendly message safe to display in UI

### Example Error Handling

```tsx
onError={(error) => {
  // Show user-friendly message in UI
  showNotification(error.userMessage);

  // Handle specific errors programmatically
  switch (error.code) {
    case 'POPUP_CLOSED':
      // User closed the popup, maybe offer to retry
      break;
    case 'SESSION_EXPIRED':
      // Session expired, clear cache and retry
      clearSession();
      break;
    case 'INVALID_FORMAT':
      // Invalid prescription data format
      highlightFormErrors();
      break;
  }

  // Log technical details for debugging
  console.error(error.message, error.code);
}}
```

### Common Error Codes

- `POPUP_CLOSED` - User closed authentication popup
- `POPUP_BLOCKED` - Browser blocked popup window
- `SESSION_EXPIRED` - Authentication session expired
- `INVALID_TOKEN` - Invalid or expired access token
- `INVALID_FORMAT` - Malformed prescription data
- `HIN_ERROR` - HIN service error
- `API_CONNECTION_FAILED` - Network connection failed
- `TIMEOUT` - Operation timed out

## Environment Configuration

- `demo` - Demo environment with non-production data (safe for testing and development)
- `prod` - _coming soon_

## Usage Examples

### Basic Implementation

```tsx
<PrescriptionSign environment="demo" accessToken="your-token" chmed="CHMED16A1H4sI..." />
```

### With Event Handlers

```tsx
<PrescriptionSign
  environment="demo"
  accessToken="your-token"
  chmed="CHMED16A1H4sI..."
  onSuccess={(signedCHMED) => {
    console.log('Prescription signed:', signedCHMED);
    // Save to database, redirect user, etc.
  }}
  onError={(error) => {
    // Display user-friendly message
    showNotification(error.userMessage);
    // Log technical details for debugging
    console.error('Error code:', error.code, error.message);
  }}
/>
```

### With PDF Generation

```tsx
<PrescriptionSign
  environment="prod"
  accessToken="your-token"
  chmed="CHMED16A1H4sI..."
  generatePdf={true}
  onSuccess={(signedCHMED, generatedPdf) => {
    console.log('Signed CHMED:', signedCHMED);
    if (generatedPdf) {
      console.log('Generated PDF:', generatedPdf);
      // Save or display the PDF
    }
  }}
/>
```

### Using the Hook for Custom UI

```tsx
import { usePrescriptionSigning } from '@documedis-components/prescription-sign/react';

function CustomSigningButton({ chmed, environment, accessToken }) {
  const { start, interrupt, isActive, isSuccess, isError, signedCHMED } = usePrescriptionSigning({
    environment,
    accessToken,
    onSuccess: (signedCHMED) => console.log('Signed!', signedCHMED),
    onError: (error) => {
      // You can access error.userMessage for UI display
      console.error('Error:', error.code, '-', error.userMessage);
    },
  });

  if (isSuccess) {
    return <div>✅ Prescription signed: {signedCHMED?.substring(0, 20)}...</div>;
  }

  if (isError) {
    return (
      <div>
        ❌ Signing failed.
        <button onClick={() => start(chmed)}>Retry</button>
      </div>
    );
  }

  return (
    <div>
      <button onClick={() => start(chmed)} disabled={isActive}>
        {isActive ? 'Signing...' : 'Sign Prescription'}
      </button>
      {isActive && <button onClick={interrupt}>Cancel</button>}
    </div>
  );
}
```

## Full Documentation

For complete documentation, examples, and interactive demos, visit: https://documentation.apps.documedis.ch

## License

Copyright (c) 2025 Galenica AG. All rights reserved.

This software is proprietary and confidential. Unauthorized copying, modification, distribution, or use of this software, via any medium, is strictly prohibited without the express written permission of Galenica AG.

## Support

Issues: Please contact your Documedis support representative
