Điểm:2

Gỡ lỗi tiêu đề "UNCACHEABLE"

lá cờ in

Chúng tôi có một trang web mà trang chủ không được lưu trong bộ nhớ cache và chứa các tiêu đề:

x-cache: BỎ LỠ, BỎ LỠ
x-cache-hit: 0, 0
tùy chọn loại nội dung x: nosniff
x-drupal-dynamic-cache: UNCACHEABLE

Tôi đã thu hẹp nội dung này xuống nội dung của vùng nội dung và tắt "Nội dung trang chính" cho trang nhất. Điều này sau đó đã cho tôi một HIT bộ đệm và không còn phản hồi là KHÔNG THỂ GỬI ĐƯỢC nữa.Từ đó, tôi thu hẹp nó xuống thành một bộ định dạng trường đang được sử dụng trên một đoạn văn. Chúng tôi có một tùy chỉnh mở rộng trình định dạng kết xuất thực thể thông thường.

Nếu tôi trao đổi nó trở lại trình định dạng "Thực thể kết xuất" ban đầu, thì mọi thứ đều ổn. Vì vậy, đó phải là điều chúng tôi đang làm trong trình định dạng tùy chỉnh này gây ra sự cố.

Tôi có thể thấy khi tôi làm theo xdebug rằng shouldCacheResponse của DynamicPageCacheSubscriber trả về SAI, bởi vì có thứ gì đó đang đặt tuổi tối đa thành 0 (không phải theo mã). Có vẻ như lệnh gọi addCacheableDependency có thể kích hoạt hành vi này trong trình định dạng:

