mirror of
https://github.com/vega-org/vega-providers.git
synced 2026-04-17 15:41:45 +00:00
186 lines
5.0 KiB
JavaScript
186 lines
5.0 KiB
JavaScript
const express = require("express");
|
||
const cors = require("cors");
|
||
const path = require("path");
|
||
const fs = require("fs");
|
||
const { execSync } = require("child_process");
|
||
const os = require("os");
|
||
|
||
/**
|
||
* Local development server for testing providers
|
||
*/
|
||
class DevServer {
|
||
constructor() {
|
||
this.app = express();
|
||
this.port = 3001;
|
||
this.distDir = path.join(__dirname, "dist");
|
||
this.currentDir = path.join(__dirname);
|
||
|
||
this.setupMiddleware();
|
||
this.setupRoutes();
|
||
}
|
||
|
||
setupMiddleware() {
|
||
// Enable CORS for mobile app
|
||
this.app.use(
|
||
cors({
|
||
origin: "*",
|
||
methods: ["GET", "POST", "OPTIONS"],
|
||
allowedHeaders: ["Content-Type", "Authorization"],
|
||
})
|
||
);
|
||
|
||
// Serve static files from dist directory
|
||
this.app.use("/dist", express.static(this.distDir));
|
||
|
||
// JSON parsing
|
||
this.app.use(express.json());
|
||
|
||
// Logging
|
||
this.app.use((req, res, next) => {
|
||
console.log(`${new Date().toISOString()} - ${req.method} ${req.url}`);
|
||
next();
|
||
});
|
||
}
|
||
|
||
setupRoutes() {
|
||
// Serve manifest.json
|
||
this.app.get("/manifest.json", (req, res) => {
|
||
const manifestPath = path.join(this.currentDir, "manifest.json");
|
||
console.log(`Serving manifest from: ${manifestPath}`);
|
||
|
||
if (fs.existsSync(manifestPath)) {
|
||
res.sendFile(manifestPath);
|
||
} else {
|
||
res.status(404).json({ error: "Manifest not found. Run build first." });
|
||
}
|
||
});
|
||
|
||
// Serve individual provider files
|
||
this.app.get("/dist/:provider/:file", (req, res) => {
|
||
const { provider, file } = req.params;
|
||
const filePath = path.join(this.distDir, provider, file);
|
||
|
||
if (fs.existsSync(filePath)) {
|
||
res.sendFile(filePath);
|
||
} else {
|
||
res.status(404).json({
|
||
error: `File not found: ${provider}/${file}`,
|
||
hint: "Make sure to run build first",
|
||
});
|
||
}
|
||
});
|
||
|
||
// Build endpoint - trigger rebuild
|
||
this.app.post("/build", (req, res) => {
|
||
try {
|
||
console.log("🔨 Triggering rebuild...");
|
||
execSync("node build.js", { stdio: "inherit" });
|
||
res.json({ success: true, message: "Build completed" });
|
||
} catch (error) {
|
||
console.error("Build failed:", error);
|
||
res.status(500).json({
|
||
success: false,
|
||
error: error.message,
|
||
});
|
||
}
|
||
});
|
||
|
||
// Status endpoint
|
||
this.app.get("/status", (req, res) => {
|
||
const providers = this.getAvailableProviders();
|
||
res.json({
|
||
status: "running",
|
||
port: this.port,
|
||
providers: providers.length,
|
||
providerList: providers,
|
||
buildTime: this.getBuildTime(),
|
||
});
|
||
});
|
||
|
||
// List available providers
|
||
this.app.get("/providers", (req, res) => {
|
||
const providers = this.getAvailableProviders();
|
||
res.json(providers);
|
||
});
|
||
|
||
// Health check
|
||
this.app.get("/health", (req, res) => {
|
||
res.json({ status: "healthy", timestamp: new Date().toISOString() });
|
||
});
|
||
|
||
// 404 handler
|
||
this.app.use((req, res) => {
|
||
res.status(404).json({
|
||
error: "Not found",
|
||
availableEndpoints: [
|
||
"GET /manifest.json",
|
||
"GET /dist/:provider/:file",
|
||
"POST /build",
|
||
"GET /status",
|
||
"GET /providers",
|
||
"GET /health",
|
||
],
|
||
});
|
||
});
|
||
}
|
||
|
||
getAvailableProviders() {
|
||
if (!fs.existsSync(this.distDir)) {
|
||
return [];
|
||
}
|
||
|
||
return fs
|
||
.readdirSync(this.distDir, { withFileTypes: true })
|
||
.filter((item) => item.isDirectory())
|
||
.map((item) => item.name);
|
||
}
|
||
|
||
getBuildTime() {
|
||
const manifestPath = path.join(this.rootDir, "manifest.json");
|
||
if (fs.existsSync(manifestPath)) {
|
||
const stats = fs.statSync(manifestPath);
|
||
return stats.mtime.toISOString();
|
||
}
|
||
return null;
|
||
}
|
||
|
||
start() {
|
||
// Get local IP address
|
||
const interfaces = os.networkInterfaces();
|
||
let localIp = "localhost";
|
||
for (const name of Object.keys(interfaces)) {
|
||
for (const iface of interfaces[name]) {
|
||
if (iface.family === "IPv4" && !iface.internal) {
|
||
localIp = iface.address;
|
||
break;
|
||
}
|
||
}
|
||
if (localIp !== "localhost") break;
|
||
}
|
||
this.app.listen(this.port, "0.0.0.0", () => {
|
||
console.log(`
|
||
🚀 Vega Providers Dev Server Started!
|
||
|
||
📡 Server URL: http://localhost:${this.port}
|
||
📱 Mobile Test URL: http://${localIp}:${this.port}
|
||
|
||
💡 Usage:
|
||
1. Run 'npm run auto' to to start the dev server ☑️
|
||
2. Update vega app to use: http://${localIp}:${this.port}
|
||
3. Test your providers!
|
||
|
||
🔄 Auto-rebuild: POST to /build to rebuild after changes
|
||
`);
|
||
|
||
// Check if build exists
|
||
if (!fs.existsSync(this.distDir)) {
|
||
console.log('\n⚠️ No build found. Run "node build.js" first!\n');
|
||
}
|
||
});
|
||
}
|
||
}
|
||
|
||
// Start the server
|
||
const server = new DevServer();
|
||
server.start();
|