36강 구현 중심 ⏱ 약 25분

 

0. 학습 목표

→ 새 기능 없이 흩어져 있던 코드를 정리하고, 제출·시연 가능한 최종 프로젝트 형태로 구조를 확정합니다.

더보기

0.1 이번 글에서 다룰 내용

이번 글은 구현 중심 강의입니다.

 

지금까지 35강에 걸쳐 기능을 하나씩 추가하며 프로젝트를 키워 왔습니다.

  • GUI 채팅 송수신,
  • 사용자 목록 동기화,
  • 귓속말,
  • 파일 전송과 저장까지

모두 동작합니다.

 

이번 강의에서는 새 기능을 추가하지 않습니다.

대신 흩어져 있던 코드의 자리를 정리하고, 제출·시연이 가능한 최종 프로젝트 형태로 구조를 확정합니다.

구분 내용
이해할 것 최종 프로젝트에서 각 파일이 맡는 역할과 역할 경계
정리할 것 제출 가능한 프로젝트 폴더 구조와 최종 실행 흐름
확인할 것 정리 후에도 채팅·귓속말·파일 전송이 깨지지 않고 동작하는지

 

0.2 이번 강의에서 직접 다루는 구조

이번 강의에서는 새 파일을 만들지 않고, 35강까지 만든 파일들의 위치와 역할을 정리합니다. 폴더 구조는 1강에서 예고한 서버 프로젝트·클라이언트 프로젝트 분리 구조를 그대로 최종 형태로 확정합니다.

chat_server/                 ← 서버 프로젝트
├── protocol.py              ← 유지 (메시지 송수신 규칙)
├── server.py                ← 유지 (서버 실행·접속자 관리·귓속말·파일 저장)
└── received_files/          ← 유지 (서버가 수신한 파일 저장, 자동 생성)

chat_client/                 ← 클라이언트 프로젝트
├── protocol.py              ← 유지 (서버와 동일 사본)
├── client.py                ← 유지 (소켓 연결·송수신)
└── main.py                  ← 유지 (GUI 화면, ChatWindow)

(➕ 새로 생성 · ✏️ 수정 · 표시 없음은 변경 없음 — 이번 강의는 구조 정리이므로 모두 유지)

파일 정리 방향
protocol.py 메시지 전송·수신 규칙만 담당 (서버·클라이언트 양쪽 동일 사본)
server.py 서버 기능을 역할별 함수로 정리, 디버깅용 print 정리
client.py 소켓 연결·송수신만 담당, GUI 로직과 분리
main.py GUI 화면과 사용자 동작 처리 담당 (ChatWindow)

 

1. 통합 기준 정리하기

→ 최종 프로젝트에 포함될 기능 목록과 통합 시 지킬 기준을 정리합니다.

더보기

1.1 최종 프로젝트에 포함될 기능

지금까지 만든 기능을 한자리에 모으면 다음과 같습니다. 이번 강의에서 새로 만들 기능은 없고, 이 목록이 모두 하나의 프로젝트 안에서 동작하는 것이 목표입니다.

서버 접속
실시간 메시지 수신
전체 채팅
사용자 목록 동기화
상대 선택
귓속말 / 귓속말 오류 처리
파일 선택
파일 전송 진행률 표시
파일 수신 저장
연결 종료 처리

 

1.2 최종 통합 기준

구조를 정리할 때는 다음 다섯 가지 기준을 따릅니다. 코드를 새로 짜는 것이 아니라, 이 기준에 맞게 위치만 맞추는 작업입니다.

기준 설명
실행 파일이 명확해야 한다 서버는 chat_server/server.py, GUI는 chat_client/main.py
공통 규칙은 분리해야 한다 메시지 송수신 규칙은 protocol.py로 양쪽에 동일하게 둔다
임시 로그는 줄인다 꼭 필요한 안내 출력만 남기고 디버깅용 print는 제거한다
저장 폴더는 고정한다 서버가 수신한 파일은 chat_server/received_files/에 저장 (34강 구현 기준)
실행 순서가 단순해야 한다 서버 실행 후 GUI 클라이언트 실행

✔ 확인 기준: 구조를 정리해도 채팅·귓속말·파일 전송이 깨지지 않으면 완료. 만약 깨지면 import 경로와 파일 위치가 바뀌지 않았는지 먼저 확인하세요.

 

2. 파일별 역할 경계 정리하기

→ 각 파일이 담당하는 것과 담당하지 않는 것을 구분하고, 함수 배치 순서를 정리합니다.

