Magento 2: bezpieczeństwo szablonów: jakiej metody użyć?

29

Wiem, że Magento 2 ma kilka metod zabezpieczania szablonu:

  • $block->escapeHtml()
  • $block->escapeQuote()
  • $block->escapeUrl()
  • $block->escapeXssInUrl()

Ale zastanawiam się, kiedy użyć każdej z tych metod?

Raphael at Digital Pianism
źródło

Odpowiedzi:

35

Metody zmiany znaczenia we AbstractBlockwszystkich wywołaniach delegowanych do Magento\Framework\Escaper, więc znajdziesz tam przegląd.

Spójrzmy na publiczne metody i ich dokumentację:

escapeHtml ()

/**
 * Escape string for HTML context. allowedTags will not be escaped, except the following: script, img, embed,
 * iframe, video, source, object, audio
 *
 * @param string|array $data
 * @param array|null $allowedTags
 * @return string|array
 */
public function escapeHtml($data, $allowedTags = null)

Powinna to być domyślna metoda zmiany znaczenia dla dowolnego wyniku. Konwencja jest taka, że ​​wynik wszystkich metod, które nie zawierają „HTML”, musi być poprzedzony znakiem ucieczki.

escapeHtmlAttr ()

( od Magento 2.2 )

/**
 * Escape a string for the HTML attribute context
 *
 * @param string $string
 * @param boolean $escapeSingleQuote
 * @return string
 */
public function escapeHtmlAttr($string, $escapeSingleQuote = true)

Użyj tego, aby na przykład uciec danych wyjściowych w atrybucie HTML

title="<?php echo $block->escapeHtmlAttr($title) ?>"

