728x90
1. TCP 블로킹 채널
- NIO에서 TCP 네트워크 통신을 위해 사용하는 채널 : java.nio.channels.ServerSocketChannel과 java.nio.channels.SocketChannel
- ServerSocketChannel과 SocketChannel은 블로킹과 넌블로킹 방식을 모두 지원.
- 사용 방법은 IO와 큰 차이점이 없다.
TCP 블로킹 채널의 서버소켓 채널 생성과 연결 수락
- 서버를 개발하려면 ServerSocketChannel 객체를 얻어야 한다.
ServerSocketChannel 생성 방법
ServerSocketChannel serverSocketChannel = ServerSocketChannel.open(); // ServerSocketChannel 객체 생성
serverSocketChannel.configureBlocking(true); //블로킹 방식 사용
serverSocketChannel.bind(new InetSocketAddress(5001)); // 바인딩 포트 5001로 설정
- 포트 바인딩이 끝나면 ServerSocketChannel은 클라이언트 연결 수락을 위해 accept()메소드를 실행해야 한다.
- accept()메소드는 클라이언트가 연결 요청 전까지는 블로킹되므로 UI및 이벤트 처리 스레드에서 사용하면 안됨
ServerSocketChannel의 accept() 생성 방법
SocketChannel socketChannel = serverSocketChannel.accept();// 클라이언트와 통신할 SocketChannel 객체를 리턴함
- 연결된 클라이언트 IP와 포트 정보를 알고 싶다면 SocketChannel의 getRemoteAddress()메소드를 호출해서 SocketAddress를 얻음
InetSocketAddress socketAddress = (InetSocketAddress)socketChannel.getRemoteAddress();
InetSocketAddress에는 다음과 같은 IP와 포트 정보를 리턴함
- 더 이상 클라이언트와 연락 수락할 필요 없다면 ServerSocketChannel의 close()메소드를 호출
serverSocketChannel.close();
TCP 블로킹 채널의 소켓 채널 생성과 연결 요청
- 클라이언트가 서버에 연결 요청을 할 때에는 java.nio.channels.SocketChannel을 이용
SocketChannel 생성 방법
SocketChannel socketChannel = SocketChannel.open();
socketChannel.configureBlocking(true); // 블로킹 방식으로 동작시키기 위해서 호출
socketChannel.connect(new InetSocketAddress("localhost",5001));
//InetSocketAddress객체에 연결 요청할 서버의 IP와 포트번호를 매개값으로 넣는다.
- connect()메소드는 서버와 연결될 때까지 블로킹되므로 UI및 이벤트를 처리하는 스레드에선 호출하지 않음
- 연결을 끊고 싶다면 SocketChannel의 close()메소드 호출
SocketChannel.close();
TCP 블로킹 채널의 소켓 채널 데이터 통신
- 서버와 클라이언트 양쪽의 SocketChannel객체의 read(), write()메소드를 호출해서 데이터 통신을 할 수 있다.
- read(), write()메소드 모두 버퍼를 이용하기 때문에 버퍼를 읽고 쓰는 작업이 필요.
ex. SocketChannel의 write()메소드를 이용하여 문자열 보내기
Charset charset = Charset.forName("UTF-8");
ByteBuffer byteBuffer = charset.encode("Hello Server");
socketChannel.write(byteBuffer);
ex. SocketChannel의 read()메소르를 이용하여 문자열 받기
ByteBuffer byteBuffer = ByteBuffer.allocate(100):
int byteCount = socketChannel.read(byteBuffer);
byteBuffer.filp(); // 사용 이유: 처음부터 받기 위해서
Charset charset = Charset.forName("UTF-8");
String message = charset.decode(byteBuffer).toString();
- read() 메소드를 호출하면 상대방이 데이터를 보내기 전까지 블로킹되는데, read()메소드 블로킹 해제되고, 리턴되는 경우는 세가지가 있다.
스레드 병렬 처리
- read()와 write()메소드로 인한 블로킹때문에 스레드를 새로 생성하여 처리 작업을 해주어야 한다.
- 그러나 모든 작업에 스레드를 하나씩 할당해서 병렬 처리 시 작업 수가 많아지면 서버가 다운되는 상황이 일어날 수 있다.
※ 프로그램의 성능을 위해서 스레드 풀을 이용하여 작업 스레드 수를 한정 시켜주어 해결 가능한다.
728x90
'👨🏫Study > JAVA' 카테고리의 다른 글
[JAVA] 19. NIO 기반 입출력 및 네트워킹(6) (0) | 2022.04.06 |
---|---|
[JAVA] 19. NIO 기반 입출력 및 네트워킹(5) (0) | 2022.04.06 |
[JAVA] 19. NIO 기반 입출력 및 네트워킹(3) (0) | 2022.04.06 |
[JAVA] 19. NIO 기반 입출력 및 네트워킹(2) (0) | 2022.04.06 |
[JAVA] 19. NIO 기반 입출력 및 네트워킹(1) (0) | 2022.04.06 |
댓글