내가 하는 프로젝트등 작은 프로젝트의 경우에는 보통 package.json을 보면 명령어가 지정되어있습니다.
그래서 package.json에서 start 명령어를 찾으면 힌트를 얻을 수 있지 않을까? 생각하였습니다.
그런데 실제로 package.json을 확인해 보았더니.
start
명령어는 찾아 볼 수 없었습니다 🥲
package json ⇒ https://github.com/vercel/next.js/blob/canary/package.json
그래서 next 프로젝트에서 코드를 둘러보는 중
관련있어 보이는 pakages와 scripts 폴더를 발견하였습니다.
packages 폴더를 타고 연관되어 보이는 폴더들을 거쳐 cli 폴더까지 접근을 해보니
next-start.ts
파일을 발견할 수 있었습니다. 😀
yarn start
와 같은 스크립트를 우리는 CLI라고 부릅니다.
CLI란?
명령줄 인터페이스, Command-Line Interface의 줄임말로
글자를 입력하여 컴퓨터에 명령을 내리는 방식이다.
그래서 Next.js 프로젝트에서 yarn start
를 실행했을 때 실행되는 코드를 찾으려면,
cli도 염두에 두고 찾아보면 되지 않을까 생각하였고, 예측이 맞았습니다!
yarn start == npm run start == next start (이 세개는 같은 의미입니다!)
next.js/packages/next/src/cli/next-start.ts
전체 코드 링크 : https://github.com/vercel/next.js/blob/canary/packages/next/src/cli/next-start.ts
const validArgs: arg.Spec = {
// Types
'--help': Boolean,
'--port': Number,
'--hostname': String,
'--keepAliveTimeout': Number,
// Aliases
'-h': '--help',
'-p': '--port',
'-H': '--hostname',
}
뒤에 붙을 수 있는 옵션들을 정의해두고,
let args: arg.Result<arg.Spec>
try {
args = arg(validArgs, { argv })
} catch (error) {
if (isError(error) && error.code === 'ARG_UNKNOWN_OPTION') {
return printAndExit(error.message, 1)
}
throw error
}
입력받은 명령어가 valid에 맞는지 확인합니다.
만약 valid에 실패하면, catch문을 통해 에러를 띄우고 실행을 종료합니다.
if (args['--help']) {
...
process.exit(0)
}
만약 명령어에 '--help'
가 포함되어 있었다면 help 메시지를 띄우고, 실행을 종료합니다.
const keepAliveTimeoutArg: number | undefined = args['--keepAliveTimeout']
if (
typeof keepAliveTimeoutArg !== 'undefined' &&
(Number.isNaN(keepAliveTimeoutArg) ||
!Number.isFinite(keepAliveTimeoutArg) ||
keepAliveTimeoutArg < 0)
) {
printAndExit(
`Invalid --keepAliveTimeout, expected a non negative number but received "${keepAliveTimeoutArg}"`,
1
)
}
먼저 —keepAliveTimeout
옵션 값이 제대로 들어왔는지, 무결성을 체크합니다.
만약 올바르지 않은 값이라면 실행을 종료합니다.
const keepAliveTimeout = keepAliveTimeoutArg
? Math.ceil(keepAliveTimeoutArg)
: undefined
--keepAliveTimeout
명령어를 통해 서버로 부터 연결을 끊는 시간을 조정할 수 있도록 합니다.
--keepAliveTimeout
이 필요한 이유가 뭘까요?웹 서버는 일정 시간동안 클라이언트로부터 요청이 없으면, 서버에서 자동으로 연결을 끊어버립니다.
일정 시간의 기본값은 10s인데, 이를 조정하고 싶을 때 --keepAliveTimeout
옵션을 사용합니다.
만약, 시간을 너무 길게 설정하면 이미 사용하고 있지 않은, 쓸데없는 연결까지 계속 연결되어있어 메모리 사용량이 증가하고, 많은 요청에 대해 병목현상이 발생할 수 있습니다.
반대로, 시간을 너무 짧게 설정한다면 지속되는 요청에 대해 연결 요청이 수없이 반복될 수 있기 때문에 로딩 및 네트워크 오류가 발생할 확률이 높아집니다.
그러므로 중간점인 10s로 기본값이 세팅되어 있습니다.
const config = await loadConfig(
PHASE_PRODUCTION_SERVER,
resolve(dir || '.'),
undefined,
undefined,
true
)
await startServer({
dir,
isDev: false,
hostname: host,
port,
keepAliveTimeout,
useWorkers: !!config.experimental.appDir,
})
위에서 불러온 변수들을 이용해, server의 config 설정을 세팅합니다.
이를 startServer를 실행할 때에 변수로 넘겨 원하는 세팅 값으로 서버를 실행합니다.
export { nextStart }
위의 과정을 실행하는 nextStart
메소드를 파일에서 내보냄으로써,
다른 파일에서 사용할 수 있도록 합니다.