Liquid Filters
This page documents standard filters that are available with every Environment
by default. See custom filters for examples of how to write your own and the extra filter reference for some non-standard filters.
Some of the examples here are borrowed from Shopify's Liquid documentation. You can find their license here.
abs
<number> | abs
Return the absolute value of a number. Works on integers, floats and string representations of integers or floats.
{{ -42 | abs }}
{{ 7.5 | abs }}
{{ '42.0' | abs }}
42
7.5
42.0
Given a value that can't be cast to an integer or float, 0
will be returned.
{{ 'hello' | abs }}
{{ nosuchthing | abs }}
0
0
append
<string> | append: <string>
Return the input value concatenated with the argument value.
{{ 'Hello, ' | append: 'World!' }}
Hello, World!
If either the input value or argument are not a string, they will be coerced to a string before concatenation.
{% assign a_number = 7.5 -%}
{{ 42 | append: a_number }}
{{ nosuchthing | append: 'World!' }}
427.5
World!
at_least
<number> | at_least: <number>
Return the maximum of the filter's input value and its argument. If either input value or argument are string representations of an integer or float, they will be cast to an integer or float prior to comparison.
{{ -5.1 | at_least: 8 }}
{{ 8 | at_least: '5' }}
8
8
If either input value or argument can not be cast to an integer or float, 0
will be used instead.
{{ "hello" | at_least: 2 }}
{{ "hello" | at_least: -2 }}
{{ -1 | at_least: "abc" }}
2
0
0
at_most
<number> | at_most: <number>
Return the minimum of the filter's input value and its argument. If either input value or argument are string representations of an integer or float, they will be cast to an integer or float prior to comparison.
{{ 5 | at_most: 8 }}
{{ '8' | at_most: 5 }}
5
5
If either input value or argument can not be cast to an integer or float, 0
will be used instead.
{{ "hello" | at_most: 2 }}
{{ "hello" | at_most: -2 }}
{{ -1 | at_most: "abc" }}
0
-2
-1
base64_decode
<string> | base64_decode
Decode a base64 encoded string. The decoded value is assumed to be UTF-8 and will be decoded as UTF-8.
While Python Liquid assumes UTF-8 character encoding, Ruby Liquid does not seem to do so, potentially introducing byte strings into the render context.
{{ 'SGVsbG8sIFdvcmxkIQ==' | base64_decode }}
Hello, World!
If the input value is not a valid base64 encoded string, an exception will be raised.
{{ 'notbase64' | base64_decode }}
FilterError: invalid base64-encoded string, on line 1
base64_encode
<string> | base64_encode
Encode a string using base64.
Python Liquid returns a str
from base64_encode
, not bytes
.
{{ 'Hello, World!' | base64_encode }}
SGVsbG8sIFdvcmxkIQ==
If the input value is not a string, it will be converted to a string before base64 encoding.
{{ 5 | base64_encode }}
NQ==
base64_url_safe_decode
<string> | base64_url_safe_decode
Decode a URL safe base64 encoded string. Substitutes -
instead of +
and _
instead of /
in
the standard base64 alphabet. The decoded value is assumed to be UTF-8 and will be decoded as UTF-8.
While Python Liquid assumes UTF-8 character encoding, Ruby Liquid does not seem to do so, potentially introducing byte strings into the render context.
{{ 'SGVsbG8sIFdvcmxkIQ==' | base64_url_safe_decode }}
Hello, World!
If the input value is not a valid base64 encoded string, an exception will be raised.
{{ 'notbase64' | base64_url_safe_decode }}
FilterError: invalid base64-encoded string, on line 1
base64_url_safe_encode
<string> | base64_url_safe_encode
Encode a string using URL safe base64. Substitutes -
instead of +
and _
instead of /
in
the standard base64 alphabet.
Python Liquid returns a str
from base64_url_safe_encode
, not bytes
.
{{ 'Hello, World!' | base64_url_safe_encode }}
SGVsbG8sIFdvcmxkIQ==
If the input value is not a string, it will be converted to a string before base64 encoding.
{{ 5 | base64_url_safe_encode }}
NQ==
capitalize
<string> | capitalize
Return the input string with the first character in upper case and the rest lowercase.
{{ 'heLLO, World!' | capitalize }}
Hello, world!
If the input value is not a string, it will be converted to a string.
{{ 42 | capitalize }}
42
ceil
<number> | ceil
Round the input value up to the nearest whole number. The input value will be converted to a number if it is not an integer or float.
{{ 5.1 | ceil }}
{{ 5.0 | ceil }}
{{ 5 | ceil }}
{{ '5.4' | ceil }}
6
5
5
5
If the input is undefined or can't be converted to a number, 0
is returned.
{{ 'hello' | ceil }}
{{ nosuchthing | ceil }}
0
0
compact
<array> | compact[: <string>]
Remove nil
(or None
in Python) values from an array-like object. If given, the argument should be the name of a property that exists on each object (hash, dict etc.) in the array-like sequence.
If pages
is an array of objects, some of which have a category
property:
{
"pages": [
{ "category": "business" },
{ "category": "celebrities" },
{},
{ "category": "lifestyle" },
{ "category": "sports" },
{},
{ "category": "technology" }
]
}
Without compact
, iterating those categories will include nil
values.
{% assign categories = pages | map: "category" -%}
{% for category in categories -%}
- {{ category }}
{%- endfor %}
- business
- celebrities
-
- lifestyle
- sports
-
- technology
With compact
, we can remove those missing categories before the loop.
{% assign categories = pages | map: "category" | compact %}
{% for category in categories %}
- {{ category }}
{% endfor %}
- business
- celebrities
- lifestyle
- sports
- technology
Using the optional argument to compact
, we could avoid using map
and create an array of pages with a category
property, rather than an array of categories.
{% assign pages_with_category = pages | compact: "category" %}
{% for page in pages_with_category %}
- {{ page.category }}
{% endfor %}
- business
- celebrities
- lifestyle
- sports
- technology
concat
<array> | concat: <array>
Create a new array by joining one array-like object with another.
{% assign fruits = "apples, oranges, peaches" | split: ", " %}
{% assign vegetables = "carrots, turnips, potatoes" | split: ", " %}
{% assign everything = fruits | concat: vegetables %}
{% for item in everything %}
- {{ item }}
{% endfor %}
- apples
- oranges
- peaches
- carrots
- turnips
- potatoes
If the input value is not array-like, it will be converted to an array. No conversion is attempted for the argument value.
{% assign fruits = "apples, oranges, peaches" | split: ", " %}
{% assign things = "hello" | concat: fruits %}
{% for item in things %}
- {{ item }}
{% endfor %}
- hello
- apples
- oranges
- peaches
If the input is a nested array, it will be flattened before concatenation. The argument is not flattened.
{
"a": [
["a", "x"],
["b", ["y", ["z"]]]
],
"b": ["c", "d"]
}
{{ a | concat: b | join: '#' }}
a#x#b#y#z#c#d
date
<datetime> | date: <string>
Format a date and/or time according the the given format string. The input can be a string, in which case the string will be parsed as a date/time before formatting.
Python Liquid uses dateutil for parsing strings to
datetimes
, and strftime
for formatting. There are likely to be some inconsistencies between this
and Ruby Liquid's Time.parse
equivalent parsing and formatting of dates and times.
In general, Python Liquid will raise an exception if the input value can not be converted to a date and/or time. Whereas Ruby Liquid will usually return something without erroring.
{{ "March 14, 2016" | date: "%b %d, %y" }}
Mar 14, 16
The special 'now'
or 'today'
input values can be used to get the current timestamp. 'today'
is an alias for 'now'
. Both include time information.
{{ "now" | date: "%Y-%m-%d %H:%M" }}
2021-12-02 10:17
If the input is undefined, an empty string is returned.
{{ nosuchthing | date: "%Y-%m-%d %H:%M" }}
default
<object> | default[: <object>[, allow_false:<bool>]]
Return a default value if the input is undefined, nil
, false
or empty, or return the input unchanged otherwise.
The default
filter is the only built-in filter to use a keyword argument.
{{ product_price | default: 2.99 }}
{%- assign product_price = "" %}
{{ product_price | default: 2.99 }}
{%- assign product_price = 4.99 %}
{{ product_price | default: 2.99 }}
2.99
2.99
4.99
If the optional allow_false
argument is true
, an input of false
will not return the default. allow_false
defaults to false
.
{% assign product_reduced = false -%}
{{ product_reduced | default: true, allow_false: true }}
false
If no argument is given, the default value will be an empty string.
{{ product_price | default }}
Empty strings, arrays and objects all cause the default value to be returned. 0
does not.
{{ "" | default: "hello" }}
{{ 0 | default: 99 }}
hello
0
divided_by
<number> | divided_by: <number>
Divide a number by another number. The result is rounded down to the nearest integer if the divisor is an integer.
{{ 16 | divided_by: 4 }}
{{ 5 | divided_by: 3 }}
4
1
If you divide by a float, the result will be a float.
{{ 20 | divided_by: 7 }}
{{ 20 | divided_by: 7.0 }}
2
2.857142857142857
If either the input or argument are not an integer or float, Liquid will try to convert them to an integer or float. If the input can't be converted, 0
will be used instead. If the argument can't be converted, an exception is raised.
{{ "20" | divided_by: "7" }}
{{ "hello" | divided_by: 2 }}
2
0
downcase
<string> | downcase
Return the input string with all characters in lowercase.
{{ 'Hello, World!' | downcase }}
hello, world!
If the input is not a string, Liquid will convert it to a string before forcing characters to lowercase.
{{ 5 | downcase }}
5
If the input is undefined, an empty string is returned.
escape
<string> | escape
Return the input string with characters &
, <
and >
converted to HTML-safe sequences.
{{ "Have you read 'James & the Giant Peach'?" | escape }}
Have you read 'James & the Giant Peach'?
escape_once
<string> | escape_once
Return the input string with characters &
, <
and >
converted to HTML-safe sequences, while
preserving existing HTML escape sequences.
{{ "Have you read 'James & the Giant Peach'?" | escape_once }}
Have you read 'James & the Giant Peach'?
first
<sequence> | first
Return the first item of the input sequence. The input could be array-like or a mapping, but not a string.
{{ "Ground control to Major Tom." | split: " " | first }}
Ground
If the input sequence is undefined, empty or not a sequence, nil
is returned.
floor
<number> | floor
Return the input down to the nearest whole number. Liquid tries to convert the input to a number before the filter is applied.
{{ 1.2 | floor }}
{{ 2.0 | floor }}
{{ 183.357 | floor }}
{{ -5.4 | floor }}
{{ "3.5" | floor }}
1
2
183
-6
3
If the input can't be converted to a number, 0
is returned.
join
<array> | join[: <string>]
Return the items in the input array as a single string, separated by the argument string. If the input is not an array, Liquid will convert it to one. If input array items are not strings, they will be converted to strings before joining.
{% assign beatles = "John, Paul, George, Ringo" | split: ", " -%}
{{ beatles | join: " and " }}
John and Paul and George and Ringo
If an argument string is not given, it defaults to a single space.
{% assign beatles = "John, Paul, George, Ringo" | split: ", " -%}
{{ beatles | join }}
John Paul George Ringo
last
<array> | last
Return the last item in the array-like input.
{{ "Ground control to Major Tom." | split: " " | last }}
Tom.
If the input is undefined, empty, string or a number, nil
will be returned.
lstrip
<string> | lstrip
Return the input string with all leading whitespace removed. If the input is not a string, it will be converted to a string before stripping whitespace.
{{ " So much room for activities " | lstrip }}!
So much room for activities !
map
<array> | map: <string>
Extract properties from an array of objects into a new array.
If pages
is an array of objects with a category
property:
{
"pages": [
{ "category": "business" },
{ "category": "celebrities" },
{ "category": "lifestyle" },
{ "category": "sports" },
{ "category": "technology" }
]
}
{% assign categories = pages | map: "category" -%}
{% for category in categories -%}
- {{ category }}
{%- endfor %}
- business
- celebrities
- lifestyle
- sports
- technology
minus
<number> | minus: <number>
Subtract one number from another. If either the input or argument are not a number, Liquid will try
to convert them to a number. If that conversion fails, 0
is used instead.
{{ 4 | minus: 2 }}
{{ "16" | minus: 4 }}
{{ 183.357 | minus: 12.2 }}
{{ "hello" | minus: 10 }}
2
12
171.157
-10
modulo
<number> | modulo: <number>
Return the remainder from the division of the input by the argument.
{{ 3 | modulo: 2 }}
{{ "24" | modulo: "7" }}
{{ 183.357 | modulo: 12 }}
1
3
3.357
If either the input or argument are not an integer or float, Liquid will try to convert them to an
integer or float. If the input can't be converted, 0
will be used instead. If the argument can't
be converted, an exception is raised.
newline_to_br
<string> | newline_to_br
Return the input string with \n
and \r\n
replaced with <br />\n
.
{% capture string_with_newlines %}
Hello
there
{% endcapture %}
{{ string_with_newlines | newline_to_br }}
<br />
Hello<br />
there<br />
plus
<number> | plus: <number>
Add one number to another. If either the input or argument are not a number, Liquid will try to
convert them to a number. If that conversion fails, 0
is used instead.
{{ 4 | plus: 2 }}
{{ "16" | plus: "4" }}
{{ 183.357 | plus: 12 }}
6
20
195.357
prepend
<string> | prepend: <string>
Return the argument concatenated with the filter input.
{{ "apples, oranges, and bananas" | prepend: "Some fruit: " }}
Some fruit: apples, oranges, and bananas
If either the input value or argument are not a string, they will be coerced to a string before concatenation.
{% assign a_number = 7.5 -%}
{{ 42 | prepend: a_number }}
{{ nosuchthing | prepend: 'World!' }}
7.542
World!
remove
<string> | remove: <string>
Return the input with all occurrences of the argument string removed.
{{ "I strained to see the train through the rain" | remove: "rain" }}
I sted to see the t through the
If either the filter input or argument are not a string, they will be coerced to a string before substring removal.
remove_first
<string> | remove_first: <string>
Return a copy of the input string with the first occurrence of the argument string removed.
{{ "I strained to see the train through the rain" | remove_first: "rain" }}
I sted to see the train through the rain
If either the filter input or argument are not a string, they will be coerced to a string before substring removal.
remove_last
<string> | remove_last: <string>
Return a copy of the input string with the last occurrence of the argument string removed.
{{ "I strained to see the train through the rain" | remove_last: "rain" }}
I strained to see the train through the
If either the filter input or argument are not a string, they will be coerced to a string before substring removal.
replace
<string> | replace: <string>[, <string>]
Return the input with all occurrences of the first argument replaced with the second argument. If
the second argument is omitted, it will default to an empty string, making replace
behave like
remove
.
{{ "Take my protein pills and put my helmet on" | replace: "my", "your" }}
Take your protein pills and put your helmet on
If either the filter input or argument are not a string, they will be coerced to a string before replacement.
replace_first
<string> | replace_first: <string>[, <string>]
Return a copy of the input string with the first occurrence of the first argument replaced with the second argument. If the second argument is omitted, it will default to an empty string, making replace_first
behave like remove_first
.
{{ "Take my protein pills and put my helmet on" | replace_first: "my", "your" }}
Take your protein pills and put my helmet on
If either the filter input or argument are not a string, they will be coerced to a string before replacement.
replace_last
<string> | replace_last: <string>, <string>
Return a copy of the input string with the last occurrence of the first argument replaced with the second argument.
{{ "Take my protein pills and put my helmet on" | replace_first: "my", "your" }}
Take my protein pills and put your helmet on
If either the filter input or argument are not a string, they will be coerced to a string before replacement.
reverse
<array> | reverse
Return a copy of the input array with the items in reverse order. If the filter input is a string,
reverse
will return the string unchanged.
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " -%}
{{ my_array | reverse | join: ", " }}
plums, peaches, oranges, apples
round
<number> | round[: <number>]
Return the input number rounded to the given number of decimal places. The number of digits defaults
to 0
.
{{ 1.2 | round }}
{{ 2.7 | round }}
{{ 183.357 | round: 2 }}
1
3
183.36
If either the filter input or its optional argument are not an integer or float, they will be converted to an integer or float before rounding.
rstrip
<string> | rstrip
Return the input string with all trailing whitespace removed. If the input is not a string, it will be converted to a string before stripping whitespace.
{{ " So much room for activities " | rstrip }}!
So much room for activities!
safe
<string> | safe
Return the input string marked as safe to use in an HTML or XML document. If the filter input is not a string, it will be converted to an HTML-safe string.
safe
is a non-standard feature added to Python Liquid for use with
HTML auto-escaping.
With auto-escape enabled and the following global variables:
{
"username": "Sally",
"greeting": "</p><script>alert('XSS!');</script>"
}
<p>{{ greeting }}, {{ username }}</p>
<p>{{ greeting | safe }}, {{ username }}</p>
<p></p><script>alert("XSS!");</script>, Sally</p>
<p></p><script>alert('XSS!');</script>, Sally</p>
size
<object> | size
Return the size of the input object. Works on strings, arrays and hashes.
{{ "Ground control to Major Tom." | size }}
{{ "apples, oranges, peaches, plums" | split: ", " | size }}
28
4
slice
<sequence> | slice: <int>[, <int>]
Return a substring or subsequence of the input string or array. The first argument is the zero-based
start index. The second, optional argument is the length of the substring or sequence, which
defaults to 1
.
{{ "Liquid" | slice: 0 }}
{{ "Liquid" | slice: 2 }}
{{ "Liquid" | slice: 2, 5 }}
{% assign beatles = "John, Paul, George, Ringo" | split: ", " -%}
{{ beatles | slice: 1, 2 | join: " " }}
L
q
quid
Paul George
If the first argument is negative, the start index is counted from the end of the sequence.
{{ "Liquid" | slice: -3 }}
{{ "Liquid" | slice: -3, 2 }}
{% assign beatles = "John, Paul, George, Ringo" | split: ", " -%}
{{ beatles | slice: -2, 2 | join: " " }}
u
ui
George Ringo
sort
<array> | sort[: <string>]
Return a copy of the input array with its elements sorted.
{% assign my_array = "zebra, octopus, giraffe, Sally Snake" | split: ", " -%}
{{ my_array | sort | join: ", " }}
Sally Snake, giraffe, octopus, zebra
The optional argument is a sort key. If given, it should be the name of a property and the filter's input should be an array of objects.
{
"collection": {
"products": [
{ "title": "A Shoe", "price": "9.95" },
{ "title": "A Tie", "price": "0.50" },
{ "title": "A Hat", "price": "2.50" }
]
}
}
{% assign products_by_price = collection.products | sort: "price" -%}
{% for product in products_by_price %}
<h4>{{ product.title }}</h4>
{% endfor %}
<h4>A Tie</h4>
<h4>A Hat</h4>
<h4>A Shoe</h4>
sort_natural
<array> | sort_natural[: <string>]
Return a copy of the input array with its elements sorted case-insensitively. Array elements compared by their string representations, forced to lowercase.
{% assign my_array = "zebra, octopus, giraffe, Sally Snake" | split: ", " -%}
{{ my_array | sort_natural | join: ", " }}
giraffe, octopus, Sally Snake, zebra
The optional argument is a sort key. If given, it should be the name of a property and the filter's input should be an array of objects. Array elements are compared using the lowercase string representation of that property.
{
"collection": {
"products": [
{ "title": "A Shoe", "company": "Cool Shoes" },
{ "title": "A Tie", "company": "alpha Ties" },
{ "title": "A Hat", "company": "Beta Hats" }
]
}
}
{% assign products_by_company = collection.products | sort_natural: "company" %}
{% for product in products_by_company %}
<h4>{{ product.title }}</h4>
{% endfor %}
<h4>A Tie</h4>
<h4>A Hat</h4>
<h4>A Shoe</h4>
split
<string> | split: <string>
Return an array of strings that are the input string split on the filter's argument string.
{% assign beatles = "John, Paul, George, Ringo" | split: ", " -%}
{% for member in beatles %}
{{- member }}
{% endfor %}
John
Paul
George
Ringo
If the argument is undefined or an empty string, the input will be split at every character.
{{ "Hello there" | split: nosuchthing | join: "#" }}
H#e#l#l#o# #t#h#e#r#e
strip
<string> | strip
Return the input string with all leading and trailing whitespace removed. If the input is not a string, it will be converted to a string before stripping whitespace.
{{ " So much room for activities " | strip }}!
So much room for activities!
strip_html
<string> | strip_html
Return the input string with all HTML tags removed.
{{ "Have <em>you</em> read <strong>Ulysses</strong>?" | strip_html }}
Have you read Ulysses?
strip_newlines
<string> | strip_newlines
Return the input string with \n
and \r\n
removed.
{% capture string_with_newlines %}
Hello
there
{% endcapture -%}
{{ string_with_newlines | strip_newlines }}
Hellothere
sum
<array> | sum[: <string>]
New in version 1.9.3
Return the sum of all numeric elements in an array.
{% assign array = '1,2,3' | split: ',' -%}
{{ array | sum }}
6
If the optional string argument is given, it is assumed that array items are hash/mapping-like, and the argument should be the name of a property/key. The values at array[property]
will be summed.
times
<number> | times: <number>
Return the product of the input number and the argument number. If either the input or argument are
not a number, Liquid will try to convert them to a number. If that conversion fails, 0
is used
instead.
{{ 3 | times: 2 }}
{{ "24" | times: "7" }}
{{ 183.357 | times: 12 }}
6
168
2200.284
truncate
<string> | truncate[: <integer>[, <string>]]
Return a truncated version of the input string. The first argument, length, defaults to 50
. The
second argument defaults to an ellipsis (...
).
If the length of the input string is less than the given length (first argument), the input string
will be truncated to length
minus the length of the second argument, with the second argument
appended.
{{ "Ground control to Major Tom." | truncate: 20 }}
{{ "Ground control to Major Tom." | truncate: 25, ", and so on" }}
{{ "Ground control to Major Tom." | truncate: 20, "" }}
Ground control to...
Ground control, and so on
Ground control to Ma
truncatewords
<string> | truncatewords[: <integer>[, <string>]]
Return the input string truncated to the specified number of words, with the second argument
appended. The number of words (first argument) defaults to 15
. The second argument defaults to an
ellipsis (...
).
If the input string already has fewer than the given number of words, it is returned unchanged.
{{ "Ground control to Major Tom." | truncatewords: 3 }}
{{ "Ground control to Major Tom." | truncatewords: 3, "--" }}
{{ "Ground control to Major Tom." | truncatewords: 3, "" }}
Ground control to...
Ground control to--
Ground control to
uniq
<array> | uniq[: <string>]
Return a copy of the input array with duplicate elements removed.
{% assign my_array = "ants, bugs, bees, bugs, ants" | split: ", " -%}
{{ my_array | uniq | join: ", " }}
ants, bugs, bees
If an argument is given, it should be the name of a property and the filter's input should be an array of objects.
{
"collection": {
"products": [
{ "title": "A Shoe", "company": "Cool Shoes" },
{ "title": "A Tie", "company": "alpha Ties" },
{ "title": "Another Tie", "company": "alpha Ties" },
{ "title": "A Hat", "company": "Beta Hats" }
]
}
}
{% assign one_product_from_each_company = collections.products | uniq: "company" -%}
{% for product in one_product_from_each_company -%}
- product.title
{% endfor %}
- A Shoe
- A Tie
- A Hat
upcase
<string> | upcase
Return the input string with all characters in uppercase.
{{ 'Hello, World!' | upcase }}
HELLO, WORLD!
url_decode
<string> | url_decode
Return the input string with %xx
escapes replaced with their single-character equivalents. Also
replaces '+'
with ' '
.
{{ "My+email+address+is+bob%40example.com%21" | url_decode }}
My email address is bob@example.com!
url_encode
<string> | url_encode
Return the input string with URL reserved characters %-escaped. Also replaces ' '
with '+'
.
{{ My email address is bob@example.com! | url_encode }}
My+email+address+is+bob%40example.com%21
where
<array> | where: <string>[, <object>]
Return a copy of the input array including only those objects that have a property, named with the first argument, equal to a value, given as the second argument. If a second argument is not given, only elements with the named property that are truthy will be included.
{
"products": [
{ "title": "Vacuum", "type": "house", "available": true },
{ "title": "Spatula", "type": "kitchen", "available": false },
{ "title": "Television", "type": "lounge", "available": true },
{ "title": "Garlic press", "type": "kitchen", "available": true }
]
}
All products:
{% for product in products -%}
- {{ product.title }}
{% endfor %}
{%- assign kitchen_products = products | where: "type", "kitchen" -%}
Kitchen products:
{% for product in kitchen_products -%}
- {{ product.title }}
{% endfor %}
{%- assign available_products = products | where: "available" -%}
Available products:
{% for product in available_products -%}
- {{ product.title }}
{% endfor %}
All products:
- Vacuum
- Spatula
- Television
- Garlic press
Kitchen products:
- Spatula
- Garlic press
Available product:
- Vacuum
- Television
- Garlic press