render_block_editor_notice();
$this->render_key_rejected_notice();
$this->render_failed_saves_notice();
}
/**
* Обрабатывает «Скрыть» у уведомления о несохранённых фото.
*
* Проверяет право редактировать товары и одноразовый ключ формы (nonce), убирает товар
* из списка и возвращает человека на страницу, где он нажал ссылку.
*
* @return void
*/
public function handle_hide_failed_save(): void {
$product_id = isset( $_GET['product_id'] ) ? absint( wp_unslash( $_GET['product_id'] ) ) : 0;
check_admin_referer( self::HIDE_FAILED_SAVE_ACTION . '_' . $product_id );
if ( ! current_user_can( 'edit_products' ) ) {
wp_die( esc_html__( 'You are not allowed to do this.', 'aimodelka' ), 403 );
}
self::remove_failed_save( $product_id );
wp_safe_redirect( wp_get_referer() ? wp_get_referer() : admin_url() );
exit;
}
/**
* «Включён экспериментальный редактор товара» — в редакторе товара и в настройках плагина.
*
* @return void
*/
private function render_block_editor_notice(): void {
if ( ! current_user_can( 'edit_products' ) || ! Plugin::product_block_editor_enabled() ) {
return;
}
$screen = function_exists( 'get_current_screen' ) ? get_current_screen() : null;
if ( null === $screen || ! in_array( $screen->id, array( 'product', 'woocommerce_page_' . Settings_Page::PAGE_SLUG ), true ) ) {
return;
}
self::print_notice( 'warning', esc_html__( 'The new product editor (beta) is turned on in WooCommerce. The aiModelka button in the product works only in the classic product editor. Turn the new editor off in WooCommerce → Settings → Advanced → Features.', 'aimodelka' ) );
}
/**
* «Ключ aiModelka не работает» — тем, кто может поменять ключ.
*
* @return void
*/
private function render_key_rejected_notice(): void {
if ( ! current_user_can( 'manage_woocommerce' ) || ! get_option( self::KEY_REJECTED_OPTION ) || ! self::on_relevant_screen() ) {
return;
}
self::print_notice(
'error',
sprintf(
'%1$s %3$s',
esc_html__( 'The aiModelka key does not work. Get a new key in your aiModelka account and paste it in the plugin settings.', 'aimodelka' ),
esc_url( Settings_Page::url() ),
esc_html__( 'Open settings', 'aimodelka' )
)
);
}
/**
* «Не удалось сохранить фото в товар» — по уведомлению на товар, со ссылкой на товар
* и «Скрыть».
*
* @return void
*/
private function render_failed_saves_notice(): void {
if ( ! current_user_can( 'edit_products' ) || ! self::on_relevant_screen() ) {
return;
}
foreach ( array_keys( self::failed_saves() ) as $product_id ) {
$product = wc_get_product( $product_id );
if ( ! $product ) {
// Товар удалили — уведомлять больше не о чем.
self::remove_failed_save( (int) $product_id );
continue;
}
$hide_url = wp_nonce_url(
add_query_arg(
array(
'action' => self::HIDE_FAILED_SAVE_ACTION,
'product_id' => $product_id,
),
admin_url( 'admin-post.php' )
),
self::HIDE_FAILED_SAVE_ACTION . '_' . $product_id
);
self::print_notice(
'error',
sprintf(
'%1$s %3$s · %5$s',
esc_html(
sprintf(
/* translators: %s: product name. */
__( 'aiModelka could not save the photos to the product “%s”. The photos are safe in the aiModelka photo session: open the product, click “Open photo shoot” and save them again.', 'aimodelka' ),
$product->get_name()
)
),
esc_url( (string) get_edit_post_link( $product_id ) ),
esc_html__( 'Open the product', 'aimodelka' ),
esc_url( $hide_url ),
esc_html__( 'Hide', 'aimodelka' )
)
);
}
}
/**
* Открыта ли страница, где уведомления плагина к месту (см. описание класса).
*
* Страница настроек aiModelka — подменю WooCommerce, поэтому её id собирается из
* адреса страницы настроек.
*
* @return bool
*/
private static function on_relevant_screen(): bool {
$screen = function_exists( 'get_current_screen' ) ? get_current_screen() : null;
if ( null === $screen ) {
return false;
}
return in_array( $screen->id, self::SCREENS, true ) || 'woocommerce_page_' . Settings_Page::PAGE_SLUG === $screen->id;
}
/**
* Список несохранённых товаров из настроек; испорченная запись — пустой список.
*
* @return array Id товара → момент отказа.
*/
private static function failed_saves(): array {
$failed = get_option( self::FAILED_SAVES_OPTION, array() );
return is_array( $failed ) ? $failed : array();
}
/**
* Печатает уведомление в разметке WordPress.
*
* @param string $type error, warning, success или info.
* @param string $html Уже экранированное содержимое.
* @return void
*/
private static function print_notice( string $type, string $html ): void {
printf(
'',
esc_attr( $type ),
wp_kses(
$html,
array(
'a' => array( 'href' => array() ),
)
)
);
}
}