우선, 이번 학교에서 있는 캡스톤 대회 준비하는데 필요한 소켓통신 부분을 python 으로 시도해 보았다.
먼저 메모장의 데이터를 python 으로 소켓통신 하기 전에
간단한 메시지를 주고 받는 예제를 이용하여 조금 각색해 보았다.
[ 서버 -- 라즈베리파이 / 클라이언트 -- PC ]
다음은 간단한 예제 코드이다.
< Server.py >
import socket
# 접속할 서버 주소입니다. 여기에서는 루프백(loopback) 인터페이스 주소 즉 localhost를 사용합니다.
HOST = '127.0.0.1'
# 클라이언트 접속을 대기하는 포트 번호입니다.
PORT = 9999
# 소켓 객체를 생성합니다.
# 주소 체계(address family)로 IPv4, 소켓 타입으로 TCP 사용합니다.
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
# 포트 사용중이라 연결할 수 없다는
# WinError 10048 에러 해결를 위해 필요합니다.
server_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
# bind 함수는 소켓을 특정 네트워크 인터페이스와 포트 번호에 연결하는데 사용됩니다.
# HOST는 hostname, ip address, 빈 문자열 ""이 될 수 있습니다.
# 빈 문자열이면 모든 네트워크 인터페이스로부터의 접속을 허용합니다.
# PORT는 1-65535 사이의 숫자를 사용할 수 있습니다.
server_socket.bind((HOST, PORT))
# 서버가 클라이언트의 접속을 허용하도록 합니다.
server_socket.listen()
# accept 함수에서 대기하다가 클라이언트가 접속하면 새로운 소켓을 리턴합니다.
client_socket, addr = server_socket.accept()
# 접속한 클라이언트의 주소입니다.
print('Connected by', addr)
# 무한루프를 돌면서
while True:
# 클라이언트가 보낸 메시지를 수신하기 위해 대기합니다.
data = client_socket.recv(1024)
# 빈 문자열을 수신하면 루프를 중지합니다.
if not data:
break
# 수신받은 문자열을 출력합니다.
print('Received from', addr, data.decode())
# 받은 문자열을 다시 클라이언트로 전송해줍니다.(에코)
client_socket.sendall(data)
# 소켓을 닫습니다.
client_socket.close()
server_socket.close()
< Client.py >
import socket
# 서버의 주소입니다. hostname 또는 ip address를 사용할 수 있습니다.
HOST = '127.0.0.1'
# 서버에서 지정해 놓은 포트 번호입니다.
PORT = 9999
# 소켓 객체를 생성합니다.
# 주소 체계(address family)로 IPv4, 소켓 타입으로 TCP 사용합니다.
client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
# 지정한 HOST와 PORT를 사용하여 서버에 접속합니다.
client_socket.connect((HOST, PORT))
# 메시지를 전송합니다.
client_socket.sendall('안녕'.encode())
# 메시지를 수신합니다.
data = client_socket.recv(1024)
print('Received', repr(data.decode()))
# 소켓을 닫습니다.
client_socket.close()
위의 코드를 조금 각색하여 내가 준비하는 것에 어울리는 코드로 만들어 보았다.
서버에서 메모장의 내용을 읽어 클라이언트로 보내주는데
여기서 중요한 건 메모장의 내용을 실시간으로 읽는다는 것이다.
실시간으로 메모장을 읽어 내용이 바뀌게 되면 바뀐 내용의 것으로 바꾸어 보내주어 클라이언트의 메모장에 정확히 바뀌게 된다.
우선 서버 코드이다. [ 메모장의 데이터를 읽고 보내주는 소켓 통신 코드 ]
< Server.py >
import socket
# 접속할 서버 주소입니다. 여기에서는 루프백(loopback) 인터페이스 주소 즉 localhost를 사용합니다.
HOST = '127.0.0.1'
# 클라이언트 접속을 대기하는 포트 번호입니다.
PORT = 9999
# 소켓 객체를 생성합니다.
# 주소 체계(address family)로 IPv4, 소켓 타입으로 TCP 사용합니다.
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
# 포트 사용중이라 연결할 수 없다는
# WinError 10048 에러 해결를 위해 필요합니다.
server_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
# bind 함수는 소켓을 특정 네트워크 인터페이스와 포트 번호에 연결하는데 사용됩니다.
# HOST는 hostname, ip address, 빈 문자열 ""이 될 수 있습니다.
# 빈 문자열이면 모든 네트워크 인터페이스로부터의 접속을 허용합니다.
# PORT는 1-65535 사이의 숫자를 사용할 수 있습니다.
server_socket.bind((HOST, PORT))
# 서버가 클라이언트의 접속을 허용하도록 합니다.
server_socket.listen()
# accept 함수에서 대기하다가 클라이언트가 접속하면 새로운 소켓을 리턴합니다.
client_socket, addr = server_socket.accept()
# 접속한 클라이언트의 주소입니다.
print('Connected by', addr)
copy ='0'
# 무한루프를 돌면서
while True:
f = open('hello.txt', 'r')
s = f.read()
f.close()
if copy == s:
continue
else:
print('메모장의 내용',s)
# 메모장의 내용을 클라이언트로 전송
copy = s
client_socket.sendall(s.encode())
# 소켓을 닫습니다.
client_socket.close()
server_socket.close()
여기서 while 문이 중요하다. copy 라는 변수를 while 문 이전에 설정해주고, 반복을 실시 할 것인데 우선 hello.txt 라는 메모장의 을 열어 읽을 것이다. 그것을 s라는 변수에 저장하고 미리 설정해 준 copy 라는 것과 같다면 continue 되어 아랫줄은 실행되지 않고 계속 실시간으로 읽어오는 것만 반복 될 것이다. 하지만 같지 않다면 (새로운 것이 메모장에 적힌다면) 그 내용을 프린트하며 copy 입력된 s의 값을 넣어주고 client로 보내준다. 여기서 s를 넣어주는 이유는 다시 반복될 때 if의 조건대로 같아야 한 번만 print하고 send 할 것이기 때문이다
다음은 Client 코드이다.
< Client.py >
import socket
# 서버의 주소입니다. hostname 또는 ip address를 사용할 수 있습니다.
HOST = '127.0.0.1'
# 서버에서 지정해 놓은 포트 번호입니다.
PORT = 9999
# 소켓 객체를 생성합니다.
# 주소 체계(address family)로 IPv4, 소켓 타입으로 TCP 사용합니다.
client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
# 지정한 HOST와 PORT를 사용하여 서버에 접속합니다.
client_socket.connect((HOST, PORT))
# 메시지를 전송합니다.
# 메시지를 수신합니다.
copy ='0'
while True:
data = client_socket.recv(1024)
if copy == data:
continue
else:
print('서버로 부터 받은 메모장의 내용', repr(data.decode()))
copy = data
f = open('helloClient.txt', 'w')
f.write(data.decode())
f.close()
# 소켓을 닫습니다.
client_socket.close()
여기도 마찬가지로 while 문을 이용해서 반복을 수행하였다.
조건은 위 서버의 설명과 비슷하다.
위와 같은 코드를 실행 결과이다.
영상 왼쪽이 서버 , 오른쪽이 클라이언트 이다.
위와 같이 메모장을 실시간으로 읽어 클라이언트로 보내는 것이 가능하다.
라즈베리파이에 적용시켜 라즈베리파이와 PC의 소켓통신도 가능하다.
참고 블로그 : webnautes.tistory.com/1381
'Socket' 카테고리의 다른 글
소켓통신으로 받은 데이터 mysql 서버에 저장하기 (python으로 쿼리문 이용) (0) | 2020.09.14 |
---|---|
라즈베리파이 C - Android (0) | 2020.03.02 |
C (win) - Android (6) | 2020.03.02 |
라즈베리파이 (python) - android (0) | 2020.02.24 |
라즈베리파이(리눅스) - win <C 언어> (0) | 2020.02.24 |