Chương 10: Các Ràng Buộc

The previous chapter introduced the ability to add some business logic to our model. We can now link buttons to business code, but how can we prevent users from entering incorrect data? For example, in our real estate module nothing prevents users from setting a negative expected price.

SoOn cung cấp hai cách để thiết lập các bất biến được xác minh tự động: Ràng buộc PythonRàng buộc SQL.

SQL

Tham khảo: tài liệu liên quan đến chủ đề này có thể được tìm thấy trong Người mẫu và trong tài liệu của PostgreSQL.

Ghi chú

Mục tiêu: ở cuối phần này:

  • Số tiền phải (nghiêm ngặt) dương

Hạn chế về số lượng
  • Các loại thuộc tính và thẻ phải có tên duy nhất

Hạn chế về tên

Các ràng buộc SQL được xác định thông qua thuộc tính mô hình _sql_constraints. Thuộc tính này được gán một danh sách các bộ ba chứa các chuỗi (name, sql_def định, message), trong đó name là tên ràng buộc SQL hợp lệ, sql_def định là biểu thức table_constraintmessage là thông báo lỗi.

Bạn có thể tìm thấy một ví dụ đơn giản tại đây.

Exercise

Thêm các ràng buộc SQL.

Thêm các ràng buộc sau vào các mô hình tương ứng của chúng:

  • Giá kỳ vọng của tài sản phải hoàn toàn dương

  • Giá bán bất động sản phải dương

  • Giá chào bán phải hoàn toàn tích cực

  • Tên thẻ thuộc tính và tên loại thuộc tính phải là duy nhất

Mẹo: tìm kiếm từ khóa duy nhất trong cơ sở mã SoOn để biết ví dụ về các tên duy nhất.

Khởi động lại máy chủ với tùy chọn -u Estate để xem kết quả. Lưu ý rằng bạn có thể có dữ liệu ngăn cản việc đặt ràng buộc SQL. Một thông báo lỗi tương tự như sau có thể bật lên:

ERROR rd-demo odoo.schema: Table 'estate_property_offer': unable to add constraint 'estate_property_offer_check_price' as CHECK(price > 0)

Ví dụ: nếu một số ưu đãi có giá bằng 0 thì không thể áp dụng ràng buộc. Bạn có thể xóa dữ liệu có vấn đề để áp dụng các ràng buộc mới.

Python

Tham khảo: tài liệu liên quan đến chủ đề này có thể được tìm thấy trong constrains().

Ghi chú

Mục tiêu: ở cuối phần này, sẽ không thể chấp nhận mức giá thấp hơn 90% giá dự kiến.

Ràng buộc Python

Ràng buộc SQL là một cách hiệu quả để đảm bảo tính nhất quán của dữ liệu. Tuy nhiên, có thể cần phải thực hiện các kiểm tra phức tạp hơn đòi hỏi phải có mã Python. Trong trường hợp này chúng ta cần một ràng buộc Python.

Ràng buộc Python được định nghĩa là một phương thức được trang trí bằng constrains() và được gọi trên một tập bản ghi. Trình trang trí chỉ định trường nào có liên quan đến ràng buộc. Ràng buộc được đánh giá tự động khi bất kỳ trường nào trong số này được sửa đổi. Phương thức này dự kiến sẽ đưa ra một ngoại lệ nếu tính bất biến của nó không được thỏa mãn:

from odoo.exceptions import ValidationError

...

@api.constrains('date_end')
def _check_date_end(self):
    for record in self:
        if record.date_end < fields.Date.today():
            raise ValidationError("The end date cannot be set in the past")
    # all records passed the test, don't return anything

Bạn có thể tìm thấy một ví dụ đơn giản tại đây.

Exercise

Thêm các ràng buộc Python.

Thêm một ràng buộc để giá bán không thể thấp hơn 90% giá dự kiến.

Mẹo: giá bán bằng 0 cho đến khi ưu đãi được xác thực. Bạn sẽ cần phải tinh chỉnh séc của mình để tính đến điều này.

Cảnh báo

Luôn sử dụng các phương thức float_compare()float_is_zero() từ odoo.tools.float_utils khi làm việc với float!

Đảm bảo ràng buộc được kích hoạt mỗi khi giá bán hoặc giá dự kiến thay đổi!

Ràng buộc SQL thường hiệu quả hơn ràng buộc Python. Khi hiệu suất quan trọng, hãy luôn ưu tiên SQL hơn các ràng buộc Python.

Our real estate module is starting to look good. We added some business logic, and now we make sure the data is consistent. However, the user interface is still a bit rough. Let's see how we can improve it in the next chapter.