Skip to content

Wszystko o WordPressie, tworzeniu stron — i nie tylko

📝 Dodawanie notatek do zamówienia WooCommerce w e-mailu: pełny poradnik

📝 Dodawanie notatek do zamówienia WooCommerce w e-mailu: pełny poradnik

Klient złożył zamówienie, a Pan zostawił notatkę w panelu administracyjnym, doprecyzował termin dostawy, dodał numer śledzenia lub po prostu napisał „zadzwonić przed wysyłką". Ale klient tego nie widzi. Notatki do zamówienia WooCommerce domyślnie istnieją tylko w panelu administracyjnym, na bocznym panelu edycji zamówienia. W e-mailach wysyłanych do kupującego ich nie ma.

Problem rozwiązuje jeden snippet w functions.php. Bez wtyczek, bez edycji szablonów, czysty hook, który wyświetla notatki w treści e-maila. W praktyce stosujemy to podejście w sklepach klientów już od kilku lat, ani jednej awarii po aktualizacjach WooCommerce. W tym poradniku przeanalizujemy, jak WooCommerce przechowuje notatki do zamówień, jakiego hooka użyć i jak dostosować wyświetlanie do własnych zadań.

💡 Szybki przegląd:

  • Jak WooCommerce przechowuje notatki do zamówień: typ komentarza order_note i funkcja wc_get_order_notes()
  • Dwa podejścia do dostosowywania e-maili: nadpisywanie szablonów lub hooki, które wybrać i kiedy
  • Gotowy snippet do wyświetlania notatek w e-mailu o zrealizowaniu zamówienia z analizą każdej linii
  • Dostosowywanie: stylizacja listy, filtrowanie tylko notatek klienta, obsługa e-maili w formacie plain-text
  • Testowanie przez podgląd e-maili w panelu administracyjnym, bez spamowania rzeczywistych klientów

Krok 1: Jak WooCommerce przechowuje notatki do zamówień

WooCommerce przechowuje notatki jako komentarze WordPress typu order_note. Każda akcja dotycząca zamówienia, zmiana statusu, zwrot, notatka administratora lub wiadomość do klienta, jest zapisywana w tabeli wp_comments z flagą comment_type = 'order_note'.

Różnica między notatkami wewnętrznymi a notatkami klienta jest określana przez meta pole is_customer_note. Jeśli checkbox „Visible in My Account" jest zaznaczony podczas dodawania notatki, WooCommerce ustawia is_customer_note = true, a kupujący widzi ją na swoim koncie. Zwykłe notatki wewnętrzne (is_customer_note = false) nie są klientowi nigdzie pokazywane.

Wraz z wprowadzeniem High Performance Order Storage (HPOS) w WooCommerce 8.2+ notatki trafiły do osobnej tabeli wp_wc_order_notes. Bezpośrednie zapytania SQL do wp_comments przy włączonym HPOS mogą zwracać pusty wynik. Dlatego zamiast get_comments() lepiej używać wc_get_order_notes(), działa ona poprawnie w każdym trybie przechowywania.

Krok 2: Szablony czy hooki, które podejście wybrać

W WooCommerce są dwie ścieżki dostosowywania e-maili: nadpisywanie szablonów i używanie hooków akcji. Każda ma swój scenariusz.

Nadpisywanie szablonów. Kopiuje Pan plik z woocommerce/templates/emails/ do yourtheme/woocommerce/emails/ i edytuje HTML bezpośrednio. Plus, pełna kontrola nad znacznikami. Minus, przy dużych aktualizacjach WooCommerce Pana szablon może się rozjechać z aktualną wersją i e-maile zaczną się psuć. Dokumentacja struktury szablonów jest teraz na woocommerce.com, a nie na starym docs.woothemes.com.

Hooki. Podpina Pan callback do akcji woocommerce_email_order_meta, a WooCommerce samo wywołuje Pana funkcję w odpowiednim miejscu e-maila. Plus, nie zależy od wersji szablonów, działa „od ręki" po aktualizacjach rdzenia. Minus, jest Pan ograniczony pozycją hooka (uruchamia się on w bloku metadanych zamówienia, po tabeli z produktami).

Kryterium

Szablony

Hooki

Kontrola nad znacznikami

Pełna

W granicach pozycji hooka

Odporność na aktualizacje

Niska

Wysoka

Złożoność wdrożenia

Wyższa

Niższa

Odpowiednie dla

Gruntownej przebudowy e-maila

Dodania jednego bloku

Dla naszego zadania, wyświetlenia notatek, hook jest więcej niż wystarczający. Jeśli potrzebuje Pan całkowicie przekroić projekt e-maili, proszę wziąć szablony i zaplanować czas na ich aktualizację co pół roku.

Krok 3: Dodajemy kod do functions.php

