Compare commits

..

No commits in common. "cdfb501952d4757ac80160daa4c062e0606c940a" and "9ff76bd210b6ebc8b48e8477a3b46730784737a2" have entirely different histories.

14 changed files with 179 additions and 189 deletions

3
.gitignore vendored
View File

@ -67,6 +67,3 @@ public/assets/build/
package-lock.json package-lock.json
bun.lockb bun.lockb
bundle.js bundle.js
mydb.sqlite
public/poster/
output/

5
app.ts
View File

@ -1,19 +1,20 @@
import express from "express"; import express from "express";
import path from 'path' import path from 'path'
import 'dotenv/config'
const hostname = '127.0.0.1'; const hostname = '127.0.0.1';
const httpPort = 4080; const httpPort = 4080;
const app = express(); const app = express();
app.set('views', 'views'); app.set('views', path.join(__dirname, 'views'));
app.set('view engine', 'hbs'); app.set('view engine', 'hbs');
// import morgan from 'morgan' // import morgan from 'morgan'
// app.use(morgan('dev')); // app.use(morgan('dev'));
app.use(express.json()); app.use(express.json());
app.use(express.urlencoded({ extended: false })); app.use(express.urlencoded({ extended: false }));
app.use(express.static('public')); app.use(express.static(path.join(__dirname, 'public')));
import mainRouter from './routes/main'; import mainRouter from './routes/main';
import apiRouter from './routes/api/apiRouter'; import apiRouter from './routes/api/apiRouter';

View File

@ -1,6 +0,0 @@
mkdir output
bun build ./app.ts --outfile=output/app.js --target=bun --minify
bun build ./frontend/list/list.tsx --outfile=public/assets/build/list.js --minify
cp -r views/ output/
cp -r public/ output/

20
build.ts Normal file
View File

@ -0,0 +1,20 @@
async function build() {
const minify = {
whitespace: true,
syntax: true,
identifiers: true,
}
const sa = await Bun.build({
entrypoints: ["./frontend/list/list"],
outdir: "./public/assets/build/",
minify,
})
console.log(sa);
}
build();
export default build;

View File

