GraphQL Schema Designer
Run ID: 69ccc0d73e7fb09ff16a4cb02026-04-01Development
PantheraHive BOS
BOS Dashboard

GraphQL Schema Design: Project Management System

This document outlines a comprehensive GraphQL schema for a Project Management System. It includes detailed type definitions, root query, mutation, and subscription operations, conceptual resolver descriptions, and client-side integration examples. This design aims for flexibility, scalability, and an intuitive API for managing projects, tasks, and users.


1. Introduction and Overview

GraphQL provides a powerful and flexible way for clients to request exactly the data they need. This schema design for a Project Management System leverages GraphQL's capabilities to offer a unified API for managing users, projects, tasks, and comments.

Key Benefits of this GraphQL Schema:


2. Schema Definition Language (SDL)

The following defines the GraphQL schema using the Schema Definition Language (SDL).

2.1. Scalar Types

In addition to the built-in String, Int, Float, Boolean, and ID scalars, we define a custom DateTime scalar for handling date and time values.

text • 1,096 chars
---

### 3. Resolver Concepts and Structure

Resolvers are functions that tell the GraphQL server how to fetch the data for a specific field. Each field in the schema (e.g., `User.name`, `Query.project`, `Mutation.createTask`) has a corresponding resolver function.

**Resolver Structure:**

A resolver function typically takes four arguments: `(parent, args, context, info)`.

*   **`parent` (or `root`)**: The result from the parent resolver. For a top-level `Query` or `Mutation` field, this is often the root value (e.g., an empty object or a special object provided by the server).
*   **`args`**: An object containing all arguments provided to the field in the GraphQL query (e.g., `id` for `project(id: ID!)`).
*   **`context`**: An object shared across all resolvers in a single GraphQL operation. It's used for carrying authentication information, database connections, data loaders, or other shared resources.
*   **`info`**: An object containing information about the execution state of the query, including the field's AST (Abstract Syntax Tree).

**Conceptual Resolver Examples:**

Sandboxed live preview

This document outlines a detailed study plan designed to equip individuals or teams with the comprehensive knowledge and practical skills required for professional GraphQL schema design. This plan focuses on a structured, week-by-week approach, covering fundamental concepts to advanced architectural considerations, ensuring a robust understanding and practical application of GraphQL principles.


Detailed Study Plan for GraphQL Schema Design

1. Introduction & Overall Goal

This study plan provides a structured curriculum for mastering GraphQL schema design. The objective is to enable participants to design, implement, and maintain efficient, scalable, and secure GraphQL APIs for various applications. By the end of this plan, participants will be proficient in defining GraphQL types, queries, mutations, subscriptions, understanding resolver architectures, and applying best practices for real-world scenarios.

2. Weekly Schedule & Learning Objectives

Each week focuses on specific modules, building upon previous knowledge.

Week 1: GraphQL Fundamentals & Core Type System

  • Learning Objectives:

* Understand the core concepts of GraphQL (schema, types, fields, arguments).

* Differentiate between GraphQL and REST APIs.

* Master GraphQL's built-in Scalar types (String, Int, Float, Boolean, ID).

* Define Object types and their fields.

* Understand the use of Lists and Non-null fields.

* Set up a basic GraphQL server and explore it with GraphiQL/Apollo Studio.

  • Key Activities:

* Read GraphQL specification introduction.

* Implement a simple schema with 2-3 interconnected Object types (e.g., User, Post).

* Practice writing basic queries for defined types.

Week 2: Advanced Type System & Relationships

  • Learning Objectives:

* Utilize advanced type constructs: Interfaces, Unions, and Enums.

* Design Input types for structured data input.

* Model complex relationships between types (one-to-many, many-to-many).

* Understand the role of custom scalar types.

  • Key Activities:

* Refactor existing types to use Interfaces/Unions (e.g., Content interface for Post and Comment).

* Define an Enum for a field (e.g., PostStatus: [DRAFT, PUBLISHED]).

* Design Input types for creating/updating entities.