Hook woocommerce_email_order_meta uruchamia się we wszystkich transakcyjnych e-mailach WooCommerce: potwierdzenie zamówienia, realizacja, anulowanie, faktura i inne. Do callbacka przekazywane są cztery parametry: obiekt zamówienia $order, flaga $sent_to_admin, flaga $plain_text i obiekt e-maila $email.

Proszę umieścić ten kod w functions.php aktywnego motywu (lub przez wtyczkę Code Snippets, bezpieczniej, nie zniknie przy zmianie motywu):

1add_action( 'woocommerce_email_order_meta', 'sd_add_order_notes_to_email', 10, 4 );
2
3function sd_add_order_notes_to_email( $order, $sent_to_admin, $plain_text, $email ) {
4 // Не ломаем plain-text версию письма
5 if ( $plain_text ) {
6 echo "\n\n" . esc_html__( 'Order Notes:', 'woocommerce' ) . "\n";
7
8 $notes = wc_get_order_notes( array(
9 'order_id' => $order->get_id(),
10 'type' => 'customer',
11 ) );
12
13 if ( empty( $notes ) ) {
14 echo esc_html__( 'No notes for this order.', 'woocommerce' ) . "\n";
15 return;
16 }
17
18 foreach ( $notes as $note ) {
19 echo '- ' . wp_strip_all_tags( $note->content ) . "\n";
20 }
21 return;
22 }
23
24 // HTML-версия: получаем только клиентские заметки
25 $notes = wc_get_order_notes( array(
26 'order_id' => $order->get_id(),
27 'type' => 'customer',
28 ) );
29
30 if ( empty( $notes ) ) {
31 return;
32 }
33
34 echo '<h2>' . esc_html__( 'Order Notes', 'woocommerce' ) . '</h2>';
35 echo '<ul class="order-notes-list" style="list-style:none;padding:0;margin:0 0 24px;">';
36
37 foreach ( $notes as $note ) {
38 $note_date = sprintf(
39 '%1$s в %2$s',
40 date_i18n( get_option( 'date_format' ), strtotime( $note->date_created ) ),
41 date_i18n( get_option( 'time_format' ), strtotime( $note->date_created ) )
42 );
43
44 printf(
45 '<li style="background:#f9f9f9;border-left:4px solid #7f54b3;padding:12px 16px;margin-bottom:10px;border-radius:0 4px 4px 0;">'
46 . '<div style="margin-bottom:4px;">%s</div>'
47 . '<small style="color:#888;">%s</small>'
48 . '</li>',
49 wp_kses_post( nl2br( $note->content ) ),
50 esc_html( $note_date )
51 );
52 }
53
54 echo '</ul>';
55}

Co tu się dzieje linia po linii:

  • Linia 1. Rejestrujemy hook z priorytetem 10 i przyjmujemy wszystkie 4 parametry. Bez 10, 4 WooCommerce przekaże tylko pierwszy argument, otrzyma Pan błąd.
  • Linie 5-20. Obsługa e-maili plain-text. Niektóre e-maile idą w formacie tekstowym, wyświetlamy notatki listą z myślnikami, bez HTML.
  • Linie 24-28. wc_get_order_notes() pobiera tylko notatki klienta (type => 'customer'). Proszę usunąć filtr, aby pokazać wszystkie notatki, w tym wewnętrzne (zmiana statusu, zwrot). Tablica pusta → nic nie wyświetlamy, nie zaśmiecamy e-maila.
  • Linie 34-38. Formatujemy datę przez date_i18n(), respektując ustawienia regionalne witryny i format daty/czasu.
  • Linie 40-48. printf() wyświetla każdą notatkę w stylizowanym bloku: fioletowy pasek po lewej, jasne tło, data na dole na szaro.

Kod nie używa zewnętrznych zależności i jest kompatybilny z WooCommerce 3.2+ (funkcja wc_get_order_notes pojawiła się właśnie w tej wersji) oraz HPOS (natywna obsługa od 8.2+).

Krok 4: Testujemy bez spamowania klientów

Po dodaniu kodu proszę nie czekać na rzeczywiste zamówienie, aby sprawdzić. WooCommerce daje wbudowany podgląd e-maili: WooCommerce → Ustawienia → Emails → proszę kliknąć na dowolny e-mail → przycisk „Preview" na dole. Zobaczy Pan e-mail w HTML i plain-text, z prawdziwym zamówieniem (brane jest ostatnie istniejące). Jeśli nie ma zamówień, proszę utworzyć testowe ręcznie.

Co sprawdzić:

  • Notatka klienta z włączoną opcją „Visible in My Account" wyświetla się w e-mailu;
  • Notatka wewnętrzna (bez zaznaczenia) nie wyświetla się (jeśli pozostawił Pan type => 'customer');
  • Wersja plain-text e-maila nie jest uszkodzona (proszę przełączyć się przez link pod podglądem);
  • Blok z notatkami nie duplikuje się w e-mailach do administratora (proszę dodać sprawdzenie if ( $sent_to_admin ) return; jeśli potrzebne).

