Điều kiện cuộc đua Ajax


8

Có một mô hình hoặc cách tiêu chuẩn để xử lý các điều kiện cuộc đua Ajax không? Lấy ví dụ sau. Bạn có hai bảng. Nhấp vào một hàng trên bảng 1 sẽ xóa dữ liệu khỏi DB và sau đó cập nhật bảng 2 (hiện sẽ hiển thị tất cả các hàng của bảng 1 trừ hàng được nhấp).

Nếu ai đó nhấp vào một loạt các hàng liên tiếp, bạn có thể nhận được một kịch bản trong đó bảng 2 không cập nhật cho tất cả các lần nhấp làm cho các vấn đề về thời gian / độ trễ.

Điều gì có thể là một cách tốt để tiếp cận điều này? Tôi đã nghĩ đến việc sử dụng một hàng đợi có thể nhưng loại đó đánh bại mục đích làm nó không đồng bộ. Tuy nhiên tôi vẫn có lợi ích của UI không bị khóa.


AJAX và cơ sở dữ liệu? Làm thế nào để hai người đến với nhau trong này?
Oded

vâng tôi là loại mơ hồ. Đây là một ứng dụng web với dữ liệu được gửi / truy xuất thông qua ajax cụ thể hơn là jQuery.get / post.
Ominus

Câu trả lời:


8

Chỉ cần một suy nghĩ, có lẽ bạn có thể tạo một danh sách cho các phương thức gọi lại Ajax của bạn. Bạn sẽ bọc cuộc gọi lại Ajax thực tế của mình theo phương thức thêm cuộc gọi lại đó vào một vị trí trong danh sách.

Danh sách này chờ các cuộc gọi lại theo một thứ tự cụ thể và chỉ thực hiện nếu phần tử trên cùng (cuộc gọi lại mà bạn muốn gọi đầu tiên) được điền.


1
Lập trình lồng nhau các cuộc gọi lại là một giải pháp vững chắc.
Sam

7

Đây không phải là một điều kiện chủng tộc.

Một điều kiện cuộc đua sẽ xảy ra khi hành vi giữa hai luồng không đồng bộ trở nên không xác định. Bạn có thể giải quyết vấn đề này bằng cách lồng cuộc gọi lại từ cuộc gọi đầu tiên


6
Không phải tất cả các cuộc gọi AJAX sẽ hoàn thành ở cùng một tốc độ do các trục trặc mạng có thể xảy ra. Chúng tôi thấy nó ngay cả khi đang phát triển trên mạng cục bộ của mình, nơi cuộc gọi AJAX sau đó sẽ kết thúc trước cuộc gọi trước đó và giao diện người dùng kết thúc sai. Các cuộc gọi lại lồng / xếp hàng sẽ giải quyết nó, nhưng đây một điều kiện cuộc đua.
Izkata

1
@Izkata Điều này không chính xác, Javascript không có điều kiện chủng tộc vì nó chạy trên một luồng duy nhất. Tình huống bạn mô tả gần giống với việc chạy hai chức năng cùng một lúc, một để mở tệp và một để đọc nội dung của tệp đã mở. Hàm mở tệp phải chạy trước hàm đọc, nhưng thực thi cả hai cùng một lúc có nghĩa là đôi khi hàm thứ hai sẽ chạy trước. Đây không phải là một điều kiện chủng tộc, nó không đặt hàng đúng cách. Câu trả lời chính xác cho Javascript trong năm 2017 là sử dụng Promise.then()để chạy các cuộc gọi lại async theo đúng thứ tự.
Daniel T.

1
@Izkata Đây không phải là một điều kiện cuộc đua, đó là một vấn đề đặt hàng. Bản thân yêu cầu được xử lý tự nhiên bởi trình duyệt, nhưng cuộc gọi lại chạy trong luồng JS. Điều kiện cuộc đua được gây ra khi hai luồng chạy cùng lúc chia sẻ cùng một tài nguyên và đọc / ghi vào tài nguyên cùng một lúc, dẫn đến đầu ra không xác định. Nếu bạn có hai yêu cầu AJAX đồng thời, đầu ra là xác định; đó là kết quả của cuộc gọi lại A hoặc cuộc gọi lại B. Điều bạn không biết là thứ tự mà cuộc gọi lại sẽ được gọi. Điều này không khác gì việc cung cấp hai nút cho người dùng và
Daniel T.

1
không biết nút nào người dùng sẽ nhấp vào đầu tiên. Kết quả sẽ là cuộc gọi lại cho nút A hoặc cuộc gọi lại cho nút B, nhưng không bao giờ là một đầu ra không thể đoán trước, không xác định. Nếu bạn cần kiểm soát thứ tự gọi lại được gọi, thì bạn cần sử dụng lời hứa. Nhưng thời gian gọi lại không thể đoán trước không giống như điều kiện cuộc đua.
Daniel T.

1
@Izkata Một "kết quả không mong muốn" trong điều kiện cuộc đua có nghĩa là một hàm không mang tính quyết định, điều gì đó không xảy ra trong JS vì chính xác những gì bạn đã nói: "khi bất kỳ hành vi đồng thời nào cũng có thể gây ra kết quả không mong muốn". Từ khóa ở đây là đồng thời; Yêu cầu AJAX đồng thời, các cuộc gọi lại thì không. Do đó, kết quả của các hàm gọi lại trong JS luôn mang tính xác định vì chúng được thực hiện tuần tự, không bao giờ đồng thời. Bài đăng này rất hay đọc: blog.raananweber.com/2015/06/17/ Kẻ
Daniel T.

6

Nói chung, các cuộc gọi lại là công cụ phổ biến để xử lý các tác vụ không đồng bộ và thực sự các cuộc gọi lại là cơ chế để xử lý các yêu cầu AJAX trong JavaScript. Trong ngữ cảnh của cuộc gọi lại, bạn thậm chí có thể có tham chiếu đến hàng được nhấp (nếu đóng trong đóng). Bạn có thể tìm thấy các bài viết sau hữu ích: jQuery hoãn lạiSử dụng Trì hoãn trong jQuery

Một điều khác mà bạn nên có, nếu người dùng được phép nhấp vào nhiều nút, đó là nhiều yêu cầu sẽ được bắt đầu. Tuy nhiên, các trình duyệt khác nhau có thể xử lý đồng thời số lượng yêu cầu AJAX khác nhau: đồng thời-ajax-xmlhttprequest-request . Để khắc phục điều này, bạn nên thực hiện một số hàng đợi yêu cầu cơ bản.


+1 vì là người duy nhất nói về công cụ hoãn lại.
Florian Margaine
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.