Cloudflare Blog
85

Sản phẩm

Cloudflare Workers RPC: Kết nối linh hoạt giữa Python và JavaScript

(giờ Việt Nam)

Tóm tắt AI

Tính năng mới cho phép các Worker viết bằng Python và JavaScript giao tiếp trực tiếp, gọi hàm và chia sẻ đối tượng mà không cần định nghĩa API hay cấu trúc dữ liệu phức tạp.

Bản dịch AI

Workers RPC now works across Python and JavaScript

Hai năm trước, chúng tôi đã giới thiệu Workers RPC, được xây dựng dựa trên Cap’n Proto RPC. Điều này cho phép các Worker gọi các Worker khác và các phương thức của Durable Objects, trả về các đối tượng trực tiếp (live objects) và gọi các phương thức của chúng, trả về các hàm, luồng và nhận được tất cả những lợi ích của hệ thống Remote Procedure Call (RPC) mà không cần định nghĩa schema hay thêm bất kỳ phụ thuộc nào. Chúng tôi gọi đó là “JavaScript-native RPC” vì nó giúp việc sử dụng RPC mang lại cảm giác tự nhiên như chính ngôn ngữ này vậy.

Năm ngoái, chúng tôi đã hiện thực hóa điều này giữa trình duyệt web và máy chủ, đồng thời giới thiệu Cap’n Web.

Giờ đây, chúng tôi đang mở rộng nó sang đa ngôn ngữ.

Thông thường, việc để các chương trình được viết bằng những ngôn ngữ khác nhau giao tiếp với nhau rất phức tạp: các nhà phát triển thường phải xây dựng API tùy chỉnh hoặc áp dụng các định dạng tuần tự hóa bất kể ngôn ngữ như protobuf để hai hệ thống có thể hiểu nhau. Hệ thống RPC được tích hợp trong Workers có khả năng chuyển đổi giữa JavaScript và Python mà không cần thêm bất kỳ thao tác nào.

Giờ đây, bạn có thể gọi các phương thức được định nghĩa trong một Python Worker từ một JavaScript Worker và ngược lại. Bạn có thể chia sẻ các đối tượng giữa Python và JavaScript, đồng thời gọi các phương thức trên một đối tượng Python từ TypeScript. Mọi thứ đều hoạt động trơn tru.

Nếu bạn định nghĩa một phương thức add trong một Worker được viết bằng TypeScript:

…bạn có thể gọi nó một cách đơn giản từ Python:

Không cần bất kỳ phụ thuộc nào. Tất cả những gì bạn cần cấu hình là một Service binding:

Vậy, bạn có thể làm gì với nó?

Hệ thống RPC này cho phép bạn xây dựng một hệ thống đa ngôn ngữ phức tạp như thể bạn đang sử dụng một thư viện. Dưới đây là một số tính năng của RPC đa ngôn ngữ.

Nhưng khoan đã, làm thế nào để bạn chuyển đổi kiểu dữ liệu giữa các ngôn ngữ?

Rào cản chính để tạo ra RPC liền mạch giữa các JavaScript Worker và Python Worker là việc kết nối các hệ thống kiểu dữ liệu riêng biệt của chúng. Các nhà phát triển JavaScript mong đợi làm việc với các kiểu dữ liệu JavaScript gốc, và các nhà phát triển Python cũng mong đợi điều tương tự đối với Python. Việc kết nối hai ngôn ngữ riêng biệt với hệ thống kiểu dữ liệu riêng đòi hỏi một chiến lược chuyển đổi kiểu dữ liệu cẩn thận và có tính toán.

Hãy xem xét cách mỗi ngôn ngữ xử lý các đối số của hàm. Một cách điển hình để định nghĩa một hàm phức tạp trong JavaScript là truyền một Object làm đối số:

Ngược lại, một nhà phát triển Python thường sẽ định nghĩa cùng một hàm đó bằng cách sử dụng các đối số từ khóa (keyword arguments):

Mục tiêu của chúng tôi là làm cho RPC đa ngôn ngữ trở nên hoàn toàn trong suốt. Các nhà phát triển sẽ có cảm giác như họ đang viết mã cho một ứng dụng đơn ngôn ngữ mà không cần lo lắng về lớp chuyển đổi bên dưới. Chúng tôi đạt được điều này bằng cách kết hợp Foreign Function Interface (FFI) của Pyodide với một lớp chuyển đổi kiểu dữ liệu tùy chỉnh dành cho các Python Worker.

