아파치 톰캣에서 아파치는 서버의 역할을 한다. 서버는 자원을 들고 있어야 하므로 공유할 자원들을 모은 타겟 폴더가 필요하고, Spring 프로젝트에는 Webapp이라는 하드디스크 폴더가 있다. 여기에 파일(자원을) 놔두면 된다.
클라이언트와 서버가 외부에서 접근하려면 Stream 연결이 필요하다.Stream이 연결되려면 소켓이 필요한데, 아파치가 소켓연결을 자동으로 연결시켜준다.
클라이언트가 서버와 연결되기 위해서는 (여기서는 기본적인 url 요청 방식을 가정한다.)
1) ip 주소
2) 포트 번호
3) 파일명이 필요하다.
기본적으로 아파치와 톰캣과 연결되는 포트번호는 8080이다.
아파치 톰캣에는 설정 파일이 있는데 세 가지 중요한 설정 파일이 있다. (아파치가 설치될 때 같이 설치되는 파일)
각 파일의 대표적인 역할은 이러하다.
server.xml : 포트설정 가능(8080) - (아파치가 들고있음)
context.xml : DB연결 설정 - (톰켓이 들고있음)
web.xml : 필터 역할 ex)중국 IP 차단
카타리나 : 타겟 폴더 설정 (그러나 스프링에서는 자동으로 타겟폴더 설정해줘서 건드릴 일이 별로 없다.)
Spring에서는 설정 변수 파일이 하는 역할을 application.properties에서 모두 설정이 가능하다.
서버는 많은 클라이언트들이 동시에 접속해야 한다. 동시에 처리를 해야하므로 아파치(서버)는 스레드를 기반으로 실행되고 있다.
🤔 이 스레드는 단일 스레드로 되어있다. 왜일까?
💻 웹의 프로토콜은 요청이 오는 걸 기다렸다가 요청이 오면 응답하는 '동기적' 요청이기 때문이다.
요청을 하지 않았는데도 응답을 해야 하면 스레드가 두 개가 필요하나, 웹은 요청이 올 때에만 답을 하면 되어서 단일 스레드이다.
👉 그래서 BufferedReader와 BufferedWriter는 하나의 스레드로 묶여 있다.
파일을 url방식으로 요청하면(ip주소/8080/파일명.확장자) 파일 내의 데이터가 전송된다.
✍️ 통신은 ByteStream이기 때문이다. 즉, 파일을 읽어서 파일 안에 있는 내용을 Stream에 넣어서 응답하는 것이다.
request를 BufferedReader로 읽고 나서 BufferedWriter로 response하는데
response에는
가 있다.
.txt 파일이나 .html 파일은 웹 브라우저가 읽을 수 있으나, .java 파일의 경우 브라우저가 해석하지 못한다. 브라우저는 정적파일만 해석하기 때문이다.
브라우저가 해석하지 못하는 파일 중 java, jsp 파일 등을 읽게 컨버팅 해주는 프로그램이 '톰캣'이다. (아파치는 서버고, 톰캣은 서버가 아니다.)
아파치가 request받은 파일이 이해할 수 없는 파일임을 알아채고, 그 파일이 java프로그램이면 톰캣에게로 넘긴다.
톰캣은 java파일을 class파일로 compile하고 실행한다. 그러면 java파일은 이제 Data가 된다.
최종적으로 톰캣은 PrintWrite로 Stream에다 결과값(Data)를 response한다.
Data는 이제 java파일이 아닌 그저 Data이므로(Data 자체가 넘겨지는 것이므로) header에는 원복할 정보가 없고, Data라고 적혀있다.
톰켓은 소켓에 있는 정보를 알아서 parsing해서 class화 해준다.
이 때, httpServlet의 request-response와
톰캣이 하는 request-response는 다르다.