더보기

2.1 파일이 담당하는 것 / 담당하지 않는 것

통합에서 가장 흔한 실수는 한 파일이 너무 많은 일을 하는 것입니다. 예를 들어 GUI 파일이 서버를 직접 실행하거나, 서버 파일이 화면 코드를 가지고 있으면 구조가 무너집니다. 아래 경계를 기준으로 코드의 자리를 점검합니다.

파일 담당하는 것 담당하지 않는 것
protocol.py JSON 변환, 구분자 처리, 메시지 송수신 GUI 화면, 서버 로직
server.py 접속자 관리, 메시지 분기, 전체 채팅, 귓속말, 파일 저장 GUI 화면
client.py 소켓 연결, 메시지 송수신 루프 GUI 위젯, 서버 실행
main.py GUI 화면, 사용자 입력, 메시지 표시, 파일 선택 서버 실행

 

2.2 server.py와 main.py 함수 배치 순서

파일 안에서 함수가 뒤섞여 있으면 읽기 어렵습니다. 최종 server.py는 다음 순서로 함수를 모아 둡니다. 위에서 아래로 읽으면 서버가 무엇을 하는지 순서대로 드러납니다.

import → 상수 → 전역 상태
→ 공통 유틸 함수
→ 사용자 목록 함수      (get_user_list, broadcast_user_list)
→ 메시지 전송 함수      (broadcast, send_error, find_client_by_identifier, send_whisper)
→ 파일 처리 함수        (handle_file_info, handle_file_chunk, handle_file_end)
→ 클라이언트 처리 함수  (handle_client)
→ 서버 실행 코드

최종 GUI 클래스 ChatWindow(main.py)에 들어 있는 주요 메서드는 다음과 같습니다. 화면 구성 → 접속 → 송수신 → 종료 순서로 묶여 있습니다.

set_connected_state, connect_to_server, receive_loop
on_send_clicked, on_whisper_clicked, on_file_clicked, send_file
disconnect_from_server, display_message, update_user_list
on_user_selected, show_error, show_system, closeEvent

✔ 확인 기준: 각 파일을 열었을 때 "이 파일이 하지 말아야 할 일"이 섞여 있지 않으면 완료. 특히 main.py에 서버 실행 코드가, server.py에 위젯 코드가 들어 있지 않은지 확인하세요.

 

3. 실행 흐름과 메시지 타입 정리하기

→ 최종 실행 순서를 확정하고, 메시지 타입별 송수신 처리와 로그 정리 기준을 정합니다.

더보기

3.1 최종 실행 흐름과 메시지 타입

최종 프로젝트의 실행 순서는 다음과 같습니다. 서버를 먼저 띄우고, GUI 클라이언트를 필요한 만큼 실행합니다.

1. 터미널 1: python chat_server/server.py
2. 터미널 2: python chat_client/main.py
3. GUI에서 서버 접속 버튼 클릭
4. 필요하면 GUI 클라이언트를 추가 실행
5. 전체 채팅, 귓속말, 파일 전송 테스트
6. exit 입력 또는 창 닫기로 종료

프로젝트에서 오가는 메시지 타입과 처리 주체를 한 표로 정리하면, 어느 기능이 어디서 처리되는지 한눈에 보입니다.

메시지 타입 보내는 쪽 받는 쪽 처리
chat GUI 클라이언트 서버가 다른 클라이언트에게 브로드캐스트
system 서버 GUI가 시스템 메시지로 표시
error 서버 GUI가 오류 메시지로 표시
exit GUI 클라이언트 서버가 접속자 제거
user_list 서버 GUI가 사용자 목록 갱신
whisper GUI 클라이언트 또는 서버 서버는 대상에게 전달, GUI는 귓속말로 표시
file_info GUI 클라이언트 서버가 파일 저장 준비
file_chunk GUI 클라이언트 서버가 파일 조각 저장
file_end GUI 클라이언트 서버가 파일 저장 완료

 

3.2 임시 로그 정리 기준

개발 중에는 동작 확인을 위해 많은 print를 넣지만, 최종 프로젝트에서는 꼭 필요한 안내만 남깁니다. 다음 기준으로 정리합니다.

출력 종류 최종 프로젝트에서
서버 시작 메시지 유지
클라이언트 접속·종료 메시지 유지
접속자 수 출력 유지 가능
모든 파일 조각마다 출력 줄이는 것 권장 (시작·완료만)
오류 메시지 유지
디버깅용 임시 print 제거