Pyodide FFI đã thực hiện việc chuyển đổi giữa các kiểu dữ liệu Python và JavaScript

Pyodide là trình thông dịch CPython được biên dịch sang WebAssembly, và nó đã hỗ trợ các Python Worker ngay từ đầu. Nó bao gồm một FFI mạnh mẽ giúp tự động chuyển đổi các kiểu dữ liệu giữa JavaScript và Python.

Khi một Python Worker giao tiếp với một JavaScript Worker thông qua Service bindings, FFI của Pyodide sẽ chuyển đổi các đối tượng một cách trong suốt trong quá trình gọi RPC. Các nhà phát triển ở cả hai phía không cần biết Worker kia được viết bằng ngôn ngữ nào, và mọi thứ đều được xử lý ở phía sau.

Pyodide ánh xạ các kiểu dữ liệu gốc giữa cả hai môi trường một cách mặc định:

Kiểu dữ liệu Python

Kiểu dữ liệu tương đương trong JavaScript

int, float

Number

bool

Boolean

dict

Object

list

Array

Khi không thể chuyển đổi trực tiếp (chẳng hạn như với các lớp hoặc hàm tùy chỉnh), Pyodide sẽ tạo ra một đối tượng Proxy. Proxy này chuyển tiếp các truy cập thuộc tính và các lệnh gọi phương thức qua ranh giới, cho phép các mô hình như truyền trực tiếp một hàm Python làm callback cho các trình xử lý JavaScript.

Pyodide FFI cũng ánh xạ các đối số từ khóa của Python trực tiếp sang các tham số kiểu đối tượng của JavaScript. Ví dụ, hãy tưởng tượng một JavaScript Worker có một phương thức nhận một đối tượng tùy chọn (options object):

Khi gọi JavaScript Worker này từ Python, bạn có thể truyền một từ điển (dictionary) Python để đại diện cho đối tượng JavaScript:

Tuy nhiên, bạn cũng có thể sử dụng các đối số từ khóa gốc của Python:

Pyodide FFI chuyển đổi cả hai lệnh gọi thành cấu trúc chính xác mà JavaScript Worker mong đợi, mang lại cho các nhà phát triển Python trải nghiệm API sạch sẽ và tự nhiên.

Để khám phá chi tiết hơn về việc chuyển đổi kiểu dữ liệu, hãy xem tài liệu của Pyodide.

Xử lý các đối tượng Cloudflare Workers

Mặc dù Pyodide FFI chuyển đổi liền mạch các kiểu dữ liệu tích hợp tiêu chuẩn, nhưng nó không tự động hiểu các đối tượng Web API như Request, Response, Blob hoặc File. Chúng thường được sử dụng trong Cloudflare Workers, nhưng không có kiểu dữ liệu tương đương trực tiếp nào trong Python.

Như đã giải thích trong phần trước, theo mặc định, Pyodide coi các đối tượng không tiêu chuẩn này là các JavaScript Proxy. Thay vì chuyển đổi chúng thành các đối tượng Python, nó tạo ra một proxy chuyển tiếp cho các truy vấn thuộc tính và lệnh gọi phương thức. Mặc dù có thể hoạt động, cách tiếp cận này làm lộ các chi tiết triển khai JavaScript bên dưới vào Python. Các nhà phát triển Python sẽ phải liên tục ghi nhớ rằng họ đang tương tác với các proxy JavaScript, gây thêm gánh nặng tâm lý không cần thiết.

Để khắc phục điều này, chúng tôi đã giới thiệu gói Python `workers-runtime-sdk`. Nó đóng vai trò như một lớp chuyển đổi mỏng được xây dựng đặc biệt để xử lý các kiểu dữ liệu Workers tùy chỉnh thông qua RPC. Khi bạn triển khai một Python Worker bằng `uv run pywrangler deploy`, gói này sẽ được bao gồm theo mặc định. Trên thực tế, nếu bạn import từ namespace `workers`, bạn đã và đang sử dụng nó rồi:

CloudflareWorkersPythonJavaScriptLập trình
Đọc bài gốc

Bài viết được AI dịch và tổng hợp tự động từ Cloudflare Blog. Liên kết bài gốc ở phía trên. AIHOT.vn luôn dẫn nguồn đầy đủ — nếu bạn thấy điểm cần chỉnh sửa, hãy gửi ý kiến tại trang phản hồi.