ii-agent-dogovory-arendy-ots/server.js

98 lines
3.9 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

const http = require('http');
const fs = require('fs');
const path = require('path');
const PORT = process.env.PORT || 3000;
const DATA_FILE = path.join(__dirname, 'data.json');
function readData() {
try { return JSON.parse(fs.readFileSync(DATA_FILE, 'utf8')); }
catch (_) { return []; }
}
function writeData(arr) { fs.writeFileSync(DATA_FILE, JSON.stringify(arr, null, 2)); }
// Mock functions replace with real integrations later
function extractRequest(reqBody) {
// Expect fields: initiator, object, area, termMonths, price (optional)
return reqBody;
}
function getTariffFromSAP(object) {
// Mock: return 4800 per m2
return 4800;
}
function generateContract(data) {
const { initiator, object, area, termMonths, price } = data;
const total = area * price * termMonths;
return `Договор аренды\nСтороны: ${initiator} и ОЦО ЮС\nОбъект: ${object}\nПлощадь: ${area} м²\nСрок: ${termMonths} мес.\nТариф: ${price} ₸/м²\nСумма: ${total}`;
}
function checkCompliance(contract, tariff) {
const flags = [];
// Simple rule: price must not be lower than tariff
const priceMatch = contract.match(/Тариф: (\d+) /);
if (priceMatch && Number(priceMatch[1]) < tariff) {
flags.push({ type: 'tariff', message: `Тариф ниже актуального (${priceMatch[1]} < ${tariff})` });
}
// Add more checks later
return flags;
}
function compareWithCounterparty(version) {
// Mock: assume two deviations
return [{ clause: 'Пункт 3', diff: 'Изменена площадь' }, { clause: 'Пункт 7', diff: 'Срок аренды 12 мес → 24 мес' }];
}
const server = http.createServer(async (req, res) => {
const url = req.url.split('?')[0];
// API: create contract from Lotus request (mocked POST /api/contract)
if (req.method === 'POST' && url === '/api/contract') {
let body = '';
req.on('data', chunk => body += chunk);
req.on('end', () => {
try {
const json = JSON.parse(body);
const requestData = extractRequest(json);
// validate required fields
const missing = [];
['initiator','object','area','termMonths'].forEach(f => { if (!requestData[f]) missing.push(f); });
if (missing.length) {
res.writeHead(400, {'Content-Type':'application/json'});
return res.end(JSON.stringify({error:'Missing fields', missing}));
}
// price from request or tariff
const tariff = getTariffFromSAP(requestData.object);
const price = requestData.price || tariff;
const contract = generateContract({ ...requestData, price });
const flags = checkCompliance(contract, tariff);
const deviations = requestData.counterpartyVersion ? compareWithCounterparty(requestData.counterpartyVersion) : [];
const record = { id: Date.now(), request: requestData, contract, tariff, price, flags, deviations };
const data = readData();
data.push(record);
writeData(data);
res.writeHead(200, {'Content-Type':'application/json'});
res.end(JSON.stringify({ok:true, record}));
} catch (e) {
res.writeHead(500, {'Content-Type':'application/json'});
res.end(JSON.stringify({error:e.message}));
}
});
return;
}
// Serve static files
let filePath = url === '/' ? '/index.html' : url;
const fullPath = path.join(__dirname, filePath);
if (fs.existsSync(fullPath) && fs.statSync(fullPath).isFile()) {
const ext = path.extname(fullPath);
const mime = {
'.html':'text/html',
'.css':'text/css',
'.js':'application/javascript',
'.json':'application/json'
}[ext] || 'application/octet-stream';
res.writeHead(200, {'Content-Type': mime + '; charset=utf-8'});
res.end(fs.readFileSync(fullPath));
return;
}
res.writeHead(404); res.end('Not found');
});
server.listen(PORT, () => console.log('Server listening on port ' + PORT));