PluginProbe
Packeta / 1.2.4
Packeta v1.2.4
2.3.2 2.3.1 trunk 1.2.2 1.2.3 1.2.4 1.2.5 1.2.6 1.3.0 1.3.1 1.3.2 1.4 1.4.1 1.4.2 1.4.3 1.5.0 1.5.1 1.5.2 1.5.3 1.5.4 1.6.0 1.6.1 1.6.2 1.6.3 1.6.4 All 56 releases
packeta / src / Packetery / Module / Plugin.php

Plugin.php in Packeta 1.2.4, at src/Packetery/Module/Plugin.php

810 lines 22.1 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Main Packeta plugin class.
4 *
5 * @package Packetery
6 */
7
8 declare( strict_types=1 );
9
10 namespace Packetery\Module;
11
12 use Packetery\Core\Log\ILogger;
13 use Packetery\Core\Log\Record;
14 use Packetery\Module\Carrier\Downloader;
15 use Packetery\Module\Carrier\OptionsPage;
16 use Packetery\Module\Carrier\Repository;
17 use Packetery\Module\Log;
18 use Packetery\Module\Options;
19 use Packetery\Module\Order;
20 use Packetery\Module\Product;
21 use PacketeryLatte\Engine;
22 use PacketeryNette\Http\Request;
23 use WC_Order;
24
25 /**
26 * Class Plugin
27 *
28 * @package Packetery
29 */
30 class Plugin {
31
32 public const VERSION = '1.2.4';
33 public const DOMAIN = 'packetery';
34 public const MIN_LISTENER_PRIORITY = -9998;
35
36 /**
37 * Options page.
38 *
39 * @var Options\Page Options page,
40 */
41 private $options_page;
42
43 /**
44 * PacketeryLatte engine.
45 *
46 * @var Engine
47 */
48 private $latte_engine;
49
50 /**
51 * Carrier downloader object.
52 *
53 * @var Downloader
54 */
55 private $carrier_downloader;
56
57 /**
58 * Carrier repository.
59 *
60 * @var Repository
61 */
62 private $carrierRepository;
63
64 /**
65 * Country options page.
66 *
67 * @var OptionsPage
68 */
69 private $carrierOptionsPage;
70
71 /**
72 * Path to main plugin file.
73 *
74 * @var string Path to main plugin file.
75 */
76 private $main_file_path;
77
78 /**
79 * Admin edit order page Packeta metabox.
80 *
81 * @var Order\Metabox
82 */
83 private $order_metabox;
84
85 /**
86 * Message manager.
87 *
88 * @var MessageManager
89 */
90 private $message_manager;
91
92 /**
93 * Checkout object.
94 *
95 * @var Checkout
96 */
97 private $checkout;
98
99 /**
100 * Order BulkActions.
101 *
102 * @var Order\BulkActions
103 */
104 private $orderBulkActions;
105
106 /**
107 * Label printing.
108 *
109 * @var Order\LabelPrint
110 */
111 private $labelPrint;
112
113 /**
114 * Order collection printing.
115 *
116 * @var Order\CollectionPrint
117 */
118 private $orderCollectionPrint;
119
120 /**
121 * Order grid extender.
122 *
123 * @var Order\GridExtender
124 */
125 private $gridExtender;
126
127 /**
128 * Product tab.
129 *
130 * @var Product\DataTab
131 */
132 private $productTab;
133
134 /**
135 * Log page.
136 *
137 * @var Log\Page
138 */
139 private $logPage;
140
141 /**
142 * Log manager.
143 *
144 * @var ILogger
145 */
146 private $logger;
147
148 /**
149 * Order controller.
150 *
151 * @var Order\Controller
152 */
153 private $orderController;
154
155 /**
156 * Order modal.
157 *
158 * @var Order\Modal
159 */
160 private $orderModal;
161
162 /**
163 * Options exporter.
164 *
165 * @var Options\Exporter
166 */
167 private $exporter;
168
169 /**
170 * Packet synchronizer.
171 *
172 * @var Order\PacketSynchronizer
173 */
174 private $packetSynchronizer;
175
176 /**
177 * Request.
178 *
179 * @var Request
180 */
181 private $request;
182
183 /**
184 * Order repository.
185 *
186 * @var Order\Repository
187 */
188 private $orderRepository;
189
190 /**
191 * Plugin upgrade.
192 *
193 * @var Upgrade
194 */
195 private $upgrade;
196
197 /**
198 * QueryProcessor.
199 *
200 * @var QueryProcessor
201 */
202 private $queryProcessor;
203
204 /**
205 * Log repository.
206 *
207 * @var Log\Repository
208 */
209 private $logRepository;
210
211 /**
212 * Plugin constructor.
213 *
214 * @param Order\Metabox $order_metabox Order metabox.
215 * @param MessageManager $message_manager Message manager.
216 * @param Options\Page $options_page Options page.
217 * @param Repository $carrierRepository Carrier repository.
218 * @param Downloader $carrier_downloader Carrier downloader object.
219 * @param Checkout $checkout Checkout class.
220 * @param Engine $latte_engine PacketeryLatte engine.
221 * @param OptionsPage $carrierOptionsPage Carrier options page.
222 * @param Order\BulkActions $orderBulkActions Order BulkActions.
223 * @param Order\LabelPrint $labelPrint Label printing.
224 * @param Order\GridExtender $gridExtender Order grid extender.
225 * @param Product\DataTab $productTab Product tab.
226 * @param Log\Page $logPage Log page.
227 * @param ILogger $logger Log manager.
228 * @param Order\Controller $orderController Order controller.
229 * @param Order\Modal $orderModal Order modal.
230 * @param Options\Exporter $exporter Options exporter.
231 * @param Order\CollectionPrint $orderCollectionPrint Order collection print.
232 * @param Order\PacketSynchronizer $packetSynchronizer Packet synchronizer.
233 * @param Request $request HTTP request.
234 * @param Order\Repository $orderRepository Order repository.
235 * @param Upgrade $upgrade Plugin upgrade.
236 * @param QueryProcessor $queryProcessor QueryProcessor.
237 * @param Log\Repository $logRepository Log repository.
238 */
239 public function __construct(
240 Order\Metabox $order_metabox,
241 MessageManager $message_manager,
242 Options\Page $options_page,
243 Repository $carrierRepository,
244 Downloader $carrier_downloader,
245 Checkout $checkout,
246 Engine $latte_engine,
247 OptionsPage $carrierOptionsPage,
248 Order\BulkActions $orderBulkActions,
249 Order\LabelPrint $labelPrint,
250 Order\GridExtender $gridExtender,
251 Product\DataTab $productTab,
252 Log\Page $logPage,
253 ILogger $logger,
254 Order\Controller $orderController,
255 Order\Modal $orderModal,
256 Options\Exporter $exporter,
257 Order\CollectionPrint $orderCollectionPrint,
258 Order\PacketSynchronizer $packetSynchronizer,
259 Request $request,
260 Order\Repository $orderRepository,
261 Upgrade $upgrade,
262 QueryProcessor $queryProcessor,
263 Log\Repository $logRepository
264 ) {
265 $this->options_page = $options_page;
266 $this->latte_engine = $latte_engine;
267 $this->carrierRepository = $carrierRepository;
268 $this->carrier_downloader = $carrier_downloader;
269 $this->main_file_path = PACKETERY_PLUGIN_DIR . '/packeta.php';
270 $this->order_metabox = $order_metabox;
271 $this->message_manager = $message_manager;
272 $this->checkout = $checkout;
273 $this->carrierOptionsPage = $carrierOptionsPage;
274 $this->orderBulkActions = $orderBulkActions;
275 $this->labelPrint = $labelPrint;
276 $this->gridExtender = $gridExtender;
277 $this->productTab = $productTab;
278 $this->logPage = $logPage;
279 $this->logger = $logger;
280 $this->orderController = $orderController;
281 $this->orderModal = $orderModal;
282 $this->exporter = $exporter;
283 $this->orderCollectionPrint = $orderCollectionPrint;
284 $this->packetSynchronizer = $packetSynchronizer;
285 $this->request = $request;
286 $this->orderRepository = $orderRepository;
287 $this->upgrade = $upgrade;
288 $this->queryProcessor = $queryProcessor;
289 $this->logRepository = $logRepository;
290 }
291
292 /**
293 * Method to register hooks
294 */
295 public function run(): void {
296 add_action( 'init', [ $this, 'loadTranslation' ] );
297
298 if ( ! self::isWooCommercePluginActive() ) {
299 add_action( 'admin_notices', [ $this, 'echoInactiveWooCommerceNotice' ] );
300
301 return;
302 }
303
304 add_action( 'init', [ $this->upgrade, 'check' ] );
305 add_action( 'init', [ $this->logger, 'register' ] );
306 add_action( 'init', [ $this->message_manager, 'init' ] );
307 add_action( 'rest_api_init', [ $this->orderController, 'registerRoutes' ] );
308
309 add_action( 'admin_enqueue_scripts', array( $this, 'enqueueAdminAssets' ) );
310 add_action( 'wp_enqueue_scripts', [ $this, 'enqueueFrontAssets' ] );
311
312 add_action(
313 'admin_notices',
314 function () {
315 $this->message_manager->render( MessageManager::RENDERER_WORDPRESS );
316 },
317 self::MIN_LISTENER_PRIORITY
318 );
319 add_action( 'init', array( $this, 'init' ) );
320
321 register_activation_hook( $this->main_file_path, array( $this, 'activate' ) );
322
323 // TODO: deactivation_hook.
324 register_deactivation_hook(
325 $this->main_file_path,
326 static function () {
327 }
328 );
329
330 register_uninstall_hook( $this->main_file_path, array( __CLASS__, 'uninstall' ) );
331
332 add_action( 'woocommerce_email_footer', array( $this, 'render_email_footer' ) );
333 add_filter( 'woocommerce_shipping_methods', array( $this, 'add_shipping_method' ) );
334
335 add_filter( 'views_edit-shop_order', [ $this->gridExtender, 'addFilterLinks' ] );
336 add_action( 'restrict_manage_posts', [ $this->gridExtender, 'renderOrderTypeSelect' ] );
337 $this->queryProcessor->register();
338
339 add_filter( 'manage_edit-shop_order_columns', [ $this->gridExtender, 'addOrderListColumns' ] );
340 add_action( 'manage_shop_order_posts_custom_column', [ $this->gridExtender, 'fillCustomOrderListColumns' ] );
341
342 add_filter( 'woocommerce_order_data_store_cpt_get_orders_query', [ $this->upgrade, 'handleCustomQueryVar' ], 10, 2 );
343
344 add_action( 'admin_menu', array( $this, 'add_menu_pages' ) );
345 add_action( 'admin_head', array( $this->labelPrint, 'hideFromMenus' ) );
346 add_action( 'admin_head', array( $this->orderCollectionPrint, 'hideFromMenus' ) );
347 $this->orderModal->register();
348 $this->order_metabox->register();
349
350 $this->checkout->register_hooks();
351 $this->productTab->register();
352
353 add_action(
354 'packetery_cron_carriers_hook',
355 function () {
356 $this->carrier_downloader->runAndRender();
357 }
358 );
359 if ( ! wp_next_scheduled( 'packetery_cron_carriers_hook' ) ) {
360 wp_schedule_event( time(), 'daily', 'packetery_cron_carriers_hook' );
361 }
362
363 // TODO: Packet status sync.
364 wp_clear_scheduled_hook( 'packetery_cron_packet_status_sync_hook' );
365
366 add_action( 'woocommerce_admin_order_data_after_shipping_address', [ $this, 'renderDeliveryDetail' ] );
367 add_action( 'woocommerce_order_details_after_order_table', [ $this, 'renderOrderDetail' ] );
368
369 // Adding custom actions to dropdown in admin order list.
370 add_filter( 'bulk_actions-edit-shop_order', [ $this->orderBulkActions, 'addActions' ], 20, 1 );
371 // Execute the action for selected orders.
372 add_filter(
373 'handle_bulk_actions-edit-shop_order',
374 [
375 $this->orderBulkActions,
376 'handleActions',
377 ],
378 10,
379 3
380 );
381 // Print packets export result.
382 add_action( 'admin_notices', [ $this->orderBulkActions, 'renderPacketsExportResult' ], self::MIN_LISTENER_PRIORITY );
383
384 add_action( 'admin_init', [ $this->labelPrint, 'outputLabelsPdf' ] );
385 add_action( 'admin_init', [ $this->orderCollectionPrint, 'print' ] );
386
387 add_action( 'admin_init', [ $this->exporter, 'outputExportTxt' ] );
388 add_filter( 'woocommerce_order_data_store_cpt_get_orders_query', [ $this, 'transformGetOrdersQuery' ] );
389 }
390
391 /**
392 * Print inactive WooCommerce notice.
393 *
394 * @return void
395 */
396 public function echoInactiveWooCommerceNotice(): void {
397 if ( self::isWooCommercePluginActive() ) {
398 // When Packeta plugin is active and WooCommerce plugin is inactive.
399 // If user decides to activate WooCommerce plugin then invalid notice will not be rendered.
400 // Packeta plugin probably bootstraps twice in such case.
401 return;
402 }
403
404 $this->latte_engine->render(
405 PACKETERY_PLUGIN_DIR . '/template/admin-notice.latte',
406 [
407 'message' => [
408 'type' => 'error',
409 'message' => __( 'packetaPluginRequiresWooCommerce', 'packetery' ),
410 ],
411 ]
412 );
413 }
414
415 /**
416 * Is WC plugin active.
417 *
418 * @return bool
419 */
420 private static function isWooCommercePluginActive(): bool {
421 return in_array( 'woocommerce/woocommerce.php', (array) get_option( 'active_plugins', [] ), true );
422 }
423
424 /**
425 * Filter queries.
426 *
427 * @param array $query Query.
428 *
429 * @return array
430 */
431 public function transformGetOrdersQuery( array $query ): array {
432 if ( ! empty( $query['packetery_meta_query'] ) ) {
433 // @codingStandardsIgnoreStart
434 $query['meta_query'] = $query['packetery_meta_query'];
435 // @codingStandardsIgnoreEnd
436 }
437
438 return $query;
439 }
440
441 /**
442 * Renders delivery detail for packetery orders.
443 *
444 * @param WC_Order $order WordPress order.
445 */
446 public function renderDeliveryDetail( WC_Order $order ): void {
447 $orderEntity = $this->orderRepository->getByWcOrder( $order );
448 if ( null === $orderEntity ) {
449 return;
450 }
451
452 $carrierId = $orderEntity->getCarrierId();
453 $carrierOptions = Carrier\Options::createByCarrierId( $carrierId );
454
455 $this->latte_engine->render(
456 PACKETERY_PLUGIN_DIR . '/template/order/delivery-detail.latte',
457 [
458 'pickupPoint' => $orderEntity->getPickupPoint(),
459 'validatedDeliveryAddress' => $orderEntity->getValidatedDeliveryAddress(),
460 'carrierAddressValidation' => $carrierOptions->getAddressValidation(),
461 ]
462 );
463 }
464
465 /**
466 * Renders delivery detail for packetery orders, on "thank you" page and in frontend detail.
467 *
468 * @param WC_Order $wcOrder WordPress order.
469 */
470 public function renderOrderDetail( WC_Order $wcOrder ): void {
471 $order = $this->orderRepository->getById( $wcOrder->get_id() );
472 if ( null === $order ) {
473 return;
474 }
475
476 $pickupPoint = $order->getPickupPoint();
477 $validatedDeliveryAddress = $order->getValidatedDeliveryAddress();
478 if ( null === $pickupPoint && null === $validatedDeliveryAddress ) {
479 return;
480 }
481
482 $this->latte_engine->render(
483 PACKETERY_PLUGIN_DIR . '/template/order/detail.latte',
484 [
485 'pickupPoint' => $pickupPoint,
486 'validatedDeliveryAddress' => $validatedDeliveryAddress,
487 ]
488 );
489 }
490
491 /**
492 * Renders email footer.
493 *
494 * @param \WC_Email|null $email Email data.
495 */
496 public function render_email_footer( ?\WC_Email $email ): void {
497 if ( null === $email || ! $email->object instanceof \WC_Order ) {
498 return;
499 }
500
501 $packeteryOrder = $this->orderRepository->getByWcOrder( $email->object );
502 if ( null === $packeteryOrder ) {
503 return;
504 }
505
506 $pickupPoint = $packeteryOrder->getPickupPoint();
507 $validatedDeliveryAddress = $packeteryOrder->getValidatedDeliveryAddress();
508
509 $this->latte_engine->render(
510 PACKETERY_PLUGIN_DIR . '/template/email/footer.latte',
511 [
512 'pickupPoint' => $pickupPoint,
513 'validatedDeliveryAddress' => $validatedDeliveryAddress,
514 ]
515 );
516 }
517
518 /**
519 * Enqueues admin JS file.
520 *
521 * @param string $name Name of script.
522 * @param string $file Relative file path.
523 * @param bool $inFooter Tells where to include script.
524 * @param array $deps Script dependencies.
525 */
526 private function enqueueScript( string $name, string $file, bool $inFooter, array $deps = [] ): void {
527 wp_enqueue_script(
528 $name,
529 plugin_dir_url( $this->main_file_path ) . $file,
530 $deps,
531 md5( (string) filemtime( PACKETERY_PLUGIN_DIR . '/' . $file ) ),
532 $inFooter
533 );
534 }
535
536 /**
537 * Enqueues CSS file.
538 *
539 * @param string $name Name of script.
540 * @param string $file Relative file path.
541 */
542 private function enqueueStyle( string $name, string $file ): void {
543 wp_enqueue_style(
544 $name,
545 plugin_dir_url( $this->main_file_path ) . $file,
546 [],
547 md5( (string) filemtime( PACKETERY_PLUGIN_DIR . '/' . $file ) )
548 );
549 }
550
551 /**
552 * Builds asset URL.
553 *
554 * @param string $asset Relative asset path without leading slash.
555 *
556 * @return string
557 */
558 public static function buildAssetUrl( string $asset ): string {
559 $url = plugin_dir_url( PACKETERY_PLUGIN_DIR . '/packeta.php' ) . $asset;
560 $filename = PACKETERY_PLUGIN_DIR . '/' . $asset;
561
562 return add_query_arg( [ 'v' => md5( (string) filemtime( $filename ) ) ], $url );
563 }
564
565 /**
566 * Enqueues javascript files and stylesheets for checkout.
567 */
568 public function enqueueFrontAssets(): void {
569 if ( is_checkout() ) {
570 $this->enqueueStyle( 'packetery-front-styles', 'public/front.css' );
571 $this->enqueueScript( 'packetery-checkout', 'public/checkout.js', false, [ 'jquery' ] );
572 }
573 }
574
575 /**
576 * Enqueues javascript files and stylesheets for administration.
577 */
578 public function enqueueAdminAssets(): void {
579 global $pagenow, $typenow;
580
581 $page = $this->request->getQuery( 'page' );
582 $isOrderGridPage = 'edit.php' === $pagenow && 'shop_order' === $typenow;
583 $isOrderDetailPage = 'post.php' === $pagenow && 'shop_order' === $typenow;
584
585 if ( $isOrderGridPage || $isOrderDetailPage || in_array( $page, [ Carrier\OptionsPage::SLUG, Options\Page::SLUG ], true ) ) {
586 $this->enqueueScript( 'live-form-validation-options', 'public/live-form-validation-options.js', false );
587 $this->enqueueScript( 'live-form-validation', 'public/libs/live-form-validation/live-form-validation.js', false, [ 'live-form-validation-options' ] );
588 }
589
590 if ( Carrier\OptionsPage::SLUG === $page ) {
591 $this->enqueueScript( 'packetery-admin-country-carrier', 'public/admin-country-carrier.js', true, [ 'jquery' ] );
592 }
593
594 if ( $isOrderGridPage || $isOrderDetailPage || in_array( $page, [ Options\Page::SLUG, Carrier\OptionsPage::SLUG, Log\Page::SLUG, Order\labelPrint::MENU_SLUG ], true ) ) {
595 $this->enqueueStyle( 'packetery-admin-styles', 'public/admin.css' );
596 }
597
598 if ( $isOrderGridPage ) {
599 $this->enqueueScript( 'packetery-admin-grid-order-edit-js', 'public/admin-grid-order-edit.js', true, [ 'jquery', 'wp-util', 'backbone' ] );
600 }
601
602 if ( $isOrderDetailPage ) {
603 $this->enqueueScript( 'packetery-admin-pickup-point-picker', 'public/admin-pickup-point-picker.js', false, [ 'jquery' ] );
604 }
605 }
606
607 /**
608 * Add links to left admin menu.
609 */
610 public function add_menu_pages(): void {
611 $this->options_page->register();
612 $this->carrierOptionsPage->register();
613 $this->labelPrint->register();
614 $this->orderCollectionPrint->register();
615 $this->logPage->register();
616 }
617
618 /**
619 * Gets current locale.
620 */
621 private function getLocale(): string {
622 return apply_filters(
623 'plugin_locale',
624 ( is_admin() ? get_user_locale() : get_locale() ),
625 self::DOMAIN
626 );
627 }
628
629 /**
630 * Loads plugin translation file by user locale.
631 */
632 public function loadTranslation(): void {
633 $domain = self::DOMAIN;
634 $locale = $this->getLocale();
635
636 $moFile = PACKETERY_PLUGIN_DIR . "/languages/$domain-$locale.mo";
637 $result = load_textdomain( $domain, $moFile );
638
639 if ( false === $result ) {
640 $moFile = PACKETERY_PLUGIN_DIR . "/languages/$domain-en_US.mo";
641 load_textdomain( $domain, $moFile );
642 }
643 }
644
645 /**
646 * Inits plugin.
647 */
648 public function init(): void {
649 add_filter(
650 'plugin_action_links_' . plugin_basename( $this->main_file_path ),
651 [
652 $this,
653 'addPluginActionLinks',
654 ]
655 );
656 add_filter( 'plugin_row_meta', [ $this, 'addPluginRowMeta' ], 10, 2 );
657 }
658
659 /**
660 * Activates plugin.
661 */
662 public function activate(): void {
663 global $wpdb;
664
665 $this->logRepository->createTable();
666 if ( false === PACKETERY_DEBUG ) {
667 $this->options_page->setDefaultValues();
668 }
669
670 $this->init();
671
672 $createResult = $this->carrierRepository->createTable();
673 if ( false === $createResult ) {
674 $lastError = $wpdb->last_error;
675 $this->message_manager->flash_message( __( 'carrierTableNotCreatedMoreInformationInPacketaLog', 'packetery' ), MessageManager::TYPE_ERROR );
676
677 $record = new Record();
678 $record->action = Record::ACTION_CARRIER_TABLE_NOT_CREATED;
679 $record->status = Record::STATUS_ERROR;
680 $record->title = __( 'carrierTableNotCreated', 'packetery' );
681 $record->params = [
682 'errorMessage' => $lastError,
683 ];
684 $this->logger->add( $record );
685 }
686
687 $createResult = $this->orderRepository->createTable();
688 if ( false === $createResult ) {
689 $lastError = $wpdb->last_error;
690 $this->message_manager->flash_message( __( 'orderTableNotCreatedMoreInformationInPacketaLog', 'packetery' ), MessageManager::TYPE_ERROR );
691
692 $record = new Record();
693 $record->action = Record::ACTION_ORDER_TABLE_NOT_CREATED;
694 $record->status = Record::STATUS_ERROR;
695 $record->title = __( 'orderTableNotCreated', 'packetery' );
696 $record->params = [
697 'errorMessage' => $lastError,
698 ];
699 $this->logger->add( $record );
700 }
701
702 $this->upgrade->check();
703 }
704
705 /**
706 * Uninstalls plugin and drops custom database table.
707 * Only a static class method or function can be used in an uninstall hook.
708 */
709 public static function uninstall(): void {
710 if ( defined( 'PACKETERY_DEBUG' ) && PACKETERY_DEBUG === true ) {
711 return;
712 }
713
714 $container = require PACKETERY_PLUGIN_DIR . '/bootstrap.php';
715
716 $optionsRepository = $container->getByType( Options\Repository::class );
717 $pluginOptions = $optionsRepository->getPluginOptions();
718 foreach ( $pluginOptions as $option ) {
719 delete_option( $option->option_name );
720 }
721
722 $logRepository = $container->getByType( Log\Repository::class );
723 $logRepository->drop();
724
725 $carrierRepository = $container->getByType( Carrier\Repository::class );
726 $carrierRepository->drop();
727
728 $orderRepository = $container->getByType( Order\Repository::class );
729 $orderRepository->drop();
730 }
731
732 /**
733 * Adds action links visible at the plugin screen.
734 *
735 * @link https://developer.wordpress.org/reference/hooks/plugin_action_links_plugin_file/
736 *
737 * @param array $links Plugin Action links.
738 *
739 * @return array
740 */
741 public function addPluginActionLinks( array $links ): array {
742 $settingsLink = '<a href="' . esc_url( admin_url( 'admin.php?page=' . Options\Page::SLUG ) ) . '" aria-label="' .
743 esc_attr__( 'View Packeta settings', 'packetery' ) . '">' .
744 esc_html__( 'Settings', 'packetery' ) . '</a>';
745
746 array_unshift( $links, $settingsLink );
747
748 return $links;
749 }
750
751 /**
752 * Show row meta on the plugin screen.
753 *
754 * @link https://developer.wordpress.org/reference/hooks/plugin_row_meta/
755 *
756 * @param array $links Plugin Row Meta.
757 * @param string $pluginFileName Plugin Base file.
758 *
759 * @return array
760 */
761 public function addPluginRowMeta( array $links, string $pluginFileName ): array {
762 if ( ! strpos( $pluginFileName, basename( $this->main_file_path ) ) ) {
763 return $links;
764 }
765 $links[] = '<a href="' . esc_url( 'https://github.com/Zasilkovna/WooCommerce/wiki' ) . '" aria-label="' .
766 esc_attr__( 'View Packeta documentation', 'packetery' ) . '">' .
767 esc_html__( 'Documentation', 'packetery' ) . '</a>';
768
769 return $links;
770 }
771
772 /**
773 * Adds Packeta method to available shipping methods.
774 *
775 * @param array $methods Previous state.
776 *
777 * @return array
778 */
779 public function add_shipping_method( array $methods ): array {
780 $methods[ ShippingMethod::PACKETERY_METHOD_ID ] = ShippingMethod::class;
781
782 return $methods;
783 }
784
785 /**
786 * Hides submenu item. Must not be called too early.
787 *
788 * @param string $itemSlug Item slug.
789 */
790 public static function hideSubmenuItem( string $itemSlug ): void {
791 global $submenu;
792 if ( isset( $submenu[ Options\Page::SLUG ] ) ) {
793 foreach ( $submenu[ Options\Page::SLUG ] as $key => $menu ) {
794 if ( $itemSlug === $menu[2] ) {
795 unset( $submenu[ Options\Page::SLUG ][ $key ] );
796 }
797 }
798 }
799 }
800
801 /**
802 * Gets software identity for Packeta APIs.
803 *
804 * @return string
805 */
806 public static function getAppIdentity(): string {
807 return 'Woocommerce: ' . get_bloginfo( 'version' ) . ', WordPress: ' . WC_VERSION . ', plugin Packeta: ' . self::VERSION;
808 }
809 }
810