위도우에서는 process.env 설정 불가
cross-env 패키지로 운영체제 상관 없이 환경변수 설정 가능
//package.json
{
...
"sciprt": {
"start": "cross-env NODE_ENV=produevtion PORT=80 node server",
},
XXS 공격 방어
const sanitizeHTML = require('sanitize-html');
const html = "<script>location.href = 'https://google.com`</script>";
console.log(sanitizeHtml(html)); // ''
사용자가 업로드한 HTML을 sanitize-html 함수로 감싸면 허용되지 않는 태그, 스크립트는 제거됨.(두 번째 인수로 옵션 넣을 수 있음.)
CSRF 공격 방어
form 렌더링 시 CSRF토큰을 제공.
req.csrfToken()으로 가져올 수 있고,
form 제출 시 토큰도 함께 제출해야 함.
app.get('/form, csrfProtection, (req, res) => {
res.render('csrf', { csrfToken: req.csrfToken() });
});
app.post('/form', csrfProtection, (req, res) => {
res.send('ok');
});
csrfProtection 미들웨어가 전송된 토큰이 유효한지 확인함.
개발할 때 nodemon의 역할
서버가 에러로 꺼지면 다시 서버를 켜 주는 역할
또한 멀티 프로세싱을 지원해서, 노드 프로세스를 한 개 이상으로 늘릴 수 있음.
//packge.json
"start": "cross-env NODE_ENV=production PORT=80 pm2 start server.js"
pm2는 노드를 백그라운드로 돌린다.
// 백그라운드에서 노드 프로세스 확인
npx pm2 list
// 로그 확인
npx pm2 logs
// 에러 로그만 확인
npx pm2 logs --err
// 프로세스 종료
npm pm2 kill
// 서버 재시작
npx pm2 reload all
"start": "cross-env NODE_ENV=production PORT=80 pm2 start server.js -i 0",
i가 프로세스 개수
0은 현재 cpu 개수만큼 생성
-1은 현재 코더 개수보다 한 개 덜 생성
// 클러스터링 모니터
npx pm2 monit
console.log와 console.error 대체 모듈
로그를 파일이나 DB에 저장하는 용도
// logger.js
const { createLogger, format, transports } = require('winston');
const logger = createLogger({
level: 'info',
format: format.json(),
transports: [
new transports.File({ filename: 'combined.log' }),
new transports.File({ filename: 'error.log', level: 'error' }),
],
});
if (process.env.NODE_ENV !== 'production') {
logger.add(new transports.Console({ format: format.simple() }));
}
module.exports = logger;
// 사용 예시
app.use((req, res, next) => {
const error = new Error('라우터가 없습니다.');
error.status = 404;
logger.info('hello');
logger.error(error.message);
next(error);
winston-daily-rotate-file 패키지도 참고하기
서버 취약점 보완
익스프레스 미들웨어로 사용
app.user(
helmet({
contentSecurityPolicy: false,
crossOriginEmbedderPolicy: false,
crossOriginResourcePolicy: false,
}),
);
세션은 메모리에 저장하기 않고 레디스에 저장함.
이 패키지로 레디스를 쉽게 사용 가능
const hpp = requir('hpp');
const redis = require('redis');
const RedisStore = require('connect-redis')(session);
dotenv.config();
const redisClient = redis.createClient({
url: 'redis://',
pasword: process.env.REDIS_PASSWORD,
legacyMode: true,
});
redisClient.connectr().catch(console.error);
const pageRouter = require('./routes/page');
const sessionOption = {
resave: false,
saveUninitialized: false,
secret: process.env.COOKIE_SECRET,
cookie: {
httpOnly: true,
secure: false,
},
store: new RedisStore({ client: redisClient }),
};
express-rate-limit 메모리 사용량도 레디스에 기록하는 것이 좋음