npm package: @kosmas10/app-loader
Description: Universal app loader for AI Chat Extensions. Stage 2 of the two-stage bootstrap architecture that loads apps from CDN.
Author: Kosmas Karadimitriou
Latest version: 0.0.3

# @kosmas10/app-loader

Universal app loader for AI Chat Extensions. This is **Stage 2** of the two-stage bootstrap architecture.

## Architecture

The two-stage loader architecture ensures that bootstrap files distributed to clients never need to be updated:

```
┌─────────────────────────────────────────────────────────────────┐
│ Stage 1: Bootstrap HTML (distributed to clients, PERMANENT)    │
│ - Ultra-minimal (~20 lines)                                    │
│ - Sets window.__APP__ = 'app-name'                             │
│ - Loads Stage 2 from CDN with cache-busting                    │
└─────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────┐
│ Stage 2: App Loader (this package, updatable via npm)          │
│ - Derives package and file path from app name                  │
│ - Convention: @kosmas10/{app}/dist/{app}.html                  │
│ - Fetches app HTML from CDN                                    │
│ - Replaces document with fetched app                           │
└─────────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────────┐
│ Stage 3: App (any npm package following the convention)        │
│ - The actual application code                                  │
│ - Loaded and executed by Stage 2                               │
└─────────────────────────────────────────────────────────────────┘
```

## Benefits

- **Permanent bootstrap files**: Stage 1 is so simple it never needs updates
- **Minimal config**: Just set `window.__APP__` to the app name
- **Centralized control**: If an app moves, update the loader - not all bootstrap files
- **Easy to add apps**: Just create a bootstrap file with the app name

## Configuration

The bootstrap only needs to set one variable:

```javascript
window.__APP__ = 'my-app';
```

The loader derives from the app name:
- **Package**: `@kosmas10/{app}`
- **File**: `dist/{app}.html`
- **Title**: Converts kebab-case to Title Case

## Stage 1 Bootstrap Template

Distribute this to clients (only the app name changes):

```html
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>My App</title>
</head>
<body>
    <div id="root"></div>
    <script>
    /**
     * App Loader Bootstrap v1
     * Copyright (c) 2025 Nova Science Ventures LLC
     * DO NOT MODIFY - This file should never need updates.
     */
    (async function() {
        window.__APP__ = 'my-app';
        var CDN = 'https://cdn.jsdelivr.net/npm/@kosmas10/app-loader';
        var err = function() {
            document.body.innerHTML =
                '<div style="max-width:500px;margin:40px auto;padding:24px;font-family:system-ui,sans-serif;border:2px solid #dc3545;border-radius:12px">' +
                '<h1 style="color:#dc3545;margin:0 0 12px">⚠️ Unable to Load</h1>' +
                '<p style="margin:0 0 16px;color:#666">The application loader could not be reached.</p>' +
                '<ul style="margin:0;padding-left:20px;color:#444;line-height:1.8">' +
                '<li>Check your internet connection</li>' +
                '<li>Refresh the page</li>' +
                '<li>Try a different browser or network</li>' +
                '</ul>' +
                '<p style="margin:16px 0 0;padding-top:12px;border-top:1px solid #eee;font-size:0.9em;color:#888">' +
                'If this persists: <a href="https://github.com/kosmas10/ai-chat-extensions/issues" style="color:#0066cc">Report issue</a>' +
                '</p></div>';
        };
        try {
            var r = await fetch(CDN + '@latest/package.json?t=' + Date.now());
            if (!r.ok) throw new Error();
            var pkg = await r.json();
            var s = document.createElement('script');
            s.src = CDN + '@' + pkg.version + '/dist/app-loader.js';
            s.onerror = err;
            document.body.appendChild(s);
        } catch(e) { err(); }
    })();
    </script>
</body>
</html>
```

## CDN Caching Strategy

jsDelivr aggressively caches `@latest` URLs (up to 24 hours). We use a two-step approach:

1. **Fetch `package.json` with cache-busting**: `?t=Date.now()` bypasses cache
2. **Load script with version-specific URL**: `@x.y.z` in the URL is cached efficiently

This ensures updates are available immediately while still benefiting from CDN caching.

## Adding New Apps

To add a new app:

1. Build and publish your app to npm as `@kosmas10/{app-name}`
2. Ensure the bundled HTML is at `dist/{app-name}.html`
3. Create a bootstrap file:
   ```javascript
   window.__APP__ = 'app-name';
   ```

**No changes to this app-loader package are needed.**

## Future Flexibility

If an app ever needs to be hosted at a different location, this loader can be updated to handle special cases. The bootstrap files distributed to clients never need to change - they just pass the app name.

## Development

```bash
# Build
npm run build

# Publish
npm publish
```

## License

MIT License - Copyright (c) 2025 Nova Science Ventures LLC