Express ilovani ishga tushirish (deploy)
Ilovangiz localhost:3000 da ishlaydi va uni faqat siz ko’rasiz.
Terminalni yopsangiz server o’chadi, kompyuteringizni uxlatib qo’ysangiz
ham. Haqiqiy foydalanuvchiga ko’rsatish uchun ilova boshqa mashinada,
uzluksiz ishlashi kerak.
Bu darsda localhost bilan server o’rtasidagi farqni qamraymiz.
Jarayonning tashkiliy tomoni
deploy va operatsiyalar darsida
yoritilgan.
NODE_ENV nima o’zgartiradi
const express = require("express");
const app = express();
app.get("/ip", (request, response) => {
response.json({
ip: request.ip,
protocol: request.protocol,
secure: request.secure,
env: app.get("env"),
});
});
app.listen(3000);
O’zgaruvchisiz:
curl http://localhost:3000/ip
{"ip":"::1","protocol":"http","secure":false,"env":"development"}
NODE_ENV berilganda:
NODE_ENV=production node server.js
{"ip":"::1","protocol":"http","secure":false,"env":"production"}
production rejimida Express uch narsani o’zgartiradi: shablonlarni
keshlaydi, xato sahifasida stack ko’rsatmaydi va ba’zi tekshiruvlarni
tashlab ketadi. Natijada ilova tezroq va kamroq ma’lumot oshkor
qiladi.
Sizning kodingiz ham shu o’zgaruvchiga tayanadi — xavfsizlik darsida ko’rilgan cookie sozlamasi bunga misol:
cookie: {
httpOnly: true,
secure: process.env.NODE_ENV === "production",
sameSite: "lax",
}
Portni qattiq yozmang
Xosting muhitlarining ko’pchiligi portni o’zi tanlaydi va uni muhit o’zgaruvchisida beradi:
const app = require("./app");
const PORT = process.env.PORT || 3000;
app.listen(PORT, () => {
console.log(`Server ishga tushdi: ${PORT}-portda`);
});
app.listen(3000) deb qattiq yozilsa, server xosting kutgan portni
tinglamaydi va sayt ochilmaydi. Xato xabari esa chalg’ituvchi bo’ladi:
“ilova javob bermadi”.
Ilovani doimiy ishlatish
node server.js deb qo’ysangiz, SSH ulanishini uzganingizda jarayon
o’ladi. Xato yuz berib ilova yiqilsa, uni hech kim qayta ko’tarmaydi.
Yechim — jarayon menejeri. PM2 ni o’rnatish va asosiy buyruqlari cluster va PM2 darsida batafsil ko’rilgan; bu yerda Express ilovasiga tegishli qismini yig’amiz.
pm2 start server.js --name task-app
pm2 status
┌────┬──────────┬─────────┬─────────┬──────────┬────────┐
│ id │ name │ mode │ status │ cpu │ memory │
├────┼──────────┼─────────┼─────────┼──────────┼────────┤
│ 0 │ task-app │ fork │ online │ 0% │ 52.1mb │
└────┴──────────┴─────────┴─────────┴──────────┴────────┘
Sozlamalarni faylga chiqarish qulayroq. ecosystem.config.js:
module.exports = {
apps: [
{
name: "task-app",
script: "./server.js",
instances: 1,
env: {
NODE_ENV: "production",
PORT: 3000,
},
},
],
};
pm2 start ecosystem.config.js
pm2 save
pm2 save hozirgi ro’yxatni eslab qoladi — server qayta yuklanganda
ilova o’zi ko’tariladi.
Reverse proxy
Nega to’g’ridan-to’g’ri Express tinglamaydi:
| Vazifa | Kim bajaradi |
|---|---|
| HTTPS sertifikati | Nginx |
| Statik fayllarni berish | Nginx (tezroq) |
| Bir nechta sayt bitta serverda | Nginx |
| Ilova mantig’i | Express |
Nginx sozlamasi:
server {
listen 80;
server_name example.com;
location / {
proxy_pass http://localhost:3000;
proxy_http_version 1.1;
# Ilovaga haqiqiy mijoz ma'lumotini uzatamiz
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
Oxirgi uch qator muhim: ularsiz Express hamma so’rovni Nginx’dan kelgan deb biladi va haqiqiy mijoz IP’sini ko’rmaydi.
trust proxy
Nginx sarlavhalarni yubordi, lekin Express ularga standart holatda ishonmaydi. Buni ataylab yoqish kerak:
app.set("trust proxy", 1);
Farqni ko’rish uchun sarlavhalarni qo’lda yuboring. trust proxy
yoqilmagan holatda:
curl -H "X-Forwarded-For: 203.0.113.9" -H "X-Forwarded-Proto: https" http://localhost:3000/ip
{"ip":"::1","protocol":"http","secure":false,"env":"development"}
Yoqilgandan keyin:
{"ip":"203.0.113.9","protocol":"https","secure":true,"env":"development"}
request.ip haqiqiy mijoz manzilini ko’rsatdi, request.secure esa
true bo’ldi.
HTTPS
Sertifikatni Express emas, Nginx boshqaradi. Let’s Encrypt bepul sertifikat beradi:
sudo certbot --nginx -d example.com
Buyruq sertifikat oladi, Nginx sozlamasini o’zi yangilaydi va avtomatik yangilanishni sozlaydi. Sertifikat 90 kun amal qiladi.
Express tomonda bitta qo’shimcha kerak bo’lishi mumkin — http so’rovni
https ga yo’naltirish:
app.use((request, response, next) => {
if (process.env.NODE_ENV === "production" && !request.secure) {
return response.redirect(`https://${request.get("host")}${request.originalUrl}`);
}
next();
});
Bu middleware trust proxy ga tayanadi: usiz request.secure hech
qachon true bo’lmaydi va sahifa cheksiz yo’naltirish siklida qoladi.
HTTPS nima uchun kerakligi
HTTPS va web xavfsizligi darsida
tushuntirilgan.
Sog’liq tekshiruvi
Deploy vositalari va monitoring xizmatlari ilova tirikligini so’rab turadi. Buning uchun yengil marshrut qoldiriladi:
app.get("/health", (request, response) => {
response.json({ status: "ok", uptime: Math.round(process.uptime()) });
});
curl http://localhost:3000/health
{"status":"ok","uptime":42}
Marshrut ataylab sodda: bazaga bormaydi, fayl o’qimaydi. Vazifasi — “Node jarayoni javob beryaptimi?” degan savolga tez javob berish.
Deploy ketma-ketligi
Serverda bajariladigan qadamlar tartibi muhim:
git pull
npm ci --omit=dev
npm run migrate
pm2 reload task-app
- Yangi kodni olish;
- Paketlarni o’rnatish —
npm cipackage-lock.jsonga aniq amal qiladi; - Migratsiyalarni bajarish — baza tuzilishini yangilash;
- Ilovani qayta yuklash.
Tartibni buzmang: migratsiya ilovadan oldin bajariladi, aks holda yangi kod hali mavjud bo’lmagan ustunni so’raydi va xato beradi.
pm2 reload (restart emas) ilovani navbat bilan qayta ko’taradi —
so’rovlar uzilmaydi.
Log va monitoring
console.log PM2 jurnaliga tushadi:
pm2 logs task-app --lines 50
So’rovlarni yozib borish uchun morgan ulanadi:
npm install morgan
const morgan = require("morgan");
// Serverda qisqaroq format
app.use(morgan(process.env.NODE_ENV === "production" ? "combined" : "dev"));
::1 - - [12/Sep/2026:14:30:11 +0000] "GET /api/tasks HTTP/1.1" 200 81
Deploy oldidan ro’yxat
| Tekshiruv | Nega |
|---|---|
NODE_ENV=production qo’yilganmi |
Kesh va xato xulqi |
Sirlar .env da, kodda emasmi |
Kalit sizib ketmasligi |
.env, *.db, uploads/ .gitignore dami |
Keraksiz fayl repozitoriyda qolmasin |
Port process.env.PORT dan olinadimi |
Xosting o’z portini beradi |
app.set("trust proxy", 1) bormi |
IP va secure cookie |
| Migratsiyalar bajarilganmi | Yangi kod eski bazada ishlamaydi |
npm test o’tadimi |
Buzilgan kod serverga chiqmasin |
| Zaxira nusxa sozlanganmi | Baza yo’qolmasin |
Oxirgi band ko’pincha “keyinroq” deb qoldiriladi va aynan shu holatda kerak bo’ladi.
Amaliy mashq
task-app loyihasida davom eting:
app.listen(3000)niprocess.env.PORT || 3000ga o’zgartirib, boshqa port bilan ishga tushiring;NODE_ENV=productionbilan yurgizib,app.get("env")qiymati o’zgarishini tasdiqlang;app.set("trust proxy", 1)ni qo’shib,X-Forwarded-Forsarlavhalicurlso’rovidarequest.ipo’zgarishini ko’ring;/healthmarshrutini yozib, javobdauptimeo’sishini kuzating;ecosystem.config.jsyozib, PM2 bilan ishga tushiring vapm2 statusdaonlineholatini ko’ring;- Deploy ketma-ketligini bitta
deploy.shfayliga yozing — migratsiyapm2 reloaddan oldin turishiga e’tibor bering.
3-qadam eng ko’p vaqt yo’qotadigan muammoni oldindan ko’rsatadi:
trust proxy siz IP, secure cookie va rate limiting jimgina
noto’g’ri ishlaydi.
Qisqacha xulosa
NODE_ENV=productionExpress’ning keshlash va xato ko’rsatish xulqini o’zgartiradi.- Port
process.env.PORTdan olinadi, kodga qattiq yozilmaydi. - PM2 ilovani yiqilganda tiklaydi va server qayta yuklanganda ko’taradi;
sessiya xotirada bo’lsa
instances: 1qoldiriladi. - Nginx reverse proxy HTTPS, statik fayl va bir nechta saytni o’ziga oladi, Express esa faqat ilova mantig’ini.
app.set("trust proxy", 1)sizrequest.ipvarequest.securenoto’g’ri qiymat beradi.- Deploy tartibi: kod → paketlar → migratsiya → qayta yuklash;
seedserverda bajarilmaydi. /healthmarshruti yengil bo’lsin — baza tekshiruvi alohida manzilda.
Keyingi darsda yakuniy loyiha — o’n ikki darsdagi hamma narsani bitta ilovaga yig’amiz.