Jeśli korzysta Pan z Code Snippets, wystarczy dezaktywować snippet, aby cofnąć zmiany. Jeśli edytował Pan functions.php, proszę zakomentować lub usunąć kod. Żadne ślady w bazie danych nie pozostają.

⁉️🤔 Często zadawane pytania

Czy można wyświetlać WSZYSTKIE notatki, a nie tylko notatki klienta?

Tak. Proszę zamienić 'type' => 'customer' na 'type' => 'internal', otrzyma Pan tylko notatki wewnętrzne. Proszę całkowicie usunąć parametr type, otrzyma Pan wszystkie notatki po kolei. Proszę wziąć pod uwagę, że notatki wewnętrzne mogą zawierać informacje serwisowe (ID zwrotu, kwoty), których klient nie powinien widzieć. Dla większości sklepów wystarczy 'type' => 'customer'. Jeśli chce Pan rozdzielić wyświetlanie, proszę zrobić dwa bloki: najpierw notatki klienta z nagłówkiem „Komentarze do zamówienia", potem wewnętrzne pod nagłówkiem „Szczegóły realizacji" (to już dla e-maili do administratora, flaga $sent_to_admin).

Kod działa dla konkretnego e-maila czy dla wszystkich naraz?

Hook woocommerce_email_order_meta uruchamia się we wszystkich transakcyjnych e-mailach: Completed Order, Processing Order, Order on Hold, Customer Invoice i tak dalej. Jeśli potrzebuje Pan ograniczyć wyświetlanie tylko do e-maila o zrealizowaniu zamówienia, proszę opakować kod w sprawdzenie:

1if ( 'customer_completed_order' !== $email->id ) {
2 return;
3}

Lista wszystkich ID e-maili jest dostępna w dokumentacji WooCommerce: customer_completed_order · customer_processing_order · customer_on_hold_order · customer_invoice · customer_refunded_order · customer_new_account · new_order · cancelled_order · failed_order.

Czy bezpiecznie jest edytować functions.php na działającej stronie?

Edycja functions.php bezpośrednio to ryzykowna ścieżka. Błąd składni (dodatkowy nawias, niezamknięty cudzysłów) powoduje biały ekran na całej stronie. Bezpieczniej jest używać wtyczki Code Snippets, pozwala ona dodawać snippety PHP przez panel administracyjny i automatycznie wyłącza kod z błędem krytycznym. Alternatywa: WPCode (darmowa wersja na wordpress.org), ta sama funkcjonalność plus logika warunkowa (tylko dla administratorów, tylko na określonych stronach). Jeśli mimo wszystko edytuje Pan functions.php, proszę zrobić kopię zapasową pliku i mieć pod ręką dostęp FTP. Biały ekran leczy się przez zastąpienie functions.php oryginałem z kopii zapasowej.

Notatki duplikują się w e-mailach, co zrobiłem nie tak?

Dwie prawdopodobne przyczyny. Pierwsza: dodał Pan kod jednocześnie w functions.php i przez wtyczkę snippetów, hook uruchamia się dwukrotnie. Proszę zostawić jedno. Druga: motyw lub inna wtyczka już podpinają callback do tego samego hooka. Proszę sprawdzić przez wyszukiwanie w kodzie projektu (grep -r "woocommerce_email_order_meta" wp-content/). Jeśli duplikacja pochodzi od wtyczki, wystarczy usunąć Pana kod. Jeśli od motywu, proszę opakować swój callback w remove_action() przed add_action(), aby zagwarantować wykonanie tylko jednej procedury obsługi.

Co w rezultacie: czy warto dodawać notatki do e-maili do klientów

Przejrzystość komunikacji to jeden z najtańszych sposobów na zmniejszenie obciążenia działu wsparcia. Kiedy klient widzi w e-mailu „Numer śledzenia: X123456789, dostawa 15 czerwca", nie idzie pisać na czacie „gdzie jest moje zamówienie?". Jeden snippet, zero wtyczek, pięć minut na wdrożenie, a efekt mierzy się dziesiątkami zaoszczędzonych zgłoszeń miesięcznie.

Jeśli e-maile są już dostosowane przez szablony, proszę wbudować wyświetlanie notatki bezpośrednio w szablon, a nie przez hook. Jeśli korzysta Pan z wtyczki do dostosowywania e-maili (Kadence, YayMail, ShopMagic), każda z nich ma swój mechanizm dodawania bloków dynamicznych, proszę użyć go zamiast kodu.

Proszę spróbować z jednym typem e-maili (Completed Order), sprawdzić na zamówieniu testowym i po tygodniu ocenić, czy jest mniej powtarzalnych pytań od klientów. Prawie na pewno tak.