Week 3: Query Design & Data Fetching

  • Learning Objectives:

* Design the root Query type effectively.

* Implement arguments for fields to enable filtering, sorting, and pagination.

* Understand and apply pagination patterns (e.g., cursor-based vs. offset-based).

* Learn about data fetching strategies and potential N+1 problems.

  • Key Activities:

* Implement queries with arguments (e.g., userById(id: ID!), posts(status: PostStatus, limit: Int)).

* Design and implement a paginated list query using the Relay connection specification or a custom approach.

Week 4: Mutation Design & Data Modification

  • Learning Objectives:

* Design the root Mutation type for data manipulation.

* Implement various mutation patterns (create, update, delete).

* Understand how to use Input types for mutation arguments.

* Learn about common mutation payload patterns and error handling.

  • Key Activities:

* Design and implement createUser, updatePost, and deleteComment mutations.

* Ensure mutations return meaningful payloads and handle potential errors gracefully.

Week 5: Subscriptions & Real-time Data

  • Learning Objectives:

* Understand the concept and purpose of GraphQL Subscriptions.

* Design the root Subscription type for real-time data updates.

* Implement common subscription patterns (e.g., itemAdded, itemUpdated).

* Grasp the underlying technologies (e.g., WebSockets) for subscriptions.

  • Key Activities:

* Implement a newPostAdded subscription.

* Test subscription functionality using a GraphQL client.

Week 6: Resolver Architecture, Data Sources & Best Practices

  • Learning Objectives:

* Understand the role of resolver functions in connecting schema to data sources.

* Learn to integrate GraphQL with various backends (databases, REST APIs, microservices).

* Implement DataLoader for efficient data fetching and solving the N+1 problem.

* Discuss schema modularity, versioning strategies, and security considerations (AuthN/AuthZ).

* Explore performance optimization techniques and caching strategies.

  • Key Activities:

* Integrate a simple database (e.g., SQLite, PostgreSQL, MongoDB) with the GraphQL server.

* Implement DataLoader for a common relationship (e.g., fetching author for multiple posts).

* Discuss and plan for authentication and authorization middleware.

3. Recommended Resources

  • Official Documentation:

