mmrwinston001 commited on
Commit
7a04ebe
·
verified ·
1 Parent(s): 0b2c057

Upload 5 files

Browse files
server/firebase.js ADDED
@@ -0,0 +1,11 @@
 
 
 
 
 
 
 
 
 
 
 
 
1
+ // server/firebase.js
2
+ const admin = require('firebase-admin');
3
+ const serviceAccount = require('./serviceAccountKey.json'); // download from Firebase Console
4
+
5
+ admin.initializeApp({
6
+ credential: admin.credential.cert(serviceAccount)
7
+ });
8
+
9
+ const db = admin.firestore();
10
+
11
+ module.exports = { db };
server/routes.js ADDED
The diff for this file is too large to render. See raw diff
 
server/server.js ADDED
@@ -0,0 +1,86 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const express = require("express");
2
+ const cors = require("cors");
3
+ const axios = require("axios");
4
+ const helmet = require("helmet");
5
+ const path = require("path");
6
+
7
+ const app = express();
8
+ const PORT = process.env.PORT || 3001;
9
+
10
+ // Security headers
11
+ app.use(helmet());
12
+
13
+ // CORS (restrict in production)
14
+ app.use(
15
+ cors({
16
+ origin: process.env.CLIENT_URL || "*",
17
+ methods: ["GET", "POST", "PUT", "DELETE", "OPTIONS"],
18
+ allowedHeaders: ["Content-Type", "Authorization"],
19
+ })
20
+ );
21
+
22
+ app.use(express.json({ limit: "50mb" }));
23
+ app.use(express.urlencoded({ extended: true, limit: "50mb" }));
24
+
25
+ // =============================
26
+ // Serve Frontend (React/Vite)
27
+ // =============================
28
+ app.use(
29
+ express.static(path.join(__dirname, "dist"), {
30
+ setHeaders: (res, filePath) => {
31
+ if (filePath.endsWith(".js") || filePath.endsWith(".css")) {
32
+ // Cache hashed assets for 1 year
33
+ res.setHeader("Cache-Control", "public, max-age=31536000, immutable");
34
+ } else {
35
+ // Cache other assets (images, etc.) for 1 hour
36
+ res.setHeader("Cache-Control", "public, max-age=3600");
37
+ }
38
+ },
39
+ })
40
+ );
41
+
42
+ // SPA fallback → always return index.html
43
+ app.get("*", (req, res, next) => {
44
+ if (req.path.startsWith("/api")) return next(); // skip API routes
45
+ res.sendFile(path.join(__dirname, "dist", "index.html"));
46
+ });
47
+
48
+ // =============================
49
+ // Proxy /api requests
50
+ // =============================
51
+ app.use("/api", async (req, res, next) => {
52
+ try {
53
+ const url = `https://humanizerx.pro/api/routes.php${req.originalUrl.replace(
54
+ "/api",
55
+ ""
56
+ )}`;
57
+ const method = req.method.toLowerCase();
58
+
59
+ const { data, status } = await axios({
60
+ url,
61
+ method,
62
+ headers: {
63
+ "Content-Type": req.headers["content-type"],
64
+ Authorization: req.headers["authorization"],
65
+ },
66
+ data: req.body,
67
+ });
68
+
69
+ res.status(status).json(data);
70
+ } catch (error) {
71
+ console.error("API Proxy Error:", error.message);
72
+ res.status(error.response?.status || 500).json({
73
+ success: false,
74
+ error: error.message,
75
+ });
76
+ }
77
+ });
78
+
79
+ // Test route
80
+ app.get("/test", (req, res) => {
81
+ res.json({ msg: "Hello from Humanizer X backend 🚀" });
82
+ });
83
+
84
+ app.listen(PORT, () => {
85
+ console.log(`✅ Humanizer X Backend running on http://localhost:${PORT}`);
86
+ });
server/serviceAccountKey.json ADDED
@@ -0,0 +1,13 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "type": "service_account",
3
+ "project_id": "humanizer-x-16baa",
4
+ "private_key_id": "21350178209a3ac2f49055fb1fad3dc739826af1",
5
+ "private_key": "-----BEGIN PRIVATE KEY-----\nMIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQC5INQBpCty2UU0\nLEBXlt2nopHFuf7Wfb+FC6dkGW6RKQO5TU0VnydJnXeD43bB3GkJZ47DYa7cccSo\nGze74UxsghT6CpZ8zGVDu57kCICSsIy/evUfX9IQjYB5a7mJFT/rPmQuBFAt0hSP\nj3J9y2DGU4JsT3xJlfglOuF2DwSGpjAbExbPdu3egsXR8tB3MHe3/hvOO+gZegzT\nYf90fs1No7efrhTll4nCGMzmiAu9OXiYO9oAzCaQFo3zibitwVeBwPHIS+e9tmRJ\nyxT72CiVpq1CxaWUEgU3cS0AQN9FBEXDoF71j6o5Wd8OQekkwhh1EYWfZ5OwioeU\nL6aUKAajAgMBAAECggEAPdLGuh2XHO2N/NRiUF3je94AjGWGwx6PXOD9b6JGmFd4\nFOPJwFS8DAt4JCVMPYVb1nYs6PawLJIZuIIOZMHigcIXO0FZ7CdeEfaQI1rrhRFM\nj42CWo3nWvvGUcY12Z+tDuRxFCUAmay0jRS8iWHn2ZN91KneubxJeDVnocN2IXjA\n1xx4QsgBzgIBRm4DhtcoAgaU5sIFHOFbKvLzxSLOEGRBqITb+sgNvWwgD9MahBAz\n4VoQmcaCoGQu9xEz+PEwFY8s+a0qOCLsd1la57VCOPV0l+RVbMqfQbCw1hjeIjvI\ncsIGoNvG/GAjTmd5IzJ2Fwmzy2xV8b11bWaViEuLcQKBgQDfrsfqajvTW3Wfn6Xe\nI8R1Ba59pqIqggX7UKmFOJisT/jvwuYTw+AO0Y0M3elNFp75iw82UIFVd57ZVllY\nmPUyQNhc3i8CnHQpJMFO7iVTatoXMCdwspFySqBDvN858Jhu5HWCxU6KQ99GCqll\ntuloRrbkvovxbsyYsNCKbsKBfwKBgQDT4A4TZWQ5KGbrkO/6wtbdOp7jmH0tl2Cy\nmQl7eQtDsYoZSaaRkfXjojl6ycUzTYLMg5hefb+SP7aSlad2NdDt5QyUJ+sFNhDi\n2kvtw5WpRxAVP/fQOhg2g+sPOO2D+wKy7qwMdphi1yWub8Kgu961c1hfdKjOYH0S\nS+tAj2fE3QKBgQCUkVlVWHQeAQxSFk6sCeOtujVYXbouM6hXcQ73Xk0BfiigzznT\n/PCvxv1Bg4821YSHyJY1BCmzI72NK24yi32ogCt1G1nsCRCaV0BR9ZkzG7B5YFGB\n6Aj0+Z4S/7rgl+4XEYT/c5+j9EqzEdfLqD7FNNq7edgnZulbrW0F1WU5bwKBgQC0\njTJxhO2rZ6qNA639WxwO2m2cNc42k9FrYM6b0cKvpROyCPlRA7kuiofBA0BxP5Q/\nA8VMgIxH7NOAhtd1/NZWY+IcPwggILqzFqOtsgZPgqdJ9IERiPApRLGC/1goKDdc\nk9c5p7akRANwavzITFC0/95HOfrAI6lxdhC7q3kaYQKBgDyzp7RQMfNI/n3fzN5h\nISbyx4KEBhd/6qCyQ0xfNu2pIgBakQ7pka07rWSyhBizdzkicSDQ1hwME+J9N63f\nG4pZ9MvXBkO6muv4nSzvQ0bJwf5v/4c4uVQr8RRzk/l1tKl9XLZJq5NEGgCAXMOz\ngYb6NAwZ6QpbbBfQYv92FjS5\n-----END PRIVATE KEY-----\n",
6
+ "client_email": "firebase-adminsdk-fbsvc@humanizer-x-16baa.iam.gserviceaccount.com",
7
+ "client_id": "114780934799698707217",
8
+ "auth_uri": "https://accounts.google.com/o/oauth2/auth",
9
+ "token_uri": "https://oauth2.googleapis.com/token",
10
+ "auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
11
+ "client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/firebase-adminsdk-fbsvc%40humanizer-x-16baa.iam.gserviceaccount.com",
12
+ "universe_domain": "googleapis.com"
13
+ }
server/upload.js ADDED
@@ -0,0 +1,30 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ // backend/upload.js
2
+ const path = require('path');
3
+ const multer = require('multer');
4
+ const fs = require('fs');
5
+
6
+ // Ensure uploads folder exists
7
+ const uploadsDir = path.join(__dirname, 'uploads');
8
+ if (!fs.existsSync(uploadsDir)) {
9
+ fs.mkdirSync(uploadsDir, { recursive: true });
10
+ }
11
+
12
+ const upload = multer({
13
+ dest: uploadsDir, // Absolute path to uploads folder
14
+ limits: { fileSize: 15 * 1024 * 1024 }, // 15MB max
15
+ fileFilter: (req, file, cb) => {
16
+ const allowedTypes = [
17
+ 'application/pdf',
18
+ 'application/msword',
19
+ 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',
20
+ 'text/plain'
21
+ ];
22
+ if (allowedTypes.includes(file.mimetype)) {
23
+ cb(null, true);
24
+ } else {
25
+ cb(new Error('Invalid file type. Only PDF, Word, and TXT files are allowed.'));
26
+ }
27
+ }
28
+ });
29
+
30
+ module.exports = upload;