✔ 확인 기준: 서버 로그가 핵심 상태(시작·접속·종료·오류·파일 시작/완료)만 보여 주면 완료. 파일 조각마다 수백 줄씩 출력하고 있지 않은지 확인하세요.

 

4. 실행 결과 확인하기

→ 서버와 GUI를 실행해 최종 통합 구조에서 모든 기능이 동작하는지 확인합니다.

더보기

4.1 기능별 통합 테스트

서버를 먼저 실행하고 GUI 클라이언트를 2개 이상 띄운 뒤, 아래 기능을 순서대로 확인합니다.

# 터미널 1 — 서버 실행
python chat_server/server.py
# 터미널 2, 3 — GUI 클라이언트 실행 (여러 개 가능)
python chat_client/main.py
기능 테스트 방법 성공 기준
전체 채팅 GUI 2개에서 메시지 전송 상대 GUI에 메시지 표시
사용자 목록 GUI 2개 이상 접속 목록에 접속자 표시
상대 선택 사용자 목록 클릭 선택 라벨 변경
귓속말 상대 선택 후 귓속말 전송 선택한 상대에게만 표시
파일 전송 파일 선택 후 전송 진행률 100, chat_server/received_files/에 저장
종료 처리 exit 입력 또는 창 닫기 접속자 목록에서 제거

✔ 확인 기준: 채팅·귓속말·파일 전송·종료 처리까지 오류 없이 확인되면 완료. 실패하면 어느 기능에서 끊기는지 표의 위에서부터 차례로 점검하세요.

 

4.2 흔한 오류와 해결 방법

구조를 정리하면서 파일을 옮기다 보면 다음 오류가 자주 발생합니다. 대부분 위치나 실행 순서 문제입니다.

오류 상황 원인과 해결 방법
ModuleNotFoundError: protocol protocol.py가 실행 파일과 같은 폴더에 없습니다. 서버용·클라이언트용 사본을 각 폴더에 둡니다
GUI는 켜지지만 서버 접속이 안 됨 서버가 먼저 실행되지 않았습니다. python chat_server/server.py를 먼저 실행합니다
사용자 목록이 비어 있음 broadcast_user_list() 호출 위치를 확인합니다 (접속·종료 시 호출되어야 함)
귓속말 대상이 계속 없다고 나옴 on_user_selected()와 목록 itemClicked 연결을 확인합니다
파일 전송 후 저장이 안 됨 file_info · file_chunk · file_end 분기가 모두 있는지 확인합니다
received_files/가 엉뚱한 위치에 생김 RECEIVE_DIR가 단순 문자열 "received_files"입니다. os.path.dirname(os.path.abspath(__file__)) 기반으로 수정합니다
파일 전송 중 GUI가 잠시 멈춤 전송이 GUI 메인 흐름에서 실행되기 때문입니다. 작은 파일로 테스트하고 37강에서 개선합니다 (정상 동작)
종료 후 서버에 접속자가 남음 disconnect_from_server()closeEvent() 처리를 확인합니다

 

5. 최종 코드 정리하기

→ 최종 프로젝트 폴더 구조와 실행 명령어, 기능-파일 대응을 한곳에 정리합니다.

더보기

5.1 최종 프로젝트 구조와 실행 명령어

이번 강의에서 확정한 최종 폴더 구조입니다. README.md는 40강 최종 발표 단계에서 작성합니다.

chat_server/
├── protocol.py
├── server.py
└── received_files/       ← 서버 실행 시 자동 생성 (파일 수신 저장)

chat_client/
├── protocol.py
├── client.py
├── main.py
└── README.md             ← (40강에서 작성 예정)
python chat_server/server.py
python chat_client/main.py

GUI 클라이언트는 여러 개 실행할 수 있습니다.

 

5.2 기능-파일 대응 표

기능 관련 파일
JSON 메시지 송수신 protocol.py
다중 접속 서버 server.py
사용자 목록 동기화 server.py, main.py
전체 채팅 server.py, main.py
귓속말 server.py, main.py
파일 전송 main.py
파일 저장 server.py, chat_server/received_files/
GUI 상태 관리 main.py

→ 다음 강의 (37강): 36강이 기능 통합이라면 37강은 안정화입니다. 이번 강의에서 정리한 구조 위에서 예외 처리, 연결 끊김 처리, 파일명 중복 처리, 큰 파일 전송 시 GUI 멈춤 문제, 입력값 검증을 점검하고 기능별 테스트 시나리오로 버그를 잡습니다.