@ -1,14 +1,7 @@
import { type Request, type Response } from "express"; import { type Request, type Response } from "express";
import UserModel, { values } from '../models/userModel'; import UserModel, { values } from '../models/userModel';
import MediaModel, { Table, Media } from '../models/mediaModel'; import MediaModel, { Table } from '../models/mediaModel';
interface omdbRes{
Title: string,
Released: string,
Response: string,
Poster: string,
Type: string
}
function fromStringToTable(value: string): (Table | undefined) { function fromStringToTable(value: string): (Table | undefined) {
if (value.localeCompare("games") == 0) return Table.games; if (value.localeCompare("games") == 0) return Table.games;
@ -17,31 +10,10 @@ function fromStringToTable(value: string): (Table | undefined) {
return; return;
} }
async function downloadImage(mData: Media, type: Table) {
// Specify the path where you want to save the image
const outputPath = '/poster/' + type + '/' + mData.code + '.jpg';
// Use Bun's built-in fetch to download the image
const response = await fetch(mData.webImg);
// Check if the request was successful
if (!response.ok) {
console.log("fetch image error");
return
}
// Convert the response to a blob
const imageBlob = await response.blob();
// Use Bun's write to save the image to a file
await Bun.write('./public/' + outputPath, await imageBlob.arrayBuffer());
MediaModel.updateWebImg(type, mData.code, outputPath);
}
async function createMed(req: Request, res: Response) { async function createMed(req: Request, res: Response) {
const mediaCode: string = req.body.code; const mediaCode: string = req.body.code;
const omdb_key = UserModel.getValue(values.omdb_key); const omdb_key = await UserModel.getValue(values.omdb_key);
if (!omdb_key) { if (!omdb_key) {
return res.status(500).json({ message: 'Error when creating media' }); return res.status(500).json({ message: 'Error when creating media' });
@ -55,44 +27,39 @@ async function createMed(req: Request, res: Response) {
const uri = `http://www.omdbapi.com/?i=${mediaCode}&apikey=${omdb_key}`; const uri = `http://www.omdbapi.com/?i=${mediaCode}&apikey=${omdb_key}`;
const mJson = await fetch(uri); const mJson = await fetch(uri);
const mData: omdbRes = await mJson.json(); const mData = await mJson.json();
if (mData.Response == 'False') { if (mData.Response == 'False') {
return res.status(404).json({ message: 'wrong code' }); return res.status(404).json({ message: 'wrong code' });
} }
const media: Media = { const seriesFound = await MediaModel.findOne(Table.series, cleanCode);
id:0, if (seriesFound.length != 0) {
code: cleanCode, await MediaModel.updateWebImg(Table.series, cleanCode, mData.Poster);
return res.status(409).json({ message: 'Media already exists' });
}
const moviesFound = await MediaModel.findOne(Table.movies, cleanCode);
if (moviesFound.length != 0) {
await MediaModel.updateWebImg(Table.movies, cleanCode, mData.Poster);
return res.status(409).json({ message: 'Media already exists' });
}
if (mData.Type.localeCompare("movie") == 0) {
const savedMedia = await MediaModel.save(Table.movies, cleanCode, mData.Title, mData.Released, mData.Poster);
}
else if (mData.Type.localeCompare("series") == 0) {
const savedMedia = await MediaModel.save(Table.series, cleanCode, mData.Title, mData.Released, mData.Poster);
}
const media = {
code: mediaCode,
title: mData.Title, title: mData.Title,
released: mData.Released, released: mData.Released,
webImg: mData.Poster, webImg: mData.Poster,
}; };
const seriesFound = MediaModel.findOne(Table.series, cleanCode); return res.status(201).json(media);
if (seriesFound.length != 0) {
res.status(409).json({ message: 'Media already exists' });
await downloadImage(media, Table.series);
return;
}
const moviesFound = MediaModel.findOne(Table.movies, cleanCode);
if (moviesFound.length != 0) {
res.status(409).json({ message: 'Media already exists' });
await downloadImage(media, Table.movies);
return;
}
if (mData.Type.localeCompare("movie") == 0) {
const savedMedia = MediaModel.save(Table.movies, cleanCode, mData.Title, mData.Released, mData.Poster);
await downloadImage(media, Table.movies);
}
else if (mData.Type.localeCompare("series") == 0) {
const savedMedia = MediaModel.save(Table.series, cleanCode, mData.Title, mData.Released, mData.Poster);
await downloadImage(media, Table.series);
}
res.status(201).json(media);
} catch (err) { } catch (err) {
return res.status(500).json({ message: 'Error when creating media' }); return res.status(500).json({ message: 'Error when creating media' });
} }
@ -101,15 +68,15 @@ async function createMed(req: Request, res: Response) {
async function createGame(req: Request, res: Response) { async function createGame(req: Request, res: Response) {
var gameCode = req.body.code; var gameCode = req.body.code;
const twitch_client_id = UserModel.getValue(values.twitch_client_id); const twitch_client_id = await UserModel.getValue(values.twitch_client_id);
const twitch_client_secret = UserModel.getValue(values.twitch_client_secret); const twitch_client_secret = await UserModel.getValue(values.twitch_client_secret);
if (!twitch_client_id || !twitch_client_secret) { if (!twitch_client_id || !twitch_client_secret) {
return res.status(500).json({ message: 'Error when creating game' }); return res.status(500).json({ message: 'Error when creating game' });
} }
try { try {
const gameFound = MediaModel.findOne(Table.games, gameCode); const gameFound = await MediaModel.findOne(Table.games, gameCode);
if (gameFound) { if (gameFound) {
return res.status(409).json({ message: 'Game already exists' }); return res.status(409).json({ message: 'Game already exists' });
} }
@ -154,15 +121,14 @@ async function createGame(req: Request, res: Response) {
) )
const coverData = await response.json() const coverData = await response.json()
const game: Media = { const game = {
id: 0,
code: gameCode, code: gameCode,
title: gameData[0].name, title: gameData[0].name,
released: dateStr, released: dateStr,
webImg: `https://images.igdb.com/igdb/image/upload/t_cover_big/${coverData[0].image_id}.jpg`, webImg: `https://images.igdb.com/igdb/image/upload/t_cover_big/${coverData[0].image_id}.jpg`,
}; };
const savedGame = MediaModel.save(Table.games, game.code, game.title, game.released, game.webImg); const savedGame = await MediaModel.save(Table.games, game.code, game.title, game.released, game.webImg);
return res.status(201).json(game); return res.status(201).json(game);
} catch (error) { } catch (error) {
@ -184,8 +150,16 @@ export default {
}); });
} }
const media = MediaModel.find(mediaTable); MediaModel.find(mediaTable)
return res.json(media); .then(media => {
return res.json(media);
})
.catch(err => {
return res.status(500).json({
message: 'Error when getting media.',
error: err
});
});
}, },
create: async function (req: Request, res: Response) { create: async function (req: Request, res: Response) {
@ -200,7 +174,7 @@ export default {
/** /**
* mediaController.delete() * mediaController.delete()
*/ */
remove: function (req: Request, res: Response) { remove: async function (req: Request, res: Response) {
const mediaTable = fromStringToTable(req.params.mediaType); const mediaTable = fromStringToTable(req.params.mediaType);
if (!mediaTable) { if (!mediaTable) {
return res.status(500).json({ return res.status(500).json({
@ -212,7 +186,7 @@ export default {
try { try {
const mediaTable = req.baseUrl.includes('movies') ? Table.movies : Table.series; const mediaTable = req.baseUrl.includes('movies') ? Table.movies : Table.series;
const media = MediaModel.findOneAndDelete(mediaTable, code); const media = await MediaModel.findOneAndDelete(mediaTable, code);
if (!media) { if (!media) {
return res.status(404).json({ message: 'No such media' }); return res.status(404).json({ message: 'No such media' });
} }

View File

@ -3,20 +3,20 @@ import UserModel, { values } from '../models/userModel';
export default { export default {
render: function (req: Request, res: Response) { render: async function (req: Request, res: Response) {
res.render('user', { keys: UserModel.namesOfValues }); res.render('user', { keys: UserModel.namesOfValues });
}, },
create: function (req: Request, res: Response) { create: async function (req: Request, res: Response) {
const reqPassword: string = req.body.reqPassword; const reqPassword: string = req.body.reqPassword;
if (!reqPassword) return res.render('user', { keys: UserModel.namesOfValues }); if (!reqPassword) return res.render('user', { keys: UserModel.namesOfValues });
const password = UserModel.getValue(values.pass); const password = await UserModel.getValue(values.pass);
// if no password in db save reqPassword // if no password in db save reqPassword
if (!password) { if (!password) {
const affectedRows = UserModel.updateValue("pass", reqPassword); const affectedRows = await UserModel.updateValue("pass", reqPassword);
if (affectedRows > 0) { if (affectedRows > 0) {
return res.redirect('/list'); return res.redirect('/list');
} }
@ -35,7 +35,7 @@ export default {
return res.render('user', { keys: UserModel.namesOfValues }); return res.render('user', { keys: UserModel.namesOfValues });
} }
const affectedRows = UserModel.updateValue(name, value); const affectedRows = await UserModel.updateValue(name, value);
if (affectedRows == 0) { if (affectedRows == 0) {
return res.render('user', { keys: UserModel.namesOfValues }); return res.render('user', { keys: UserModel.namesOfValues });
} }
@ -43,8 +43,8 @@ export default {
return res.redirect('/list'); return res.redirect('/list');
}, },
get: function (req: Request, res: Response) { get: async function (req: Request, res: Response) {
const usersFound = UserModel.getAll(); const usersFound = await UserModel.getAll();
return res.status(200).json(usersFound); return res.status(200).json(usersFound);
}, },
}; };

1
dev.ts
View File

@ -1,4 +1,5 @@
const build_cash = Bun.spawn(["bun", "build", "./frontend/cash/cash.tsx", "--outfile=public/assets/build/cash/cash.js", "--watch"]);
const build_list = Bun.spawn(["bun", "build", "./frontend/list/list.tsx", "--outfile=public/assets/build/list/list.js", "--watch"]); const build_list = Bun.spawn(["bun", "build", "./frontend/list/list.tsx", "--outfile=public/assets/build/list/list.js", "--watch"]);
const build_app = Bun.spawn(["bun", "--watch", "./app.ts"]); const build_app = Bun.spawn(["bun", "--watch", "./app.ts"]);

View File

@ -1,9 +1,9 @@
import { type NextFunction, type Request, type Response } from "express"; import { type NextFunction, type Request, type Response } from "express";
import userModel, { values } from 'models/userModel'; import userModel, { values } from 'models/userModel';
function checkAuthenticated(req: Request, res: Response, next: NextFunction) { async function checkAuthenticated(req: Request, res: Response, next: NextFunction) {
const pass = req.body.pass; const pass = req.body.pass;
const password = userModel.getValue(values.pass); const password = await userModel.getValue(values.pass);
if (pass && password) { if (pass && password) {
if (pass == password) { if (pass == password) {
return next(); return next();

View File

@ -1,65 +1,34 @@
import { Database } from "bun:sqlite"; import mysql, { type PoolOptions } from 'mysql2/promise'
const pool = new Database("mydb.sqlite", { strict: true }); const poolOptions: PoolOptions = {
host: "",
pool.exec(` port: 0,
CREATE TABLE IF NOT EXISTS series ( user: "",
id INTEGER PRIMARY KEY AUTOINCREMENT, password: "",
code INT NOT NULL, database: ""
title TEXT NOT NULL,
released TEXT NOT NULL,
webImg TEXT NOT NULL,
UNIQUE (code)
);
`);
pool.exec(`
CREATE TABLE IF NOT EXISTS movies (
id INTEGER PRIMARY KEY AUTOINCREMENT,
code INT NOT NULL,
title TEXT NOT NULL,
released TEXT NOT NULL,
webImg TEXT NOT NULL,
UNIQUE (code)
);
`);
pool.exec(`
CREATE TABLE IF NOT EXISTS games (
id INTEGER PRIMARY KEY AUTOINCREMENT,
code INT NOT NULL,
title TEXT NOT NULL,
released TEXT NOT NULL,
webImg TEXT NOT NULL,
UNIQUE (code)
);
`);
pool.exec(`
CREATE TABLE IF NOT EXISTS userData (
id INTEGER PRIMARY KEY AUTOINCREMENT,
name TEXT NOT NULL,
value TEXT NOT NULL
);
`);
function inset_keys() {
class co {
count!: number;
}
const result = pool.query("SELECT count(*) as count FROM userData;").as(co).get();
if(result && result.count >= 4){
return;
}
pool.exec(`
INSERT INTO userData (name, value) VALUES ("pass", "");
INSERT INTO userData (name, value) VALUES ("omdb_key", "");
INSERT INTO userData (name, value) VALUES ("twitch_client_id", "");
INSERT INTO userData (name, value) VALUES ("twitch_client_secret", "");
`);
} }
inset_keys(); if (process.env.DBIP) {
poolOptions.host = process.env.DBIP;
}
if (process.env.DBPort) {
poolOptions.port = parseInt(process.env.DBPort);
}
if (process.env.DBUser) {
poolOptions.user = process.env.DBUser;
}
if (process.env.DBPassword) {
poolOptions.password = process.env.DBPassword;
}
if (process.env.DBDatabase) {
poolOptions.database = process.env.DBDatabase;
}
const pool = mysql.createPool(poolOptions);
export default pool; export default pool;

View File

@ -1,12 +1,13 @@
import { type ResultSetHeader, type RowDataPacket, type QueryOptions } from "mysql2"
import pool from 'miscellaneous/db' import pool from 'miscellaneous/db'
export class Media { interface Media extends RowDataPacket {
id!: number; id?: number;
code!: number; code?: number;
title!: string; title?: string;
released!: string; released?: string;
webImg!: string; webImg?: string;
} }
export enum Table { export enum Table {
@ -15,12 +16,14 @@ export enum Table {
games = "games", games = "games",
} }
function save(table: Table, code: number, title: string, released: string, webImg: string): number { async function save(table: Table, code: number, title: string, released: string, webImg: string): Promise<number> {
try { try {
const sql = "INSERT INTO " + table + " (code, title, released, webImg) VALUES (?,?,?,?)"; const options: QueryOptions = {
sql: "INSERT INTO " + table + " (code, title, released, webImg) VALUES (?,?,?,?)",
const result = pool.query(sql).run(code, title, released, webImg); values: [code, title, released, webImg]
return result.changes; };
const [result, fields] = await pool.query<ResultSetHeader>(options);
return result.affectedRows;
} }
catch (err) { catch (err) {
console.log(err); console.log(err);
@ -28,11 +31,14 @@ function save(table: Table, code: number, title: string, released: string, webIm
return 0; return 0;
} }
function updateWebImg(table: Table, code: number, webImg: string): number { async function updateWebImg(table: Table, code: number, webImg: string): Promise<number> {
try { try {
const sql = "UPDATE " + table + " SET webImg = ? WHERE code = ?;"; const options: QueryOptions = {
const result = pool.query(sql).run(webImg, code); sql: "UPDATE " + table + "SET webImg = ? WHERE code = ?;",
return result.changes; values: [webImg, code]
};
const [result, fields] = await pool.query<ResultSetHeader>(options);
return result.affectedRows;
} }
catch (err) { catch (err) {
console.log(err); console.log(err);
@ -40,10 +46,10 @@ function updateWebImg(table: Table, code: number, webImg: string): number {
return 0; return 0;
} }
function findOneAndDelete(table: Table, code: number): number { async function findOneAndDelete(table: Table, code: number): Promise<number> {
try { try {
const result = pool.query("DELETE FROM " + table + " WHERE code = ?;").run(code); const [result, fields] = await pool.query<ResultSetHeader>("DELETE FROM " + table + " WHERE code = ?;", [code]);
return result.changes; return result.affectedRows;
} }
catch (err) { catch (err) {
console.log(err); console.log(err);
@ -51,9 +57,9 @@ function findOneAndDelete(table: Table, code: number): number {
return 0; return 0;
} }
function findOne(table: Table, code: number): Media[] { async function findOne(table: Table, code: number): Promise<Media[]> {
try { try {
const rows = pool.query("SELECT * FROM " + table + " WHERE code = ?;").as(Media).all(code); const [rows, fields] = await pool.query<Media[]>("SELECT * FROM " + table + " WHERE code = ?;", [code]);
return rows; return rows;
} }
catch (err) { catch (err) {
@ -62,9 +68,9 @@ function findOne(table: Table, code: number): Media[] {
return []; return [];
} }
function find(table: Table): Media[] { async function find(table: Table): Promise<Media[]> {
try { try {
const rows = pool.query("SELECT * FROM " + table + ";").as(Media).all(); const [rows, fields] = await pool.query<Media[]>("SELECT * FROM " + table + ";");
return rows; return rows;
} }
catch (err) { catch (err) {

View File

@ -1,6 +1,7 @@
import { type ResultSetHeader, type RowDataPacket } from "mysql2"
import pool from 'miscellaneous/db' import pool from 'miscellaneous/db'
class UserD { interface UserD extends RowDataPacket {
name?: string; name?: string;
value?: string; value?: string;
} }
@ -14,9 +15,9 @@ export enum values {
const namesOfValues: string[] = ["", "pass", "omdb_key", "twitch_client_id", "twitch_client_secret"]; const namesOfValues: string[] = ["", "pass", "omdb_key", "twitch_client_id", "twitch_client_secret"];
function getValue(name: values): string | undefined { async function getValue(name: values): Promise<string | undefined> {
try { try {
const rows = pool.query("SELECT name, value FROM userData where id = ?;").as(UserD).all(name); const [rows, fields] = await pool.query<UserD[]>("SELECT name, value FROM userData where id = ?;", [name]);
if (rows.length > 0) if (rows.length > 0)
return rows[0].value; return rows[0].value;
} }
@ -26,10 +27,10 @@ function getValue(name: values): string | undefined {
return; return;
} }
function updateValue(name: string, value: string): number { async function updateValue(name: string, value: string): Promise<number> {
try { try {
const result = pool.query("UPDATE userData SET value = ? WHERE name = ?").run(value, name); const [result, fields] = await pool.query<ResultSetHeader>("UPDATE userData SET value = ? WHERE name = ?", [value, name]);
return result.changes; return result.affectedRows;
} }
catch (err) { catch (err) {
console.log(err); console.log(err);
@ -37,9 +38,9 @@ function updateValue(name: string, value: string): number {
return 0; return 0;
} }
function getAll(): UserD[] { async function getAll(): Promise<UserD[]> {
try { try {
const rows = pool.query("SELECT name, value FROM userData;").as(UserD).all(); const [rows, fields] = await pool.query<UserD[]>("SELECT name, value FROM userData;");
return rows; return rows;
} }
catch (err) { catch (err) {

View File

@ -2,12 +2,19 @@
"name": "web", "name": "web",
"version": "0.0.0", "version": "0.0.0",
"private": true, "private": true,
"scripts": {
"start": "bun ./app.ts",
"build_app": "bun build ./app.ts --outfile=bundle.js --target=bun"
},
"dependencies": { "dependencies": {
"@types/express": "^4.17.21", "@types/express": "^4.17.21",
"@types/morgan": "^1.9.9", "@types/morgan": "^1.9.9",
"dotenv": "^16.4.5",
"express": "^4.18.2", "express": "^4.18.2",
"hbs": "^4.2.0", "hbs": "^4.2.0",
"morgan": "~1.9.1", "morgan": "~1.9.1",
"mysql2": "^3.10.3",
"chart.js": "^4.4.1",
"bun-types": "^1.0.23", "bun-types": "^1.0.23",
"typescript": "^5.3.3" "typescript": "^5.3.3"
} }

View File

@ -1,4 +1,4 @@
CREATE TABLE IF NOT EXISTS series ( CREATE TABLE series (
id INT NOT NULL AUTO_INCREMENT, id INT NOT NULL AUTO_INCREMENT,
code INT NOT NULL, code INT NOT NULL,
title TEXT NOT NULL, title TEXT NOT NULL,
@ -6,9 +6,9 @@ CREATE TABLE IF NOT EXISTS series (
webImg TEXT NOT NULL, webImg TEXT NOT NULL,
PRIMARY KEY (id), PRIMARY KEY (id),
UNIQUE code (code) UNIQUE code (code)
); ) ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS movies ( CREATE TABLE movies (
id INT NOT NULL AUTO_INCREMENT, id INT NOT NULL AUTO_INCREMENT,
code INT NOT NULL, code INT NOT NULL,
title TEXT NOT NULL, title TEXT NOT NULL,
@ -16,9 +16,9 @@ CREATE TABLE IF NOT EXISTS movies (
webImg TEXT NOT NULL, webImg TEXT NOT NULL,
PRIMARY KEY (id), PRIMARY KEY (id),
UNIQUE code (code) UNIQUE code (code)
); ) ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS games ( CREATE TABLE games (
id INT NOT NULL AUTO_INCREMENT, id INT NOT NULL AUTO_INCREMENT,
code INT NOT NULL, code INT NOT NULL,
title TEXT NOT NULL, title TEXT NOT NULL,
@ -26,14 +26,14 @@ CREATE TABLE IF NOT EXISTS games (
webImg TEXT NOT NULL, webImg TEXT NOT NULL,
PRIMARY KEY (id), PRIMARY KEY (id),
UNIQUE code (code) UNIQUE code (code)
); ) ENGINE = InnoDB;
CREATE TABLE IF NOT EXISTS userData ( CREATE TABLE userData (
id INT NOT NULL AUTO_INCREMENT, id INT NOT NULL AUTO_INCREMENT,
name TEXT NOT NULL, name TEXT NOT NULL,
value TEXT NOT NULL, value TEXT NOT NULL,
PRIMARY KEY (id), PRIMARY KEY (id),
); ) ENGINE = InnoDB;
INSERT INTO userData (name, value) VALUES ("pass", ""); INSERT INTO userData (name, value) VALUES ("pass", "");
@ -41,4 +41,19 @@ INSERT INTO userData (name, value) VALUES ("omdb_key", "");
INSERT INTO userData (name, value) VALUES ("twitch_client_id", ""); INSERT INTO userData (name, value) VALUES ("twitch_client_id", "");
INSERT INTO userData (name, value) VALUES ("twitch_client_secret", ""); INSERT INTO
userData (name, value) VALUES ("twitch_client_secret", "");
CREATE TABLE bankCardTransaction (
id INT NOT NULL AUTO_INCREMENT,
day INT NOT NULL,
month INT NOT NULL,
year INT NOT NULL,
amount INT NOT NULL,
type INT NOT NULL,
raw TEXT NOT NULL,
company TEXT NOT NULL,
PRIMARY KEY (id),
INDEX date(day, month, year),
INDEX type (type)
) ENGINE = InnoDB;

5
templ.env Normal file
View File

@ -0,0 +1,5 @@
DBIP=''
DBPort=
DBUser=''
DBPassword=''
DBDatabase=''