* [GraphQL.org](https://graphql.org/): The official GraphQL specification and documentation.

  • Books:

* "Learning GraphQL" by Eve Porcello & Alex Banks (O'Reilly)

* "Fullstack GraphQL" by Nader Dabit

  • Online Courses & Platforms:

* Apollo Odyssey: Comprehensive free and paid courses on GraphQL and Apollo ecosystem.

* Udemy/Coursera: Numerous courses on GraphQL, Node.js, and specific backend integrations.

* Egghead.io: Short, focused video lessons on various GraphQL topics.

  • Blogs & Articles:

* Apollo Blog: Industry insights, best practices, and updates from Apollo GraphQL.

* Prisma Blog: Articles on GraphQL, databases, and data access layers.

  • Tools & Playgrounds:

* GraphiQL: In-browser GraphQL IDE for exploration and testing.

* Apollo Studio: Powerful GraphQL development platform with schema management, testing, and monitoring.

* Postman/Insomnia: API clients with GraphQL support.

4. Milestones

Achieving these milestones indicates significant progress and understanding:

  • End of Week 2: Successfully design a GraphQL schema for a moderate domain (e.g., a blogging platform, e-commerce product catalog) including types, relationships, interfaces, and enums.
  • End of Week 4: Implement a functional GraphQL server with a complete set of queries and mutations for a chosen domain, demonstrating data fetching and modification capabilities.
  • End of Week 5: Successfully integrate real-time capabilities via subscriptions into the GraphQL API.
  • End of Week 6: Connect the GraphQL API to a persistent data store (e.g., database), implement efficient data loading with DataLoader, and outline a basic authentication/authorization strategy.
  • Overall Project Milestone: Complete a small, end-to-end application demonstrating a well-designed GraphQL schema, robust resolvers, and client-side integration.

5. Assessment Strategies

To ensure effective learning and skill development, various assessment strategies will be employed:

  • Weekly Practical Exercises: Each week will conclude with hands-on coding exercises, where participants apply the learned concepts to extend their evolving GraphQL schema and server.
  • Code Reviews: Regular peer or expert code reviews of implemented schemas and resolvers to provide constructive feedback on design choices, efficiency, and adherence to best practices.
  • Self-Assessment Checklists: Participants will use provided checklists to evaluate their understanding against weekly learning objectives.
  • Mini-Project Implementation: At the end of the plan, participants will design and implement a small GraphQL-powered application from scratch, showcasing their ability to integrate all learned components.
  • Conceptual Discussions/Quizzes: Periodic discussions or short quizzes to assess theoretical understanding of GraphQL concepts, specifications, and design patterns.
  • Performance Benchmarking (Optional): For advanced learners, assessing the performance of queries and mutations, identifying bottlenecks, and implementing optimizations.

This study plan is designed to be flexible and can be adapted based on individual learning pace and prior experience. Consistent practice and engagement with the GraphQL community are highly encouraged for continuous growth.

gemini Output

This deliverable outlines a comprehensive GraphQL schema design for a content management system (CMS) or blogging platform. It includes detailed Schema Definition Language (SDL) for types, queries, mutations, and subscriptions, along with conceptual resolver implementations and client-side integration examples. The design prioritizes clarity, scalability, and adherence to best practices, making it suitable for production environments.


GraphQL Schema Design: Content Management System (CMS)

This document provides a detailed GraphQL schema for a Content Management System (CMS), covering essential entities like Users, Posts, Comments, Categories, and Tags. It includes the full Schema Definition Language (SDL), conceptual resolver logic, and examples of client-side integration.

1. Introduction

The goal is to provide a robust and flexible API for managing content.

graphql

query GetProjectDetails($projectId: ID!) {

project(id: $projectId) {

id

name

description

status

startDate

endDate

owner {

id

name

email

}

members {

id

graphql_schema_designer.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
"); 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' import ReactDOM from 'react-dom/client' import App from './App' import './index.css' ReactDOM.createRoot(document.getElementById('root')!).render( ) "); 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' import './App.css' function App(){ return(

"+slugTitle(pn)+"

Built with PantheraHive BOS

) } export default App "); zip.file(folder+"src/index.css","*{margin:0;padding:0;box-sizing:border-box} body{font-family:system-ui,-apple-system,sans-serif;background:#f0f2f5;color:#1a1a2e} .app{min-height:100vh;display:flex;flex-direction:column} .app-header{flex:1;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:12px;padding:40px} h1{font-size:2.5rem;font-weight:700} "); 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)+" Generated by PantheraHive BOS. ## Setup ```bash npm install npm run dev ``` ## Build ```bash npm run build ``` ## Open in IDE Open the project folder in VS Code or WebStorm. "); zip.file(folder+".gitignore","node_modules/ dist/ .env .DS_Store *.local "); } /* --- 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",'{ "name": "'+pn+'", "version": "0.0.0", "type": "module", "scripts": { "dev": "vite", "build": "vue-tsc -b && vite build", "preview": "vite preview" }, "dependencies": { "vue": "^3.5.13", "vue-router": "^4.4.5", "pinia": "^2.3.0", "axios": "^1.7.9" }, "devDependencies": { "@vitejs/plugin-vue": "^5.2.1", "typescript": "~5.7.3", "vite": "^6.0.5", "vue-tsc": "^2.2.0" } } '); zip.file(folder+"vite.config.ts","import { defineConfig } from 'vite' import vue from '@vitejs/plugin-vue' import { resolve } from 'path' export default defineConfig({ plugins: [vue()], resolve: { alias: { '@': resolve(__dirname,'src') } } }) "); zip.file(folder+"tsconfig.json",'{"files":[],"references":[{"path":"./tsconfig.app.json"},{"path":"./tsconfig.node.json"}]} '); zip.file(folder+"tsconfig.app.json",'{ "compilerOptions":{ "target":"ES2020","useDefineForClassFields":true,"module":"ESNext","lib":["ES2020","DOM","DOM.Iterable"], "skipLibCheck":true,"moduleResolution":"bundler","allowImportingTsExtensions":true, "isolatedModules":true,"moduleDetection":"force","noEmit":true,"jsxImportSource":"vue", "strict":true,"paths":{"@/*":["./src/*"]} }, "include":["src/**/*.ts","src/**/*.d.ts","src/**/*.tsx","src/**/*.vue"] } '); zip.file(folder+"env.d.ts","/// "); zip.file(folder+"index.html"," "+slugTitle(pn)+"
"); 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' import { createPinia } from 'pinia' import App from './App.vue' import './assets/main.css' const app = createApp(App) app.use(createPinia()) app.mount('#app') "); var hasApp=Object.keys(extracted).some(function(k){return k.indexOf("App.vue")>=0;}); if(!hasApp) zip.file(folder+"src/App.vue"," "); 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} "); 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)+" Generated by PantheraHive BOS. ## Setup ```bash npm install npm run dev ``` ## Build ```bash npm run build ``` Open in VS Code or WebStorm. "); zip.file(folder+".gitignore","node_modules/ dist/ .env .DS_Store *.local "); } /* --- 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",'{ "name": "'+pn+'", "version": "0.0.0", "scripts": { "ng": "ng", "start": "ng serve", "build": "ng build", "test": "ng test" }, "dependencies": { "@angular/animations": "^19.0.0", "@angular/common": "^19.0.0", "@angular/compiler": "^19.0.0", "@angular/core": "^19.0.0", "@angular/forms": "^19.0.0", "@angular/platform-browser": "^19.0.0", "@angular/platform-browser-dynamic": "^19.0.0", "@angular/router": "^19.0.0", "rxjs": "~7.8.0", "tslib": "^2.3.0", "zone.js": "~0.15.0" }, "devDependencies": { "@angular-devkit/build-angular": "^19.0.0", "@angular/cli": "^19.0.0", "@angular/compiler-cli": "^19.0.0", "typescript": "~5.6.0" } } '); zip.file(folder+"angular.json",'{ "$schema": "./node_modules/@angular/cli/lib/config/schema.json", "version": 1, "newProjectRoot": "projects", "projects": { "'+pn+'": { "projectType": "application", "root": "", "sourceRoot": "src", "prefix": "app", "architect": { "build": { "builder": "@angular-devkit/build-angular:application", "options": { "outputPath": "dist/'+pn+'", "index": "src/index.html", "browser": "src/main.ts", "tsConfig": "tsconfig.app.json", "styles": ["src/styles.css"], "scripts": [] } }, "serve": {"builder":"@angular-devkit/build-angular:dev-server","configurations":{"production":{"buildTarget":"'+pn+':build:production"},"development":{"buildTarget":"'+pn+':build:development"}},"defaultConfiguration":"development"} } } } } '); zip.file(folder+"tsconfig.json",'{ "compileOnSave": false, "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"]}, "references":[{"path":"./tsconfig.app.json"}] } '); zip.file(folder+"tsconfig.app.json",'{ "extends":"./tsconfig.json", "compilerOptions":{"outDir":"./dist/out-tsc","types":[]}, "files":["src/main.ts"], "include":["src/**/*.d.ts"] } '); zip.file(folder+"src/index.html"," "+slugTitle(pn)+" "); zip.file(folder+"src/main.ts","import { bootstrapApplication } from '@angular/platform-browser'; import { appConfig } from './app/app.config'; import { AppComponent } from './app/app.component'; bootstrapApplication(AppComponent, appConfig) .catch(err => console.error(err)); "); zip.file(folder+"src/styles.css","* { margin: 0; padding: 0; box-sizing: border-box; } body { font-family: system-ui, -apple-system, sans-serif; background: #f9fafb; color: #111827; } "); 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'; import { RouterOutlet } from '@angular/router'; @Component({ selector: 'app-root', standalone: true, imports: [RouterOutlet], templateUrl: './app.component.html', styleUrl: './app.component.css' }) export class AppComponent { title = '"+pn+"'; } "); zip.file(folder+"src/app/app.component.html","

"+slugTitle(pn)+"

Built with PantheraHive BOS

"); 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} "); } zip.file(folder+"src/app/app.config.ts","import { ApplicationConfig, provideZoneChangeDetection } from '@angular/core'; import { provideRouter } from '@angular/router'; import { routes } from './app.routes'; export const appConfig: ApplicationConfig = { providers: [ provideZoneChangeDetection({ eventCoalescing: true }), provideRouter(routes) ] }; "); zip.file(folder+"src/app/app.routes.ts","import { Routes } from '@angular/router'; export const routes: Routes = []; "); 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)+" Generated by PantheraHive BOS. ## Setup ```bash npm install ng serve # or: npm start ``` ## Build ```bash ng build ``` Open in VS Code with Angular Language Service extension. "); zip.file(folder+".gitignore","node_modules/ dist/ .env .DS_Store *.local .angular/ "); } /* --- Python --- */ function buildPython(zip,folder,app,code){ var title=slugTitle(app); var pn=pkgName(app); var src=code.replace(/^```[w]* ?/m,"").replace(/ ?```$/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(" "):"# add dependencies here "; zip.file(folder+"main.py",src||"# "+title+" # Generated by PantheraHive BOS print(title+" loaded") "); zip.file(folder+"requirements.txt",reqsTxt); zip.file(folder+".env.example","# Environment variables "); zip.file(folder+"README.md","# "+title+" Generated by PantheraHive BOS. ## Setup ```bash python3 -m venv .venv source .venv/bin/activate pip install -r requirements.txt ``` ## Run ```bash python main.py ``` "); zip.file(folder+".gitignore",".venv/ __pycache__/ *.pyc .env .DS_Store "); } /* --- Node.js --- */ function buildNode(zip,folder,app,code){ var title=slugTitle(app); var pn=pkgName(app); var src=code.replace(/^```[w]* ?/m,"").replace(/ ?```$/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)+" "; zip.file(folder+"package.json",pkgJson); var fallback="const express=require("express"); const app=express(); app.use(express.json()); app.get("/",(req,res)=>{ res.json({message:""+title+" API"}); }); const PORT=process.env.PORT||3000; app.listen(PORT,()=>console.log("Server on port "+PORT)); "; zip.file(folder+"src/index.js",src||fallback); zip.file(folder+".env.example","PORT=3000 "); zip.file(folder+".gitignore","node_modules/ .env .DS_Store "); zip.file(folder+"README.md","# "+title+" Generated by PantheraHive BOS. ## Setup ```bash npm install ``` ## Run ```bash npm run dev ``` "); } /* --- 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:" "+title+" "+code+" "; zip.file(folder+"index.html",indexHtml); zip.file(folder+"style.css","/* "+title+" — styles */ *{margin:0;padding:0;box-sizing:border-box} body{font-family:system-ui,-apple-system,sans-serif;background:#fff;color:#1a1a2e} "); zip.file(folder+"script.js","/* "+title+" — scripts */ "); zip.file(folder+"assets/.gitkeep",""); zip.file(folder+"README.md","# "+title+" Generated by PantheraHive BOS. ## Open Double-click `index.html` in your browser. Or serve locally: ```bash npx serve . # or python3 -m http.server 3000 ``` "); zip.file(folder+".gitignore",".DS_Store node_modules/ .env "); } /* ===== 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(/ {2,}/g,"

"); h+="

"+hc+"

Generated by PantheraHive BOS
"; zip.file(folder+app+".html",h); zip.file(folder+"README.md","# "+title+" Generated by PantheraHive BOS. Files: - "+app+".md (Markdown) - "+app+".html (styled HTML) "); } 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);}});}