Về cơ bản, trình định dạng thêm dữ liệu bộ đệm vào kết xuất, vì vậy nếu bất kỳ mục nào trong số các mục được tham chiếu của nó được cập nhật, bộ đệm sẽ bị vô hiệu hóa cho đoạn máy chủ đó để nó kết xuất lại:

     $view_builder = \Drupal::entityTypeManager()->getViewBuilder($entity->getEntityTypeId());
      $elements[$delta] = $view_builder->view($entity, $view_mode, $entity->language()->getId());

      cố gắng {
        $parent = $items->getParent();
        $parent_entity = $parent->getValue();
        $elements[$delta]['#cache']['keys'][] = $parent_entity->id();
        $elements[$delta]['#cache']['keys'][] = $parent_entity->bundle();
        $elements[$delta]['#cache']['keys'][] = $parent_entity->getEntityTypeId();
        $elements[$delta]['#cache']['keys'][] = 'delta_' . $đồng bằng;
        $elements[$delta]['#cache']['keys'][] = 'context_aware';

        $this->renderer->addCacheableDependency($elements[$delta], $parent);

        if ($entity->hasField('field_author')) {
          $child = $entity->field_author->entity;

          if (isset($child)) {
            $this->renderer->addCacheableDependency($elements[$delta], $child);
          }
        }

        // câu lệnh tương tự với addCacheableDependency

Nếu tôi nhận xét dòng đầu tiên này:

$this->renderer->addCacheableDependency($elements[$delta], $parent);

Sau đó, tôi nhận được phản hồi có thể lưu vào bộ nhớ cache.Điều này có vẻ là do mục $parent (mặc dù nó là một nút hoặc đoạn hoặc thực thể phương tiện) kích hoạt điều này:

  /**
   * Tạo một đối tượng CacheableMetadata từ một đối tượng phụ thuộc.
   *
   * @param \Drupal\Core\Cache\CacheableDependencyInterface|đối tượng $ hỗn hợp
   * Đối tượng có siêu dữ liệu khả năng lưu vào bộ nhớ cache để truy xuất. Nếu nó thực hiện
   * CacheableDependencyInterface, siêu dữ liệu về khả năng lưu vào bộ nhớ đệm của nó sẽ được sử dụng,
   * mặt khác, đối tượng được truyền vào phải được coi là không thể lưu vào bộ đệm, vì vậy
   * tuổi tối đa 0 được đặt.
   *
   * @return tĩnh
   */
  hàm tĩnh công cộng createFromObject($object) {
    if ($object instanceof CacheableDependencyInterface) {
      $meta = tĩnh mới();
      $meta->cacheContexts = $object->getCacheContexts();
      $meta->cacheTags = $object->getCacheTags();
      $meta->cacheMaxAge = $object->getCacheMaxAge();
      trả về $meta;
    }

    // Các đối tượng không triển khai CacheableDependencyInterface phải được giả định
    // không thể truy cập vào bộ đệm, vì vậy hãy đặt tuổi tối đa là 0.
    $meta = tĩnh mới();
    $meta->cacheMaxAge = 0;
    trả về $meta;
  }

Đặt cacheMaxAge thành 0 vì đây không phải là phiên bản của CacheableDependencyInterface.

Nếu tôi đã đặt các khóa bộ đệm, thì dòng này có cần thiết không:

$this->renderer->addCacheableDependency($elements[$delta], $parent);

Nếu tôi xóa nó, liệu có tác dụng phụ nào không (chẳng hạn như hiển thị kết xuất không hiển thị lại khi các mục được tham chiếu được lưu)?

4uk4 avatar
lá cờ cn
Đặt các khóa bộ đệm là không đủ, bạn cũng cần các thẻ bộ đệm. Vì vậy, đừng xóa dòng này, chỉ cần kiểm tra đối tượng không phải là NULL.
sonfd avatar
lá cờ in
Vâng, các khóa bộ nhớ cache không thực sự làm bất cứ điều gì - bối cảnh, thẻ và tuổi tối đa là những gì bạn muốn đảm bảo chuyển sang.
Kevin avatar
lá cờ in
$parent không phải là null, nhưng được nhận trong createFromObject như một phiên bản của EntityAdapter (chứa nút thực thể hoặc đoạn văn) mà tôi không thể theo dõi khi triển khai CacheableDependencyInterface
4uk4 avatar
lá cờ cn
OK, bây giờ tôi đã hiểu vấn đề, thực thể có dữ liệu bộ đệm là `$parent_entity`.
Kevin avatar
lá cờ in
Đó là những gì tôi nghi ngờ, cảm ơn vì đã xác nhận. Việc thay đổi đó sẽ trả về phản hồi có thể lưu trong bộ nhớ cache cho trình duyệt.
Điểm:4
lá cờ in

Đây là một lặn sâu gỡ lỗi tốt. Như 4k4 đã đề cập, vấn đề là lần đầu tiên addCacheableDependency dòng.

Thay vì chuyển chính thực thể máy chủ, tôi đã chuyển nhầm đối tượng được trả về từ getParent mà là một Đã nhập dữ liệu trường hợp không thực hiện Cacheable DependencyGiao diện - do đó khiến độ tuổi tối đa được đặt thành 0 và KHÔNG THỂ LƯU TRỮ kết quả tiêu đề.

Truyền thực thể (được trả về từ getValue()) đã giải quyết vấn đề:

    $parent = $items->getParent();
    $parent_entity = $parent->getValue();
    ...
    $this->renderer->addCacheableDependency($elements[$delta], $parent_entity);

Đăng câu trả lời

Hầu hết mọi người không hiểu rằng việc đặt nhiều câu hỏi sẽ mở ra cơ hội học hỏi và cải thiện mối quan hệ giữa các cá nhân. Ví dụ, trong các nghiên cứu của Alison, mặc dù mọi người có thể nhớ chính xác có bao nhiêu câu hỏi đã được đặt ra trong các cuộc trò chuyện của họ, nhưng họ không trực giác nhận ra mối liên hệ giữa câu hỏi và sự yêu thích. Qua bốn nghiên cứu, trong đó những người tham gia tự tham gia vào các cuộc trò chuyện hoặc đọc bản ghi lại các cuộc trò chuyện của người khác, mọi người có xu hướng không nhận ra rằng việc đặt câu hỏi sẽ ảnh hưởng—hoặc đã ảnh hưởng—mức độ thân thiện giữa những người đối thoại.