API Documentation Generator
Run ID: 69cc41646beabe319cec8f5d2026-03-31Development
PantheraHive BOS
BOS Dashboard

This output represents the completion of Step 2: gemini → generate_code for the "API Documentation Generator" workflow. This step focuses on providing a comprehensive, detailed, and production-ready code framework for generating professional API documentation.

The generated code provides a Python-based solution leveraging a templating engine (Jinja2) to transform a structured API specification into human-readable documentation (Markdown format in this example). This approach ensures flexibility, maintainability, and scalability for your API documentation needs.


API Documentation Generator: Code Framework

This section provides a robust, Python-based code framework designed to generate detailed API documentation. It utilizes a structured data model for API specifications and a templating engine (Jinja2) to render this data into a professional Markdown document.

Core Concepts

  1. Structured API Specification: Define your API endpoints, parameters, request/response examples, and authentication details in a clear, programmatically accessible data structure (e.g., a Python dictionary). This acts as the single source of truth for your documentation.
  2. Templating Engine: Use a powerful templating engine (Jinja2 is chosen here for its flexibility and widespread adoption) to define the layout and formatting of your documentation. This separates content from presentation.
  3. Generator Script: A Python script orchestrates the process: loading the API specification, loading the template, rendering the documentation, and saving it to a file.

Project Structure

To follow best practices, we'll organize the code into a simple directory structure:

text • 259 chars
api_documentation_generator/
├── templates/
│   └── api_doc_template.md.j2  # Jinja2 template for documentation
├── api_spec.py                 # Defines the structured API specification
└── generate_docs.py            # Main script to generate documentation
Sandboxed live preview

API Documentation Generator: Architecture Plan

This document outlines the detailed architecture plan for the "API Documentation Generator," a system designed to produce professional, comprehensive, and interactive API documentation. This plan focuses on creating a modular, extensible, and robust solution capable of handling diverse API specifications and generating various output formats, including endpoint descriptions, request/response examples, authentication guides, and SDK usage examples.


1. Introduction and Project Goal

The primary goal of the "API Documentation Generator" is to automate the creation of high-quality API documentation from various specification formats. This system will serve as a foundational tool for developers, technical writers, and API consumers, ensuring consistent, up-to-date, and easily consumable API information.

Key Deliverables Supported by this Architecture:

*

python

api_spec.py

