
🔥 문제
자바 소켓 통신에서 Gson 라이브러리 + BufferedWriter 사용 중 host 관련 에러 발생함
자바에서 데몬을 만들고, 자바스크립트로 데이터를 보내려 했는데 통신이 되지 않는 문제
🔍 원인
결국 TCP/IP 문제였고, 서버는 IPv4, 클라이언트(나)는 IPv6로 설정되어 있어서 호환이 안 된 것이었다.
네트워크 담당자가 서버의 TCP/IP 버전을 IPv4로 설정했는데 나는 그냥 Runnable JAR을 실행해서 IPv6로 동작한 것이 원인이다.
⭐ 해결법
WSL에 nohup 명령어로 JVM 옵션 추가하면 해결 가능
nohup java -Djava.net.preferIPv4Stack=true -Dpath="경로" -jar 이름.jar >> server.log 2>&1 &
- nohup → 터미널 종료 후에도 실행 지속
- java -Djava.net.preferIPv4Stack=true → IPv4 우선 사용 설정
- -Dpath="경로" → path 환경 변수를 "경로"로 설정
- -jar 이름.jar → 실행할 JAR 파일 지정
- >> server.log 2>&1 → 출력을 server.log 파일에 저장 (표준 출력 & 에러 포함)
- & → 백그라운드 실행
🐦 TMI
여기서부터는 나 혼자 읽으려고 정리한 것
미래의 나를 위해 열심히 명령어 찾아서 정리해 해 놓음
또는 정확한 이해를 위해 궁금한 것을 찾아봄
✅ 지금 JAR 파일이 하고 있는 일이 정확히 무엇이고 어떻게 동작해?
JAR 파일로 실행된 Java 서버가 특정 포트를 점유하면서 작동하는 방식이다. 소켓 통신(ServerSocket)을 열어 클라이언트의 요청을 대기하는 상태에서 nohup 명령어를 사용하면 백그라운드에서 실행되면서 로그가 저장이 되고,
-Djava.net.preferIPv4Stack=true 옵션이 적용되어 IPv4 환경에서 동작하는 원리이다.
1. 서버 역할
- ServerSocket을 사용해 특정 포트를 점유
- 클라이언트(예: 자바스크립트)에서 데이터 요청을 받을 준비
- JSON 데이터를 Gson을 사용해 파싱함
2. 백그라운드 실행 중
- nohup을 사용했기 때문에 터미널을 닫아도 계속 작동할 수 있게 함
- server.log에 실행 로그가 저장됨
✅ TCP/IP 버전을 IPv4로 설정하는 세 가지 방법
한 번만 실행할 거면? 방법 1 (-Djava.net.preferIPv4Stack=true 옵션 추가해서 실행)
java -Djava.net.preferIPv4Stack=true -jar myapp.jar
자바 코드에서 설정하고 싶다면? 방법 2 (System.setProperty() 사용)
public class Main {
public static void main(String[] args) {
System.setProperty("java.net.preferIPv4Stack", "true");
// 기존 코드 실행
}
}
항상 IPv4로 실행하고 싶다면? 방법 3 (환경 변수 설정)
만약 실행할 때마다 -Djava.net.preferIPv4Stack=true를 추가하는 게 귀찮다면, 환경 변수로 설정하면 됨.
환경 변수 편집기 열고 새 시스템 변수 추가
변수 이름: JAVA_TOOL_OPTIONS
변수 값: -Djava.net.preferIPv4Stack=true
적용 후 재부팅 하면 Java 실행할 때 자동으로 IPv4 우선 사용한다.
혹시 몰라서 관련 에러도 같이 검색함
- java.net.UnknownHostException: somehost DNS 설정 문제 (올바른 호스트명 사용하자)
- java.net.BindException: Address already in use 포트 충돌
- java.net.SocketException: Connection reset 클라이언트-서버 IP 불일치
✅ 서버/클라이언트에서 네트워크 관련 에러 났을 때 대처법
1. 포트가 이미 점유된 상태인지 확인하자! (포트 충돌인가?)
- 어떻게 포트 문제인지 아는가?
- 서버에서 이미 사용 중인 포트에 바인딩하려 하면 BindException 발생함
★ 아래 명령어로 JAR 파일이 점유한 포트를 확인하는 법
netstat -tulnp | grep java
- netstat : 네트워크 연결 상태 확인
- -t : TCP 포트
- -u : UDP 포트
- -l : LISTEN 상태
- -n : 포트 번호 숫자로 표시
- -p : 프로세스 정보 포함
- grep java → 결과 중 java 관련된 것만 필터링
출력 예시
tcp 0 0 0.0.0.0:9090 0.0.0.0:* LISTEN 12345/java
// 9090 포트를 사용 중임
★ 반대로 특정 포트를 사용 중인 프로세스(서버)가 있는지 확인하는 법
netstat -tulnp | grep 8080
- 8080 포트 대신 JAR 파일이 점유한 포트를 확인해 보자
- -t → TCP 포트만 출력
- -u → UDP 포트도 출력
- -l → 현재 LISTEN 중인 포트만 표시 (즉, 서버가 점유 중인 포트)
- -n → 포트 번호 및 IP를 숫자로 표시 (도메인 해석 안 함, 속도 ↑)
- -p → 프로세스 ID(PID)와 이름 표시
- | grep 8080 → 결과 중 8080 포트 관련된 것만 필터링
2. JSON 데이터를 받을 때 BufferedWriter에서 문제인지 확인하자
- Gson으로 JSON을 변환할 때 BufferedWriter로 전송하는 과정에서 잘못된 JSON 형식이 들어갔을 가능성을 확인하자. BufferedWriter를 사용할 때 .flush()를 호출하지 않으면, 데이터가 제대로 전송되지 않는 경우도 있다.
BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
Gson gson = new Gson();
String json = gson.toJson(myObject);
writer.write(json);
writer.newLine();
writer.flush(); // 꼭 flush 호출
3. 서버가 정상작동하는가?
실시간으로 로그를 보면서, 에러 메시지가 없는지 확인 가능
tail -f server.log
험한 세상에서 살아 남기 = 노력과 실력
정리하느라 너무 힘들었고 이거 찾는데 2시간은 걸린거 같다
할 게 얼마나 많은데 네트워크까지 알아야 한다니... 이게 진짜야?
프로그래밍 언어도 중요하지만 기본적인 네트워크 개념이 없으면 남에게 의존할 수밖에 없고,
그것은 결국 인간관계에서 불필요한 부담으로 이어지기 마련이다.
TCP/IP, DNS, HTTP, WebSocket 같은 개념은 최소한 알고 있어야 하고, 네트워크 디버깅도 어느 정도 할 줄 알아야 한다.
'Java' 카테고리의 다른 글
[Eclipse] 이클립스 제이유닛 Junit java.lang.NoClassDefFoundError 해결법 (11) | 2025.02.27 |
---|---|
[Eclipse] restore 명령어로 복구한 파일이 이클립스 패키지 익스플로러에는 복구 안 되는 문제 해결법 (10) | 2025.02.14 |
[Eclipse] 내가 보려고 만든 이클립스 유용한 단축키 (12) | 2025.02.05 |
[Java] 자바 Runtime addShutdownHook() 에 대해 알아보자 (15) | 2025.02.04 |
[Java] 자바 배열 정렬 할 때 오버플로우 방지하는 법 (11) | 2025.02.01 |

