SpringBoot 응용 프로그램 시작 내 장 된 Tomcat 프로 세 스 소스 분석
6244 단어 SpringBoot내장Tomcat시동 을 걸다
커 넥 터 는 Tomcat 에서 제공 하 는 클래스 입 니 다.
// Connector
@Override
protected void startInternal() throws LifecycleException {
// Validate settings before starting
if (getPortWithOffset() < 0) {
throw new LifecycleException(sm.getString(
"coyoteConnector.invalidPort", Integer.valueOf(getPortWithOffset())));
}
setState(LifecycleState.STARTING);
try {
//
protocolHandler.start();
} catch (Exception e) {
throw new LifecycleException(
sm.getString("coyoteConnector.protocolHandlerStartFailed"), e);
}
}
springboot 은 기본적으로 8080 포트 에서 HTTP 서 비 스 를 제공 하기 때문에 HTTP 프로 토 콜 요청 을 처리 하 는 Http11NioProtocol 인 스 턴 스 입 니 다.NIO 방식 으로 HTTP 프로 토 콜 을 처리 합 니 다.Connector 가 HTTP 요청 에 대한 수신 과 처 리 는 직접 완 료 된 것 이 아니 라 이 Http11NioProtocol protocol Handler 에 의뢰 한 것 입 니 다.
프로 토 콜 핸들 러 는 NioEndpoint 에 요청 처 리 를 맡 겼 다.
AbstractProtocol
@Override
public void start() throws Exception {
if (getLog().isInfoEnabled()) {
getLog().info(sm.getString("abstractProtocolHandler.start", getName()));
logPortOffset();
}
endpoint.start();
monitorFuture = getUtilityExecutor().scheduleWithFixedDelay(
new Runnable() {
@Override
public void run() {
if (!isPaused()) {
startAsyncTimeout();
}
}
}, 0, 60, TimeUnit.SECONDS);
}
호출 체인:AbstractEndpoint
public final void start() throws Exception {
if (bindState == BindState.UNBOUND) {
bindWithCleanup();
bindState = BindState.BOUND_ON_START;
}
startInternal();
}
tomcat 의 세 가지 모드 를 볼 수 있 습 니 다.기본적으로 NIO 모드 를 사용 합 니 다.
@Override
public void bind() throws Exception {
initServerSocket();
setStopLatch(new CountDownLatch(1));
// Initialize SSL if needed
initialiseSsl();
selectorPool.open(getName());
}
protected void initServerSocket() throws Exception {
if (!getUseInheritedChannel()) {
//
serverSock = ServerSocketChannel.open();
socketProperties.setProperties(serverSock.socket());
InetSocketAddress addr = new InetSocketAddress(getAddress(), getPortWithOffset());
//
serverSock.socket().bind(addr,getAcceptCount());
} else {
// Retrieve the channel provided by the OS
Channel ic = System.inheritedChannel();
if (ic instanceof ServerSocketChannel) {
serverSock = (ServerSocketChannel) ic;
}
if (serverSock == null) {
throw new IllegalArgumentException(sm.getString("endpoint.init.bind.inherited"));
}
}
// serverSock
serverSock.configureBlocking(true); //mimic APR behavior
}
server Socket 은 차단 모드 를 설정 합 니 다.기본적으로 NIO 모드 를 사용 하 는데 왜 차단 모드 를 설정 합 니까?왜 NIO 를 사용 합 니까?BIO 의 accept 는 차단 방법 이기 때문에 write 와 read 도 모두 차단 되 어 있 습 니 다.새 연결 이 왔 을 때 만 새 스 레 드 를 만들어 서 이 연결 을 처리 할 수 있 습 니 다.이렇게 해서 가장 큰 문 제 는 대량의 연결 을 동시에 처리 할 수 없다 는 것 이다.대량의 연결 이 가 져 온 것 은 많은 스 레 드 를 만 드 는 것 이기 때문에 대량의 스 레 드 는 운영 체제 가 무 너 지기 쉽다.또한 병발 도가 높 지만 많은 스 레 드 가 공전 하고 많은 시간 을 스 레 드 의 헛걸음 과 스 레 드 전환 에 낭비 하 며 효율 도 떨어진다.
그래서 니 오 가 탄생 했다.
사실 연결 을 처리 하 는 작업 은 백 스테이지 스 레 드 에 두 지 않 아 도 됩 니 다.백 스테이지 스 레 드 는 연결 이 제때에 이 루어 지지 않 을 수 있 기 때문에 이 를 메 인 스 레 드 에 두 고 병발 도 를 증가 하 는 것 이 좋 습 니 다(장점 이 뚜렷 하 지 는 않 지만).
중요 한 관심 사 는 연결 이 만들어 진 후에 클 라 이언 트 와 상호작용 을 하 는 socket 입 니 다.이 동작 은 반드시 차단 되 어야 합 니 다.이것 은 분명 합 니 다.긴 연결 을 처리 할 때,우리 가 관심 을 가 지 는 것 은 이번 연결 안의 데이터 읽 기와 쓰기 이기 때문이다.
NioEndpoint 는 차단 모드 의 ServerSocketChannel 을 사용 하여 연결 이 들 어 오 기 를 막 고 기다 리 고 있 으 며,accept 후에 만 이 들 어 오 는 socket channel 을 비 차단 방식 으로 처리 하고 있 습 니 다(setSocketOptions 방법 참조).
저자 가 지적 한 바 와 같이 ServerSocketChannel 을 비 차단 으로 만 들 면 읽 기 가 바 쁠 것 입 니 다.즉,하나의 스 레 드 는 들 어 오 는 연결 이 있 는 지 계속 문의 할 것 입 니 다.비 차단 모드 에서 accept()가 null 로 돌아 갈 수 있 기 때 문 입 니 다.
APR 은 Apache Portable Runtime 을 대표 합 니 다.
Tomcat 는 socket 을 받 았 을 때 다음 과 같은 동작 을 했 습 니 다.
레 퍼 런 스
https://blog.csdn.net/andy_zhang2007/article/details/78641974
https://stackoverflow.com/questions/23168910/why-tomcats-non-blocking-connector-is-using-a-blocking-socket
여기 서 SpringBoot 애플 리 케 이 션 이 내 장 된 Tomcat 를 시작 하 는 과정 에 대한 분석 에 관 한 글 을 소개 합 니 다.더 많은 SpringBoot 내 장 된 Tomcat 시작 내용 은 우리 의 이전 글 을 검색 하거나 아래 의 관련 글 을 계속 조회 하 시기 바 랍 니 다.앞으로 많은 응원 부 탁 드 리 겠 습 니 다!
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
【Java・SpringBoot・Thymeleaf】 에러 메세지를 구현(SpringBoot 어플리케이션 실천편 3)로그인하여 사용자 목록을 표시하는 응용 프로그램을 만들고, Spring에서의 개발에 대해 공부하겠습니다 🌟 마지막 데이터 바인딩에 계속 바인딩 실패 시 오류 메시지를 구현합니다. 마지막 기사🌟 src/main/res...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.