Tôi đang duy trì một mô-đun mà tôi đã có một nhà phát triển bên thứ 3 xây dựng cho mình. Tôi D9 vấn đề này đã xuất hiện khi sử dụng mô-đun hoạt động trong D8 và phải tương thích với 8 & 9.
Mô-đun tạo các khối có ngày sự kiện được lấy từ dịch vụ Songkick nhưng trên các trang D9 có bật khối songkick sẽ gây ra lỗi này:
Drupal\Core\Security\UntrustedCallbackException: Kết xuất #pre_render
các cuộc gọi lại phải là các phương thức của một lớp thực hiện
\Drupal\Core\Security\TrustedCallbackInterface hoặc ẩn danh
chức năng. Cuộc gọi lại là _songkick_block_poweredby_prerender. Nhìn thấy
https://www.drupal.org/node/2966725 Trong
Drupal\Core\Render\Renderer->doTrustedCallback() (dòng 96 của
/var/www/html/web/core/lib/Drupal/Core/Security/DoTrustedCallbackTrait.php).
Tôi chỉ là một người xây dựng trang web với kinh nghiệm mã hóa hạn chế nên tôi đang tìm trợ giúp để khắc phục sự cố. Lỗi đề cập trang này giải thích vấn đề.
Mã bên dưới từ các tệp .module của tôi bao gồm pre_render được đề cập.
/**
* Triển khai hook_block_view_alter().
*/
hàm songkick_block_content_view_alter(mảng &$build) {
$id = $build['#block_content']->id();
$block = \Drupal\block_content\Entity\BlockContent::load($id);
$block_type = $block->type[0]->target_id;
if ($block_type == 'songkick_block') {
$build['#pre_render'][] = '_songkick_block_poweredby_prerender';
}
}
/**
* Nhận dữ liệu API sự kiện sắp tới và trong quá khứ.
*/
function _songkick_block_poweredby_prerender(mảng &$build) {
$id = $build['#block_content']->id();
$block = \Drupal\block_content\Entity\BlockContent::load($id);
$block_type = $block->type[0]->target_id;
if ($block_type == 'songkick_block') {
// Nhận dữ liệu Khối tùy chỉnh.
$artis_id = $block->field_artist_id[0]->value;
$upcoming_show = $block->field_display_upcoming_shows[0]->value;
$past_show = $block->field_display_past_shows[0]->value;
$event_details = $block->field_ticket_button[0]->value;
$sự_kiện_dữ_liệu = [
'event_details' => $event_details,
'upcoming_show' => $upcoming_show,
'past_show' => $past_show
];
$sự_kiện_dữ_liệu = [
'#theme' => 'songkick_events',
'#events_data' => $events_data
];
$client = \Drupal::httpClient();
$api_key = \Drupal::config('songkick.settings')->get('songkick_key');
$url = 'http://api.songkick.com/api/3.0/artists/';
// Dữ liệu sự kiện sắp tới.
if ($upcoming_show == '1') {
$apikey = $url . $artis_id. "/calendar.json" . "?apikey=". $api_key;
$request = $client->get($apikey);
$body = $request->getBody()->getContents();
$AllData = (mảng)json_decode($body);
// Dữ liệu trang cuối
$per_page = $AllData['resultsPage']->perPage;
$total_entry = $AllData['resultsPage']->totalEntries;
$page = (int)($total_entry / $per_page);
//$mainData = $AllData['resultsPage']->results->event;
$temp_var = [];
for ($x = $page; $x >= 0; $x--){
$final_api_key = $apikey . "&trang=" . $x;
$upcoming_event_request = $client->get($final_api_key);
$upcoming_event_body = $upcoming_event_request->getBody()->getContents();
$UpcomingEventAllData = json_decode($upcoming_event_body);
$mainData = array_reverse($UpcomingEventAllData->resultsPage->results->event);
//$temp_data[] = $mainData;
foreach ($mainData dưới dạng $value) {
$temp_var[] = $value;
}
}
$upcoming_events_data = [
'#theme' => 'songkick_events',
'#upcoming_event' => $temp_var
];
}
khác{
$upcoming_events_data = [
'#theme' => 'songkick_events',
'#sự kiện_sắp tới' => ''
];
}
// Dữ liệu sự kiện trong quá khứ.
nếu ($past_show == '1') {
$apikey = $url . $artis_id. "/gigography.json" . "?apikey=". $api_key;
$request = $client->get($apikey);
$body = $request->getBody()->getContents();
$AllData = (mảng)json_decode($body);
// Dữ liệu trang cuối
$per_page = $AllData['resultsPage']->perPage;
$total_entry = $AllData['resultsPage']->totalEntries;
$page = (int)($total_entry / $per_page);
$temp_var = [];
for ($x = $page; $x >= 0; $x--){
$final_api_key = $apikey . "&trang=" . $x;
$past_event_request = $client->get($final_api_key);
$past_event_body = $past_event_request->getBody()->getContents();
$PastEventAllData = json_decode($past_event_body);
$mainData = array_reverse($PastEventAllData->resultsPage->results->event);
//$temp_data[] = $mainData;
foreach ($mainData dưới dạng $value) {
$temp_var[] = $value;
}
}
//$final_api_key = $apikey . "&trang=" . trang $;
// $past_event_request = $client->get($final_api_key);
// $past_event_body = $past_event_request->getBody()->getContents();
// $PastEventAllData = (mảng)json_decode($past_event_body);
// $mainData = array_reverse($PastEventAllData['resultsPage']->results->event);
$past_events_data = [
'#theme' => 'songkick_events',
'#past_event' => $temp_var
];
}
khác{
$past_events_data = [
'#theme' => 'songkick_events',
'#sự_kiện_quá_khứ' => ''
];
}
// Hợp nhất dữ liệu sự kiện sắp tới và quá khứ.
$event_data = array_merge($upcoming_events_data,$past_events_data,$events_data);
// Trả về dữ liệu sự kiện.
trả lại dữ liệu sự kiện $;
}
}
Tôi đã thử làm theo hướng dẫn trong bình luận này và đã thêm một tệp có tên SongkickBlockPoweredByViewBuilder.php trong thư mục src với mã này:
<?php
không gian tên Drupal\Songkick;
sử dụng Drupal\Core\Security\TrustedCallbackInterface;
/**
* Cung cấp một cuộc gọi lại đáng tin cậy cho khối Songkick Poweredby.
*
*/
lớp SongkickBlockPoweredByViewBuilder triển khai TrustedCallbackInterface {
/**
* {@inheritdoc}
*/
hàm tĩnh công khai TrustedCallbacks() {
trả về ['kết xuất trước'];
}
/**
* Đặt Songkick - gọi lại #pre_render.
*/
hàm tĩnh công cộng preRender($build) {
$count = $build['content']['#count'];
$build['content']['#count_text'] = \Drupal::translation()->formatPlural($count, '(@count)', '(@count)');
trả lại bản dựng $;
}
}
Và tôi đã thêm phần sau vào tệp .module của mình:
sử dụng Drupal\Songkick\SongkickBlockPoweredByViewBuilder;
/**
* Triển khai TrustedCallbackInterface
*/
function _songkick_block_poweredby_prerender(mảng &$build, Drupal\Core\Block\BlockPluginInterface $block) {
$build['#pre_render'][] = [SongkickBlockPoweredByViewBuilder::class, 'preRender'];
}
Sau đó, trang web đưa ra lỗi nghiêm trọng này:
Lỗi nghiêm trọng: Không thể khai báo lại _songkick_block_poweredby_prerender()
(được khai báo trước đây trong
/var/www/html/web/modules/contrib/songkick/songkick.module:14) trong
/var/www/html/web/modules/contrib/songkick/songkick.module trên dòng 51
Lỗi nghiêm trọng sẽ biến mất nếu tôi xóa khai báo ở dòng 14, nhưng lỗi ban đầu vẫn tồn tại. Tôi không biết làm thế nào để xác định chức năng trong dòng 51 theo cách giải quyết vấn đề. Dòng 51 bắt đầu ngay sau nhận xét này trong đoạn trích trên từ tệp .module:
/*** Nhận dữ liệu API về các sự kiện sắp diễn ra và trước đây. */
Có mẹo nào không?