API_SPECIFICATION = {

"info": {

"title": "PantheraHive Core API",

"version": "1.0.0",

"description": "The PantheraHive Core API provides programmatic access to manage users, projects, and tasks within the PantheraHive ecosystem. This documentation guides developers through available endpoints, authentication methods, and usage examples.",

"base_url": "https://api.pantherahive.com/v1",

"contact": {

"name": "API Support",

"url": "https://pantherahive.com/support",

"email": "support@pantherahive.com"

}

},

"authentication": {

"methods": [

{

"name": "API Key",

"type": "apiKey",

"in": "header",

"param_name": "X-API-Key",

"description": "Authenticate requests by including your unique API Key in the X-API-Key header. You can generate an API Key from your PantheraHive dashboard under 'API Settings'."

},

{

"name": "OAuth 2.0",

"type": "oauth2",

"flow": "clientCredentials",

"token_url": "https://auth.pantherahive.com/oauth/token",

"scopes": {

"read:users": "Allows reading user profiles.",

"write:projects": "Allows creating and updating projects.",

"delete:tasks": "Allows deleting tasks."

},

"description": "For applications requiring user consent or more granular access, OAuth 2.0 is supported. Obtain an access token by following the Client Credentials flow."

}

]

},

"endpoints": [

{

"path": "/users",

"method": "GET",

"summary": "Retrieve a list of all users",

"description": "Fetches a paginated list of all active user accounts.",

"tags": ["Users"],

"parameters": [

{

"name": "page",

"in": "query",

"type": "integer",

"required": False,

"description": "The page number to retrieve.",

"example": 1

},

{

"name": "limit",

"in": "query",

"type": "integer",

"required": False,

"description": "The number of items per page (max 100).",

"example": 20

}

],

"responses": {

"200": {

"description": "A list of user objects.",

"schema": {

"type": "array",

"items": {

"$ref": "#/components/schemas/User"

}

},

"example": {

"page": 1,

"limit": 20,

"total": 50,

"users": [

{"id": "usr_abc123", "name": "Alice Smith", "email": "alice@example.com", "status": "active"},

{"id": "usr_def456", "name": "Bob Johnson", "email": "bob@example.com", "status": "active"}

]

}

},

"401": {

"description": "Unauthorized: API Key is missing or invalid."

}

},

"sdk_examples": {

"python": """

import requests

api_key = "YOUR_API_KEY"

headers = {"X-API-Key": api_key}

response = requests.get("https://api.pantherahive.com/v1/users?page=1&limit=10", headers=headers)

if response.status_code == 200:

print(response.json())

else:

print(f"Error: {response.status_code} - {response.text}")

""",

"curl": """

curl -X GET \\

'https://api.pantherahive.com/v1/users?page=1&limit=10' \\

-H 'X-API-Key: YOUR_API_KEY'

"""

}

},

{

"path": "/users/{user_id}",

"method": "GET",

"summary": "Retrieve a specific user by ID",

"description": "Fetches details for a single user account using their unique ID.",

"tags": ["Users"],

"parameters": [

{

"name": "user_id",

"in": "path",

"type": "string",

"required": True,

"description": "The unique identifier of the user.",

"example": "usr_abc123"

}

],

"responses": {

"200": {

"description": "A single user object.",

"schema": {

"$ref": "#/components/schemas/User"

},

"example": {"id": "usr_abc123", "name": "Alice Smith", "email": "alice@example.com", "status": "active"}

},

"401": {

"description": "Unauthorized: API Key is missing or invalid."

},

"404": {

"description": "Not Found: User with the specified ID does not exist."

}

},

"sdk_examples": {

"python": """

import requests

api_key = "YOUR_API_KEY"

user_id = "usr_abc123"

headers = {"X-API-Key": api_key}

response = requests.get(f"https://api.pantherahive.com/v1/users/{user_id}", headers=headers)

if response.status_code == 200:

print(response.json())

else:

print(f"Error: {response.status_code} - {response.text}")

""",

"curl": """

curl -X GET \\

'https://api.pantherahive.com/v1/users/usr_abc123' \\

-H 'X-API-Key: YOUR_API_KEY'

"""

}

},

{

"path": "/projects",

"method": "POST",

"summary": "Create a new project",

"description": "Adds a new project to the PantheraHive system.",

"tags": ["Projects"],

"parameters": [

{

"name": "X-Request-ID",

"in": "header",

"type": "string",

"required": False,

"description": "A unique identifier for the request, useful for tracing.",

"example": "req_uuid_12345"

}

],

"request_body": {

"content_type": "application/json",

"schema": {

"type": "object",

"properties": {

"name": {"type": "string", "description": "The name of the project."},

"description": {"type": "string", "description": "A brief description of the project."},

"owner_id": {"type": "string", "description": "The ID of the project owner."},

"status": {"type": "string", "enum": ["active", "archived"], "default": "active"}

},

"required": ["name", "owner_id"]

},

"example": {

"name": "Marketing Campaign Q3",

"description": "Plan and execute Q3 marketing initiatives.",

"owner_id": "usr_abc123",

"status": "active"

}

},

"responses": {

"201": {

"description": "Project created successfully.",

"schema": {

"$ref": "#/components/schemas/Project"

},

"example": {"id": "prj_xyz789", "name": "Marketing Campaign Q3", "owner_id": "usr_abc123", "status": "active", "created_at": "2023-10-27T10:00:00Z"}

},

"400": {

"description": "Bad Request: Invalid input data."

},

"401": {

"description": "Unauthorized: Missing or invalid authentication."

},

"403": {

"description": "Forbidden: User does not have permission to create projects."

}

},

"sdk_examples": {

"python": """

import requests

import json

api_key = "YOUR_API_KEY"

headers = {

"X-API-Key": api_key,

"Content-Type": "application/json"

}

data = {

"name": "Marketing Campaign Q3",

"description": "Plan and execute Q3 marketing initiatives.",

"owner_id": "usr_abc123"

}

response = requests.post("https://api.pantherahive.com/v1/projects", headers=headers, data=json.dumps(data))

if response.status_code == 201:

print(response.json())

else:

print(f"Error: {response.status_code} - {response.text}")

""",

"curl": """

curl -X POST \\

'https://api.pantherahive.com/v1/projects' \\

-H 'X-API-Key: YOUR_API_KEY' \\

-H 'Content-Type: application/json' \\

-d '{

"name": "Marketing Campaign Q3",

"description": "Plan and execute Q3 marketing initiatives.",

"owner_id": "usr_abc123"

}'

"""

}

}

],

"components": {

"schemas": {

"User": {

"type": "object",

"properties": {

"id": {"type": "string", "description": "Unique identifier for the user."},

"name": {"type": "string", "description": "Full name of the user."},

"email": {"type": "string", "format": "email", "description": "Email address of the user."},

"status": {"type": "string", "enum": ["active", "inactive", "suspended"], "description": "Current status of the user account."}

},

"required": ["id", "name", "email", "status"]

},

"Project": {

"type": "object",

gemini Output

PantheraHive API Documentation: User Management

Welcome to the PantheraHive User Management API documentation! This guide provides detailed information on how to integrate with our API, manage user resources, and leverage its capabilities. Whether you're building a new application or integrating with existing systems, this documentation will help you get started quickly and efficiently.


Table of Contents

  1. [Introduction](#1-introduction)

* [API Overview](#api-overview)

* [Base URL](#base-url)

* [Data Formats](#data-formats)

* [Error Handling](#error-handling)

* [Rate Limiting](#rate-limiting)

  1. [Authentication](#2-authentication)

* [API Key Authentication](#api-key-authentication)

* [Bearer Token (OAuth 2.0)](#bearer-token-oauth-20)

  1. [Endpoints](#3-endpoints)

* [Users](#users)

* [List All Users (GET /users)](#list-all-users-get-users)

* [Create a New User (POST /users)](#create-a-new-user-post-users)

* [Retrieve a Specific User (GET /users/{id})](#retrieve-a-specific-user-get-usersid)

* [Update a User (PUT /users/{id})](#update-a-user-put-usersid)

* [Delete a User (DELETE /users/{id})](#delete-a-user-delete-usersid)

  1. [SDK Usage Examples](#4-sdk-usage-examples)

* [Python SDK](#python-sdk)

* [JavaScript SDK](#javascript-sdk)

  1. [Common Error Codes](#5-common-error-codes)
  2. [Support & Feedback](#6-support--feedback)

1. Introduction

API Overview

The PantheraHive User Management API allows you to programmatically manage user accounts within your PantheraHive ecosystem. You can create, retrieve, update, and delete user records, making it easy to integrate user management into your applications, services, or internal tools.

Base URL

All requests to the PantheraHive User Management API should be prefixed with the following base URL:

https://api.pantherahive.com/v1

Data Formats

All request and response bodies are formatted as JSON.

  • Request Header: Content-Type: application/json
  • Response Header: Content-Type: application/json

Error Handling

The API uses standard HTTP status codes to indicate the success or failure of an API request. In case of an error, the response body will contain a JSON object with details about the error. See the [Common Error Codes](#5-common-error-codes) section for more details.

Rate Limiting

To ensure fair usage and system stability, the API enforces rate limits.

  • Limit: 100 requests per minute per IP address/API Key.
  • Headers:

* X-RateLimit-Limit: The maximum number of requests allowed in the current rate limit window.

* X-RateLimit-Remaining: The number of requests remaining in the current rate limit window.

* X-RateLimit-Reset: The time at which the current rate limit window resets (UTC epoch seconds).

  • Exceeding Limit: If you exceed the rate limit, a 429 Too Many Requests status code will be returned.

2. Authentication

The PantheraHive User Management API supports two primary authentication methods: API Key Authentication for server-to-server communication and Bearer Token (OAuth 2.0) for user-contextual operations, often obtained via an OAuth flow.

API Key Authentication

For simple, server-side integrations where a user context is not required, you can use an API Key. Your API Key should be kept confidential and never exposed in client-side code.

To authenticate, include your API Key in the X-API-Key header for every request:

Header: X-API-Key: YOUR_API_KEY

Example (cURL):


curl -X GET \
  https://api.pantherahive.com/v1/users \
  -H 'Accept: application/json' \
  -H 'X-API-Key: YOUR_API_KEY'

Bearer Token (OAuth 2.0)

For applications that interact with the API on behalf of a user, Bearer Token authentication (typically obtained via an OAuth 2.0 flow) is recommended. The token represents the user's authorization to access specific resources.

Include the Bearer Token in the Authorization header:

Header: Authorization: Bearer YOUR_ACCESS_TOKEN

Example (cURL):


curl -X POST \
  https://api.pantherahive.com/v1/users \
  -H 'Content-Type: application/json' \
  -H 'Accept: application/json' \
  -H 'Authorization: Bearer YOUR_ACCESS_TOKEN' \
  -d '{
    "firstName": "John",
    "lastName": "Doe",
    "email": "john.doe@example.com"
  }'

3. Endpoints

Users

##### List All Users (GET /users)

Retrieves a paginated list of all users in the system.

  • Description: This endpoint returns an array of user objects. You can filter and paginate the results using query parameters.
  • Method: GET
  • Path: /users

Parameters:

| Name | Type | Required | Description |

| :-------- | :------- | :------- | :---------------------------------------------- |

| limit | integer| No | Maximum number of users to return (default: 10, max: 100) |

| offset | integer| No | The number of users to skip (for pagination) |

| email | string | No | Filter users by email address |

| status | string | No | Filter users by status (e.g., active, inactive, pending) |

Request Example (cURL):


curl -X GET \
  'https://api.pantherahive.com/v1/users?limit=5&status=active' \
  -H 'Accept: application/json' \
  -H 'X-API-Key: YOUR_API_KEY'

Response Example (200 OK):


{
  "data": [
    {
      "id": "usr_abc123",
      "firstName": "Alice",
      "lastName": "Smith",
      "email": "alice.smith@example.com",
      "status": "active",
      "createdAt": "2023-01-15T10:00:00Z",
      "updatedAt": "2023-01-15T10:00:00Z"
    },
    {
      "id": "usr_def456",
      "firstName": "Bob",
      "lastName": "Johnson",
      "email": "bob.j@example.com",
      "status": "active",
      "createdAt": "2023-01-16T11:30:00Z",
      "updatedAt": "2023-01-16T11:30:00Z"
    }
  ],
  "meta": {
    "total": 2,
    "limit": 5,
    "offset": 0
  }
}

##### Create a New User (POST /users)

Registers a new user in the system.

  • Description: Creates a new user account with the provided details. A unique email address is required.
  • Method: POST
  • Path: /users

Parameters (Body):

| Name | Type | Required | Description |

| :---------- | :------- | :------- | :---------------------------------------------- |

| firstName | string | Yes | The user's first name. |

| lastName | string | Yes | The user's last name. |

| email | string | Yes | The user's unique email address. |

| password | string | Yes | The user's password (will be hashed). |

| metadata | object | No | Optional key-value pairs for additional user data. |

Request Example (cURL):


curl -X POST \
  https://api.pantherahive.com/v1/users \
  -H 'Content-Type: application/json' \
  -H 'Accept: application/json' \
  -H 'X-API-Key: YOUR_API_KEY' \
  -d '{
    "firstName": "Jane",
    "lastName": "Doe",
    "email": "jane.doe@example.com",
    "password": "SecurePassword123!",
    "metadata": {
      "source": "api_signup",
      "marketingOptIn": true
    }
  }'

Response Example (201 Created):


{
  "id": "usr_ghi789",
  "firstName": "Jane",
  "lastName": "Doe",
  "email": "jane.doe@example.com",
  "status": "pending",
  "createdAt": "2023-07-20T14:15:22Z",
  "updatedAt": "2023-07-20T14:15:22Z",
  "metadata": {
    "source": "api_signup",
    "marketingOptIn": true
  }
}

Error Response Example (409 Conflict - Email already exists):


{
  "statusCode": 409,
  "error": "Conflict",
  "message": "A user with this email already exists."
}

##### Retrieve a Specific User (GET /users/{id})

Fetches the details of a single user by their unique ID.

  • Description: Returns a single user object if the ID is found.
  • Method: GET
  • Path: /users/{id}

Parameters (Path):

| Name | Type | Required | Description |

| :--- | :------- | :------- | :---------------------------------------------- |

| id | string | Yes | The unique identifier of the user. |

Request Example (cURL):


curl -X GET \
  https://api.pantherahive.com/v1/users/usr_ghi789 \
  -H 'Accept: application/json' \
  -H 'X-API-Key: YOUR_API_KEY'

Response Example (200 OK):


{
  "id": "usr_ghi789",
  "firstName": "Jane",
  "lastName": "Doe",
  "email": "jane.doe@example.com",
  "status": "pending",
  "createdAt": "2023-07-20T14:15:22Z",
  "updatedAt": "2023-07-20T14:15:22Z",
  "metadata": {
    "source": "api_signup",
    "marketingOptIn": true
  }
}

Error Response Example (404 Not Found):


{
  "statusCode": 404,
  "error": "Not Found",
  "message": "User with ID 'usr_invalid' not found."
}

##### Update a User (PUT /users/{id})

Modifies the details of an existing user.

  • Description: Updates one or more fields for a specified user. Only fields provided in the request body will be updated.
  • Method: PUT
  • Path: /users/{id}

Parameters (Path):

| Name | Type | Required | Description |

| :--- | :------- | :------- | :---------------------------------------------- |

| id | string | Yes | The unique identifier of the user to update. |

Parameters (Body):

| Name | Type | Required | Description |

| :---------- | :------- | :------- | :---------------------------------------------- |

| firstName | string | No | The user's updated first name. |

| lastName | string | No | The user's updated last name. |

| email | string | No | The user's updated unique email address. |

| status | string | No | The user's updated status (e.g., active). |

| metadata | object | No | Optional key-value pairs for additional user data (replaces existing metadata). |

Request Example (cURL):


curl -X PUT \
  https://api.pantherahive.com/v1/users/usr_ghi789 \
  -H 'Content-Type: application/json' \
  -H 'Accept: application/json' \
  -H 'X-API-Key: YOUR_API_KEY' \
  -d '{
    "status": "active",
    "metadata": {
      "marketingOptIn": false,
      "lastUpdateSource": "admin_panel"
    }
  }'

Response Example (200 OK):


{
api_documentation_generator.txt
Download source file
Copy all content
Full output as text
Download ZIP
IDE-ready project ZIP
Copy share link
Permanent URL for this run
Get Embed Code
Embed this result on any website
Print / Save PDF
Use browser print dialog
\n\n\n"); var hasSrcMain=Object.keys(extracted).some(function(k){return k.indexOf("src/main")>=0;}); if(!hasSrcMain) zip.file(folder+"src/main."+ext,"import React from 'react'\nimport ReactDOM from 'react-dom/client'\nimport App from './App'\nimport './index.css'\n\nReactDOM.createRoot(document.getElementById('root')!).render(\n \n \n \n)\n"); var hasSrcApp=Object.keys(extracted).some(function(k){return k==="src/App."+ext||k==="App."+ext;}); if(!hasSrcApp) zip.file(folder+"src/App."+ext,"import React from 'react'\nimport './App.css'\n\nfunction App(){\n return(\n
\n
\n

"+slugTitle(pn)+"

\n

Built with PantheraHive BOS

\n
\n
\n )\n}\nexport default App\n"); zip.file(folder+"src/index.css","*{margin:0;padding:0;box-sizing:border-box}\nbody{font-family:system-ui,-apple-system,sans-serif;background:#f0f2f5;color:#1a1a2e}\n.app{min-height:100vh;display:flex;flex-direction:column}\n.app-header{flex:1;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:12px;padding:40px}\nh1{font-size:2.5rem;font-weight:700}\n"); zip.file(folder+"src/App.css",""); zip.file(folder+"src/components/.gitkeep",""); zip.file(folder+"src/pages/.gitkeep",""); zip.file(folder+"src/hooks/.gitkeep",""); Object.keys(extracted).forEach(function(p){ var fp=p.startsWith("src/")?p:"src/"+p; zip.file(folder+fp,extracted[p]); }); zip.file(folder+"README.md","# "+slugTitle(pn)+"\n\nGenerated by PantheraHive BOS.\n\n## Setup\n\`\`\`bash\nnpm install\nnpm run dev\n\`\`\`\n\n## Build\n\`\`\`bash\nnpm run build\n\`\`\`\n\n## Open in IDE\nOpen the project folder in VS Code or WebStorm.\n"); zip.file(folder+".gitignore","node_modules/\ndist/\n.env\n.DS_Store\n*.local\n"); } /* --- Vue (Vite + Composition API + TypeScript) --- */ function buildVue(zip,folder,app,code,panelTxt){ var pn=pkgName(app); var C=cc(pn); var extracted=extractCode(panelTxt); zip.file(folder+"package.json",'{\n "name": "'+pn+'",\n "version": "0.0.0",\n "type": "module",\n "scripts": {\n "dev": "vite",\n "build": "vue-tsc -b && vite build",\n "preview": "vite preview"\n },\n "dependencies": {\n "vue": "^3.5.13",\n "vue-router": "^4.4.5",\n "pinia": "^2.3.0",\n "axios": "^1.7.9"\n },\n "devDependencies": {\n "@vitejs/plugin-vue": "^5.2.1",\n "typescript": "~5.7.3",\n "vite": "^6.0.5",\n "vue-tsc": "^2.2.0"\n }\n}\n'); zip.file(folder+"vite.config.ts","import { defineConfig } from 'vite'\nimport vue from '@vitejs/plugin-vue'\nimport { resolve } from 'path'\n\nexport default defineConfig({\n plugins: [vue()],\n resolve: { alias: { '@': resolve(__dirname,'src') } }\n})\n"); zip.file(folder+"tsconfig.json",'{"files":[],"references":[{"path":"./tsconfig.app.json"},{"path":"./tsconfig.node.json"}]}\n'); zip.file(folder+"tsconfig.app.json",'{\n "compilerOptions":{\n "target":"ES2020","useDefineForClassFields":true,"module":"ESNext","lib":["ES2020","DOM","DOM.Iterable"],\n "skipLibCheck":true,"moduleResolution":"bundler","allowImportingTsExtensions":true,\n "isolatedModules":true,"moduleDetection":"force","noEmit":true,"jsxImportSource":"vue",\n "strict":true,"paths":{"@/*":["./src/*"]}\n },\n "include":["src/**/*.ts","src/**/*.d.ts","src/**/*.tsx","src/**/*.vue"]\n}\n'); zip.file(folder+"env.d.ts","/// \n"); zip.file(folder+"index.html","\n\n\n \n \n "+slugTitle(pn)+"\n\n\n
\n \n\n\n"); var hasMain=Object.keys(extracted).some(function(k){return k==="src/main.ts"||k==="main.ts";}); if(!hasMain) zip.file(folder+"src/main.ts","import { createApp } from 'vue'\nimport { createPinia } from 'pinia'\nimport App from './App.vue'\nimport './assets/main.css'\n\nconst app = createApp(App)\napp.use(createPinia())\napp.mount('#app')\n"); var hasApp=Object.keys(extracted).some(function(k){return k.indexOf("App.vue")>=0;}); if(!hasApp) zip.file(folder+"src/App.vue","\n\n\n\n\n"); zip.file(folder+"src/assets/main.css","*{margin:0;padding:0;box-sizing:border-box}body{font-family:system-ui,sans-serif;background:#fff;color:#213547}\n"); zip.file(folder+"src/components/.gitkeep",""); zip.file(folder+"src/views/.gitkeep",""); zip.file(folder+"src/stores/.gitkeep",""); Object.keys(extracted).forEach(function(p){ var fp=p.startsWith("src/")?p:"src/"+p; zip.file(folder+fp,extracted[p]); }); zip.file(folder+"README.md","# "+slugTitle(pn)+"\n\nGenerated by PantheraHive BOS.\n\n## Setup\n\`\`\`bash\nnpm install\nnpm run dev\n\`\`\`\n\n## Build\n\`\`\`bash\nnpm run build\n\`\`\`\n\nOpen in VS Code or WebStorm.\n"); zip.file(folder+".gitignore","node_modules/\ndist/\n.env\n.DS_Store\n*.local\n"); } /* --- Angular (v19 standalone) --- */ function buildAngular(zip,folder,app,code,panelTxt){ var pn=pkgName(app); var C=cc(pn); var sel=pn.replace(/_/g,"-"); var extracted=extractCode(panelTxt); zip.file(folder+"package.json",'{\n "name": "'+pn+'",\n "version": "0.0.0",\n "scripts": {\n "ng": "ng",\n "start": "ng serve",\n "build": "ng build",\n "test": "ng test"\n },\n "dependencies": {\n "@angular/animations": "^19.0.0",\n "@angular/common": "^19.0.0",\n "@angular/compiler": "^19.0.0",\n "@angular/core": "^19.0.0",\n "@angular/forms": "^19.0.0",\n "@angular/platform-browser": "^19.0.0",\n "@angular/platform-browser-dynamic": "^19.0.0",\n "@angular/router": "^19.0.0",\n "rxjs": "~7.8.0",\n "tslib": "^2.3.0",\n "zone.js": "~0.15.0"\n },\n "devDependencies": {\n "@angular-devkit/build-angular": "^19.0.0",\n "@angular/cli": "^19.0.0",\n "@angular/compiler-cli": "^19.0.0",\n "typescript": "~5.6.0"\n }\n}\n'); zip.file(folder+"angular.json",'{\n "$schema": "./node_modules/@angular/cli/lib/config/schema.json",\n "version": 1,\n "newProjectRoot": "projects",\n "projects": {\n "'+pn+'": {\n "projectType": "application",\n "root": "",\n "sourceRoot": "src",\n "prefix": "app",\n "architect": {\n "build": {\n "builder": "@angular-devkit/build-angular:application",\n "options": {\n "outputPath": "dist/'+pn+'",\n "index": "src/index.html",\n "browser": "src/main.ts",\n "tsConfig": "tsconfig.app.json",\n "styles": ["src/styles.css"],\n "scripts": []\n }\n },\n "serve": {"builder":"@angular-devkit/build-angular:dev-server","configurations":{"production":{"buildTarget":"'+pn+':build:production"},"development":{"buildTarget":"'+pn+':build:development"}},"defaultConfiguration":"development"}\n }\n }\n }\n}\n'); zip.file(folder+"tsconfig.json",'{\n "compileOnSave": false,\n "compilerOptions": {"baseUrl":"./","outDir":"./dist/out-tsc","forceConsistentCasingInFileNames":true,"strict":true,"noImplicitOverride":true,"noPropertyAccessFromIndexSignature":true,"noImplicitReturns":true,"noFallthroughCasesInSwitch":true,"paths":{"@/*":["src/*"]},"skipLibCheck":true,"esModuleInterop":true,"sourceMap":true,"declaration":false,"experimentalDecorators":true,"moduleResolution":"bundler","importHelpers":true,"target":"ES2022","module":"ES2022","useDefineForClassFields":false,"lib":["ES2022","dom"]},\n "references":[{"path":"./tsconfig.app.json"}]\n}\n'); zip.file(folder+"tsconfig.app.json",'{\n "extends":"./tsconfig.json",\n "compilerOptions":{"outDir":"./dist/out-tsc","types":[]},\n "files":["src/main.ts"],\n "include":["src/**/*.d.ts"]\n}\n'); zip.file(folder+"src/index.html","\n\n\n \n "+slugTitle(pn)+"\n \n \n \n\n\n \n\n\n"); zip.file(folder+"src/main.ts","import { bootstrapApplication } from '@angular/platform-browser';\nimport { appConfig } from './app/app.config';\nimport { AppComponent } from './app/app.component';\n\nbootstrapApplication(AppComponent, appConfig)\n .catch(err => console.error(err));\n"); zip.file(folder+"src/styles.css","* { margin: 0; padding: 0; box-sizing: border-box; }\nbody { font-family: system-ui, -apple-system, sans-serif; background: #f9fafb; color: #111827; }\n"); var hasComp=Object.keys(extracted).some(function(k){return k.indexOf("app.component")>=0;}); if(!hasComp){ zip.file(folder+"src/app/app.component.ts","import { Component } from '@angular/core';\nimport { RouterOutlet } from '@angular/router';\n\n@Component({\n selector: 'app-root',\n standalone: true,\n imports: [RouterOutlet],\n templateUrl: './app.component.html',\n styleUrl: './app.component.css'\n})\nexport class AppComponent {\n title = '"+pn+"';\n}\n"); zip.file(folder+"src/app/app.component.html","
\n
\n

"+slugTitle(pn)+"

\n

Built with PantheraHive BOS

\n
\n \n
\n"); zip.file(folder+"src/app/app.component.css",".app-header{display:flex;flex-direction:column;align-items:center;justify-content:center;min-height:60vh;gap:16px}h1{font-size:2.5rem;font-weight:700;color:#6366f1}\n"); } zip.file(folder+"src/app/app.config.ts","import { ApplicationConfig, provideZoneChangeDetection } from '@angular/core';\nimport { provideRouter } from '@angular/router';\nimport { routes } from './app.routes';\n\nexport const appConfig: ApplicationConfig = {\n providers: [\n provideZoneChangeDetection({ eventCoalescing: true }),\n provideRouter(routes)\n ]\n};\n"); zip.file(folder+"src/app/app.routes.ts","import { Routes } from '@angular/router';\n\nexport const routes: Routes = [];\n"); Object.keys(extracted).forEach(function(p){ var fp=p.startsWith("src/")?p:"src/"+p; zip.file(folder+fp,extracted[p]); }); zip.file(folder+"README.md","# "+slugTitle(pn)+"\n\nGenerated by PantheraHive BOS.\n\n## Setup\n\`\`\`bash\nnpm install\nng serve\n# or: npm start\n\`\`\`\n\n## Build\n\`\`\`bash\nng build\n\`\`\`\n\nOpen in VS Code with Angular Language Service extension.\n"); zip.file(folder+".gitignore","node_modules/\ndist/\n.env\n.DS_Store\n*.local\n.angular/\n"); } /* --- Python --- */ function buildPython(zip,folder,app,code){ var title=slugTitle(app); var pn=pkgName(app); var src=code.replace(/^\`\`\`[\w]*\n?/m,"").replace(/\n?\`\`\`$/m,"").trim(); var reqMap={"numpy":"numpy","pandas":"pandas","sklearn":"scikit-learn","tensorflow":"tensorflow","torch":"torch","flask":"flask","fastapi":"fastapi","uvicorn":"uvicorn","requests":"requests","sqlalchemy":"sqlalchemy","pydantic":"pydantic","dotenv":"python-dotenv","PIL":"Pillow","cv2":"opencv-python","matplotlib":"matplotlib","seaborn":"seaborn","scipy":"scipy"}; var reqs=[]; Object.keys(reqMap).forEach(function(k){if(src.indexOf("import "+k)>=0||src.indexOf("from "+k)>=0)reqs.push(reqMap[k]);}); var reqsTxt=reqs.length?reqs.join("\n"):"# add dependencies here\n"; zip.file(folder+"main.py",src||"# "+title+"\n# Generated by PantheraHive BOS\n\nprint(title+\" loaded\")\n"); zip.file(folder+"requirements.txt",reqsTxt); zip.file(folder+".env.example","# Environment variables\n"); zip.file(folder+"README.md","# "+title+"\n\nGenerated by PantheraHive BOS.\n\n## Setup\n\`\`\`bash\npython3 -m venv .venv\nsource .venv/bin/activate\npip install -r requirements.txt\n\`\`\`\n\n## Run\n\`\`\`bash\npython main.py\n\`\`\`\n"); zip.file(folder+".gitignore",".venv/\n__pycache__/\n*.pyc\n.env\n.DS_Store\n"); } /* --- Node.js --- */ function buildNode(zip,folder,app,code){ var title=slugTitle(app); var pn=pkgName(app); var src=code.replace(/^\`\`\`[\w]*\n?/m,"").replace(/\n?\`\`\`$/m,"").trim(); var depMap={"mongoose":"^8.0.0","dotenv":"^16.4.5","axios":"^1.7.9","cors":"^2.8.5","bcryptjs":"^2.4.3","jsonwebtoken":"^9.0.2","socket.io":"^4.7.4","uuid":"^9.0.1","zod":"^3.22.4","express":"^4.18.2"}; var deps={}; Object.keys(depMap).forEach(function(k){if(src.indexOf(k)>=0)deps[k]=depMap[k];}); if(!deps["express"])deps["express"]="^4.18.2"; var pkgJson=JSON.stringify({"name":pn,"version":"1.0.0","main":"src/index.js","scripts":{"start":"node src/index.js","dev":"nodemon src/index.js"},"dependencies":deps,"devDependencies":{"nodemon":"^3.0.3"}},null,2)+"\n"; zip.file(folder+"package.json",pkgJson); var fallback="const express=require(\"express\");\nconst app=express();\napp.use(express.json());\n\napp.get(\"/\",(req,res)=>{\n res.json({message:\""+title+" API\"});\n});\n\nconst PORT=process.env.PORT||3000;\napp.listen(PORT,()=>console.log(\"Server on port \"+PORT));\n"; zip.file(folder+"src/index.js",src||fallback); zip.file(folder+".env.example","PORT=3000\n"); zip.file(folder+".gitignore","node_modules/\n.env\n.DS_Store\n"); zip.file(folder+"README.md","# "+title+"\n\nGenerated by PantheraHive BOS.\n\n## Setup\n\`\`\`bash\nnpm install\n\`\`\`\n\n## Run\n\`\`\`bash\nnpm run dev\n\`\`\`\n"); } /* --- Vanilla HTML --- */ function buildVanillaHtml(zip,folder,app,code){ var title=slugTitle(app); var isFullDoc=code.trim().toLowerCase().indexOf("=0||code.trim().toLowerCase().indexOf("=0; var indexHtml=isFullDoc?code:"\n\n\n\n\n"+title+"\n\n\n\n"+code+"\n\n\n\n"; zip.file(folder+"index.html",indexHtml); zip.file(folder+"style.css","/* "+title+" — styles */\n*{margin:0;padding:0;box-sizing:border-box}\nbody{font-family:system-ui,-apple-system,sans-serif;background:#fff;color:#1a1a2e}\n"); zip.file(folder+"script.js","/* "+title+" — scripts */\n"); zip.file(folder+"assets/.gitkeep",""); zip.file(folder+"README.md","# "+title+"\n\nGenerated by PantheraHive BOS.\n\n## Open\nDouble-click \`index.html\` in your browser.\n\nOr serve locally:\n\`\`\`bash\nnpx serve .\n# or\npython3 -m http.server 3000\n\`\`\`\n"); zip.file(folder+".gitignore",".DS_Store\nnode_modules/\n.env\n"); } /* ===== MAIN ===== */ var sc=document.createElement("script"); sc.src="https://cdnjs.cloudflare.com/ajax/libs/jszip/3.10.1/jszip.min.js"; sc.onerror=function(){ if(lbl)lbl.textContent="Download ZIP"; alert("JSZip load failed — check connection."); }; sc.onload=function(){ var zip=new JSZip(); var base=(_phFname||"output").replace(/\.[^.]+$/,""); var app=base.toLowerCase().replace(/[^a-z0-9]+/g,"_").replace(/^_+|_+$/g,"")||"my_app"; var folder=app+"/"; var vc=document.getElementById("panel-content"); var panelTxt=vc?(vc.innerText||vc.textContent||""):""; var lang=detectLang(_phCode,panelTxt); if(_phIsHtml){ buildVanillaHtml(zip,folder,app,_phCode); } else if(lang==="flutter"){ buildFlutter(zip,folder,app,_phCode,panelTxt); } else if(lang==="react-native"){ buildReactNative(zip,folder,app,_phCode,panelTxt); } else if(lang==="swift"){ buildSwift(zip,folder,app,_phCode,panelTxt); } else if(lang==="kotlin"){ buildKotlin(zip,folder,app,_phCode,panelTxt); } else if(lang==="react"){ buildReact(zip,folder,app,_phCode,panelTxt); } else if(lang==="vue"){ buildVue(zip,folder,app,_phCode,panelTxt); } else if(lang==="angular"){ buildAngular(zip,folder,app,_phCode,panelTxt); } else if(lang==="python"){ buildPython(zip,folder,app,_phCode); } else if(lang==="node"){ buildNode(zip,folder,app,_phCode); } else { /* Document/content workflow */ var title=app.replace(/_/g," "); var md=_phAll||_phCode||panelTxt||"No content"; zip.file(folder+app+".md",md); var h=""+title+""; h+="

"+title+"

"; var hc=md.replace(/&/g,"&").replace(//g,">"); hc=hc.replace(/^### (.+)$/gm,"

$1

"); hc=hc.replace(/^## (.+)$/gm,"

$1

"); hc=hc.replace(/^# (.+)$/gm,"

$1

"); hc=hc.replace(/\*\*(.+?)\*\*/g,"$1"); hc=hc.replace(/\n{2,}/g,"

"); h+="

"+hc+"

Generated by PantheraHive BOS
"; zip.file(folder+app+".html",h); zip.file(folder+"README.md","# "+title+"\n\nGenerated by PantheraHive BOS.\n\nFiles:\n- "+app+".md (Markdown)\n- "+app+".html (styled HTML)\n"); } zip.generateAsync({type:"blob"}).then(function(blob){ var a=document.createElement("a"); a.href=URL.createObjectURL(blob); a.download=app+".zip"; a.click(); URL.revokeObjectURL(a.href); if(lbl)lbl.textContent="Download ZIP"; }); }; document.head.appendChild(sc); } function phShare(){navigator.clipboard.writeText(window.location.href).then(function(){var el=document.getElementById("ph-share-lbl");if(el){el.textContent="Link copied!";setTimeout(function(){el.textContent="Copy share link";},2500);}});}function phEmbed(){var runId=window.location.pathname.split("/").pop().replace(".html","");var embedUrl="https://pantherahive.com/embed/"+runId;var code='';navigator.clipboard.writeText(code).then(function(){var el=document.getElementById("ph-embed-lbl");if(el){el.textContent="Embed code copied!";setTimeout(function(){el.textContent="Get Embed Code";},2500);}});}