WebSocket hoạt động như thế nào trong Python?
Thông thường, khi một ứng dụng web cần thứ gì đó từ máy chủ bên ngoài, máy khách sẽ gửi yêu cầu đến máy chủ đó, máy chủ sẽ phản hồi và kết nối sau đó sẽ bị đóng Show
Xem xét một ứng dụng web hiển thị giá cổ phiếu. Khách hàng phải liên tục yêu cầu giá cập nhật từ máy chủ để cung cấp giá mới nhất. Cách tiếp cận này không hiệu quả vì nó liên tục ngắt kết nối HTTP và cũng không lý tưởng vì giá theo thời gian thực của cổ phiếu được lưu trữ trong cơ sở dữ liệu có thể thay đổi trong khi ứng dụng vẫn hiển thị giá cũ Tuy nhiên, với giao tiếp hai chiều, máy chủ có thể độc lập đẩy giá cổ phiếu mới cho máy khách mỗi khi cập nhật thông tin. Các kỹ sư đã phát minh ra giao thức WebSocket để kích hoạt loại kết nối liên tục này đồng thời tránh các sự cố liên quan đến các phương pháp bỏ phiếu dài cũ hơn Một lựa chọn phổ biến để triển khai WebSockets là Socket. thư viện IO. Một trong những ưu điểm chính của nó là thư viện này có thể sử dụng được trong các môi trường ngôn ngữ lập trình khác nhau, bao gồm cả Python. Nó cũng cung cấp cho chúng tôi API đơn giản và nhất quán hơn trong cả hai môi trường mà không cần sử dụng trực tiếp API WebSocket thô. Ngoài ra, thư viện giúp dễ dàng thực hiện các biện pháp bảo mật như chia sẻ tài nguyên nguồn gốc chéo (CORS), xác thực người dùng và hạn chế kích thước tải trọng Hướng dẫn này sẽ khám phá việc xây dựng một máy chủ WebSocket an toàn bằng Python bằng cách sử dụng python-socket. Ổ cắm io và JavaScript. Máy khách IO để kết nối máy khách của chúng tôi với máy chủ Tạo máy chủ WebSocket bằng PythonCài đặt và thiết lậpĐể bắt đầu, bạn phải có Python 3. x và trình quản lý gói của nó, pip, được cài đặt trên máy của bạn. May mắn thay, tất cả các phiên bản Python gần đây đều có pip. Nếu bạn không có Python, hãy tải xuống phiên bản mới nhất cho hệ thống của bạn Bây giờ, hãy tạo một số tệp nguồn. Đầu tiên, tạo một thư mục để chứa mã ví dụ. Sau đó, cài đặt gói 1 bằng pip
Sau đó, tạo một tệp 0 mới bên trong 1. Đây là nơi bạn sẽ đặt mã máy chủ ổ cắm của mìnhTạo máy chủ WebSocket bằng PythonHãy bắt đầu bằng cách nhập Ổ cắm của Python. Thư viện IO và tạo phiên bản máy chủ ổ cắm không đồng bộ bên trong 0. Chúng tôi sẽ biến nó thành máy chủ ASGI bằng cách đặt 3 thành 4. Sau đó, thiết lập trình xử lý sự kiện trên phiên bản
Sự kiện đầu tiên sẽ kích hoạt khi một ổ cắm kết nối với máy chủ của chúng tôi. Hàm 5 tương ứng nhận hai đối số
Sự kiện cuối cùng được kích hoạt khi một nút được nhấp vào ứng dụng khách. Thông báo tải trọng (anh hùng) được sử dụng để truy cập tên tương ứng từ từ điển được xác định ở đầu tệp. Bạn cần chạy một máy chủ web hiển thị ứng dụng ổ cắm dựa trên máy chủ cho máy khách. Đối với điều này, chúng tôi sẽ sử dụng ASGI. May mắn thay, python-socket. Thư viện io đi kèm với 20 để giúp chúng tôi chuyển đổi 0 thành ứng dụng ASGI mà bạn có thể kết nối với máy chủ WSGI (như Gunicorn)Bạn sẽ muốn khởi tạo một phiên bản của lớp này trên dòng bên dưới 22, chuyển phiên bản máy chủ ổ cắm và đường dẫn đến các tệp tĩnh mà bạn đã tạo trước đó 2Cuối cùng, bạn cần triển khai ứng dụng. Có nhiều chiến lược triển khai khác nhau cho Socket. Máy chủ IO, chẳng hạn như Gunicorn và Eventlet. Hãy xem tài liệu này và chọn chiến lược triển khai phù hợp nhất với nhu cầu của bạn Tạo ứng dụng khách WebSocket bằng Socket. IOBây giờ bạn đã tạo một máy chủ WebSocket, đã đến lúc tạo một máy khách WebSocket để giao tiếp với nó Đầu tiên, tạo một thư mục 23 bên trong thư mục gốc của bạn. Sau đó, tạo hai tệp. 24 và 25Bên trong 24, xác định một số đánh dấu HTML đơn giản và nhúng các liên kết đến Ổ cắm. Ứng dụng khách IO, Bootstrap CSS và tệp tập lệnh cục bộ của bạn, 25 1Bạn sẽ xử lý tất cả các sự kiện mà máy chủ phát ra bên trong 25, phát ra một sự kiện khi bất kỳ nút nào trên trang được nhấp vào 3Đoạn mã trên lấy thuộc tính 29 của nút được nhấp và gửi giá trị đó đến máy chủ. Đáp lại, máy chủ sẽ kích hoạt sự kiện 10. Trong cuộc gọi lại cuối cùng chạy khi sự kiện 10 được thực thi, chúng tôi hiển thị tên bằng hàm Javascript 12Trong trình duyệt của bạn, điều hướng đến 127. 0. 0. 1. 8000/chỉ số. html. Trang sẽ hiển thị danh sách các nút, mỗi nút cho một anh hùng. Nhấp vào bất kỳ nút nào để phát ra sự kiện 13. Đáp lại, bạn sẽ nhận được thông báo hiển thị tên của anh hùngHãy chuyển sang bảo mật WebSocket Bảo mật WebSockets của bạnBạn sẽ cần triển khai một số tính năng nhất định trên máy chủ để bảo mật WebSockets của mình Một số tính năng này được bật trong python-socketio theo mặc định, cũng như nhiều thư viện máy chủ WebSocket khác. Ví dụ: thư viện tự động thực hiện nén HTTP trong các kết nối WebSocket, giúp cải thiện tốc độ truyền và sử dụng băng thông Bạn phải triển khai hoặc bật các tính năng khác khi khởi tạo máy chủ WebSocket Sử dụng CORS để cho phép hoặc chặn tên miềnChia sẻ tài nguyên nguồn gốc chéo (CORS) là một cơ chế cho phép máy khách web thực hiện các yêu cầu nguồn gốc chéo. Các hạn chế của CORS giúp bảo vệ máy chủ khỏi các cuộc tấn công giả mạo yêu cầu chéo trang (CSRF), trong đó kẻ tấn công thường khiến nạn nhân thực hiện các hành động ngoài ý muốn và thường gây bất lợi, chẳng hạn như chuyển tiền cá nhân. Tuy nhiên, khả năng bảo vệ mà CORS cung cấp chỉ giới hạn ở các kết nối HTTP. Chính sách CORS không áp dụng cho WebSockets vì các kết nối WebSocket sử dụng giao thức WebSocket (WS) hoặc WebSocketSecure (WSS). Trong các giao thức này, bắt tay ban đầu xảy ra thông qua yêu cầu Nâng cấp HTTP, nội dung phản hồi bị bỏ qua và giao thức HTTP/HTTPS nâng cấp lên giao thức WS/WSS Vì CORS không hạn chế quyền truy cập vào các giao thức WebSocket nên người dùng độc hại có thể dễ dàng tạo kết nối WebSocket nhiều nguồn gốc để gửi và nhận dữ liệu độc hại. Giải pháp là nâng cấp giao thức lên WS bằng cách thêm trường tiêu đề 14 vào yêu cầu của máy khách. 0Đáp lại, máy chủ sẽ gửi thông báo 15, xác nhận rằng giao tiếp tiếp theo có thể xảy ra qua WebSocket. May mắn thay, ổ cắm. Thư viện máy khách IO thực hiện quá trình này tự động. Bạn có thể xem thêm các tùy chọn cấu hình của nó tại đâyMáy chủ xác minh tiêu đề 16 trên yêu cầu 17 để ngăn các kết nối WS có nguồn gốc chéo không mong muốn. Ổ cắm trăn. thư viện io cung cấp một cách để làm điều này với 18. Tham số này có thể lấy một nguồn gốc hoặc một danh sách các nguồn gốc (một mảng URL) khi khởi tạo WebSocket ở phía máy chủBạn cũng có thể đặt đối số này thành 19 để cho phép tất cả các nguồn gốc hoặc thành 30 để chặn tất cả các nguồn gốc 7Bạn cũng có thể muốn ngăn các kết nối WebSocket từ các nguồn không phải của bạn để ngăn chặn các cuộc tấn công chiếm quyền điều khiển WebSocket trên nhiều trang web (CSWSH). Kiểu tấn công này là một biến thể của các cuộc tấn công CSRF và cho phép giao tiếp đọc/ghi qua WebSockets Tại đây, kẻ tấn công có thể tạo một trang web độc hại trên miền của chúng và thiết lập kết nối đến ổ cắm máy chủ được ngụy trang thành người dùng. Sau đó, ứng dụng độc hại có thể đọc tin nhắn mà máy chủ gửi và ghi trực tiếp vào máy chủ Lưu ý rằng một số ứng dụng khách không có trình duyệt có thể dễ dàng đặt tiêu đề Gốc. Do đó, hãy đảm bảo rằng bạn bổ sung phương pháp này bằng các hình thức xác thực ứng dụng khách khác Xác thực máy khách WebSocket trước khi kết nốiKhi web phát triển về quy mô và độ phức tạp, bản chất của các cuộc tấn công mạng cũng vậy. Hệ thống xác thực là một trong những cách hiệu quả nhất để ngăn chặn hành vi trộm cắp dữ liệu và đảm bảo quyền riêng tư trong giao tiếp giữa máy khách và máy chủ Hệ thống xác thực người dùng hoạt động như một rào cản giữa máy khách và máy chủ. Bất kỳ người dùng nào muốn truy cập tài nguyên trên máy chủ trước tiên phải cung cấp thông tin nhận dạng duy nhất trong yêu cầu đăng nhập — thường là tên người dùng và mật khẩu. Máy chủ sẽ xác minh người dùng và phê duyệt hoặc từ chối yêu cầu đăng nhập với thông tin này. Trong trường hợp máy chủ từ chối yêu cầu, nó sẽ hiển thị cho người dùng biết lỗi gì, ví dụ: “Thông tin đăng nhập của bạn không chính xác”. Điều này giúp đảm bảo rằng tài nguyên không rơi vào tay kẻ xấu Người dùng có thể tạo mật khẩu mạnh và sử dụng công cụ quản lý mật khẩu để cải thiện bảo mật xác thực. Tuy nhiên, các bước này đều phụ thuộc vào người dùng. Đây là một lý do quan trọng khác để triển khai các hệ thống xác thực mạnh mẽ ở phía máy chủ của ứng dụng Đối với phía máy chủ, có nhiều thư viện xác thực có sẵn. Lựa chọn của bạn phụ thuộc vào khung phía máy chủ mà bạn sử dụng để xây dựng ứng dụng. Đối với ví dụ về WebSocket của chúng tôi, bạn có thể tạo tệp 31 trong thư mục 32 để hiển thị biểu mẫu HTML trong trình duyệt. Sau đó, người dùng có thể cung cấp tên người dùng và mật khẩu của họSau đó, bạn sẽ đợi một sự kiện 33 bên trong tập lệnh máy khách, 34. Khi người dùng gửi biểu mẫu đăng nhập, sau đó bạn sẽ khởi tạo kết nối WebSocket giữa máy khách và máy chủ, gửi tên người dùng và mật khẩu được cung cấp dưới dạng 35 3Cấu hình trên truy xuất các giá trị tên người dùng và mật khẩu từ đầu vào dựa trên thuộc tính 29 của chúng, mã hóa chúng dưới dạng tiêu đề HTTP và vận chuyển chúng đến máy chủ WebSocket sau khi máy khách kết nối. Để xác thực người dùng trong mã máy chủ, 0, chúng tôi sẽ truy xuất tên người dùng và mật khẩu từ 38 7Tại đây, chúng tôi lấy tên người dùng và mật khẩu và thực hiện kiểm tra thử xem có dữ liệu xác thực hay không. Nếu thông tin đăng nhập không tồn tại, người dùng đã không gửi chúng và chúng tôi trả lại 39. Trong trường hợp này, chúng tôi không thể xác thực người dùngNếu không, chúng tôi tiến hành xác thực người dùng. Thông thường, bạn sẽ kiểm tra xem tên người dùng có tồn tại trong cơ sở dữ liệu hay không và sau đó sử dụng nó để truy xuất nội dung dành riêng cho người dùng. Sau đó, bạn sẽ tạo một phiên người dùng và gửi thông báo 00 tới máy khách, sử dụng JavaScript trong mã máy khách để hiển thị nội dung này cho người dùng. Nếu không xác thực WebSockets, bất kỳ ai cũng có thể kết nối với máy chủ và lấy cắp dữ liệu nhạy cảm. Lưu ý rằng khi người dùng đã được xác thực và đăng nhập, việc xác thực tiếp theo sẽ được thực hiện bằng cách sử dụng mã thông báo thay vì yêu cầu người dùng nhập lại tên người dùng và mật khẩu Ngoài ra, bạn nên cẩn thận khi xử lý dữ liệu được gửi từ máy khách. Đảm bảo xác thực mọi thông tin đầu vào của khách hàng trước khi xử lý. Một cuộc tấn công như SQL injection có thể được thực hiện trên WebSockets, giống như trong các kết nối HTTP truyền thống. Sử dụng giới hạn tốc độ để bảo vệ máy chủ WebSocket của bạn khỏi các cuộc tấn côngGiới hạn tốc độ là một kỹ thuật bảo vệ chống lại các cuộc tấn công từ chối dịch vụ (DoS) và từ chối dịch vụ phân tán (DDoS). Trong các cuộc tấn công này, kẻ tấn công sẽ cố gắng áp đảo — hoặc thậm chí làm sập — một dịch vụ bằng cách thực hiện quá nhiều cuộc gọi lặp lại khiến dịch vụ không khả dụng đối với người dùng hợp pháp Giới hạn tốc độ ngăn chặn các cuộc tấn công này bằng cách giới hạn tần suất yêu cầu API mà mỗi người dùng có thể thực hiện. Chúng tôi có thể thực thi giới hạn này dựa trên các khóa giới hạn như địa chỉ IP, khóa API hoặc mã định danh duy nhất khác, chẳng hạn như 01. Giới hạn tỷ lệ và phân bổ hoặc hạn ngạch, chỉ định số lượng yêu cầu mà khách hàng có thể thực hiện đối với API trong một khung thời gian cụ thể. Nhà cung cấp dịch vụ thường áp dụng phương pháp này để đảm bảo sử dụng hợp lý các dịch vụ và tài nguyên dựa trên API Việc thực thi giới hạn tốc độ trên máy chủ của bạn yêu cầu trước tiên bạn phải biết lý do cần thiết — để bảo vệ dịch vụ, đặt hạn ngạch cho các gói khác nhau, v.v. Tiếp theo, bạn cần xác định và chọn khóa giới hạn phù hợp nhất cho trường hợp của mình. Sau đó, bạn sử dụng triển khai giới hạn để theo dõi việc sử dụng API dựa trên khóa bạn đã chọn Mặc dù hiện tại không có gói giới hạn tốc độ dành riêng cho python-socketio, nhưng có một giải pháp bạn có thể thực hiện với một chút công việc Hạn chế kích thước tải trọng để bảo vệ máy chủ WebSocket của bạnGửi một tải trọng lớn trong WebSockets rất có thể sẽ làm giảm hiệu suất — và cuối cùng làm sập máy chủ socket Để tránh làm chậm hoặc hỏng WebSocket, bạn có thể muốn giới hạn kích thước tải trọng tối đa cho các thư được gửi qua kết nối WebSocket. Điều này sẽ giúp bạn tránh làm hỏng máy chủ bằng cách gửi một tin nhắn quá khổ (như đánh bom zip). Ngoài ra, việc điều chỉnh kích thước thư giúp giảm đáng kể độ trễ trong kết nối WebSocket và có thể cải thiện đáng kể tốc độ truyền. Giao thức WebSocket giới hạn kích thước của khung và giúp xác định mức độ nén mà thông báo cần. tin nhắn được nén. Nén luồng tin nhắn có thể tiêu tốn tài nguyên bộ nhớ và CPU, nhưng thường đáng làm vì nó có thể giảm đáng kể lưu lượng mạng. Sử dụng TLS để tạo giao tiếp ổ cắm an toànSử dụng TLS/SSL là điều cần thiết để triển khai một trang web lên Internet. Không có nó, thông tin nhạy cảm được vận chuyển giữa máy khách và máy chủ có thể dễ dàng bị đánh cắp thông qua một cuộc tấn công trung gian. Để đảm bảo vận chuyển, bạn nên sử dụng một giao thức an toàn như https. // thay vì http không an toàn. // giao thức Đối với WebSockets, bạn nên sử dụng wss. // Giao thức (WebSockets được mã hóa TLS) thay vì giao thức ws không an toàn. // giao thức. Sử dụng phương pháp thứ hai khiến kết nối dễ bị can thiệp bởi bên thứ ba. Ngược lại, wss. // giao thức mã hóa tất cả dữ liệu được gửi trong WebSocket Với mã hóa này, không bên thứ ba nào có thể đọc hoặc sửa đổi tin nhắn được gửi qua WebSocket, do đó bảo mật thông tin nhạy cảm. Các kiểu tấn công khác cũng trở nên bất khả thi nếu kết nối được bảo mật Ngoài ra, trước khi thiết lập kết nối WebSocket với máy chủ, hãy đảm bảo rằng trang web yêu cầu cũng sử dụng https. // — không có nó, các tác nhân độc hại có thể dễ dàng can thiệp vào các yêu cầu TLS là cần thiết cho bất kỳ trang web nào có hoặc không có WebSockets. May mắn thay, nhiều dịch vụ lưu trữ cung cấp TLS miễn phí khi triển khai ứng dụng. Một số nền tảng lưu trữ phổ biến nhất cho ứng dụng Python là Google Cloud, AWS, Azure, Heroku và Fly. io Tóm tắt WebSocketTrong hướng dẫn này, chúng tôi đã tạo một máy chủ WebSocket cơ bản bằng python-socketio và kết nối nó với một máy khách JavaScript. Chúng tôi cũng đã tìm hiểu cách thức hoạt động của WebSockets và thảo luận về một số lưu ý về bảo mật để đảm bảo bạn đang sử dụng chúng một cách an toàn. Giống như nhiều giao thức web khác, WebSockets dựa trên các biện pháp tương tự (TLS, CORS, giới hạn tốc độ, v.v. ) để bảo mật thông tin liên lạc đúng cách. Không có điều nào trong số này là dành riêng cho WebSockets, tuy nhiên, hiểu chúng là điều cần thiết để tránh các vấn đề bảo mật không cần thiết Thảo luận về blog này trên DiscordTham gia Cộng đồng DevSecOps trên Discord để thảo luận về chủ đề này và hơn thế nữa với các học viên tập trung vào bảo mật khác Làm cách nào để viết mã WebSocket bằng Python?Ứng dụng khách WebSocket với Python
. py” và nhập các gói như chúng ta đã làm trong mã máy chủ Create a new File “client.py” and import the packages as we did in our server code . Bây giờ, hãy tạo một hàm không đồng bộ Python (còn gọi là coroutine). kiểm tra xác định không đồng bộ (). Chúng tôi sẽ sử dụng chức năng kết nối từ mô-đun WebSockets để xây dựng kết nối máy khách WebSocket.
WebSocket hoạt động như thế nào?WebSocket sử dụng kết nối TCP hợp nhất và cần một bên chấm dứt kết nối . Cho đến khi nó xảy ra, kết nối vẫn hoạt động. HTTP cần xây dựng một kết nối riêng biệt cho các yêu cầu riêng biệt. Khi yêu cầu được hoàn thành, kết nối sẽ tự động ngắt.
Làm cách nào để lấy dữ liệu từ WebSocket Python?Đang kết nối với máy chủ websocket . Tạo một tệp Python mới có tên websocket_test. py và kết nối với Mười hai máy chủ Dữ liệu bằng thư viện trình bao bọc. # websocket_test. py. . Bây giờ hãy chạy tập lệnh Python. . Sau khi chạy tập lệnh, bạn ngay lập tức nhận được phản hồi từ máy chủ về trạng thái kết nối của mình WebSocket đẩy hay kéo?Vì gần đây các trình duyệt hỗ trợ cái được gọi là TCP/IP WebSockets. Điều này cho phép máy chủ đẩy dữ liệu trực tiếp đến trình duyệt thông qua một kết nối luôn mở . |