Nest.js 서버를 키고 요청을 날리다가 안되는 요청이 있어서 왜이러지? 하고 거의 1시간 반을 찾아봤다.
결국 이런 저런 삽질 끝에...
Controller의 url경로 때문이라는 것을 깨닫게 되었다.
자, Controller의 다음 두가지 함수가 있다.
@Controller('user')
export class UserController {
...
@Get(':id')
async getUser(@Param('id') id: number) {
return id;
}
@Get('list')
async getUserList() {
const userList = [user1, user2, ...]
return userList;
}
}
내가 아무리 /user/list 경로에 Get 요청을 보내도... getUserList함수가 타지지 않는다.
이 경우, nest.js는 위에서부터 함수를 읽기 때문에 list를 param으로 여기고, getUser함수를 먼저 타버리게 된다...
:id에 list가 들어가서 id = 'list'가 되어버리는 것이다.
그래서 id가 number인데 list는 string이라고 content-type이 application/json 이 아니라고 터미널에서 뭐라고 할 것이다 ㅎㅎ
다음은 swagger의 response에서 뜬 오류이다.
{
"statusCode": 400,
"message": "Value of the URL parameter \"id\" is not a number.",
"error": "Bad Request"
}
다음은 터미널에서 뜬 오류이다.
WARN [ExpressAdapter] Content-Type doesn't match Reply body,
you might need a custom ExceptionFilter for non-JSON responses
그러면 이제 해결 방법을 생각해보자.
- param의 위치에 따라 함수의 위치를 나눈다.
- Param이 경로의 첫번째에 들어가는 함수를 맨 아래로
- Param이 경로의 두번째에 들어가는 함수를 바로 그 위로
- Param이 경로의 세번째에 들어가는 함수를 또 그 위로
- param을 고려하여 다른 함수들의 url 경로를 정한다.
1번을 예로 들어서 함수의 순서를 정하자면 이렇게 되시겠다...
@Get('hi')
async e()
@Get('hi/bye')
async d()
@Get('hi/bye/:count')
async c()
@Get('hi/:room')
async b()
@Get(':id/:room')
async ab()
@Get(':id')
async a()
e()를 호출하려면 e가 a()보다 위에 있어야 한다.
d()를 호출하려면 d가 b()보다 위에 있어야 한다.
b()를 호출하려면 b가 ab()보다 위에 있어야 한다.
2번을 예로들면 아래와 같다.
@Get(':id')
async a()
@Get('list')
async b()
// 아래와 같이 안겹치게 바꾸자.
@Get(':id')
async a()
@Get('list/all')
async b()
1번은 너무 머리아플것 같은데,
2번은 보자마자 '아! 이거 param 때문에 경로 바꿔야지!' 라고 떠오를 것 같지가 않다.
여러분들이 하시는 방법 중에 좋은 방법이 있으면 공유해주셨으면 합니다...
포스팅 읽어주셔서 감사합니다!
'Back-end > nest.js' 카테고리의 다른 글
Nest.js : gRPC 통신 (+Python gRPC) (0) | 2023.07.25 |
---|---|
#1. Nestia : 네스티아를 배워보자 - 초기 설정 (0) | 2023.07.02 |
Nest.js : Prisma의 Date Return type 문제 (Prisma date to string) (0) | 2023.06.16 |
TypeORM : Postgresql 42703 에러 ( + as 사용시 소문자만 나오는 경우 해결법) (1) | 2023.03.11 |
Nest.js : Session을 이용한 Google OAuth 구현 (0) | 2023.03.05 |