Uniknie HTML, ale także cudzysłowów ( ")

Domyślnie będzie także unikał pojedynczych cudzysłowów, więc to też działa:

onclick="alert('<?php echo $block->escapeHtmlAttr($message) ?>')"

Ustaw drugi parametr na false, jeśli nie jest to pożądane.

escapeUrl ()

/**
 * Escape URL
 *
 * @param string $string
 * @return string
 */
public function escapeUrl($string)

Może to służyć do generowania adresów URL. Zastosuje domyślną zmianę znaczenia HTML i dodatkowo usunie javascript:, vbscript:i data:. Jeśli chcesz zapobiec takim adresom URL w linkach podanych przez użytkownika, możesz użyć tej metody.

Do Magento 2.1 ta funkcja nie była dołączana i trzeba było z niej korzystać escapeXssInUrl(). Nie było żadnego powodu, by z niego korzystać escapeUrl().

W przeciwnym razie użyj tylko $block->escapeHtmlAttr()dla adresów URL.

encodeUrlParam ()

( od Magento 2.2 )

/**
 * Encode URL
 *
 * @param string $string
 * @return string
 */
public function encodeUrlParam($string)

Dotyczy to kodowania adresów URL do parametrów. W przypadku wewnętrznych adresów URL należy zawsze używać getUrl(), gdy kodowanie adresów URL jest już dla Ciebie wykonane, więc jest to konieczne tylko wtedy, gdy ręcznie konstruujesz zewnętrzny adres URL.

escapeJs ()

( od Magento 2.2 )

/**
 * Escape string for the JavaScript context
 *
 * @param string $string
 * @return string
 */
public function escapeJs($string)

Koduje znaki Unicode język JavaScript, np staje \u2665. Użyj go do zmiany wyniku w ciągu JS . W przypadku wbudowanego Javascript (tj. onclickAtrybutów) nadal trzeba wywoływać escapeHtmlAttr().

Zauważ, że jeśli używasz json_encode(), robi to samo, ale w tym przypadku escapeJs()nie można go użyć.

escapeCss ()

( od Magento 2.2 )

/**
 * Escape string for the CSS context
 *
 * @param string $string
 * @return string
 */
public function escapeCss($string)

Koduje znaki Unicode dla CSS (patrz escapeJs()), na przykład do użycia w contentatrybucie CSS.

Przestarzałe metody (od Magento 2.2):

  • escapeJsQuote: Użyj escapeHtmlAttr()zamiast tego
  • escapeXssInUrl: użyj escapeUrl()zamiast tego
  • escapeQuote: Użyj escapeHtmlAttr()zamiast tego
Fabian Schmengler
źródło
1
Dobra robota Do mojej odpowiedzi dodałem krótką notatkę, aby odnieść się do twojej przy korzystaniu z wersji 2.1. Co ciekawe, Magento U wspomina tylko o metodach, o których wspomniałem w mojej odpowiedzi. Myślę, że kurs jest tylko 2.0
Raphael w Digital Pianism
escapeHtmlAttri escapeHtmlAttrnie istnieje w 2.1.2 ... przynajmniej nie w, /vendor/magento/framework/Escaper.phpchyba że dodali go później i ponownie
otagowali
2
Dobry chwyt, moja odpowiedź była oparta na najnowszej gałęzi rozwoju. Według devdocs, inne metody będą przestarzałe od 2.2
Fabian Schmengler
Czy istnieje metoda, której można użyć do wyczyszczenia dowolnego fragmentu kodu HTML, który może wymagać umieszczenia znacznika img?
Corgalore,
Czysty w jakim sensie?
Fabian Schmengler,
14

To dotyczy Magento 2.0. W przypadku 2.1 zapoznaj się z odpowiedzią Fabiana

escapeHtml

Użyj tej funkcji w przypadku łańcucha wyjściowego, który nie powinien zawierać HTML.

Przykład:

<span class='label'><?php echo $block->escapeHtml($block->getLabel()); ?></span>

escapeQuote

Użyj tej funkcji w przypadku atrybutów HTML

Przykład:

<span class="<?php echo $block->escapeQuote($block->getSpanClass()); ?>">Description</span>

escapeUrl

Użyj tej funkcji w przypadku wyjścia adresu URL (bez zapobiegania XSS - tylko konwersja znaków)

Przykład:

<a href="<?php echo $block->escapeUrl($block->getUrl()); ?>">Link</a>

escapeXssInUrl

Użyj tej funkcji w przypadku wyjścia adresu URL (z zapobieganiem XSS - w tym konwersacji znaków)

Przykład:

<a href="<?php echo $block->escapeXssInUrl($block->getUrl()); ?>">Link</a>

Czego nie trzeba uciekać?

  • Typ rzutowania i funkcja php count()(przykład echo (int)$var)
  • Dane wyjściowe w pojedynczych cudzysłowach (przykład echo 'test')
  • Dane wyjściowe w podwójnych cudzysłowach bez zmiennych (przykład echo "test")

__metoda

Ten służy do tłumaczenia. Użyj go, jeśli wiesz, że ciąg może zostać przetłumaczony.

Na przykład:

<caption class="table-caption"><?php /* @escapeNotVerified */ echo __('More Information') ?></caption>
Raphael at Digital Pianism
źródło
dobra robota .. rapheal
Amit Bera
1
Czy powinniśmy również unikać każdego tłumaczenia __()? Jestem trochę zmęczony wklejaniem /* @escapeNotVerified */wszędzie: /
igloczek
@BartekIgielski zobacz moją zaktualizowaną odpowiedź. __nie jest przeznaczony do celów bezpieczeństwa, ale do celów tłumaczenia
Raphael at Digital Pianism
1
Polecam również echo $this->escapeHtml(__('Text to translate'))
unikanie
2
Na stronie devdocs znajduje się informacja, że ​​niektóre metody będą przestarzałe w wersji 2.2. Pamiętaj, aby sprawdzić ponownie na stronie bezpieczeństwa szablonu. devdocs.magento.com/guides/v2.0/frontend-dev-guide/templates/…
Anna Völkl