🔥 문제
자바 소켓 통신에서 Gson 라이브러리 + BufferedWriter 사용 중 host 관련 에러 발생함
자바에서 데몬을 만들고, 자바스크립트로 데이터를 보내려 했는데 통신이 되지 않는 문제
🔍 원인
결국 TCP/IP 문제였고, 서버는 IPv4, 클라이언트(나)는 IPv6로 설정되어 있어서 호환이 안 된 것이었다.
네트워크 담당자가 서버의 TCP/IP 버전을 IPv4로 설정했는데 나는 그냥 Runnable JAR을 실행해서 IPv6로 동작한 것이 원인이다.
⭐ 해결법
WSL에 nohup 명령어로 JVM 옵션 추가하면 해결 가능
nohup java -Djava.net.preferIPv4Stack=true -Dpath="경로" -jar 이름.jar >> server.log 2>&1 &
- nohup → 터미널 종료 후에도 실행 지속
- java -Djava.net.preferIPv4Stack=true → IPv4 우선 사용 설정
- -Dpath="경로" → path 환경 변수를 "경로"로 설정
- -jar 이름.jar → 실행할 JAR 파일 지정
- >> server.log 2>&1 → 출력을 server.log 파일에 저장 (표준 출력 & 에러 포함)
- & → 백그라운드 실행
🐦 TMI
여기서부터는 나 혼자 읽으려고 정리한 것
미래의 나를 위해 열심히 명령어 찾아서 정리해 해 놓음
또는 정확한 이해를 위해 궁금한 것을 찾아봄
✅ 지금 JAR 파일이 하고 있는 일이 정확히 무엇이고 어떻게 동작해?
JAR 파일로 실행된 Java 서버가 특정 포트를 점유하면서 작동하는 방식이다. 소켓 통신(ServerSocket)을 열어 클라이언트의 요청을 대기하는 상태에서 nohup 명령어를 사용하면 백그라운드에서 실행되면서 로그가 저장이 되고,
-Djava.net.preferIPv4Stack=true 옵션이 적용되어 IPv4 환경에서 동작하는 원리이다.
1. 서버 역할
- ServerSocket을 사용해 특정 포트를 점유
- 클라이언트(예: 자바스크립트)에서 데이터 요청을 받을 준비
- JSON 데이터를 Gson을 사용해 파싱함
2. 백그라운드 실행 중
- nohup을 사용했기 때문에 터미널을 닫아도 계속 작동할 수 있게 함
- server.log에 실행 로그가 저장됨
✅ TCP/IP 버전을 IPv4로 설정하는 세 가지 방법
한 번만 실행할 거면? 방법 1 (-Djava.net.preferIPv4Stack=true 옵션 추가해서 실행)
java -Djava.net.preferIPv4Stack=true -jar myapp.jar
자바 코드에서 설정하고 싶다면? 방법 2 (System.setProperty() 사용)
public class Main { public static void main(String[] args) { System.setProperty("java.net.preferIPv4Stack", "true"); // 기존 코드 실행 } }
항상 IPv4로 실행하고 싶다면? 방법 3 (환경 변수 설정)
만약 실행할 때마다 -Djava.net.preferIPv4Stack=true를 추가하는 게 귀찮다면, 환경 변수로 설정하면 됨.
환경 변수 편집기 열고 새 시스템 변수 추가
변수 이름: JAVA_TOOL_OPTIONS
변수 값: -Djava.net.preferIPv4Stack=true
적용 후 재부팅 하면 Java 실행할 때 자동으로 IPv4 우선 사용한다.
혹시 몰라서 관련 에러도 같이 검색함
- java.net.UnknownHostException: somehost DNS 설정 문제 (올바른 호스트명 사용하자)
- java.net.BindException: Address already in use 포트 충돌
- java.net.SocketException: Connection reset 클라이언트-서버 IP 불일치
✅ 서버/클라이언트에서 네트워크 관련 에러 났을 때 대처법
1. 포트가 이미 점유된 상태인지 확인하자! (포트 충돌인가?)
- 어떻게 포트 문제인지 아는가?
- 서버에서 이미 사용 중인 포트에 바인딩하려 하면 BindException 발생함
★ 아래 명령어로 JAR 파일이 점유한 포트를 확인하는 법
netstat -tulnp | grep java
- netstat : 네트워크 연결 상태 확인
- -t : TCP 포트
- -u : UDP 포트
- -l : LISTEN 상태
- -n : 포트 번호 숫자로 표시
- -p : 프로세스 정보 포함
- grep java → 결과 중 java 관련된 것만 필터링
출력 예시
tcp 0 0 0.0.0.0:9090 0.0.0.0:* LISTEN 12345/java // 9090 포트를 사용 중임
★ 반대로 특정 포트를 사용 중인 프로세스(서버)가 있는지 확인하는 법
netstat -tulnp | grep 8080
- 8080 포트 대신 JAR 파일이 점유한 포트를 확인해 보자
- -t → TCP 포트만 출력
- -u → UDP 포트도 출력
- -l → 현재 LISTEN 중인 포트만 표시 (즉, 서버가 점유 중인 포트)
- -n → 포트 번호 및 IP를 숫자로 표시 (도메인 해석 안 함, 속도 ↑)
- -p → 프로세스 ID(PID)와 이름 표시
- | grep 8080 → 결과 중 8080 포트 관련된 것만 필터링
2. JSON 데이터를 받을 때 BufferedWriter에서 문제인지 확인하자
- Gson으로 JSON을 변환할 때 BufferedWriter로 전송하는 과정에서 잘못된 JSON 형식이 들어갔을 가능성을 확인하자. BufferedWriter를 사용할 때 .flush()를 호출하지 않으면, 데이터가 제대로 전송되지 않는 경우도 있다.
BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream())); Gson gson = new Gson(); String json = gson.toJson(myObject); writer.write(json); writer.newLine(); writer.flush(); // 꼭 flush 호출
3. 서버가 정상작동하는가?
실시간으로 로그를 보면서, 에러 메시지가 없는지 확인 가능
tail -f server.log
험한 세상에서 살아 남기 = 노력과 실력
정리하느라 너무 힘들었고 이거 찾는데 2시간은 걸린거 같다
할 게 얼마나 많은데 네트워크까지 알아야 한다니... 이게 진짜야?
프로그래밍 언어도 중요하지만 기본적인 네트워크 개념이 없으면 남에게 의존할 수밖에 없고,
그것은 결국 인간관계에서 불필요한 부담으로 이어지기 마련이다.
TCP/IP, DNS, HTTP, WebSocket 같은 개념은 최소한 알고 있어야 하고, 네트워크 디버깅도 어느 정도 할 줄 알아야 한다.
'Java' 카테고리의 다른 글
[Eclipse] 이클립스 제이유닛 Junit java.lang.NoClassDefFoundError 해결법 (11) | 2025.02.27 |
---|---|
[Eclipse] restore 명령어로 복구한 파일이 이클립스 패키지 익스플로러에는 복구 안 되는 문제 해결법 (10) | 2025.02.14 |
[Eclipse] 내가 보려고 만든 이클립스 유용한 단축키 (12) | 2025.02.05 |
[Java] 자바 Runtime addShutdownHook() 에 대해 알아보자 (15) | 2025.02.04 |
[Java] 자바 배열 정렬 할 때 오버플로우 방지하는 법 (11) | 2025.02.01 |