Compare commits
6 Commits
bb1635a5b4
...
dd88f258ed
| Author | SHA1 | Date | |
|---|---|---|---|
| dd88f258ed | |||
| c2c43b1e22 | |||
| 4b53700603 | |||
| a18cf652fa | |||
| 84ce009310 | |||
| dc04d97229 |
20
database/migrations/0015_wonderful_lady_vermin.sql
Normal file
20
database/migrations/0015_wonderful_lady_vermin.sql
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
CREATE TABLE "rfidReaders" (
|
||||||
|
"rfidReader_id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||||
|
"reader" text,
|
||||||
|
"readerIP" text,
|
||||||
|
"lastHeartBeat" timestamp DEFAULT now()
|
||||||
|
);
|
||||||
|
--> statement-breakpoint
|
||||||
|
CREATE TABLE "rfidTags" (
|
||||||
|
"rfidTag_id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||||
|
"tagHex" text,
|
||||||
|
"tag" text,
|
||||||
|
"timeStamp" timestamp DEFAULT now(),
|
||||||
|
"counts" jsonb NOT NULL,
|
||||||
|
"lastareaIn" text NOT NULL,
|
||||||
|
"runningNumber" numeric NOT NULL,
|
||||||
|
"created_at" timestamp DEFAULT now()
|
||||||
|
);
|
||||||
|
--> statement-breakpoint
|
||||||
|
CREATE UNIQUE INDEX "reader" ON "rfidReaders" USING btree ("reader");--> statement-breakpoint
|
||||||
|
CREATE UNIQUE INDEX "tagHex" ON "rfidTags" USING btree ("tagHex");
|
||||||
1033
database/migrations/meta/0015_snapshot.json
Normal file
1033
database/migrations/meta/0015_snapshot.json
Normal file
File diff suppressed because it is too large
Load Diff
@@ -106,6 +106,13 @@
|
|||||||
"when": 1741892067501,
|
"when": 1741892067501,
|
||||||
"tag": "0014_illegal_thundra",
|
"tag": "0014_illegal_thundra",
|
||||||
"breakpoints": true
|
"breakpoints": true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"idx": 15,
|
||||||
|
"version": "7",
|
||||||
|
"when": 1741952150913,
|
||||||
|
"tag": "0015_wonderful_lady_vermin",
|
||||||
|
"breakpoints": true
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
65
server/globalUtils/pingServer.ts
Normal file
65
server/globalUtils/pingServer.ts
Normal file
@@ -0,0 +1,65 @@
|
|||||||
|
import dns from "dns";
|
||||||
|
import net from "net";
|
||||||
|
|
||||||
|
// Usage example
|
||||||
|
//const hostnamePort = "example.com:80"; // Replace with your hostname:port
|
||||||
|
//checkHostnamePort(hostnamePort);
|
||||||
|
|
||||||
|
// Function to resolve a hostname to an IP address
|
||||||
|
export function resolveHostname(hostname: string) {
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
dns.lookup(hostname, (err, address) => {
|
||||||
|
if (err) {
|
||||||
|
reject(err);
|
||||||
|
} else {
|
||||||
|
resolve(address);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Function to check if a port is open
|
||||||
|
export function checkPort(ip: string, port: number): Promise<boolean> {
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
const socket = new net.Socket();
|
||||||
|
|
||||||
|
socket.setTimeout(2000); // Set a timeout for the connection attempt
|
||||||
|
|
||||||
|
socket.on("connect", () => {
|
||||||
|
socket.destroy(); // Close the connection
|
||||||
|
resolve(true); // Port is open
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on("timeout", () => {
|
||||||
|
socket.destroy(); // Close the connection
|
||||||
|
reject(new Error("Connection timed out")); // Port is not reachable
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.on("error", (err: any) => {
|
||||||
|
reject(new Error(`Unknown error: ${err}`)); // Handle non-Error types
|
||||||
|
});
|
||||||
|
|
||||||
|
socket.connect(port, ip);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Main function to check hostname:port
|
||||||
|
export async function checkHostnamePort(hostnamePort: string): Promise<boolean> {
|
||||||
|
try {
|
||||||
|
// Split the input into hostname and port
|
||||||
|
const [hostname, port] = hostnamePort.split(":");
|
||||||
|
if (!hostname || !port) {
|
||||||
|
return false; // Invalid format
|
||||||
|
}
|
||||||
|
|
||||||
|
// Resolve the hostname to an IP address
|
||||||
|
const ip = (await resolveHostname(hostname)) as string;
|
||||||
|
|
||||||
|
// Check if the port is open
|
||||||
|
const portCheck = await checkPort(ip, parseInt(port, 10));
|
||||||
|
|
||||||
|
return true; // Hostname:port is reachable
|
||||||
|
} catch (err) {
|
||||||
|
return false; // Any error means the hostname:port is not reachable
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -106,25 +106,25 @@ app.use("*", serveStatic({path: "./frontend/dist/index.html"}));
|
|||||||
// Handle app exit signals
|
// Handle app exit signals
|
||||||
process.on("SIGINT", async () => {
|
process.on("SIGINT", async () => {
|
||||||
console.log("\nGracefully shutting down...");
|
console.log("\nGracefully shutting down...");
|
||||||
await closePool();
|
//await closePool();
|
||||||
process.exit(0);
|
process.exit(0);
|
||||||
});
|
});
|
||||||
|
|
||||||
process.on("SIGTERM", async () => {
|
process.on("SIGTERM", async () => {
|
||||||
console.log("Received termination signal, closing database...");
|
console.log("Received termination signal, closing database...");
|
||||||
await closePool();
|
//await closePool();
|
||||||
process.exit(0);
|
process.exit(0);
|
||||||
});
|
});
|
||||||
|
|
||||||
process.on("uncaughtException", async (err) => {
|
process.on("uncaughtException", async (err) => {
|
||||||
console.log("Uncaught Exception:", err);
|
console.log("Uncaught Exception:", err);
|
||||||
await closePool();
|
//await closePool();
|
||||||
process.exit(1);
|
process.exit(1);
|
||||||
});
|
});
|
||||||
|
|
||||||
process.on("beforeExit", async () => {
|
process.on("beforeExit", async () => {
|
||||||
console.log("Process is about to exit...");
|
console.log("Process is about to exit...");
|
||||||
await closePool();
|
//await closePool();
|
||||||
});
|
});
|
||||||
|
|
||||||
serve(
|
serve(
|
||||||
|
|||||||
60
server/scripts/build.ps1
Normal file
60
server/scripts/build.ps1
Normal file
@@ -0,0 +1,60 @@
|
|||||||
|
param (
|
||||||
|
[string]$dir,
|
||||||
|
[string]$app
|
||||||
|
)
|
||||||
|
|
||||||
|
# Store the original directory
|
||||||
|
$originalDir = Get-Location
|
||||||
|
|
||||||
|
Write-Host $originalDir
|
||||||
|
|
||||||
|
# Check if the directory is provided
|
||||||
|
if (-not $dir) {
|
||||||
|
Write-Host "Error: Directory parameter is required."
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# Check if the directory exists
|
||||||
|
if (-not (Test-Path $dir)) {
|
||||||
|
Write-Host "Error: Directory '$dir' does not exist."
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# Navigate to the directory
|
||||||
|
Set-Location -Path $dir
|
||||||
|
|
||||||
|
Write-Host "Cleaning the app."
|
||||||
|
|
||||||
|
# Function to delete all `dist` and `.turbo` folders recursively
|
||||||
|
function Delete-Folders {
|
||||||
|
param (
|
||||||
|
[string]$folderName
|
||||||
|
)
|
||||||
|
|
||||||
|
# Define the directories to search (packages and apps)
|
||||||
|
$searchDirectories = @("/", "frontend")
|
||||||
|
|
||||||
|
foreach ($searchDir in $searchDirectories) {
|
||||||
|
$fullSearchPath = Join-Path -Path $dir -ChildPath $searchDir
|
||||||
|
|
||||||
|
# Check if the directory exists
|
||||||
|
if (Test-Path $fullSearchPath) {
|
||||||
|
# Find all folders matching the name
|
||||||
|
$folders = Get-ChildItem -Path $fullSearchPath -Recurse -Directory -Filter $folderName -ErrorAction SilentlyContinue
|
||||||
|
|
||||||
|
if ($folders) {
|
||||||
|
#Write-Host "Deleting all '$folderName' folders in $fullSearchPath and its subdirectories..."
|
||||||
|
foreach ($folder in $folders) {
|
||||||
|
#Write-Host "Deleting: $($folder.FullName)"
|
||||||
|
Remove-Item -Path $folder.FullName -Recurse -Force
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
# Write-Host "No '$folderName' folders found in $fullSearchPath and its subdirectories."
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
# Write-Host "Directory '$fullSearchPath' does not exist."
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Delete-Folders -folderName "dist"
|
||||||
3
server/services/rfid/controller/mgtMonitor.ts
Normal file
3
server/services/rfid/controller/mgtMonitor.ts
Normal file
@@ -0,0 +1,3 @@
|
|||||||
|
/**
|
||||||
|
* While in production we will monitor the readers if we have not gotten a heartbeat in the last 5 min we will send a reboot command along with an email.
|
||||||
|
*/
|
||||||
@@ -7,7 +7,7 @@ import {createLog} from "../../logger/logger.js";
|
|||||||
import fs from "fs";
|
import fs from "fs";
|
||||||
|
|
||||||
export const serversCheckPoint = async () => {
|
export const serversCheckPoint = async () => {
|
||||||
let servers: any;
|
let servers: any[] = [];
|
||||||
let filePath: string;
|
let filePath: string;
|
||||||
if (process.env.NODE_ENV === "development") {
|
if (process.env.NODE_ENV === "development") {
|
||||||
filePath = "./server/services/server/utils/serverData.json";
|
filePath = "./server/services/server/utils/serverData.json";
|
||||||
@@ -49,7 +49,7 @@ export const serversCheckPoint = async () => {
|
|||||||
}
|
}
|
||||||
createLog("info", "lst", "server", "Servers were just added/updated due to server startup");
|
createLog("info", "lst", "server", "Servers were just added/updated due to server startup");
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
createLog("error", "lst", "server", `There was an error adding serverData to the db, ${error}`);
|
createLog("error", "lst", "server", `There was an error adding/updating serverData to the db, ${error}`);
|
||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
createLog("error", "lst", "server", `There was an error adding serverData to the db, ${error}`);
|
createLog("error", "lst", "server", `There was an error adding serverData to the db, ${error}`);
|
||||||
|
|||||||
@@ -5,10 +5,18 @@ import {db} from "../../../database/dbclient.js";
|
|||||||
import {settings} from "../../../database/schema/settings.js";
|
import {settings} from "../../../database/schema/settings.js";
|
||||||
import {eq} from "drizzle-orm";
|
import {eq} from "drizzle-orm";
|
||||||
import {installed} from "../../index.js";
|
import {installed} from "../../index.js";
|
||||||
|
import {checkHostnamePort} from "../../globalUtils/pingServer.js";
|
||||||
|
|
||||||
let pool: any;
|
let pool: any;
|
||||||
let connected: boolean = false;
|
let connected: boolean = false;
|
||||||
export const initializeProdPool = async () => {
|
export const initializeProdPool = async () => {
|
||||||
|
const dbServer = await db.select().from(settings).where(eq(settings.name, "dbServer"));
|
||||||
|
const serverUp = await checkHostnamePort(`${dbServer[0].value}:1433`);
|
||||||
|
|
||||||
|
if (!serverUp) {
|
||||||
|
createLog("error", "lst", "server", `The sql ${dbServer[0].value} is not reachable`);
|
||||||
|
return;
|
||||||
|
}
|
||||||
if (!installed) {
|
if (!installed) {
|
||||||
createLog("info", "lst", "sqlProd", "The server was not installed will reconnect in 5 seconds");
|
createLog("info", "lst", "sqlProd", "The server was not installed will reconnect in 5 seconds");
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
|
|||||||
@@ -7,10 +7,9 @@ import restart from "./route/restartProdSql.js";
|
|||||||
|
|
||||||
const app = new OpenAPIHono();
|
const app = new OpenAPIHono();
|
||||||
|
|
||||||
// intially start the pool up.
|
setTimeout(async () => {
|
||||||
setTimeout(() => {
|
|
||||||
initializeProdPool();
|
initializeProdPool();
|
||||||
}, 500);
|
}, 2 * 1000);
|
||||||
|
|
||||||
app.route("/sqlprod/connect", connect);
|
app.route("/sqlprod/connect", connect);
|
||||||
app.route("/sqlprod/close", closeConnection);
|
app.route("/sqlprod/close", closeConnection);
|
||||||
|
|||||||
Reference in New Issue
Block a user