부트스트랩
ASAPJS는 Application 클래스를 통해 Express.js HTTP 서버를 부트스트랩합니다. __dirname과 설정 객체로 인스턴스를 생성한 후 run()을 호출하세요. 이 클래스는 extensions 배열에 선언된 플러그인(RouterPlugin, SequelizePlugin, SocketPlugin)을 순서대로 초기화하고 단일 호출로 서버를 시작합니다.
Application
import { Application } from '@asapjs/core';생성자
new Application(dirname: string, config: AsapJSConfig)| 파라미터 | 타입 | 설명 |
|---|---|---|
dirname | string | 컴파일된 출력 디렉터리의 절대 경로. 엔트리 파일에서 __dirname을 전달합니다. 서브모듈이 컨트롤러, 모델, 소켓 핸들러를 자동으로 탐색하는 데 사용됩니다. |
config | AsapJSConfig | 애플리케이션 설정 객체. 전역으로 저장되며 getConfig()를 통해 조회할 수 있습니다. |
run()
application.run(
initBeforeStartServer?: () => void | Promise<void>,
options?: { disableListenServer: boolean }
): Promise<express.Application>모든 모듈을 순서대로 초기화한 후 HTTP 서버를 시작합니다. Express 애플리케이션 인스턴스를 반환합니다.
| 파라미터 | 타입 | 설명 |
|---|---|---|
initBeforeStartServer | () => void | 모듈이 초기화된 후, server.listen() 이전에 호출되는 선택적 콜백. 데이터베이스 마이그레이션, 시드 데이터 삽입, 기타 시작 로직을 실행하는 데 사용합니다. |
options.disableListenServer | boolean | true이면 HTTP 서버가 생성되지만 listen()은 호출되지 않습니다. 서버 라이프사이클을 직접 제어하는 테스트 환경에 유용합니다. |
run() 내부 초기화 순서:
RouterPlugin.init()—extensions에'@asapjs/router'가 있는 경우: Express 앱을 생성하고, 전역 미들웨어(CORS, bodyParser)를 적용하며,dirname/route.ts에서 컨트롤러를 로드하고, Swagger UI를 설정합니다.SequelizePlugin.init()—extensions에'@asapjs/sequelize'가 있는 경우: 데이터베이스에 연결하고, 모델과 DTO를 등록합니다.- Sentry 초기화 —
config.sentry가 설정된 경우. http.createServer(app)— HTTP 서버를 생성합니다.SocketPlugin.init()—extensions에'@asapjs/socket'이 있는 경우: HTTP 서버에 Socket.IO를 초기화합니다. (HTTP 서버 생성 이후에 초기화되므로 라우터/DB보다 나중에 실행됩니다.)initBeforeStartServer()콜백 — 사용자 정의 시작 로직.server.listen(config.port)—disableListenServer가 설정되지 않은 경우.
getApp()
application.getApp(): express.Application내부 Express 애플리케이션 인스턴스를 동기적으로 반환합니다. run() 호출 전에는 undefined입니다.
getServer()
application.getServer(): http.Serverrun() 중에 생성된 http.Server 인스턴스를 동기적으로 반환합니다. run() 호출 전에는 undefined입니다.
destroy()
await application.destroy(): Promise<void>등록된 플러그인을 역순으로 정리하고 HTTP 서버를 종료합니다. 테스트 환경에서 서버를 정상적으로 종료하거나 graceful shutdown을 구현할 때 사용합니다.
// 종료 시
process.on('SIGTERM', async () => {
await app.destroy();
process.exit(0);
});AsapJSConfig 인터페이스
new Application()의 두 번째 인수로 전달하는 전체 설정 객체입니다. @asapjs/types에서 정의됩니다.
import { AsapJSConfig } from '@asapjs/types';
interface AsapJSConfig {
port: number;
dirname: string;
extensions: string[];
basePath?: string;
name?: string;
middleware?: any[];
auth?: {
jwt_secret?: string;
jwt_access_token_secret?: string;
};
sentry?: {
dsn: string;
environment?: string;
};
swagger?: {
title?: string;
name?: string;
version?: string;
description?: string;
path?: string;
scheme?: 'http' | 'https';
host?: string;
auth_url?: string;
useAuth?: boolean;
userObject?: { [username: string]: string };
};
database?: {
host: string;
port: number;
username: string;
password: string;
database: string;
dialect: 'mysql' | 'postgres' | 'sqlite' | 'mariadb' | 'mssql';
logging?: boolean | ((sql: string) => void);
};
[key: string]: any;
}최상위 필드
| 필드 | 타입 | 필수 여부 | 설명 |
|---|---|---|---|
port | number | 필수 | HTTP 서버가 수신 대기할 TCP 포트. |
dirname | string | 자동 | 컴파일된 출력 디렉터리의 절대 경로. Application 생성자가 첫 번째 인수에서 자동으로 설정합니다. |
extensions | string[] | 필수 | 활성화할 ASAPJS 플러그인 목록. '@asapjs/router'는 라우팅을 사용하려면 반드시 포함해야 합니다. 지원 값: '@asapjs/router', '@asapjs/sequelize', '@asapjs/socket'. |
basePath | string | 선택 | 모든 API 라우트의 URL 접두사 (예: 'api'로 설정하면 라우트가 /api/...에서 사용 가능). 기본값은 ''. |
name | string | 선택 | 사람이 읽을 수 있는 애플리케이션 이름. Swagger UI와 로그 출력에 표시됩니다. |
middleware | any[] | 선택 | 전역 Express 미들웨어 배열. CORS, bodyParser 이후에 적용됩니다. |
auth | object | 선택 | JWT 인증 설정. 어떤 라우트에서든 auth: true를 사용하는 경우 필요합니다. 아래를 참고하세요. |
sentry | object | 선택 | Sentry 에러 추적 설정. 아래를 참고하세요. |
swagger | object | 선택 | Swagger UI 설정. 생성된 API 문서를 원하는 경우 필요합니다. 아래를 참고하세요. |
database | object | 선택 | Sequelize 데이터베이스 설정. extensions에 '@asapjs/sequelize'가 있을 때 필요합니다. 아래를 참고하세요. |
[key: string] | any | 선택 | 임의의 애플리케이션별 데이터. getConfig()를 통해 조회할 수 있습니다. |
auth 필드
| 필드 | 타입 | 필수 여부 | 설명 |
|---|---|---|---|
auth.jwt_access_token_secret | string | 필수 | jwtVerification 미들웨어가 JWT 토큰을 검증하는 데 사용하는 시크릿 키. 프로덕션 환경에서는 반드시 환경 변수로 주입하세요. |
auth.jwt_secret | string | 선택 | 레거시 호환용 시크릿 키. 새 프로젝트에서는 jwt_access_token_secret을 사용하세요. |
sentry 필드
| 필드 | 타입 | 필수 여부 | 설명 |
|---|---|---|---|
sentry.dsn | string | 필수 | Sentry DSN(Data Source Name). |
sentry.environment | string | 선택 | Sentry 환경 식별자 (예: 'production'). 기본값은 'development'. |
swagger 필드
| 필드 | 타입 | 필수 여부 | 설명 |
|---|---|---|---|
swagger.name | string | 선택 | Swagger UI 상단에 표시되는 제목. |
swagger.version | string | 선택 | Swagger UI에 표시되는 API 버전 문자열 (예: '1.0.0'). |
swagger.description | string | 선택 | Swagger UI에 표시되는 설명 문단. |
swagger.scheme | 'http' | 'https' | 선택 | Swagger “Try it out” 요청에 사용되는 URL 스킴. |
swagger.host | string | 선택 | Swagger “Try it out” 요청에 사용되는 호스트명(및 선택적 포트) (예: 'localhost:3000'). |
swagger.auth_url | string | 선택 | Swagger OAuth2 플로우를 사용하는 경우의 OAuth2 인증 URL. |
swagger.useAuth | boolean | 선택 | true이면 Swagger UI에 Basic 인증을 적용합니다. userObject와 함께 사용합니다. |
swagger.userObject | { [username: string]: string } | 선택 | Swagger UI 접근 제어를 위한 Basic 인증 자격증명 맵. useAuth: true일 때 필요합니다. |
database 필드
| 필드 | 타입 | 필수 여부 | 설명 |
|---|---|---|---|
database.database | string | 필수 | 연결할 데이터베이스 이름. |
database.username | string | 필수 | 데이터베이스 사용자. |
database.password | string | 필수 | 데이터베이스 비밀번호. |
database.host | string | 필수 | 데이터베이스 호스트 주소. |
database.port | number | 필수 | 데이터베이스 포트 (예: MySQL은 3306, PostgreSQL은 5432). |
database.dialect | string | 필수 | Sequelize 다이얼렉트 식별자: 'mysql', 'postgres', 'sqlite', 'mariadb', 'mssql'. |
database.logging | boolean | ((sql: string) => void) | 선택 | SQL 쿼리 로깅. false로 비활성화하거나 커스텀 함수를 전달합니다. |
getConfig()
import { getConfig } from '@asapjs/common';
const config = getConfig(); // AsapJSConfig 반환Application 생성자가 설정한 전역 설정 객체를 반환합니다. Application이 인스턴스화되기 전에 호출하면 Error('Config not initialized. Call setConfig() first.')를 던집니다. 함수 파라미터를 통해 설정 객체를 전달하지 않고도 애플리케이션 어디서나 설정 값에 접근할 수 있습니다.
RouterPlugin
RouterPlugin은 extensions에 '@asapjs/router'가 포함된 경우 Application.run()에 의해 자동으로 초기화됩니다. 다음 설정을 수행합니다:
- 전역 미들웨어(CORS, bodyParser)를 Express 앱에 적용합니다.
config.middleware에 등록된 사용자 정의 미들웨어를 적용합니다.dirname/route.ts를 로드하고 내보낸 모든 컨트롤러를/<basePath>아래에 마운트합니다./<basePath>/docs/swagger-ui.html에 Swagger UI를 등록합니다./health-check엔드포인트를 등록합니다.- 전역 에러 핸들러를 미들웨어 체인 마지막에 등록합니다.
Application을 사용할 때는 RouterPlugin을 직접 인스턴스화할 필요가 없습니다. extensions 배열에 '@asapjs/router'를 포함하면 자동으로 활성화됩니다.
참고:
RouterModule은 레거시 호환을 위해@asapjs/router에서 여전히 export되지만, 새 프로젝트에서는 플러그인 시스템(RouterPlugin)이 자동으로 사용됩니다.
전체 예제
다음은 ASAPJS 참조 구현을 기반으로 한 동작하는 엔트리 포인트입니다.
// src/index.ts
import { Application } from '@asapjs/core';
require('dotenv').config({ path: `${__dirname}/../.env` });
const debug = process.env.NODE_ENV === 'development';
const port = parseInt(process.env.PORT || '3000', 10);
const config = {
name: 'ASAPJS Example',
port,
basePath: 'api',
extensions: ['@asapjs/router', '@asapjs/sequelize'],
auth: {
jwt_access_token_secret: process.env.JWT_SECRET || 'change-me-in-production',
},
swagger: {
name: 'ASAPJS Example API',
version: '1.0.0',
description: 'Reference implementation for the ASAPJS framework.',
scheme: (debug ? 'http' : 'https') as 'http' | 'https',
host: debug ? `localhost:${port}` : 'api.example.com',
},
db: {
database: process.env.DB_NAME || 'asapjs_example',
username: process.env.DB_USER || 'root',
password: process.env.DB_PASSWORD || '',
host: process.env.DB_HOST || 'localhost',
port: parseInt(process.env.DB_PORT || '3306', 10),
dialect: 'mysql',
logging: debug
? (query: string) => console.debug(query)
: false,
},
};
new Application(__dirname, config).run();중요:
extensions배열에'@asapjs/router'를 반드시 포함해야 합니다. 누락하면 라우팅, Swagger UI, 전역 미들웨어가 활성화되지 않습니다.
Socket.IO도 활성화하려면 extensions 배열에 '@asapjs/socket'을 추가합니다:
extensions: ['@asapjs/router', '@asapjs/sequelize', '@asapjs/socket'],관련 항목
- 데이터베이스 —
initSequelizeModule,Repository,modelsSync,healthCheck - 실시간 (Socket.IO) —
createSocket,socketSendTo,socketSendAll - 라우팅 —
RouterController, HTTP 데코레이터 - 로깅 — 프레임워크 전반에서 사용되는 구조화 로거