Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
17db93cf6f | ||
|
|
d07b12dc7d | ||
|
|
32e4f2d3b1 | ||
|
|
2cb1483d54 | ||
|
|
6c6350f18b | ||
|
|
eae24373e6 | ||
|
|
034a47a6cf | ||
|
|
51c1165f26 | ||
|
|
0b45ffeada | ||
|
|
b7b243a13d | ||
|
|
18e8ce1eb0 | ||
|
|
994f309465 | ||
|
|
02d42a1475 | ||
|
|
d099878385 | ||
|
|
6a061cbe81 | ||
|
|
c864a75903 | ||
|
|
d6fdf86acd | ||
|
|
55597b8398 | ||
|
|
c75522026b | ||
|
|
1e0e9f1f31 | ||
|
|
5fc1929b73 | ||
|
|
746a800475 | ||
|
|
85dc7ef610 | ||
|
|
bc3b066ba8 | ||
|
|
3c2de7737d | ||
|
|
adb7d2bbb8 | ||
|
|
0e56cf99ab | ||
|
|
0df3f1c372 | ||
|
|
44b9ad604f | ||
|
|
535d549978 | ||
|
|
32349033a9 | ||
|
|
fd8c30070a | ||
|
|
4cfc05e32a | ||
|
|
c4bc6cf3db | ||
|
|
0ac3ec7834 | ||
|
|
8909c9f27a | ||
|
|
51c708c8f8 | ||
|
|
f57383af37 | ||
|
|
d007c50856 | ||
|
|
101f125a69 | ||
|
|
5110ca906c | ||
|
|
ac0f63eda9 | ||
|
|
1372274fca | ||
|
|
69951be173 | ||
|
|
c9863836cd | ||
|
|
14b8d824d7 | ||
|
|
114a37d9ba | ||
|
|
30bd9ad957 | ||
|
|
2239921804 | ||
|
|
1ea178e7a8 | ||
|
|
5650c7eea1 | ||
|
|
553b0926ae | ||
|
|
2bac6267f9 | ||
|
|
628ab3dc6a | ||
|
|
2eb552c65d | ||
|
|
6e40746ce4 | ||
|
|
75068e8fa4 | ||
|
|
ad1152853a | ||
|
|
73098ac5bc | ||
|
|
8bc3792c0e | ||
|
|
3ef29c624c | ||
|
|
a85fb38769 | ||
|
|
6a1c3cff1a | ||
|
|
bde32018dd | ||
|
|
2a12f253bf | ||
|
|
fa14fd02e7 | ||
|
|
f15d24509d | ||
|
|
09e4378cfb | ||
|
|
af0e26fb16 | ||
|
|
f5502e8152 | ||
|
|
c098235baa | ||
|
|
0e2bf768ba | ||
|
|
4c477c2087 | ||
|
|
cd7fc050b1 | ||
|
|
8291c5e72c | ||
|
|
7e45155aa9 | ||
|
|
3dbb35d823 | ||
|
|
44f29a87a8 | ||
|
|
f0afbc27e0 | ||
|
|
fdf03076e0 | ||
|
|
d1bfda15e3 | ||
|
|
d8d9984a7b | ||
|
|
fbaabf3b59 | ||
|
|
7e0ef867d2 | ||
|
|
3682414cc4 | ||
|
|
af24d2c2ab | ||
|
|
4ee43bc5d2 | ||
|
|
1320a69fca | ||
|
|
3b14e27f55 | ||
|
|
face33a137 | ||
|
|
d4ecaff8b8 | ||
|
|
a5990042ff | ||
|
|
e190bbba9e | ||
|
|
4b5e41d04e | ||
|
|
4b69f6ae83 | ||
|
|
b9feb415f6 | ||
|
|
92781ec43b | ||
|
|
ff5c1f83f7 | ||
|
|
e2b337af2f | ||
|
|
f373b1003d | ||
|
|
503d924274 | ||
|
|
3efa8e8762 | ||
|
|
3c06d837b5 | ||
|
|
d3fc30ef85 | ||
|
|
f23e69d565 | ||
|
|
fa179e811d | ||
|
|
18907fc570 | ||
|
|
5f8a028a56 | ||
|
|
0a7de51e2b | ||
|
|
765751b9cb | ||
|
|
d2827bfa76 | ||
|
|
70d92b84ab | ||
|
|
808fa244ca | ||
|
|
5570f697fd | ||
|
|
8f9f12e542 | ||
|
|
17dae40707 | ||
|
|
06e2f2577f | ||
|
|
ee7edacacc | ||
|
|
62a86a25ae | ||
|
|
c6e0c1e490 | ||
|
|
43ac8d560b | ||
|
|
0388376925 | ||
|
|
57c8583dc3 | ||
|
|
a13f237d3c | ||
|
|
9ed2fa425b | ||
|
|
208c6c8800 | ||
|
|
9ec2b9da2d | ||
|
|
be7bef4d0b | ||
|
|
0ae42bbc32 | ||
|
|
0ec69890ab | ||
|
|
5e8f2f8bd0 | ||
|
|
0edb252489 | ||
|
|
5ce36f79e9 | ||
|
|
2d1f15281b | ||
|
|
4647e6d86b | ||
|
|
f5620d4670 | ||
|
|
f1a5f6899b | ||
|
|
de497eaed2 | ||
|
|
30e5f06313 | ||
|
|
d465d5e20c | ||
|
|
7989e834f3 | ||
|
|
c264459931 | ||
|
|
e667352629 | ||
|
|
2c26a880f0 | ||
|
|
cf49b06ccc | ||
|
|
f015d804ea | ||
|
|
78c42bce44 | ||
|
|
445f19d454 | ||
|
|
a599a26f1a | ||
|
|
4e14a651a7 | ||
|
|
cc982e92d0 | ||
|
|
71a386f723 | ||
|
|
2f50a0c422 | ||
|
|
a5cd661dd9 | ||
|
|
511ee7fbe1 | ||
|
|
5eddfe87d0 | ||
|
|
9b910a4e6d | ||
|
|
7e1a0be752 | ||
|
|
c9ea578b64 | ||
|
|
549777ae53 | ||
|
|
6710ef60bc | ||
|
|
5fdab083b0 | ||
|
|
0644da02bb | ||
|
|
5db1695694 | ||
|
|
a25ed17e2b | ||
|
|
fa3155fdcc | ||
|
|
534338f923 | ||
|
|
96b30a89a9 | ||
|
|
81d3733f57 | ||
|
|
2efe809e11 | ||
|
|
322ecca145 | ||
|
|
6ce0b9d705 | ||
|
|
736998df64 | ||
|
|
5b172a4c05 | ||
|
|
bd20595f1a | ||
|
|
f938756a58 | ||
|
|
1ae8c0e90a | ||
|
|
45795f8766 | ||
|
|
01d352bc51 | ||
|
|
70513fccaf | ||
|
|
a5285d3d09 | ||
|
|
fbfd5712df | ||
|
|
90593d3f18 | ||
|
|
beded415cd | ||
|
|
13c826933c | ||
|
|
7c5b3e0c3b | ||
|
|
ca5bc5d75b | ||
|
|
d4679cd550 | ||
|
|
9b2d5b7dd3 | ||
|
|
e8b41c8856 | ||
|
|
4c22bacbba | ||
|
|
09a5b57ebe | ||
|
|
8059da4938 | ||
|
|
af50f71224 | ||
|
|
136b6763e6 | ||
|
|
ad184fbfc9 | ||
|
|
380828f807 | ||
|
|
fc8c45ebe6 | ||
|
|
072c12dc47 | ||
|
|
29cdabc30e | ||
|
|
df5980f23f | ||
|
|
5ee4f960e8 | ||
|
|
0343f6dc94 | ||
|
|
40fba9ee6c | ||
|
|
0a2f21386d | ||
|
|
e7bcf04d1d | ||
|
|
0dac6fe88a | ||
|
|
f37a984fd7 | ||
|
|
0e41c2c6e9 | ||
|
|
7b52dfcb95 | ||
|
|
1fa029ab67 | ||
|
|
26eb9a0817 | ||
|
|
e305edc3b8 | ||
|
|
c94b5e87c9 | ||
|
|
dd3196b22e | ||
|
|
86ba2f4174 | ||
|
|
5bdfb62bf2 | ||
|
|
77db92de54 | ||
|
|
b0cba5298a | ||
|
|
93fcd5687c | ||
|
|
14a17520de | ||
|
|
0beb4a4793 | ||
|
|
324d26d405 | ||
|
|
047900d0dd | ||
|
|
f6f89fd0aa | ||
|
|
a57d576708 | ||
|
|
eb68a751ac | ||
|
|
355199dac4 | ||
|
|
c8f38ad9d0 | ||
|
|
ed4b61bfd3 | ||
|
|
8f978ecd1a | ||
|
|
98c184f2fb | ||
|
|
615e48fe29 | ||
|
|
6cde98319f | ||
|
|
15b53b77d6 | ||
|
|
48f50eea3b | ||
|
|
ace12e29da | ||
|
|
f98949117d | ||
|
|
7fdb789eac | ||
|
|
c92efd3ab9 | ||
|
|
ff570c3ddc | ||
|
|
824231284c | ||
|
|
ee2902761c | ||
|
|
f6eacbf875 | ||
|
|
c5afdc529a | ||
|
|
84f0c1bef8 | ||
|
|
1458396733 | ||
|
|
346e92aaa6 | ||
|
|
3b3961be39 | ||
|
|
8ca00982b6 | ||
|
|
525e1ff195 | ||
|
|
8f4b398c7a | ||
|
|
d5d41a8202 | ||
|
|
c8bd0b91b3 | ||
|
|
bc76c0daaf | ||
|
|
be4a04ed85 | ||
|
|
8dcf44e99d | ||
|
|
a892e69a88 | ||
|
|
bf53e517f5 | ||
|
|
bacacf2fd0 | ||
|
|
1b43bf5686 | ||
|
|
83e71ace99 | ||
|
|
4dc9cc0ea1 | ||
|
|
87b8ee7341 | ||
|
|
07f7d63bea | ||
|
|
1af28a6eb8 | ||
|
|
65dfd57bb5 | ||
|
|
8b1dff9d98 | ||
|
|
8896b55fa5 | ||
|
|
c0b9d53548 | ||
|
|
24ddaf1a9c | ||
|
|
673826630c | ||
|
|
554675d1f8 | ||
|
|
11e1379570 | ||
|
|
3e13ed4ba1 | ||
|
|
b004acf856 | ||
|
|
182d3fefb6 | ||
|
|
17d818b453 | ||
|
|
0453d7e299 | ||
|
|
4da7b36139 | ||
|
|
c7336e0cc1 | ||
|
|
f43e973e67 | ||
|
|
bbc405a24c | ||
|
|
f9027d54ab | ||
|
|
84be895db2 | ||
|
|
b20a594f25 | ||
|
|
76272a1afa | ||
|
|
61a6deb43b | ||
|
|
ee14775f83 | ||
|
|
2332d86156 | ||
|
|
fbfda1a189 | ||
|
|
f0ecd02199 | ||
|
|
4a103a9dde | ||
|
|
0f38fe3596 | ||
|
|
cd3f976288 | ||
|
|
b53601100f | ||
|
|
5c5e7de31e | ||
|
|
f91233450f | ||
|
|
429e492984 | ||
|
|
d36a1c518b | ||
|
|
40a37c3fb6 | ||
|
|
37309678de | ||
|
|
cfb60c2f1b | ||
|
|
668ee5e1c4 | ||
|
|
b4fbcea114 | ||
|
|
c16697746b | ||
|
|
f01d0dbea6 | ||
|
|
10c151e3aa | ||
|
|
d6e13faa43 | ||
|
|
0f5441b09e | ||
|
|
7a3746ad77 | ||
|
|
24511556d3 | ||
|
|
5621556b3a | ||
|
|
fd230bef14 | ||
|
|
e9f3a8e4d3 | ||
|
|
8ca4868bff | ||
|
|
f92da6948d | ||
|
|
a1b156f0d4 | ||
|
|
eca520025c | ||
|
|
9c9a7ce8d3 | ||
|
|
b7837ce218 | ||
|
|
b81469d183 | ||
|
|
f488058789 | ||
|
|
f5d75718e9 | ||
|
|
c280936afa | ||
|
|
e47d1af03a | ||
|
|
81f6c79c53 | ||
|
|
3174411407 | ||
|
|
f7c4b0cdec | ||
|
|
3d1f582318 | ||
|
|
27db1def63 | ||
|
|
5cfa13d7a4 | ||
|
|
cb12497859 | ||
|
|
4c2e2f8a24 | ||
|
|
a2df5a421d | ||
|
|
437e9201de | ||
|
|
fd263bba0f | ||
|
|
0d9353591b | ||
|
|
1849c24f2c | ||
|
|
f8288546f8 | ||
|
|
076ae903c0 | ||
|
|
ba5e65f685 | ||
|
|
b699c93bae | ||
|
|
85c1503378 | ||
|
|
ab760649ee | ||
|
|
f4fb2f159c | ||
|
|
a5cd494717 | ||
|
|
f8915f3cd2 | ||
|
|
e92540a9bf | ||
|
|
482115d784 | ||
|
|
94ff457744 | ||
|
|
1e8c081b42 | ||
|
|
2b17e24b16 | ||
|
|
9075b428b1 | ||
|
|
8760b5e8c4 | ||
|
|
50b2ebee56 | ||
|
|
23203c0122 | ||
|
|
27fe76c0dd | ||
|
|
8913a5615a | ||
|
|
690b3ff27f | ||
|
|
8c1bbfec57 | ||
|
|
b8fbd2b4fa | ||
|
|
ba5a9f2e47 | ||
|
|
1e309ba74b | ||
|
|
485340713a | ||
|
|
2af4ea1295 | ||
|
|
c5dfcd29b0 | ||
|
|
f9c289372d | ||
|
|
a556ae6c26 | ||
|
|
f7d1e1d0c1 | ||
|
|
28fd2222c8 | ||
|
|
1cac09831d | ||
|
|
9913895b81 | ||
|
|
d706db3bd7 | ||
|
|
17dd85868d | ||
|
|
6e967f7f3a | ||
|
|
38b4543bf1 | ||
|
|
1300210f05 | ||
|
|
a48e162237 | ||
|
|
7bcb565668 | ||
|
|
c3e6cde67f | ||
|
|
0b36540b78 | ||
|
|
50bd34fd78 | ||
|
|
ee41b3f4a3 | ||
|
|
b48ad7da3a | ||
|
|
afc3944a4a | ||
|
|
c79abf1f87 | ||
|
|
90b40ffb4b | ||
|
|
fea9c54768 | ||
|
|
05d9976e16 | ||
|
|
6c2fde5eea | ||
|
|
ce76dbf8d9 | ||
|
|
661ff2ccdf | ||
|
|
9c183bea83 | ||
|
|
484fd18612 | ||
|
|
bf86459456 | ||
|
|
d2827c561b | ||
|
|
16c34595a4 | ||
|
|
6e091909ee | ||
|
|
d7cb39ccb3 | ||
|
|
f8d46804fd | ||
|
|
5c6de2d919 | ||
|
|
a8e9327f0b | ||
|
|
f5a20ff8e8 | ||
|
|
d0184555d9 | ||
|
|
6ebdded8f2 | ||
|
|
515b31158e | ||
|
|
40cc799f3d | ||
|
|
5ac91e0837 | ||
|
|
f6cb54fa59 | ||
|
|
1606b4b705 | ||
|
|
7cfd0f15d1 | ||
|
|
25ba54fc52 | ||
|
|
1aff63ff57 | ||
|
|
08fdcbbf65 | ||
|
|
2dba9ed0ea | ||
|
|
6d02d59fbd | ||
|
|
281e3ea9c8 | ||
|
|
b51b30fac1 | ||
|
|
740cd6e762 | ||
|
|
5d0004a87e | ||
|
|
12112dee35 | ||
|
|
84ed3d9964 | ||
|
|
c10f936d2a | ||
|
|
1ee342d83b | ||
|
|
0e3b522fe2 | ||
|
|
db07e2b67e | ||
|
|
5c4938f443 | ||
|
|
b8d7b9aeda | ||
|
|
3d7c1c80a0 | ||
|
|
1b2d0198ea | ||
|
|
043d816460 | ||
|
|
4a2bbafeb4 | ||
|
|
974ea40cca | ||
|
|
d8b416187a | ||
|
|
58ad90677b | ||
|
|
2b04590d4b | ||
|
|
bce0033c65 | ||
|
|
01dea94671 | ||
|
|
1a1b4702d7 | ||
|
|
85d1dc0d07 | ||
|
|
0eafe7f2fd | ||
|
|
815e4e2b8d | ||
|
|
ef98715b12 | ||
|
|
c4d713b6bb | ||
|
|
975b17b529 | ||
|
|
745d875e79 | ||
|
|
c91cb8af6c | ||
|
|
bb73198b4f | ||
|
|
f0f2e56369 | ||
|
|
b816521563 | ||
|
|
4026f6c340 | ||
|
|
05a20c627d | ||
|
|
8e3f0c122e | ||
|
|
487b240404 | ||
|
|
f129ee33f2 | ||
|
|
cdf7f5b6a7 | ||
|
|
204d876187 | ||
|
|
8b5cf73ccc | ||
|
|
edebcaa603 | ||
|
|
6cf6d8b990 | ||
|
|
1379061398 | ||
|
|
4971b9e9bc | ||
|
|
da34d27258 | ||
|
|
cc7899aef5 | ||
|
|
0fc78a2dbb | ||
|
|
c401ffb9c3 | ||
|
|
2434c3d0e0 | ||
|
|
352f83a9d2 | ||
|
|
98c96ed86a | ||
|
|
410cce9740 | ||
|
|
a8ed72a036 | ||
|
|
4aaf750fa8 | ||
|
|
e5a3d67a32 | ||
|
|
fe25644726 | ||
|
|
c47eac1683 | ||
|
|
c10a40f1fa | ||
|
|
e4003a74a1 | ||
|
|
03065274d8 | ||
|
|
00afc9dd8a | ||
|
|
6bfdda9e17 | ||
|
|
00da0b6a42 | ||
|
|
39174ccee6 | ||
|
|
c7033ff4c8 | ||
|
|
f85bea2902 | ||
|
|
17922273e1 | ||
|
|
4087a94d88 | ||
|
|
1a4ff9547a | ||
|
|
888cbe8f09 | ||
|
|
2f11364417 | ||
|
|
74cdfc6718 | ||
|
|
d19213177a | ||
|
|
caf59940d3 | ||
|
|
8319d78c2e | ||
|
|
bc55c4d348 | ||
|
|
017f0dc342 | ||
|
|
ab556cbdd9 | ||
|
|
82e4904403 | ||
|
|
59a63e0fe5 | ||
|
|
aafb3ed9f2 | ||
|
|
935d3530af | ||
|
|
662b2983fe | ||
|
|
37a0fe213b | ||
|
|
7bbb4ff84f | ||
|
|
9926d86c91 | ||
|
|
9c49b8bbb2 | ||
|
|
f7ff9c81d3 | ||
|
|
a65c4f51bc | ||
|
|
a24049906b | ||
|
|
aa678302d6 | ||
|
|
6d0bb3303c | ||
|
|
4fec29f288 | ||
|
|
33ecb29d49 | ||
|
|
58e5820e7a | ||
|
|
bb035d96e1 | ||
|
|
3919ff6bc3 | ||
|
|
381b4f5268 | ||
|
|
97f18112b2 | ||
|
|
ca2fa587cf | ||
|
|
0526348cae | ||
|
|
a3fb7ba2b3 | ||
|
|
77cc0f2ed9 | ||
|
|
3d43efe2bc | ||
|
|
772233d881 | ||
|
|
90d1bc26d8 | ||
|
|
c00a650492 | ||
|
|
4819eb1a92 | ||
|
|
8579807d29 | ||
|
|
daf786fd28 | ||
|
|
101137045e | ||
|
|
8a0a8cfd99 | ||
|
|
8304a046c9 | ||
|
|
c72c84ea9b | ||
|
|
01145f872b | ||
|
|
5409814552 | ||
|
|
2d9331a234 | ||
|
|
c59cde9d17 | ||
|
|
29e140b655 | ||
|
|
a48332871a | ||
|
|
bd7f867759 | ||
|
|
8e4573a7bf | ||
|
|
5425679a96 | ||
|
|
6831eac902 | ||
|
|
13f98de7f3 | ||
|
|
e26f509277 | ||
|
|
0417c9e723 | ||
|
|
ffd48880e2 | ||
|
|
6b79f25c87 | ||
|
|
ff829e7996 | ||
|
|
d53a4e1834 | ||
|
|
5ff699bb8a | ||
|
|
d87500bfe3 | ||
|
|
fce8bcb1e7 | ||
|
|
97548d4f01 | ||
|
|
cbf8986745 | ||
|
|
11dc18bfdf | ||
|
|
f42ce88456 | ||
|
|
d1d6febfc1 | ||
|
|
0150067c40 | ||
|
|
2d0532e041 | ||
|
|
167825aa92 | ||
|
|
c792c29066 | ||
|
|
a4d7c80ce0 | ||
|
|
7ff4352de2 | ||
|
|
44f35c0990 | ||
|
|
a65bd76e72 | ||
|
|
8ac4d6a92a | ||
|
|
37e913f755 | ||
|
|
5e0ad75ff5 | ||
|
|
1b3b3e4958 | ||
|
|
31a5606d42 | ||
|
|
f65ce254c7 | ||
|
|
01c25a11a3 | ||
|
|
f29b9335c5 | ||
|
|
cfe3e6f3be | ||
|
|
09c0b3b391 | ||
|
|
678fdfdb8a | ||
|
|
ed1b542abf | ||
|
|
8d27864845 | ||
|
|
37580976db | ||
|
|
daadb1a2d6 | ||
|
|
68433a52a3 | ||
|
|
075341d01c | ||
|
|
981831bc49 | ||
|
|
edcc14f148 | ||
|
|
e3fd003a74 | ||
|
|
26faf512a1 | ||
|
|
56f1aa9b4a | ||
|
|
70ca647e1e | ||
|
|
13ddc6d96b | ||
|
|
88309cf415 | ||
|
|
7b9b5f31fb | ||
|
|
b165599495 | ||
|
|
96c998a944 | ||
|
|
7031d8a49a | ||
|
|
7959664c9d | ||
|
|
c15a683063 | ||
|
|
36860eab57 | ||
|
|
3d8efe04a7 | ||
|
|
edf7b5577b | ||
|
|
282786d7e2 | ||
|
|
69bc84b777 | ||
|
|
3bfde37a53 | ||
|
|
24bf446b0e | ||
|
|
916f501bde | ||
|
|
7eeb895192 | ||
|
|
7acdac2a1c | ||
|
|
50edd0f5b9 | ||
|
|
819b70204f | ||
|
|
eb609ee4aa | ||
|
|
3eddf5fb9e | ||
|
|
6dd4f716f8 | ||
|
|
5c259a3f49 | ||
|
|
1a160c5d84 | ||
|
|
56caba720d | ||
|
|
d28cbe6df7 | ||
|
|
1ccb83d7cb | ||
|
|
e0dd07811c | ||
|
|
82e5e8c188 | ||
|
|
3ef9d2f4f9 | ||
|
|
4c30922d8e | ||
|
|
ed75a6d948 | ||
|
|
63f9a05223 | ||
|
|
8f45647aa3 | ||
|
|
4c0cfae0b7 | ||
|
|
7f58cbf82d | ||
|
|
1d647361e1 |
@@ -1,42 +1,8 @@
|
||||
_site/
|
||||
.sass-cache/
|
||||
node_modules/
|
||||
*~
|
||||
*.gem
|
||||
*.swp
|
||||
pkg
|
||||
*.rbc
|
||||
.rvmrc
|
||||
.ruby-version
|
||||
Gemfile.lock
|
||||
|
||||
# Compiled source #
|
||||
###################
|
||||
*.com
|
||||
*.class
|
||||
*.dll
|
||||
*.exe
|
||||
*.o
|
||||
*.so
|
||||
|
||||
# Packages #
|
||||
############
|
||||
# it's better to unpack these files and commit the raw source
|
||||
# git has its own built in compression methods
|
||||
*.7z
|
||||
*.dmg
|
||||
*.gz
|
||||
*.iso
|
||||
*.jar
|
||||
*.rar
|
||||
*.tar
|
||||
*.zip
|
||||
|
||||
# Logs and databases #
|
||||
######################
|
||||
*.log
|
||||
*.sql
|
||||
*.sqlite
|
||||
|
||||
# OS generated files #
|
||||
######################
|
||||
.DS_Store
|
||||
.DS_Store?
|
||||
._*
|
||||
.Spotlight-V100
|
||||
.Trashes
|
||||
ehthumbs.db
|
||||
Thumbs.db
|
||||
|
||||
@@ -1,4 +1,16 @@
|
||||
install: gem install github-pages
|
||||
script: jekyll build --trace
|
||||
sudo: false
|
||||
rvm: 2.1
|
||||
rvm:
|
||||
- 1.9
|
||||
- 2.0
|
||||
- 2.1
|
||||
- jruby-19mode
|
||||
- jruby-head
|
||||
- rbx-2
|
||||
matrix:
|
||||
allow_failures:
|
||||
- rvm: rbx-2
|
||||
- rvm: jruby-head
|
||||
|
||||
script: "rake test"
|
||||
|
||||
notifications:
|
||||
disable: true
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
# How to contribute
|
||||
|
||||
## Things we will merge
|
||||
|
||||
* Bugfixes
|
||||
* Performance improvements
|
||||
* Features which are likely to be useful to the majority of Liquid users
|
||||
|
||||
## Things we won't merge
|
||||
|
||||
* Code which introduces considerable performance degrations
|
||||
* Code which touches performance critical parts of Liquid and comes without benchmarks
|
||||
* Features which are not important for most people (we want to keep the core Liquid code small and tidy)
|
||||
* Features which can easily be implemented on top of Liquid (for example as a custom filter or custom filesystem)
|
||||
* Code which comes without tests
|
||||
* Code which breaks existing tests
|
||||
|
||||
## Workflow
|
||||
|
||||
* Fork the Liquid repository
|
||||
* Create a new branch in your fork
|
||||
* If it makes sense, add tests for your code and run a performance benchmark
|
||||
* Make sure all tests pass
|
||||
* Create a pull request
|
||||
* In the description, ping one of [@boourns](https://github.com/boourns), [@fw42](https://github.com/fw42), [@camilo](https://github.com/camilo), [@dylanahsmith](https://github.com/dylanahsmith), or [@arthurnn](https://github.com/arthurnn) and ask for a code review.
|
||||
|
||||
@@ -1,3 +1,8 @@
|
||||
source 'https://rubygems.org'
|
||||
|
||||
gem 'github-pages', '>=100', group: :jekyll_plugins
|
||||
gemspec
|
||||
gem 'stackprof', platforms: :mri_21
|
||||
|
||||
group :test do
|
||||
gem 'spy', '0.4.1'
|
||||
end
|
||||
|
||||
@@ -1,145 +0,0 @@
|
||||
GEM
|
||||
remote: https://rubygems.org/
|
||||
specs:
|
||||
activesupport (4.2.7)
|
||||
i18n (~> 0.7)
|
||||
json (~> 1.7, >= 1.7.7)
|
||||
minitest (~> 5.1)
|
||||
thread_safe (~> 0.3, >= 0.3.4)
|
||||
tzinfo (~> 1.1)
|
||||
addressable (2.4.0)
|
||||
coffee-script (2.4.1)
|
||||
coffee-script-source
|
||||
execjs
|
||||
coffee-script-source (1.10.0)
|
||||
colorator (1.1.0)
|
||||
ethon (0.9.1)
|
||||
ffi (>= 1.3.0)
|
||||
execjs (2.7.0)
|
||||
faraday (0.9.2)
|
||||
multipart-post (>= 1.2, < 3)
|
||||
ffi (1.9.14)
|
||||
forwardable-extended (2.6.0)
|
||||
gemoji (2.1.0)
|
||||
github-pages (104)
|
||||
activesupport (= 4.2.7)
|
||||
github-pages-health-check (= 1.2.0)
|
||||
jekyll (= 3.3.0)
|
||||
jekyll-avatar (= 0.4.2)
|
||||
jekyll-coffeescript (= 1.0.1)
|
||||
jekyll-feed (= 0.8.0)
|
||||
jekyll-gist (= 1.4.0)
|
||||
jekyll-github-metadata (= 2.2.0)
|
||||
jekyll-mentions (= 1.2.0)
|
||||
jekyll-paginate (= 1.1.0)
|
||||
jekyll-redirect-from (= 0.11.0)
|
||||
jekyll-sass-converter (= 1.3.0)
|
||||
jekyll-seo-tag (= 2.1.0)
|
||||
jekyll-sitemap (= 0.12.0)
|
||||
jekyll-swiss (= 0.4.0)
|
||||
jemoji (= 0.7.0)
|
||||
kramdown (= 1.11.1)
|
||||
liquid (= 3.0.6)
|
||||
listen (= 3.0.6)
|
||||
mercenary (~> 0.3)
|
||||
minima (= 2.0.0)
|
||||
rouge (= 1.11.1)
|
||||
terminal-table (~> 1.4)
|
||||
github-pages-health-check (1.2.0)
|
||||
addressable (~> 2.3)
|
||||
net-dns (~> 0.8)
|
||||
octokit (~> 4.0)
|
||||
public_suffix (~> 1.4)
|
||||
typhoeus (~> 0.7)
|
||||
html-pipeline (2.4.2)
|
||||
activesupport (>= 2)
|
||||
nokogiri (>= 1.4)
|
||||
i18n (0.7.0)
|
||||
jekyll (3.3.0)
|
||||
addressable (~> 2.4)
|
||||
colorator (~> 1.0)
|
||||
jekyll-sass-converter (~> 1.0)
|
||||
jekyll-watch (~> 1.1)
|
||||
kramdown (~> 1.3)
|
||||
liquid (~> 3.0)
|
||||
mercenary (~> 0.3.3)
|
||||
pathutil (~> 0.9)
|
||||
rouge (~> 1.7)
|
||||
safe_yaml (~> 1.0)
|
||||
jekyll-avatar (0.4.2)
|
||||
jekyll (~> 3.0)
|
||||
jekyll-coffeescript (1.0.1)
|
||||
coffee-script (~> 2.2)
|
||||
jekyll-feed (0.8.0)
|
||||
jekyll (~> 3.3)
|
||||
jekyll-gist (1.4.0)
|
||||
octokit (~> 4.2)
|
||||
jekyll-github-metadata (2.2.0)
|
||||
jekyll (~> 3.1)
|
||||
octokit (~> 4.0, != 4.4.0)
|
||||
jekyll-mentions (1.2.0)
|
||||
activesupport (~> 4.0)
|
||||
html-pipeline (~> 2.3)
|
||||
jekyll (~> 3.0)
|
||||
jekyll-paginate (1.1.0)
|
||||
jekyll-redirect-from (0.11.0)
|
||||
jekyll (>= 2.0)
|
||||
jekyll-sass-converter (1.3.0)
|
||||
sass (~> 3.2)
|
||||
jekyll-seo-tag (2.1.0)
|
||||
jekyll (~> 3.3)
|
||||
jekyll-sitemap (0.12.0)
|
||||
jekyll (~> 3.3)
|
||||
jekyll-swiss (0.4.0)
|
||||
jekyll-watch (1.5.0)
|
||||
listen (~> 3.0, < 3.1)
|
||||
jemoji (0.7.0)
|
||||
activesupport (~> 4.0)
|
||||
gemoji (~> 2.0)
|
||||
html-pipeline (~> 2.2)
|
||||
jekyll (>= 3.0)
|
||||
json (1.8.3)
|
||||
kramdown (1.11.1)
|
||||
liquid (3.0.6)
|
||||
listen (3.0.6)
|
||||
rb-fsevent (>= 0.9.3)
|
||||
rb-inotify (>= 0.9.7)
|
||||
mercenary (0.3.6)
|
||||
mini_portile2 (2.1.0)
|
||||
minima (2.0.0)
|
||||
minitest (5.9.1)
|
||||
multipart-post (2.0.0)
|
||||
net-dns (0.8.0)
|
||||
nokogiri (1.6.8.1)
|
||||
mini_portile2 (~> 2.1.0)
|
||||
octokit (4.6.0)
|
||||
sawyer (~> 0.8.0, >= 0.5.3)
|
||||
pathutil (0.14.0)
|
||||
forwardable-extended (~> 2.6)
|
||||
public_suffix (1.5.3)
|
||||
rb-fsevent (0.9.8)
|
||||
rb-inotify (0.9.7)
|
||||
ffi (>= 0.5.0)
|
||||
rouge (1.11.1)
|
||||
safe_yaml (1.0.4)
|
||||
sass (3.4.22)
|
||||
sawyer (0.8.0)
|
||||
addressable (>= 2.3.5, < 2.6)
|
||||
faraday (~> 0.8, < 0.10)
|
||||
terminal-table (1.7.3)
|
||||
unicode-display_width (~> 1.1.1)
|
||||
thread_safe (0.3.5)
|
||||
typhoeus (0.8.0)
|
||||
ethon (>= 0.8.0)
|
||||
tzinfo (1.2.2)
|
||||
thread_safe (~> 0.1)
|
||||
unicode-display_width (1.1.1)
|
||||
|
||||
PLATFORMS
|
||||
ruby
|
||||
|
||||
DEPENDENCIES
|
||||
github-pages (>= 100)
|
||||
|
||||
BUNDLED WITH
|
||||
1.13.1
|
||||
@@ -1,72 +0,0 @@
|
||||
// Gruntfile
|
||||
module.exports = function(grunt) {
|
||||
require('load-grunt-tasks')(grunt);
|
||||
|
||||
// Project configuration.
|
||||
grunt.initConfig({
|
||||
|
||||
pkg: grunt.file.readJSON('package.json'),
|
||||
|
||||
watch: {
|
||||
css: {
|
||||
files: ['_sass/**/*.scss'],
|
||||
tasks: ['sass', 'postcss', 'shell:jekyllBuild'],
|
||||
options: {
|
||||
atBegin: true
|
||||
}
|
||||
},
|
||||
jekyll: {
|
||||
files: ['index.md', '_includes/*.html', 'filters/*.*', '_layouts/*.*', 'tags/*.*', 'basics/*.*'],
|
||||
tasks: ['shell:jekyllBuild']
|
||||
}
|
||||
},
|
||||
|
||||
sass: {
|
||||
dist: {
|
||||
options: {
|
||||
style: 'expanded',
|
||||
sourcemap: 'none'
|
||||
},
|
||||
files: {
|
||||
'_site/css/main.css':'_sass/main.scss'
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
shell: {
|
||||
jekyllServe: {
|
||||
command: 'jekyll serve --no-watch'
|
||||
},
|
||||
|
||||
jekyllBuild: {
|
||||
command: 'jekyll build'
|
||||
}
|
||||
},
|
||||
|
||||
postcss: {
|
||||
options: {
|
||||
map: true,
|
||||
processors: [
|
||||
require('autoprefixer-core')({browsers: 'last 2 versions'})
|
||||
]
|
||||
},
|
||||
dist: {
|
||||
src: '_site/css/*.css'
|
||||
}
|
||||
},
|
||||
|
||||
concurrent: {
|
||||
tasks: ['shell:jekyllServe', 'watch'],
|
||||
options: {
|
||||
logConcurrentOutput: true
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
grunt.loadNpmTasks('grunt-contrib-watch');
|
||||
grunt.loadNpmTasks('grunt-contrib-sass');
|
||||
grunt.loadNpmTasks('grunt-postcss');
|
||||
grunt.loadNpmTasks('grunt-concurrent');
|
||||
|
||||
grunt.registerTask('default', ['concurrent']);
|
||||
};
|
||||
@@ -0,0 +1,160 @@
|
||||
# Liquid Version History
|
||||
|
||||
## 3.0.0 / not yet released / branch "master"
|
||||
|
||||
* ...
|
||||
* Add exception_handler feature, see #397 and #254 [Bogdan Gusiev, bogdan and Florian Weingarten, fw42]
|
||||
* Optimize variable parsing to avoid repeated regex evaluation during template rendering #383 [Jason Hiltz-Laforge, jasonhl]
|
||||
* Optimize checking for block interrupts to reduce object allocation #380 [Jason Hiltz-Laforge, jasonhl]
|
||||
* Properly set context rethrow_errors on render! #349 [Thierry Joyal, tjoyal]
|
||||
* Fix broken rendering of variables which are equal to false, see #345 [Florian Weingarten, fw42]
|
||||
* Remove ActionView template handler [Dylan Thacker-Smith, dylanahsmith]
|
||||
* Freeze lots of string literals for new Ruby 2.1 optimization, see #297 [Florian Weingarten, fw42]
|
||||
* Allow newlines in tags and variables, see #324 [Dylan Thacker-Smith, dylanahsmith]
|
||||
* Tag#parse is called after initialize, which now takes options instead of tokens as the 3rd argument. See #321 [Dylan Thacker-Smith, dylanahsmith]
|
||||
* Raise `Liquid::ArgumentError` instead of `::ArgumentError` when filter has wrong number of arguments #309 [Bogdan Gusiev, bogdan]
|
||||
* Add a to_s default for liquid drops, see #306 [Adam Doeler, releod]
|
||||
* Add strip, lstrip, and rstrip to standard filters [Florian Weingarten, fw42]
|
||||
* Make if, for & case tags return complete and consistent nodelists, see #250 [Nick Jones, dntj]
|
||||
* Prevent arbitrary method invocation on condition objects, see #274 [Dylan Thacker-Smith, dylanahsmith]
|
||||
* Don't call to_sym when creating conditions for security reasons, see #273 [Bouke van der Bijl, bouk]
|
||||
* Fix resource counting bug with respond_to?(:length), see #263 [Florian Weingarten, fw42]
|
||||
* Allow specifying custom patterns for template filenames, see #284 [Andrei Gladkyi, agladkyi]
|
||||
* Allow drops to optimize loading a slice of elements, see #282 [Tom Burns, boourns]
|
||||
* Support for passing variables to snippets in subdirs, see #271 [Joost Hietbrink, joost]
|
||||
* Add a class cache to avoid runtime extend calls, see #249 [James Tucker, raggi]
|
||||
* Remove some legacy Ruby 1.8 compatibility code, see #276 [Florian Weingarten, fw42]
|
||||
* Add default filter to standard filters, see #267 [Derrick Reimer, djreimer]
|
||||
* Add optional strict parsing and warn parsing, see #235 [Tristan Hume, trishume]
|
||||
* Add I18n syntax error translation, see #241 [Simon Hørup Eskildsen, Sirupsen]
|
||||
* Make sort filter work on enumerable drops, see #239 [Florian Weingarten, fw42]
|
||||
* Fix clashing method names in enumerable drops, see #238 [Florian Weingarten, fw42]
|
||||
* Make map filter work on enumerable drops, see #233 [Florian Weingarten, fw42]
|
||||
* Improved whitespace stripping for blank blocks, related to #216 [Florian Weingarten, fw42]
|
||||
|
||||
## 2.6.1 / 2014-01-10 / branch "2-6-stable"
|
||||
|
||||
Security fix, cherry-picked from master (4e14a65):
|
||||
* Don't call to_sym when creating conditions for security reasons, see #273 [Bouke van der Bijl, bouk]
|
||||
* Prevent arbitrary method invocation on condition objects, see #274 [Dylan Thacker-Smith, dylanahsmith]
|
||||
|
||||
## 2.6.0 / 2013-11-25
|
||||
|
||||
IMPORTANT: Liquid 2.6 is going to be the last version of Liquid which maintains explicit Ruby 1.8 compatability.
|
||||
The following releases will only be tested against Ruby 1.9 and Ruby 2.0 and are likely to break on Ruby 1.8.
|
||||
|
||||
* Bugfix for #106: fix example servlet [gnowoel]
|
||||
* Bugfix for #97: strip_html filter supports multi-line tags [Jo Liss, joliss]
|
||||
* Bugfix for #114: strip_html filter supports style tags [James Allardice, jamesallardice]
|
||||
* Bugfix for #117: 'now' support for date filter in Ruby 1.9 [Notre Dame Webgroup, ndwebgroup]
|
||||
* Bugfix for #166: truncate filter on UTF-8 strings with Ruby 1.8 [Florian Weingarten, fw42]
|
||||
* Bugfix for #204: 'raw' parsing bug [Florian Weingarten, fw42]
|
||||
* Bugfix for #150: 'for' parsing bug [Peter Schröder, phoet]
|
||||
* Bugfix for #126: Strip CRLF in strip_newline [Peter Schröder, phoet]
|
||||
* Bugfix for #174, "can't convert Fixnum into String" for "replace" [wǒ_is神仙, jsw0528]
|
||||
* Allow a Liquid::Drop to be passed into Template#render [Daniel Huckstep, darkhelmet]
|
||||
* Resource limits [Florian Weingarten, fw42]
|
||||
* Add reverse filter [Jay Strybis, unreal]
|
||||
* Add utf-8 support
|
||||
* Use array instead of Hash to keep the registered filters [Tasos Stathopoulos, astathopoulos]
|
||||
* Cache tokenized partial templates [Tom Burns, boourns]
|
||||
* Avoid warnings in Ruby 1.9.3 [Marcus Stollsteimer, stomar]
|
||||
* Better documentation for 'include' tag (closes #163) [Peter Schröder, phoet]
|
||||
* Use of BigDecimal on filters to have better precision (closes #155) [Arthur Nogueira Neves, arthurnn]
|
||||
|
||||
## 2.5.5 / 2014-01-10 / branch "2-5-stable"
|
||||
|
||||
Security fix, cherry-picked from master (4e14a65):
|
||||
* Don't call to_sym when creating conditions for security reasons, see #273 [Bouke van der Bijl, bouk]
|
||||
* Prevent arbitrary method invocation on condition objects, see #274 [Dylan Thacker-Smith, dylanahsmith]
|
||||
|
||||
## 2.5.4 / 2013-11-11
|
||||
|
||||
* Fix "can't convert Fixnum into String" for "replace", see #173, [wǒ_is神仙, jsw0528]
|
||||
|
||||
## 2.5.3 / 2013-10-09
|
||||
|
||||
* #232, #234, #237: Fix map filter bugs [Florian Weingarten, fw42]
|
||||
|
||||
## 2.5.2 / 2013-09-03 / deleted
|
||||
|
||||
Yanked from rubygems, as it contained too many changes that broke compatibility. Those changes will be on following major releases.
|
||||
|
||||
## 2.5.1 / 2013-07-24
|
||||
|
||||
* #230: Fix security issue with map filter, Use invoke_drop in map filter [Florian Weingarten, fw42]
|
||||
|
||||
## 2.5.0 / 2013-03-06
|
||||
|
||||
* Prevent Object methods from being called on drops
|
||||
* Avoid symbol injection from liquid
|
||||
* Added break and continue statements
|
||||
* Fix filter parser for args without space separators
|
||||
* Add support for filter keyword arguments
|
||||
|
||||
|
||||
## 2.4.0 / 2012-08-03
|
||||
|
||||
* Performance improvements
|
||||
* Allow filters in `assign`
|
||||
* Add `modulo` filter
|
||||
* Ruby 1.8, 1.9, and Rubinius compatibility fixes
|
||||
* Add support for `quoted['references']` in `tablerow`
|
||||
* Add support for Enumerable to `tablerow`
|
||||
* `strip_html` filter removes html comments
|
||||
|
||||
|
||||
## 2.3.0 / 2011-10-16
|
||||
|
||||
* Several speed/memory improvements
|
||||
* Numerous bug fixes
|
||||
* Added support for MRI 1.9, Rubinius, and JRuby
|
||||
* Added support for integer drop parameters
|
||||
* Added epoch support to `date` filter
|
||||
* New `raw` tag that suppresses parsing
|
||||
* Added `else` option to `for` tag
|
||||
* New `increment` tag
|
||||
* New `split` filter
|
||||
|
||||
|
||||
## 2.2.1 / 2010-08-23
|
||||
|
||||
* Added support for literal tags
|
||||
|
||||
|
||||
## 2.2.0 / 2010-08-22
|
||||
|
||||
* Compatible with Ruby 1.8.7, 1.9.1 and 1.9.2-p0
|
||||
* Merged some changed made by the community
|
||||
|
||||
|
||||
## 1.9.0 / 2008-03-04
|
||||
|
||||
* Fixed gem install rake task
|
||||
* Improve Error encapsulation in liquid by maintaining a own set of exceptions instead of relying on ruby build ins
|
||||
|
||||
|
||||
## Before 1.9.0
|
||||
|
||||
* Added If with or / and expressions
|
||||
* Implemented .to_liquid for all objects which can be passed to liquid like Strings Arrays Hashes Numerics and Booleans. To export new objects to liquid just implement .to_liquid on them and return objects which themselves have .to_liquid methods.
|
||||
* Added more tags to standard library
|
||||
* Added include tag ( like partials in rails )
|
||||
* [...] Gazillion of detail improvements
|
||||
* Added strainers as filter hosts for better security [Tobias Luetke]
|
||||
* Fixed that rails integration would call filter with the wrong "self" [Michael Geary]
|
||||
* Fixed bad error reporting when a filter called a method which doesn't exist. Liquid told you that it couldn't find the filter which was obviously misleading [Tobias Luetke]
|
||||
* Removed count helper from standard lib. use size [Tobias Luetke]
|
||||
* Fixed bug with string filter parameters failing to tolerate commas in strings. [Paul Hammond]
|
||||
* Improved filter parameters. Filter parameters are now context sensitive; Types are resolved according to the rules of the context. Multiple parameters are now separated by the Liquid::ArgumentSeparator: , by default [Paul Hammond]
|
||||
{{ 'Typo' | link_to: 'http://typo.leetsoft.com', 'Typo - a modern weblog engine' }}
|
||||
* Added Liquid::Drop. A base class which you can use for exporting proxy objects to liquid which can acquire more data when used in liquid. [Tobias Luetke]
|
||||
|
||||
class ProductDrop < Liquid::Drop
|
||||
def top_sales
|
||||
Shop.current.products.find(:all, :order => 'sales', :limit => 10 )
|
||||
end
|
||||
end
|
||||
t = Liquid::Template.parse( ' {% for product in product.top_sales %} {{ product.name }} {% endfor %} ' )
|
||||
t.render('product' => ProductDrop.new )
|
||||
* Added filter parameters support. Example: {{ date | format_date: "%Y" }} [Paul Hammond]
|
||||
@@ -0,0 +1,20 @@
|
||||
Copyright (c) 2005, 2006 Tobias Luetke
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining
|
||||
a copy of this software and associated documentation files (the
|
||||
"Software"), to deal in the Software without restriction, including
|
||||
without limitation the rights to use, copy, modify, merge, publish,
|
||||
distribute, sublicense, and/or sell copies of the Software, and to
|
||||
permit persons to whom the Software is furnished to do so, subject to
|
||||
the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be
|
||||
included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
||||
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
@@ -1,9 +1,75 @@
|
||||
# New Liquid Docs
|
||||
[](http://travis-ci.org/Shopify/liquid)
|
||||
[](http://inch-ci.org/github/Shopify/liquid)
|
||||
|
||||
To run, follow these steps:
|
||||
# Liquid template engine
|
||||
|
||||
1. Download ZIP or clone in GitHub
|
||||
2. Navigate to `liquid` folder
|
||||
3. Run `jekyll watch`
|
||||
4. Open `http://127.0.0.1:4000` in your browser
|
||||
* [Contributing guidelines](CONTRIBUTING.md)
|
||||
* [Version history](History.md)
|
||||
* [Liquid documentation from Shopify](http://docs.shopify.com/themes/liquid-basics)
|
||||
* [Liquid Wiki at GitHub](https://github.com/Shopify/liquid/wiki)
|
||||
* [Website](http://liquidmarkup.org/)
|
||||
|
||||
## Introduction
|
||||
|
||||
Liquid is a template engine which was written with very specific requirements:
|
||||
|
||||
* It has to have beautiful and simple markup. Template engines which don't produce good looking markup are no fun to use.
|
||||
* It needs to be non evaling and secure. Liquid templates are made so that users can edit them. You don't want to run code on your server which your users wrote.
|
||||
* It has to be stateless. Compile and render steps have to be separate so that the expensive parsing and compiling can be done once and later on you can just render it passing in a hash with local variables and objects.
|
||||
|
||||
## Why you should use Liquid
|
||||
|
||||
* You want to allow your users to edit the appearance of your application but don't want them to run **insecure code on your server**.
|
||||
* You want to render templates directly from the database.
|
||||
* You like smarty (PHP) style template engines.
|
||||
* You need a template engine which does HTML just as well as emails.
|
||||
* You don't like the markup of your current templating engine.
|
||||
|
||||
## What does it look like?
|
||||
|
||||
```html
|
||||
<ul id="products">
|
||||
{% for product in products %}
|
||||
<li>
|
||||
<h2>{{ product.name }}</h2>
|
||||
Only {{ product.price | price }}
|
||||
|
||||
{{ product.description | prettyprint | paragraph }}
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
```
|
||||
|
||||
## How to use Liquid
|
||||
|
||||
Liquid supports a very simple API based around the Liquid::Template class.
|
||||
For standard use you can just pass it the content of a file and call render with a parameters hash.
|
||||
|
||||
```ruby
|
||||
@template = Liquid::Template.parse("hi {{name}}") # Parses and compiles the template
|
||||
@template.render('name' => 'tobi') # => "hi tobi"
|
||||
```
|
||||
|
||||
### Error Modes
|
||||
|
||||
Setting the error mode of Liquid lets you specify how strictly you want your templates to be interpreted.
|
||||
Normally the parser is very lax and will accept almost anything without error. Unfortunately this can make
|
||||
it very hard to debug and can lead to unexpected behaviour.
|
||||
|
||||
Liquid also comes with a stricter parser that can be used when editing templates to give better error messages
|
||||
when templates are invalid. You can enable this new parser like this:
|
||||
|
||||
```ruby
|
||||
Liquid::Template.error_mode = :strict # Raises a SyntaxError when invalid syntax is used
|
||||
Liquid::Template.error_mode = :warn # Adds errors to template.errors but continues as normal
|
||||
Liquid::Template.error_mode = :lax # The default mode, accepts almost anything.
|
||||
```
|
||||
|
||||
If you want to set the error mode only on specific templates you can pass `:error_mode` as an option to `parse`:
|
||||
```ruby
|
||||
Liquid::Template.parse(source, :error_mode => :strict)
|
||||
```
|
||||
This is useful for doing things like enabling strict mode only in the theme editor.
|
||||
|
||||
It is recommended that you enable `:strict` or `:warn` mode on new apps to stop invalid templates from being created.
|
||||
It is also recommended that you use it in the template editors of existing apps to give editors better error messages.
|
||||
|
||||
@@ -0,0 +1,77 @@
|
||||
require 'rake'
|
||||
require 'rake/testtask'
|
||||
$LOAD_PATH.unshift File.expand_path("../lib", __FILE__)
|
||||
require "liquid/version"
|
||||
|
||||
task :default => 'test'
|
||||
|
||||
desc 'run test suite with default parser'
|
||||
Rake::TestTask.new(:base_test) do |t|
|
||||
t.libs << '.' << 'lib' << 'test'
|
||||
t.test_files = FileList['test/{integration,unit}/**/*_test.rb']
|
||||
t.verbose = false
|
||||
end
|
||||
|
||||
desc 'run test suite with warn error mode'
|
||||
task :warn_test do
|
||||
ENV['LIQUID_PARSER_MODE'] = 'warn'
|
||||
Rake::Task['base_test'].invoke
|
||||
end
|
||||
|
||||
desc 'runs test suite with both strict and lax parsers'
|
||||
task :test do
|
||||
ENV['LIQUID_PARSER_MODE'] = 'lax'
|
||||
Rake::Task['base_test'].invoke
|
||||
ENV['LIQUID_PARSER_MODE'] = 'strict'
|
||||
Rake::Task['base_test'].reenable
|
||||
Rake::Task['base_test'].invoke
|
||||
end
|
||||
|
||||
task :gem => :build
|
||||
task :build do
|
||||
system "gem build liquid.gemspec"
|
||||
end
|
||||
|
||||
task :install => :build do
|
||||
system "gem install liquid-#{Liquid::VERSION}.gem"
|
||||
end
|
||||
|
||||
task :release => :build do
|
||||
system "git tag -a v#{Liquid::VERSION} -m 'Tagging #{Liquid::VERSION}'"
|
||||
system "git push --tags"
|
||||
system "gem push liquid-#{Liquid::VERSION}.gem"
|
||||
system "rm liquid-#{Liquid::VERSION}.gem"
|
||||
end
|
||||
|
||||
namespace :benchmark do
|
||||
|
||||
desc "Run the liquid benchmark with lax parsing"
|
||||
task :run do
|
||||
ruby "./performance/benchmark.rb lax"
|
||||
end
|
||||
|
||||
desc "Run the liquid benchmark with strict parsing"
|
||||
task :strict do
|
||||
ruby "./performance/benchmark.rb strict"
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
namespace :profile do
|
||||
|
||||
desc "Run the liquid profile/performance coverage"
|
||||
task :run do
|
||||
ruby "./performance/profile.rb"
|
||||
end
|
||||
|
||||
desc "Run the liquid profile/performance coverage with strict parsing"
|
||||
task :strict do
|
||||
ruby "./performance/profile.rb strict"
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
desc "Run example"
|
||||
task :example do
|
||||
ruby "-w -d -Ilib example/server/server.rb"
|
||||
end
|
||||
@@ -1,34 +0,0 @@
|
||||
title: Liquid template language
|
||||
description: Liquid is a template language and accompanying rendering engine. It is built for security, so is perfect for rendering custom templates from your users.
|
||||
|
||||
# Build settings
|
||||
baseurl: /liquid # the subpath of your site, e.g. /blog/
|
||||
url: http://liquidmarkup.org # the base hostname & protocol for your site
|
||||
permalink: pretty
|
||||
exclude:
|
||||
- README.md
|
||||
- CNAME
|
||||
- Gemfile
|
||||
- Gruntfile.js
|
||||
- package.json
|
||||
- node_modules
|
||||
keep_files: ["css"]
|
||||
|
||||
# Plugins
|
||||
gems:
|
||||
- jekyll-redirect-from
|
||||
|
||||
# Front matter defaults
|
||||
defaults:
|
||||
- scope:
|
||||
path: "" # an empty string here means all files in the project
|
||||
values:
|
||||
layout: default
|
||||
- scope:
|
||||
path: "filters"
|
||||
values:
|
||||
type: filter
|
||||
- scope:
|
||||
path: "tags"
|
||||
values:
|
||||
type: tag
|
||||
@@ -1,12 +0,0 @@
|
||||
<div class="home-banner">
|
||||
<h1>Liquid</h1>
|
||||
<p>Safe, customer-facing template language for flexible web apps.</p>
|
||||
<p class="btn-row">
|
||||
<a href="https://github.com/Shopify/liquid/archive/master.zip" target="_blank" class="btn">
|
||||
<span aria-hidden="true">{% include icons/desktop-download.svg %}</span> Download
|
||||
</a>
|
||||
<a href="https://github.com/Shopify/liquid" target="_blank" class="btn">
|
||||
<span aria-hidden="true">{% include icons/mark-github.svg %}</span> View on GitHub
|
||||
</a>
|
||||
</p>
|
||||
</div>
|
||||
@@ -1,24 +0,0 @@
|
||||
<div class="home-users-grid">
|
||||
<div class="home-users-grid__item">
|
||||
<a href="http://jekyllrb.com" target="_blank">
|
||||
<img src="{{ '/images/jekyll-logo.png' | prepend: site.baseurl }}" alt="Jekyll logo" />
|
||||
</a>
|
||||
</div>
|
||||
<div class="home-users-grid__item">
|
||||
<a href="http://www.desk.com" target="_blank">
|
||||
<img src="{{ '/images/salesforcedesk-logo.png' | prepend: site.baseurl }}" alt="Desk logo" />
|
||||
</a>
|
||||
</div>
|
||||
<div class="home-users-grid__item">
|
||||
<a href="//www.zendesk.com" target="_blank">
|
||||
<img src="{{ '/images/zendesk-logo.png' | prepend: site.baseurl }}" alt="ZenDesk logo" />
|
||||
</a>
|
||||
</div>
|
||||
<div class="home-users-grid__item">
|
||||
<a href="//500px.com" target="_blank">
|
||||
<img src="{{ '/images/500px-logo.png' | prepend: site.baseurl }}" alt="500px logo" />
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<p class="home-users-blurb">...and <a href="https://github.com/Shopify/liquid/wiki#who-uses-liquid" target="_blank">many more</a></p>
|
||||
@@ -1 +0,0 @@
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><title>desktop-download</title><desc>Created with Sketch.</desc><path d="M4 6h3v-6h2v6h3l-4 4-4-4zm11-4h-4v1h4v8h-14v-8h4v-1h-4c-.55 0-1 .45-1 1v9c0 .55.45 1 1 1h5.34c-.25.61-.86 1.39-2.34 2h8c-1.48-.61-2.09-1.39-2.34-2h5.34c.55 0 1-.45 1-1v-9c0-.55-.45-1-1-1z" fill-rule="evenodd"/></svg>
|
||||
|
Before Width: | Height: | Size: 372 B |
@@ -1 +0,0 @@
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg"><title>mark-github</title><desc>Created with Sketch.</desc><path d="M8 0c-4.42 0-8 3.58-8 8 0 3.54 2.29 6.53 5.47 7.59.4.07.55-.17.55-.38l-.01-1.49c-2.01.37-2.53-.49-2.69-.94-.09-.23-.48-.94-.82-1.13-.28-.15-.68-.52-.01-.53.63-.01 1.08.58 1.23.82.72 1.21 1.87.87 2.33.66.07-.52.28-.87.51-1.07-1.78-.2-3.64-.89-3.64-3.95 0-.87.31-1.59.82-2.15-.08-.2-.36-1.02.08-2.12 0 0 .67-.21 2.2.82.64-.18 1.32-.27 2-.27.68 0 1.36.09 2 .27 1.53-1.04 2.2-.82 2.2-.82.44 1.1.16 1.92.08 2.12.51.56.82 1.27.82 2.15 0 3.07-1.87 3.75-3.65 3.95.29.25.54.73.54 1.48 0 1.07-.01 1.93-.01 2.2 0 .21.15.46.55.38 3.16-1.06 5.45-4.06 5.45-7.59 0-4.42-3.58-8-8-8z" fill-rule="evenodd"/></svg>
|
||||
|
Before Width: | Height: | Size: 746 B |
@@ -1 +0,0 @@
|
||||
<svg width="12" height="16" viewBox="0 0 12 16" xmlns="http://www.w3.org/2000/svg"><title>three-bars</title><desc>Created with Sketch.</desc><path d="M11.41 9h-10.82c-.59 0-.59-.41-.59-1 0-.59 0-1 .59-1h10.81c.59 0 .59.41.59 1 0 .59 0 1-.59 1h.01zm0-4h-10.82c-.59 0-.59-.41-.59-1 0-.59 0-1 .59-1h10.81c.59 0 .59.41.59 1 0 .59 0 1-.59 1h.01zm-10.82 6h10.81c.59 0 .59.41.59 1 0 .59 0 1-.59 1h-10.81c-.59 0-.59-.41-.59-1 0-.59 0-1 .59-1z" fill="#000"/></svg>
|
||||
|
Before Width: | Height: | Size: 455 B |
@@ -1,18 +0,0 @@
|
||||
<div class="sidebar">
|
||||
<header class="sidebar__logo" role="banner">
|
||||
<a href="{{ "/" | prepend: site.baseurl }}">Liquid</a>
|
||||
</header>
|
||||
<nav class="sidebar__nav"> {% assign sections = "basics, tags, filters" | split: ", " %}
|
||||
|
||||
{% for section in sections %}
|
||||
<h3 class="section__header">{{ section | capitalize }}</h3>
|
||||
|
||||
<ul class="section__links">
|
||||
{% for item in site.pages %}{% if item.url contains section/ %}{% unless item.path contains "index" %}
|
||||
<li><a href="{{ item.url | prepend: site.baseurl }}" class="section__link{% if item.url contains page.url and page.url != '/' and page.type != 'index' %} section__link--is-active{% endif %}">{{ item.title }}</a></li>
|
||||
{% endunless %}{% endif %}{% endfor %}
|
||||
</ul>
|
||||
{% endfor %}
|
||||
|
||||
</nav>
|
||||
</div>
|
||||
@@ -1,56 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
|
||||
<title>{% if page.title %}{{ page.title }} – {% endif %}{{ site.title }}</title>
|
||||
|
||||
<meta name="description" content="{{ page.description | default: site.description }}">
|
||||
<meta name="author" content="Shopify">
|
||||
|
||||
<meta name="robots" content="index, follow">
|
||||
<meta name="mobile-web-app-capable" content="yes">
|
||||
<meta name="apple-mobile-web-app-capable" content="yes">
|
||||
<meta name="apple-mobile-web-app-status-bar-style" content="default">
|
||||
|
||||
<link rel="stylesheet" href="{{ '/css/main.css' | prepend: site.baseurl }}">
|
||||
<link rel="icon" type="image/png" href="{{ '/images/icons/water-drop-32x.png' | prepend: site.baseurl }}" sizes="32x32">
|
||||
<link rel="icon" type="image/png" href="{{ '/images/icons/water-drop-64x.png' | prepend: site.baseurl }}" sizes="64x64">
|
||||
<link rel="canonical" href="{{ page.url | replace: 'index.html','' | prepend: site.baseurl | prepend: site.url }}">
|
||||
<link rel="alternate" type="application/rss+xml" title="{{ site.title }}" href="{{ "/feed.xml" | prepend: site.baseurl | prepend: site.url }}" />
|
||||
|
||||
<meta property="og:site_name" content="{{ site.title }}">
|
||||
<meta property="og:type" content="website">
|
||||
<meta property="og:url" content="{{ site.url | append: site.baseurl }}">
|
||||
<meta property="og:title" content="{{ page.title | default: site.title }}">
|
||||
<meta property="og:description" content="{{ page.description | default: site.description }}">
|
||||
|
||||
<meta name="twitter:site" content="{{ site.title }}">
|
||||
<meta name="twitter:card" content="summary">
|
||||
<meta name="twitter:url" content="{{ site.url | append: site.baseurl }}">
|
||||
<meta name="twitter:title" content="{{ page.title | default: site.title }}">
|
||||
<meta name="twitter:description" content="{{ page.description | default: site.description }}">
|
||||
|
||||
<script src="{{ '/js/vendor/jquery-3.1.1.slim.min.js' | prepend: site.baseurl }}"></script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
|
||||
{% include sidebar.html %}
|
||||
|
||||
<div class="content__overlay"></div>
|
||||
<main class="content__area" role="main">
|
||||
<div class="content">
|
||||
<button class="menu-button">
|
||||
<span aria-hidden="true">{% include icons/three-bars.svg %}</span>
|
||||
<span>Menu</span>
|
||||
</button>
|
||||
<h1>{{ page.title }}</h1>
|
||||
{{ content }}
|
||||
</div>
|
||||
</main>
|
||||
<script src="{{ '/js/script.js' | prepend: site.baseurl }}"></script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,183 +0,0 @@
|
||||
* {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
/**
|
||||
* Reset some basic elements
|
||||
*/
|
||||
body, h1, h2, h3, h4, h5, h6,
|
||||
p, blockquote, pre, hr,
|
||||
dl, dd, ol, ul, figure {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Basic styling
|
||||
*/
|
||||
body {
|
||||
font-family: $base-font-family;
|
||||
font-size: $base-font-size;
|
||||
line-height: $base-line-height;
|
||||
font-weight: 300;
|
||||
color: $color-slate;
|
||||
-webkit-text-size-adjust: 100%;
|
||||
}
|
||||
|
||||
/** Set `margin-bottom` to maintain vertical rhythm */
|
||||
|
||||
h1, h2, h3, h4, h5, h6,
|
||||
p, blockquote, pre,
|
||||
ul, ol, dl, figure,
|
||||
%vertical-rhythm {
|
||||
margin-bottom: $spacing-unit / 2;
|
||||
}
|
||||
|
||||
/** Images */
|
||||
|
||||
img {
|
||||
max-width: 100%;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
/** Figures */
|
||||
|
||||
figure > img {
|
||||
display: block;
|
||||
}
|
||||
|
||||
figcaption {
|
||||
font-size: $small-font-size;
|
||||
}
|
||||
|
||||
/** Lists */
|
||||
ul, ol {
|
||||
margin-left: $spacing-unit;
|
||||
}
|
||||
|
||||
li {
|
||||
> ul, > ol {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
/** Links */
|
||||
a {
|
||||
color: $color-blue-5;
|
||||
|
||||
&:visited {
|
||||
color: #609;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
}
|
||||
|
||||
/** Headings */
|
||||
|
||||
h1 {
|
||||
font-size: 2em;
|
||||
font-weight: 300;
|
||||
}
|
||||
|
||||
h2 {
|
||||
font-size: 1.5em;
|
||||
font-weight: 300;
|
||||
margin-top: $spacing-unit;
|
||||
}
|
||||
|
||||
h3 {
|
||||
margin-top: $spacing-unit;
|
||||
font-size: 1em;
|
||||
}
|
||||
|
||||
h4 {
|
||||
font-size: 1em;
|
||||
}
|
||||
|
||||
blockquote {
|
||||
color: lighten($color-slate, 30%);
|
||||
border-left: 2px solid lighten($color-slate, 50%);
|
||||
padding-left: $spacing-unit / 2;
|
||||
letter-spacing: -1px;
|
||||
font-style: italic;
|
||||
|
||||
> :last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
pre, code {
|
||||
font-family: Menlo, Monaco, monospace;
|
||||
font-size: 15px;
|
||||
border-radius: 3px;
|
||||
background-color: lighten($color-blue-1, 0.9);
|
||||
}
|
||||
|
||||
code {
|
||||
padding: 1px 5px;
|
||||
}
|
||||
|
||||
pre {
|
||||
padding: 8px 12px;
|
||||
border: 1px solid $color-blue-2;
|
||||
word-wrap: break-word;
|
||||
|
||||
> code {
|
||||
border: 0;
|
||||
padding-right: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
hr {
|
||||
display: block;
|
||||
height: 1px;
|
||||
border: 0;
|
||||
background-color: lighten($color-slate, 50%);
|
||||
margin-bottom: $spacing-unit/2;
|
||||
}
|
||||
|
||||
table {
|
||||
width: 100%;
|
||||
overflow: auto;
|
||||
display: block;
|
||||
margin: 15px 0;
|
||||
border-collapse: collapse;
|
||||
thead {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
border: 0;
|
||||
font-size: 100%;
|
||||
font: inherit;
|
||||
vertical-align: baseline;
|
||||
}
|
||||
th {
|
||||
border: 1px solid #ddd;
|
||||
padding: 6px 13px;
|
||||
font-weight: bold;
|
||||
text-align: center;
|
||||
}
|
||||
tbody {
|
||||
vertical-align: middle;
|
||||
border-color: inherit;
|
||||
}
|
||||
tr {
|
||||
border-top: 1px solid #ccc;
|
||||
background-color: #fff;
|
||||
vertical-align: inherit;
|
||||
}
|
||||
td {
|
||||
border: 1px solid #ddd;
|
||||
padding: 6px 13px;
|
||||
}
|
||||
/* Don't use a margin on code samples within tables */
|
||||
pre {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
p {
|
||||
line-height: 1.8;
|
||||
}
|
||||
@@ -1,84 +0,0 @@
|
||||
.btn {
|
||||
color: $color-white;
|
||||
fill: currentColor;
|
||||
display: flex;
|
||||
background: $color-blue-5;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
padding: $spacing-unit/4 $spacing-unit/2;
|
||||
border-radius: 8px;
|
||||
text-decoration: none;
|
||||
text-align: center;
|
||||
white-space: nowrap;
|
||||
|
||||
&:hover {
|
||||
background: $color-blue-4;
|
||||
cursor: pointer;
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
&:first-child {
|
||||
margin-bottom: $spacing-unit / 2;
|
||||
}
|
||||
|
||||
@include phone-and-up {
|
||||
justify-content: center;
|
||||
|
||||
&:first-child {
|
||||
justify-content: flex-start;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
svg {
|
||||
margin-right: $spacing-unit / 4;
|
||||
width: $base-font-size * 1.5;
|
||||
height: $base-font-size * 1.5;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
.btn:visited {
|
||||
color: $color-white;
|
||||
}
|
||||
|
||||
.btn-row {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
flex-direction: column;
|
||||
margin-bottom: 0;
|
||||
|
||||
@include phone-and-up {
|
||||
flex-direction: row;
|
||||
|
||||
.btn:not(:first-child) {
|
||||
margin-left: $spacing-unit / 2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*============================================================================
|
||||
Menu button
|
||||
==============================================================================*/
|
||||
.menu-button {
|
||||
display: inline-block;
|
||||
font-size: $small-font-size;
|
||||
background: none;
|
||||
border: none;
|
||||
margin: $spacing-unit / 2 0 $spacing-unit / 2 ($spacing-unit / 4 * -1);
|
||||
padding: $spacing-unit / 4;
|
||||
color: $color-slate;
|
||||
|
||||
@include tablet-and-up {
|
||||
display: none;
|
||||
}
|
||||
|
||||
svg {
|
||||
margin-right: $spacing-unit / 4;
|
||||
width: $base-font-size;
|
||||
height: $base-font-size;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,22 +0,0 @@
|
||||
.content__item {
|
||||
margin-bottom: $spacing-unit * 2;
|
||||
}
|
||||
|
||||
.highlight {
|
||||
background: lighten($color-blue-1, 1);
|
||||
}
|
||||
|
||||
.code-label {
|
||||
padding: 4px 12px;
|
||||
margin-bottom: 0;
|
||||
font-size: 15px;
|
||||
background: darken($color-blue-1, 5);
|
||||
border: 1px solid $color-blue-2;
|
||||
border-bottom: none;
|
||||
border-radius: 3px 3px 0 0;
|
||||
}
|
||||
|
||||
.code-label + .highlighter-rouge .highlight {
|
||||
border-top: none;
|
||||
border-radius: 0 0 3px 3px;
|
||||
}
|
||||
@@ -1,23 +0,0 @@
|
||||
.home-banner {
|
||||
text-align: center;
|
||||
border-bottom: 1px solid lighten($color-slate, 50%);
|
||||
padding-bottom: $spacing-unit;
|
||||
margin-bottom: $spacing-unit;
|
||||
|
||||
h1 {
|
||||
font-size: 4em;
|
||||
|
||||
// &:after {
|
||||
// content: '\01F4A7'; // Water droplet emoji
|
||||
// vertical-align: middle;
|
||||
// }
|
||||
|
||||
@include phone-and-up {
|
||||
font-size: 5em;
|
||||
}
|
||||
}
|
||||
|
||||
p {
|
||||
color: lighten($color-slate, 20%);
|
||||
}
|
||||
}
|
||||
@@ -1,20 +0,0 @@
|
||||
.home-users-grid {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
flex-wrap: wrap;
|
||||
margin-bottom: $spacing-unit / 2;
|
||||
}
|
||||
|
||||
.home-users-grid__item{
|
||||
flex: 1;
|
||||
margin-right: $spacing-unit / 2;
|
||||
max-width: 50%;
|
||||
|
||||
&:last-child {
|
||||
margin-right: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.home-users-blurb {
|
||||
text-align: right;
|
||||
}
|
||||
@@ -1,155 +0,0 @@
|
||||
|
||||
$sidebar-width: 250px;
|
||||
$logo-height: 130px;
|
||||
$wrapper-width: 800px;
|
||||
|
||||
body {
|
||||
// display: flex;
|
||||
// flex-direction: column;
|
||||
|
||||
// @include tablet-and-up {
|
||||
// flex-direction: row;
|
||||
// }
|
||||
}
|
||||
|
||||
|
||||
/*============================================================================
|
||||
Content Area
|
||||
==============================================================================*/
|
||||
|
||||
.content__area {
|
||||
width: 100%;
|
||||
|
||||
@include tablet-and-up {
|
||||
padding: $spacing-unit $spacing-unit $spacing-unit ($spacing-unit + $sidebar-width);
|
||||
}
|
||||
}
|
||||
|
||||
.content__overlay {
|
||||
background: rgba(0, 0, 0, 0.4);
|
||||
width: 100%;
|
||||
height: 100vh;
|
||||
position: fixed;
|
||||
z-index: 1;
|
||||
display: none;
|
||||
}
|
||||
|
||||
.content__overlay--is-active {
|
||||
display: block;
|
||||
}
|
||||
|
||||
.content {
|
||||
max-width: $wrapper-width;
|
||||
margin: 0 auto;
|
||||
padding: 0 $spacing-unit;
|
||||
@extend %clearfix;
|
||||
}
|
||||
|
||||
/*============================================================================
|
||||
Sidebar
|
||||
==============================================================================*/
|
||||
|
||||
.sidebar {
|
||||
background: $color-blue-5;
|
||||
width: $sidebar-width;
|
||||
position: fixed;
|
||||
transform: translateX($sidebar-width * -1);
|
||||
transition: all 0.15s ease;
|
||||
z-index: 2;
|
||||
height: 100vh;
|
||||
-webkit-overflow-scrolling: touch;
|
||||
|
||||
@include tablet-and-up {
|
||||
transform: translateX(0);
|
||||
}
|
||||
}
|
||||
|
||||
.sidebar--is-visible {
|
||||
transform: translateX(0);
|
||||
}
|
||||
|
||||
.sidebar__logo {
|
||||
font-size: $base-font-size * 2;
|
||||
font-weight: 300;
|
||||
text-align: center;
|
||||
height: $logo-height;
|
||||
line-height: $logo-height;
|
||||
margin-bottom: 0;
|
||||
border-bottom: 1px solid $color-blue-4;
|
||||
|
||||
// &:after {
|
||||
// content: '\01F4A7'; // Water droplet emoji
|
||||
// vertical-align: middle;
|
||||
// }
|
||||
|
||||
a {
|
||||
color: $color-white;
|
||||
text-decoration: none;
|
||||
|
||||
&:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.sidebar__nav {
|
||||
padding: $spacing-unit $spacing-unit ($spacing-unit + $logo-height); // Add a bit more padding at the bottom for consistency.
|
||||
font-weight: bold;
|
||||
max-height: 100%;
|
||||
overflow-y: scroll;
|
||||
|
||||
li {
|
||||
list-style: none;
|
||||
|
||||
a {
|
||||
color: $color-white;
|
||||
|
||||
&:hover {
|
||||
text-decoration: none;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.section {
|
||||
margin: 0px;
|
||||
|
||||
> li {
|
||||
margin-bottom: $spacing-unit / 2;
|
||||
|
||||
&:last-child {
|
||||
margin-bottom: $spacing-unit;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.section__header {
|
||||
font-size: 1em;
|
||||
text-decoration: none;
|
||||
color: $color-white;
|
||||
margin-top: 0;
|
||||
margin-bottom: $spacing-unit / 4;
|
||||
}
|
||||
|
||||
.section__links {
|
||||
margin-left: $spacing-unit / 2;
|
||||
margin-bottom: $spacing-unit;
|
||||
font-weight: normal;
|
||||
font-size: 0.9em;
|
||||
}
|
||||
|
||||
.section__link {
|
||||
display: inline-block;
|
||||
margin-top: $spacing-unit/4;
|
||||
opacity: 0.75;
|
||||
text-decoration: none;
|
||||
|
||||
&:hover {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
.section__link--is-active {
|
||||
font-weight: bold;
|
||||
opacity: 1;
|
||||
}
|
||||
@@ -1,10 +0,0 @@
|
||||
// I got the blues, man.
|
||||
// 1 --> 5, lightest --> darkest.
|
||||
|
||||
$color-blue-1: #E8F8FF;
|
||||
$color-blue-2: #B4DCED;
|
||||
$color-blue-3: #91C9E8;
|
||||
$color-blue-4: #67B8DE;
|
||||
$color-blue-5: #3399CC;
|
||||
$color-white: #ffffff;
|
||||
$color-slate: #5E5E5E;
|
||||
@@ -1,5 +0,0 @@
|
||||
$base-font-family: -apple-system, BlinkMacSystemFont, San Francisco, Segoe UI, Roboto, Helvetica Neue, sans-serif;
|
||||
$base-font-size: 18px;
|
||||
$small-font-size: $base-font-size * 0.875;
|
||||
$base-line-height: 1.5;
|
||||
$spacing-unit: 40px;
|
||||
@@ -1,16 +0,0 @@
|
||||
%clearfix {
|
||||
&:after {
|
||||
content: "";
|
||||
display: table;
|
||||
clear: both;
|
||||
}
|
||||
}
|
||||
|
||||
.visually-hidden {
|
||||
position:absolute;
|
||||
left:-10000px;
|
||||
top:auto;
|
||||
width:1px;
|
||||
height:1px;
|
||||
overflow:hidden;
|
||||
}
|
||||
@@ -1,43 +0,0 @@
|
||||
/*============================================================================
|
||||
Media queries
|
||||
==============================================================================*/
|
||||
|
||||
$phone-width: 375px;
|
||||
$tablet-width: 768px;
|
||||
$desktop-width: 1024px;
|
||||
|
||||
@mixin phone {
|
||||
@media (max-width: #{$phone-width}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin phone-and-up {
|
||||
@media (min-width: #{$phone-width}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin phone-to-tablet {
|
||||
@media (min-width: #{$phone-width}) and (max-width: #{$tablet-width - 1px}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin tablet {
|
||||
@media (min-width: #{$tablet-width}) and (max-width: #{$desktop-width - 1px}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin tablet-and-up {
|
||||
@media (min-width: #{$tablet-width}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin desktop {
|
||||
@media (min-width: #{$desktop-width}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
@@ -1,67 +0,0 @@
|
||||
/**
|
||||
* Syntax highlighting styles
|
||||
*/
|
||||
.highlight {
|
||||
// background: #fff;
|
||||
@extend %vertical-rhythm;
|
||||
|
||||
.c { color: #998; font-style: italic } // Comment
|
||||
.err { color: #a61717; background-color: #e3d2d2 } // Error
|
||||
.k { font-weight: bold } // Keyword
|
||||
.o { font-weight: bold } // Operator
|
||||
.cm { color: #998; font-style: italic } // Comment.Multiline
|
||||
.cp { color: #999; font-weight: bold } // Comment.Preproc
|
||||
.c1 { color: #998; font-style: italic } // Comment.Single
|
||||
.cs { color: #999; font-weight: bold; font-style: italic } // Comment.Special
|
||||
.gd { color: #000; background-color: #fdd } // Generic.Deleted
|
||||
.gd .x { color: #000; background-color: #faa } // Generic.Deleted.Specific
|
||||
.ge { font-style: italic } // Generic.Emph
|
||||
.gr { color: #a00 } // Generic.Error
|
||||
.gh { color: #999 } // Generic.Heading
|
||||
.gi { color: #000; background-color: #dfd } // Generic.Inserted
|
||||
.gi .x { color: #000; background-color: #afa } // Generic.Inserted.Specific
|
||||
.go { color: #888 } // Generic.Output
|
||||
.gp { color: #555 } // Generic.Prompt
|
||||
.gs { font-weight: bold } // Generic.Strong
|
||||
.gu { color: #aaa } // Generic.Subheading
|
||||
.gt { color: #a00 } // Generic.Traceback
|
||||
.kc { font-weight: bold } // Keyword.Constant
|
||||
.kd { font-weight: bold } // Keyword.Declaration
|
||||
.kp { font-weight: bold } // Keyword.Pseudo
|
||||
.kr { font-weight: bold } // Keyword.Reserved
|
||||
.kt { color: #458; font-weight: bold } // Keyword.Type
|
||||
.m { color: #099 } // Literal.Number
|
||||
.s { color: #d14 } // Literal.String
|
||||
.na { color: #008080 } // Name.Attribute
|
||||
.nb { color: #0086B3 } // Name.Builtin
|
||||
.nc { color: #458; font-weight: bold } // Name.Class
|
||||
.no { color: #008080 } // Name.Constant
|
||||
.ni { color: #800080 } // Name.Entity
|
||||
.ne { color: #900; font-weight: bold } // Name.Exception
|
||||
.nf { color: #900; font-weight: bold } // Name.Function
|
||||
.nn { color: #555 } // Name.Namespace
|
||||
.nt { color: #000080 } // Name.Tag
|
||||
.nv { color: #008080 } // Name.Variable
|
||||
.ow { font-weight: bold } // Operator.Word
|
||||
.w { color: #bbb } // Text.Whitespace
|
||||
.mf { color: #099 } // Literal.Number.Float
|
||||
.mh { color: #099 } // Literal.Number.Hex
|
||||
.mi { color: #099 } // Literal.Number.Integer
|
||||
.mo { color: #099 } // Literal.Number.Oct
|
||||
.sb { color: #d14 } // Literal.String.Backtick
|
||||
.sc { color: #d14 } // Literal.String.Char
|
||||
.sd { color: #d14 } // Literal.String.Doc
|
||||
.s2 { color: #d14 } // Literal.String.Double
|
||||
.se { color: #d14 } // Literal.String.Escape
|
||||
.sh { color: #d14 } // Literal.String.Heredoc
|
||||
.si { color: #d14 } // Literal.String.Interpol
|
||||
.sx { color: #d14 } // Literal.String.Other
|
||||
.sr { color: #009926 } // Literal.String.Regex
|
||||
.s1 { color: #d14 } // Literal.String.Single
|
||||
.ss { color: #990073 } // Literal.String.Symbol
|
||||
.bp { color: #999 } // Name.Builtin.Pseudo
|
||||
.vc { color: #008080 } // Name.Variable.Class
|
||||
.vg { color: #008080 } // Name.Variable.Global
|
||||
.vi { color: #008080 } // Name.Variable.Instance
|
||||
.il { color: #099 } // Literal.Number.Integer.Long
|
||||
}
|
||||
@@ -1,3 +0,0 @@
|
||||
---
|
||||
redirect_to: /liquid/basics/introduction
|
||||
---
|
||||
@@ -1,70 +0,0 @@
|
||||
---
|
||||
title: Introduction
|
||||
description: An overview of objects, tags, and filters in the Liquid template language.
|
||||
---
|
||||
|
||||
Liquid code can be categorized into [**objects**](#objects), [**tags**](#tags), and [**filters**](#filters).
|
||||
|
||||
## Objects
|
||||
|
||||
**Objects** tell Liquid where to show content on a page. Objects and variable names are denoted by double curly braces: `{% raw %}{{{% endraw %}` and `{% raw %}}}{% endraw %}`.
|
||||
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ page.title }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
Introduction
|
||||
```
|
||||
|
||||
In this case, Liquid is rendering the content of an object called `page.title`, and that object contains the text `Introduction`.
|
||||
|
||||
## Tags
|
||||
|
||||
**Tags** create the logic and control flow for templates. They are denoted by curly braces and percent signs: `{% raw %}{%{% endraw %}` and `{% raw %}%}{% endraw %}`.
|
||||
|
||||
The markup used in tags does not produce any visible text. This means that you can assign variables and create conditions and loops without showing any of the Liquid logic on the page.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if user %}
|
||||
Hello {{ user.name }}!
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
Hello Adam!
|
||||
```
|
||||
|
||||
Tags can be categorized into three types:
|
||||
|
||||
- [Control flow]({{ "/tags/control-flow" | prepend: site.baseurl }})
|
||||
- [Iteration]({{ "/tags/iteration" | prepend: site.baseurl }})
|
||||
- [Variable assignments]({{ "/tags/variable" | prepend: site.baseurl }})
|
||||
|
||||
You can read more about each type of tag in their respective sections.
|
||||
|
||||
|
||||
## Filters
|
||||
|
||||
**Filters** change the output of a Liquid object. They are used within an output and are separated by a `|`.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "/my/fancy/url" | append: ".html" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "/my/fancy/url" | append: ".html" }}
|
||||
```
|
||||
@@ -1,89 +0,0 @@
|
||||
---
|
||||
title: Operators
|
||||
description: Using operators to perform calculations in the Liquid template language.
|
||||
---
|
||||
|
||||
Liquid includes many logical and comparison operators.
|
||||
|
||||
## Basic operators
|
||||
|
||||
<table>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td><code>==</code></td>
|
||||
<td>equals</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><code>!=</code></td>
|
||||
<td>does not equal</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><code>></code></td>
|
||||
<td>greater than</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><code><</code></td>
|
||||
<td>less than</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><code>>=</code></td>
|
||||
<td>greater than or equal to</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><code><=</code></td>
|
||||
<td>less than or equal to</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><code>or</code></td>
|
||||
<td>logical or</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><code>and</code></td>
|
||||
<td>logical and</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
For example:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if product.title == "Awesome Shoes" %}
|
||||
These shoes are awesome!
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
You can use multiple operators in a tag:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if product.type == "Shirt" or product.type == "Shoes" %}
|
||||
This is a shirt or a pair of shoes.
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
## contains
|
||||
|
||||
`contains` checks for the presence of a substring inside a string.
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if product.title contains 'Pack' %}
|
||||
This product's title contains the word Pack.
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
`contains` can also check for the presence of a string in an array of strings.
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if product.tags contains 'Hello' %}
|
||||
This product has been tagged with 'Hello'.
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
`contains` can only search strings. You cannot use it to check for an object in an array of objects.
|
||||
@@ -1,65 +0,0 @@
|
||||
---
|
||||
title: Truthy and falsy
|
||||
description: An overview of boolean logic in the Liquid template language.
|
||||
---
|
||||
|
||||
In programming, anything that returns `true` in a conditional is called **truthy**. Anything that returns `false` in a conditional is called **falsy**. All object types can be described as either truthy or falsy.
|
||||
|
||||
- [Truthy](#truthy)
|
||||
- [Falsy](#falsy)
|
||||
- [Summary](#summary)
|
||||
|
||||
## Truthy
|
||||
|
||||
All values in Liquid are truthy except `nil` and `false`.
|
||||
|
||||
In the example below, the string "Tobi" is not a boolean, but it is truthy in a conditional:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign tobi = "Tobi" %}
|
||||
|
||||
{% if tobi %}
|
||||
This condition will always be true.
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
[Strings]({{ "/basics/types/#string" | prepend: site.baseurl }}), even when empty, are truthy. The example below will result in empty HTML tags if `settings.fp_heading` is empty:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if settings.fp_heading %}
|
||||
<h1>{{ settings.fp_heading }}</h1>
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```html
|
||||
<h1></h1>
|
||||
```
|
||||
|
||||
## Falsy
|
||||
|
||||
The falsy values in Liquid are [`nil`]({{ "/basics/types/#nil" | prepend: site.baseurl }}) and [`false`]({{ "/basics/types/#boolean" | prepend: site.baseurl }}).
|
||||
|
||||
## Summary
|
||||
|
||||
The table below summarizes what is truthy or falsy in Liquid.
|
||||
|
||||
| | truthy | falsy |
|
||||
| ------------- |:-------------:|:-------------:|
|
||||
| true | • | |
|
||||
| false | | • |
|
||||
| nil | | • |
|
||||
| string | • | |
|
||||
| empty string | • | |
|
||||
| 0 | • | |
|
||||
| integer | • | |
|
||||
| float | • | |
|
||||
| array | • | |
|
||||
| empty array | • | |
|
||||
| page | • | |
|
||||
| EmptyDrop | • | |
|
||||
@@ -1,128 +0,0 @@
|
||||
---
|
||||
title: Types
|
||||
description: An overview of data types in the Liquid template language.
|
||||
---
|
||||
|
||||
Liquid objects can have one of six types:
|
||||
|
||||
- [String](#string)
|
||||
- [Number](#number)
|
||||
- [Boolean](#boolean)
|
||||
- [Nil](#nil)
|
||||
- [Array](#array)
|
||||
|
||||
You can initialize Liquid variables with the [assign]({{ "/tags/variable/#assign" | prepend: site.baseurl }}) or [capture]({{ "/tags/variable/#capture" | prepend: site.baseurl }}) tags.
|
||||
|
||||
## String
|
||||
|
||||
Declare a string by wrapping a variable's value in single or double quotes:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_string = "Hello World!" %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
## Number
|
||||
|
||||
Numbers include floats and integers:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_int = 25 %}
|
||||
{% assign my_float = 39.756 %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
## Boolean
|
||||
|
||||
Booleans are either `true` or `false`. No quotations are necessary when declaring a boolean:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign foo = true %}
|
||||
{% assign bar = false %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
## Nil
|
||||
|
||||
Nil is a special empty value that is returned when Liquid code has no results. It is **not** a string with the characters "nil".
|
||||
|
||||
Nil is [treated as false]({{ "/basics/truthy-and-falsy" | prepend: site.baseurl }}) in the conditions of `if` blocks and other Liquid tags that check the truthfulness of a statement.
|
||||
|
||||
In the following example, if the user does not exist (that is, `user` returns `nil`), Liquid will not print the greeting:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if user %}
|
||||
Hello {{ user.name }}!
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
Tags or outputs that return `nil` will not print anything to the page.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
The current user is {{ user.name }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
The current user is
|
||||
```
|
||||
|
||||
## Array
|
||||
|
||||
Arrays hold lists of variables of any type.
|
||||
|
||||
### Accessing items in arrays
|
||||
|
||||
To access all the items in an array, you can loop through each item in the array using an [iteration tag]({{ "/tags/iteration" | prepend: site.baseurl }}).
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
<!-- if site.users = "Tobi", "Laura", "Tetsuro", "Adam" -->
|
||||
{% for user in site.users %}
|
||||
{{ user }}
|
||||
{% endfor %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% raw %}
|
||||
Tobi Laura Tetsuro Adam
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
### Accessing specific items in arrays
|
||||
|
||||
You can use square bracket `[` `]` notation to access a specific item in an array. Array indexing starts at zero.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
<!-- if site.users = "Tobi", "Laura", "Tetsuro", "Adam" -->
|
||||
{{ site.users[0] }}
|
||||
{{ site.users[1] }}
|
||||
{{ site.users[3] }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
Tobi
|
||||
Laura
|
||||
Adam
|
||||
```
|
||||
|
||||
### Initializing arrays
|
||||
|
||||
You cannot initialize arrays using only Liquid.
|
||||
|
||||
You can, however, use the [split]({{ "/filters/split" | prepend: site.baseurl }}) filter to break a string into an array of substrings.
|
||||
@@ -1,24 +0,0 @@
|
||||
---
|
||||
title: Variations of Liquid
|
||||
description: An overview of the different installations of Liquid and how Liquid can change depending on where you're using it.
|
||||
---
|
||||
|
||||
Liquid is a flexible, safe language, and is used in many different environments. Liquid was created for use in [Shopify](https://www.shopify.com) stores, and is also used extensively on [Jekyll](https://jekyllrb.com) websites. Over time, both Shopify and Jekyll have added their own objects, tags, and filters to Liquid. The most popular versions of Liquid that exist are **Liquid**, **Shopify Liquid**, and **Jekyll Liquid**.
|
||||
|
||||
This site documents the latest version of **Liquid** including betas and release candidates — that is, Liquid as it exists outside of Shopify and Jekyll. If you download the Liquid repository or install it as a [gem](https://rubygems.org/gems/liquid), you will get access to whatever objects, tags, and filters are in the version of Liquid that you chose.
|
||||
|
||||
## Shopify
|
||||
|
||||
Shopify always uses the latest version of Liquid as a base, but Shopify adds a significant number of objects, tags, and filters to Liquid for use in merchants' stores. These include objects representing store, product, and customer information, and filters for displaying store data and manipulating storefront assets like product images.
|
||||
|
||||
Shopify's version of Liquid is documented in the [Shopify Help Center](https://help.shopify.com/themes/liquid). If you want to try out Shopify's version of Liquid, you can [start a free trial of Shopify](https://www.shopify.com/signup) or use a sandbox like [DropPen](http://droppen.org/).
|
||||
|
||||
## Jekyll
|
||||
|
||||
[Jekyll](https://jekyllrb.com) is a static site generator, a command-line tool that creates websites by merging templates with content files. Jekyll uses Liquid as its template language, and adds a few objects, tags, and filters. These include objects representing content pages, tags for including snippets of content in others, and filters for manipulating strings and URLs.
|
||||
|
||||
Jekyll also powers [GitHub Pages](https://pages.github.com/), a web hosting service that lets you push a Jekyll installation to a GitHub repository and have the resulting website published. This website is built using GitHub Pages.
|
||||
|
||||
Jekyll might not be using the latest version of Liquid. This means that the tags and filters listed on this site may not work in Jekyll. Often the Jekyll project will wait for a stable release of Liquid rather than using a beta or release candidate version. To see what version of Liquid Jekyll is using, check the **runtime dependencies** section of [Jekyll's gem page](https://rubygems.org/gems/jekyll).
|
||||
|
||||
Jekyll's version of Liquid is documented in the [Templates section of Jekyll's documentation](http://jekyllrb.com/docs/templates/). If you want to try out Jekyll's version of Liquid, you can clone the Jekyll project or install Jekyll as a gem and test Liquid on a static site.
|
||||
@@ -1,80 +0,0 @@
|
||||
---
|
||||
title: Whitespace control
|
||||
description: An overview of controlling whitespace between code in the Liquid template language.
|
||||
---
|
||||
|
||||
In Liquid, you can include a hyphen in your tag syntax `{% raw %}{{-{% endraw %}`, `{% raw %}-}}{% endraw %}`, `{% raw %}{%-{% endraw %}`, and `{% raw %}-%}{% endraw %}` to strip whitespace from the left or right side of a rendered tag.
|
||||
|
||||
Normally, even if it doesn't output text, any line of Liquid in your template will still output a blank line in your rendered HTML:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{% assign my_variable = "tomato" %}
|
||||
{{ my_variable }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
Notice the blank line before "tomato" in the rendered template:
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{% assign my_variable = "tomato" %}
|
||||
{{ my_variable }}
|
||||
```
|
||||
|
||||
By including hyphens in your `assign` tag, you can strip the generated whitespace from the rendered template:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{%- assign my_variable = "tomato" -%}
|
||||
{{ my_variable }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
tomato
|
||||
```
|
||||
|
||||
If you don't want any of your tags to output whitespace, as a general rule you can add hyphens to both sides of all your tags (`{% raw %}{%-{% endraw %}` and `{% raw %}-%}{% endraw %}`):
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{% assign username = "John G. Chalmers-Smith" %}
|
||||
{% if username and username.size > 10 %}
|
||||
Wow, {{ username }}, you have a long name!
|
||||
{% else %}
|
||||
Hello there!
|
||||
{% endif %}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output without whitespace control</p>
|
||||
``` text
|
||||
{% assign username = "John G. Chalmers-Smith" %}
|
||||
{% if username and username.size > 10 %}
|
||||
Wow, {{ username }}, you have a long name!
|
||||
{% else %}
|
||||
Hello there!
|
||||
{% endif %}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{%- assign username = "John G. Chalmers-Smith" -%}
|
||||
{%- if username and username.size > 10 -%}
|
||||
Wow, {{ username }}, you have a long name!
|
||||
{%- else -%}
|
||||
Hello there!
|
||||
{%- endif -%}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output with whitespace control</p>
|
||||
``` text
|
||||
Wow, John G. Chalmers-Smith, you have a long name!
|
||||
```
|
||||
@@ -1,19 +0,0 @@
|
||||
---
|
||||
layout: null
|
||||
---
|
||||
|
||||
@charset "utf-8";
|
||||
|
||||
@import "partials/defaults";
|
||||
@import "partials/colors";
|
||||
@import "partials/helpers";
|
||||
@import "partials/media-queries";
|
||||
|
||||
@import "modules/base";
|
||||
@import "modules/layout";
|
||||
@import "modules/buttons";
|
||||
@import "modules/home-banner";
|
||||
@import "modules/home-users-grid";
|
||||
@import "modules/content-area";
|
||||
|
||||
@import "vendors/syntax-highlighting";
|
||||
@@ -0,0 +1,41 @@
|
||||
module ProductsFilter
|
||||
def price(integer)
|
||||
sprintf("$%.2d USD", integer / 100.0)
|
||||
end
|
||||
|
||||
def prettyprint(text)
|
||||
text.gsub( /\*(.*)\*/, '<b>\1</b>' )
|
||||
end
|
||||
|
||||
def count(array)
|
||||
array.size
|
||||
end
|
||||
|
||||
def paragraph(p)
|
||||
"<p>#{p}</p>"
|
||||
end
|
||||
end
|
||||
|
||||
class Servlet < LiquidServlet
|
||||
|
||||
def index
|
||||
{ 'date' => Time.now }
|
||||
end
|
||||
|
||||
def products
|
||||
{ 'products' => products_list, 'description' => description, 'section' => 'Snowboards', 'cool_products' => true}
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def products_list
|
||||
[{'name' => 'Arbor Draft', 'price' => 39900, 'description' => 'the *arbor draft* is a excellent product' },
|
||||
{'name' => 'Arbor Element', 'price' => 40000, 'description' => 'the *arbor element* rocks for freestyling'},
|
||||
{'name' => 'Arbor Diamond', 'price' => 59900, 'description' => 'the *arbor diamond* is a made up product because im obsessed with arbor and have no creativity'}]
|
||||
end
|
||||
|
||||
def description
|
||||
"List of Products ~ This is a list of products with price and description."
|
||||
end
|
||||
|
||||
end
|
||||
@@ -0,0 +1,28 @@
|
||||
class LiquidServlet < WEBrick::HTTPServlet::AbstractServlet
|
||||
|
||||
def do_GET(req, res)
|
||||
handle(:get, req, res)
|
||||
end
|
||||
|
||||
def do_POST(req, res)
|
||||
handle(:post, req, res)
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def handle(type, req, res)
|
||||
@request, @response = req, res
|
||||
|
||||
@request.path_info =~ /(\w+)\z/
|
||||
@action = $1 || 'index'
|
||||
@assigns = send(@action) if respond_to?(@action)
|
||||
|
||||
@response['Content-Type'] = "text/html"
|
||||
@response.status = 200
|
||||
@response.body = Liquid::Template.parse(read_template).render(@assigns, :filters => [ProductsFilter])
|
||||
end
|
||||
|
||||
def read_template(filename = @action)
|
||||
File.read( File.dirname(__FILE__) + "/templates/#{filename}.liquid" )
|
||||
end
|
||||
end
|
||||
@@ -0,0 +1,14 @@
|
||||
require 'webrick'
|
||||
require 'rexml/document'
|
||||
|
||||
DIR = File.expand_path(File.dirname(__FILE__))
|
||||
|
||||
require DIR + '/../../lib/liquid'
|
||||
require DIR + '/liquid_servlet'
|
||||
require DIR + '/example_servlet'
|
||||
|
||||
# Setup webrick
|
||||
server = WEBrick::HTTPServer.new( :Port => ARGV[1] || 3000 )
|
||||
server.mount('/', Servlet)
|
||||
trap("INT"){ server.shutdown }
|
||||
server.start
|
||||
@@ -0,0 +1,6 @@
|
||||
<p>Hello world!</p>
|
||||
|
||||
<p>It is {{date}}</p>
|
||||
|
||||
|
||||
<p>Check out the <a href="/products">Products</a> screen </p>
|
||||
@@ -0,0 +1,49 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
|
||||
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
|
||||
<head>
|
||||
<meta http-equiv="Content-type" content="text/html; charset=utf-8" />
|
||||
<meta http-equiv="Content-Language" content="en-us" />
|
||||
|
||||
<title>products</title>
|
||||
|
||||
<meta name="ROBOTS" content="ALL" />
|
||||
<meta http-equiv="imagetoolbar" content="no" />
|
||||
<meta name="MSSmartTagsPreventParsing" content="true" />
|
||||
<meta name="Copyright" content="(c) 2005 Copyright content: Copyright design: Tobias Luetke" />
|
||||
<!-- (c) Copyright 2005 by Tobias Luetke All Rights Reserved. -->
|
||||
</head>
|
||||
|
||||
<body>
|
||||
|
||||
<h1>{{ description | split: '~' | first }}</h1>
|
||||
|
||||
<h2>{{ description | split: '~' | last }}</h2>
|
||||
|
||||
<h2>There are currently {{products | count}} products in the {{section}} catalog</h2>
|
||||
|
||||
{% if cool_products %}
|
||||
Cool products :)
|
||||
{% else %}
|
||||
Uncool products :(
|
||||
{% endif %}
|
||||
|
||||
<ul id="products">
|
||||
|
||||
{% for product in products %}
|
||||
<li>
|
||||
<h2>{{product.name}}</h2>
|
||||
Only {{product.price | price }}
|
||||
|
||||
{{product.description | prettyprint | paragraph }}
|
||||
|
||||
{{ 'it rocks!' | paragraph }}
|
||||
|
||||
</li>
|
||||
{% endfor %}
|
||||
|
||||
</ul>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
@@ -1,30 +0,0 @@
|
||||
---
|
||||
layout: null
|
||||
---
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
|
||||
<channel>
|
||||
<title>{{ site.title | xml_escape }}</title>
|
||||
<description>{{ site.description | xml_escape }}</description>
|
||||
<link>{{ site.url }}{{ site.baseurl }}/</link>
|
||||
<atom:link href="{{ "/feed.xml" | prepend: site.baseurl | prepend: site.url }}" rel="self" type="application/rss+xml"/>
|
||||
<pubDate>{{ site.time | date_to_rfc822 }}</pubDate>
|
||||
<lastBuildDate>{{ site.time | date_to_rfc822 }}</lastBuildDate>
|
||||
<generator>Jekyll v{{ jekyll.version }}</generator>
|
||||
{% for post in site.posts limit:10 %}
|
||||
<item>
|
||||
<title>{{ post.title | xml_escape }}</title>
|
||||
<description>{{ post.content | xml_escape }}</description>
|
||||
<pubDate>{{ post.date | date_to_rfc822 }}</pubDate>
|
||||
<link>{{ post.url | prepend: site.baseurl | prepend: site.url }}</link>
|
||||
<guid isPermaLink="true">{{ post.url | prepend: site.baseurl | prepend: site.url }}</guid>
|
||||
{% for tag in post.tags %}
|
||||
<category>{{ tag | xml_escape }}</category>
|
||||
{% endfor %}
|
||||
{% for cat in post.categories %}
|
||||
<category>{{ cat | xml_escape }}</category>
|
||||
{% endfor %}
|
||||
</item>
|
||||
{% endfor %}
|
||||
</channel>
|
||||
</rss>
|
||||
@@ -1,44 +0,0 @@
|
||||
---
|
||||
title: abs
|
||||
description: Liquid filter that gets the absolute value of a number.
|
||||
---
|
||||
|
||||
Returns the absolute value of a number.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ -17 | abs }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
17
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 4 | abs }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
4
|
||||
```
|
||||
|
||||
`abs` will also work on a string if the string only contains a number.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "-19.86" | abs }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
19.86
|
||||
```
|
||||
@@ -1,34 +0,0 @@
|
||||
---
|
||||
title: append
|
||||
description: Liquid filter that appends a string to another string.
|
||||
---
|
||||
|
||||
Concatenates two strings and returns the concatenated value.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "/my/fancy/url" | append: ".html" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "/my/fancy/url" | append: ".html" }}
|
||||
```
|
||||
|
||||
`append` can also be used with variables:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign filename = "/index.html" %}
|
||||
{{ "website.com" | append: filename }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign filename = "/index.html" %}
|
||||
{{ "website.com" | append: filename }}
|
||||
```
|
||||
@@ -1,32 +0,0 @@
|
||||
---
|
||||
title: capitalize
|
||||
description: Liquid filter that capitalizes the first character in a string.
|
||||
---
|
||||
|
||||
Makes the first character of a string capitalized.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "title" | capitalize }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
Title
|
||||
```
|
||||
|
||||
`capitalize` only capitalizes the first character of the string, so later words are not affected:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "my great title" | capitalize }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
My great title
|
||||
```
|
||||
@@ -1,56 +0,0 @@
|
||||
---
|
||||
title: ceil
|
||||
description: Liquid filter that gets the ceiling of a number by rounding up to the nearest integer.
|
||||
---
|
||||
|
||||
Rounds the input up to the nearest whole number. Liquid tries to convert the input to a number before the filter is applied.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 1.2 | ceil }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 1.2 | ceil }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 2.0 | ceil }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 2.0 | ceil }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 183.357 | ceil }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 183.357 | ceil }}
|
||||
```
|
||||
|
||||
Here the input value is a string:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "3.5" | ceil }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "3.5" | ceil }}
|
||||
```
|
||||
@@ -1,53 +0,0 @@
|
||||
---
|
||||
title: compact
|
||||
description: Liquid filter that removes nil values from an array.
|
||||
---
|
||||
|
||||
Removes any `nil` values from an array.
|
||||
|
||||
For this example, assume `site.pages` is an array of content pages for a website, and some of these pages have an attribute called `category` that specifies their content category. If we `map` those categories to an array, some of the array items might be `nil` if any pages do not have a `category` attribute.
|
||||
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
```liquid
|
||||
{% assign site_categories = site.pages | map: 'category' %}
|
||||
|
||||
{% for category in site_categories %}
|
||||
{{ category }}
|
||||
{% endfor %}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
business
|
||||
celebrities
|
||||
|
||||
lifestyle
|
||||
sports
|
||||
|
||||
technology
|
||||
```
|
||||
|
||||
By using `compact` when we create our `site_categories` array, we can remove all the `nil` values in the array.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
```liquid
|
||||
{% assign site_categories = site.pages | map: 'category' | compact %}
|
||||
|
||||
{% for category in site_categories %}
|
||||
{{ category }}
|
||||
{% endfor %}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
business
|
||||
celebrities
|
||||
lifestyle
|
||||
sports
|
||||
technology
|
||||
```
|
||||
@@ -1,60 +0,0 @@
|
||||
---
|
||||
title: date
|
||||
description: Liquid filter that prints and formats dates.
|
||||
---
|
||||
|
||||
Converts a timestamp into another date format. The format for this syntax is the same as [`strftime`](http://strftime.net).
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ article.published_at | date: "%a, %b %d, %y" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
Fri, Jul 17, 15
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ article.published_at | date: "%Y" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
2015
|
||||
```
|
||||
|
||||
`date` works on strings if they contain well-formatted dates:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "March 14, 2016" | date: "%b %d, %y" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "March 14, 2016" | date: "%b %d, %y" }}
|
||||
```
|
||||
|
||||
To get the current time, pass the special word `"now"` (or `"today"`) to `date`:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
This page was last updated at {{ "now" | date: "%Y-%m-%d %H:%M" }}.
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
This page was last updated at {{ "now" | date: "%Y-%m-%d %H:%M" }}.
|
||||
```
|
||||
|
||||
Note that the value will be the current time of when the page was last generated from the template, not when the page is presented to a user if caching or static site generation is involved.
|
||||
@@ -1,50 +0,0 @@
|
||||
---
|
||||
title: default
|
||||
description: Liquid filter that specifies a fallback in case a value doesn't exist.
|
||||
---
|
||||
|
||||
Allows you to specify a fallback in case a value doesn't exist. `default` will show its value if the left side is `nil`, `false`, or empty.
|
||||
|
||||
In this example, `product_price` is not defined, so the default value is used.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ product_price | default: 2.99 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
2.99
|
||||
```
|
||||
|
||||
In this example, `product_price` is defined, so the default value is not used.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign product_price = 4.99 %}
|
||||
{{ product_price | default: 2.99 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
4.99
|
||||
```
|
||||
|
||||
In this example, `product_price` is empty, so the default value is used.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign product_price = "" %}
|
||||
{{ product_price | default: 2.99 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
2.99
|
||||
```
|
||||
@@ -1,102 +0,0 @@
|
||||
---
|
||||
title: divided_by
|
||||
description: Liquid filter that divides a number by another number.
|
||||
---
|
||||
|
||||
Divides a number by the specified number.
|
||||
|
||||
The result is rounded down to the nearest integer (that is, the [floor]({{ site.baseurl }}/filters/floor)) if the divisor is an integer.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ 16 | divided_by: 4 }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ 16 | divided_by: 4 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ 5 | divided_by: 3 }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ 5 | divided_by: 3 }}
|
||||
```
|
||||
|
||||
### Controlling rounding
|
||||
|
||||
`divided_by` produces a result of the same type as the divisor — that is, if you divide by an integer, the result will be an integer. If you divide by a float (a number with a decimal in it), the result will be a float.
|
||||
|
||||
For example, here the divisor is an integer:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ 20 | divided_by: 7 }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ 20 | divided_by: 7 }}
|
||||
```
|
||||
|
||||
Here it is a float:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ 20 | divided_by: 7.0 }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ 20 | divided_by: 7.0 }}
|
||||
```
|
||||
|
||||
### Changing variable types
|
||||
|
||||
You might want to use a variable as a divisor, in which case you can't simply add `.0` to convert it to a float. In these cases, you can `assign` a version of your variable converted to a float using the `times` filter.
|
||||
|
||||
In this example, we're dividing by a variable that contains an integer, so we get an integer:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{% assign my_integer = 7 %}
|
||||
{{ 20 | divided_by: my_integer }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{% assign my_integer = 7 %}
|
||||
{{ 20 | divided_by: my_integer }}
|
||||
```
|
||||
|
||||
Here, we [multiply]({{ site.baseurl}}/filters/times) the variable by `1.0` to get a float, then divide by the float instead:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{% assign my_integer = 7 %}
|
||||
{% assign my_float = my_integer | times: 1.0 %}
|
||||
{{ 20 | divided_by: my_float }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{% assign my_integer = 7 %}
|
||||
{% assign my_float = my_integer | times: 1.0 %}
|
||||
{{ 20 | divided_by: my_float }}
|
||||
```
|
||||
@@ -1,30 +0,0 @@
|
||||
---
|
||||
title: downcase
|
||||
description: Liquid filter that coverts a string to lowercase.
|
||||
---
|
||||
|
||||
Makes each character in a string lowercase. It has no effect on strings which are already all lowercase.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Parker Moore" | downcase }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Parker Moore" | downcase }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "apple" | downcase }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "apple" | downcase }}
|
||||
```
|
||||
@@ -1,30 +0,0 @@
|
||||
---
|
||||
title: escape
|
||||
description: Liquid filter that escapes URL-unsafe characters in a string.
|
||||
---
|
||||
|
||||
Escapes a string by replacing characters with escape sequences (so that the string can be used in a URL, for example). It doesn't change strings that don't have anything to escape.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Have you read 'James & the Giant Peach'?" | escape }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Have you read 'James & the Giant Peach'?" | escape }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Tetsuro Takara" | escape }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Tetsuro Takara" | escape }}
|
||||
```
|
||||
@@ -1,30 +0,0 @@
|
||||
---
|
||||
title: escape_once
|
||||
description: Liquid filter that escapes URL-unsafe characters in a string once.
|
||||
---
|
||||
|
||||
Escapes a string without changing existing escaped entities. It doesn't change strings that don't have anything to escape.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "1 < 2 & 3" | escape_once }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "1 < 2 & 3" | escape_once }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "1 < 2 & 3" | escape_once }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "1 < 2 & 3" | escape_once }}
|
||||
```
|
||||
@@ -1,38 +0,0 @@
|
||||
---
|
||||
title: first
|
||||
description: Liquid filter that returns the first item of an array.
|
||||
---
|
||||
|
||||
Returns the first item of an array.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array.first }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array.first }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "zebra, octopus, giraffe, tiger" | split: ", " %}
|
||||
|
||||
{{ my_array.first }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "zebra, octopus, giraffe, tiger" | split: ", " %}
|
||||
|
||||
{{ my_array.first }}
|
||||
```
|
||||
@@ -1,56 +0,0 @@
|
||||
---
|
||||
title: floor
|
||||
description: Liquid filter that gets the floor of a number by rounding down to the nearest integer.
|
||||
---
|
||||
|
||||
Rounds a number down to the nearest whole number. Liquid tries to convert the input to a number before the filter is applied.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 1.2 | floor }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 1.2 | floor }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 2.0 | floor }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 2.0 | floor }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 183.357 | floor }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 183.357 | floor }}
|
||||
```
|
||||
|
||||
Here the input value is a string:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "3.5" | floor }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "3.5" | floor }}
|
||||
```
|
||||
@@ -1,3 +0,0 @@
|
||||
---
|
||||
redirect_to: /liquid/filters/abs
|
||||
---
|
||||
@@ -1,22 +0,0 @@
|
||||
---
|
||||
title: join
|
||||
description: Liquid filter that joins an array of strings into a single string.
|
||||
---
|
||||
|
||||
Combines the items in an array into a single string using the argument as a separator.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign beatles = "John, Paul, George, Ringo" | split: ", " %}
|
||||
|
||||
{{ beatles | join: " and " }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign beatles = "John, Paul, George, Ringo" | split: ", " %}
|
||||
|
||||
{{ beatles | join: " and " }}
|
||||
```
|
||||
@@ -1,38 +0,0 @@
|
||||
---
|
||||
title: last
|
||||
description: Liquid filter that gets the last value in an array.
|
||||
---
|
||||
|
||||
Returns the last item of an array.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array.last }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array.last }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "zebra, octopus, giraffe, tiger" | split: ", " %}
|
||||
|
||||
{{ my_array.last }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "zebra, octopus, giraffe, tiger" | split: ", " %}
|
||||
|
||||
{{ my_array.last }}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: lstrip
|
||||
description: Liquid filter that removes whitespace from the left side of a string.
|
||||
---
|
||||
|
||||
Removes all whitespaces (tabs, spaces, and newlines) from the beginning of a string. The filter does not affect spaces between words.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ " So much room for activities! " | lstrip }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ " So much room for activities! " | lstrip }}
|
||||
```
|
||||
@@ -1,28 +0,0 @@
|
||||
---
|
||||
title: map
|
||||
description: Liquid filter that creates an array of values by extracting a named property from an object.
|
||||
---
|
||||
|
||||
Creates an array of values by extracting the values of a named property from another object.
|
||||
|
||||
In this example, assume the object `site.pages` contains all the metadata for a website. Using `assign` with the `map` filter creates a variable that contains only the values of the `category` properties of everything in the `site.pages` object.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign all_categories = site.pages | map: "category" %}
|
||||
|
||||
{% for item in all_categories %}
|
||||
{{ item }}
|
||||
{% endfor %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
business
|
||||
celebrities
|
||||
lifestyle
|
||||
sports
|
||||
technology
|
||||
```
|
||||
@@ -1,42 +0,0 @@
|
||||
---
|
||||
title: minus
|
||||
description: Liquid filter that subtracts one number from another.
|
||||
---
|
||||
|
||||
Subtracts a number from another number.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 4 | minus: 2 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 4 | minus: 2 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 16 | minus: 4 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 16 | minus: 4 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 183.357 | minus: 12 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 183.357 | minus: 12 }}
|
||||
```
|
||||
@@ -1,42 +0,0 @@
|
||||
---
|
||||
title: modulo
|
||||
description: Liquid filter that returns the remainder from a division operation.
|
||||
---
|
||||
|
||||
Returns the remainder of a division operation.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 3 | modulo: 2 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 3 | modulo: 2 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 24 | modulo: 7 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 24 | modulo: 7 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 183.357 | modulo: 12 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 183.357 | modulo: 12 }}
|
||||
```
|
||||
@@ -1,28 +0,0 @@
|
||||
---
|
||||
title: newline_to_br
|
||||
description: Liquid filter that converts newlines in an input string to HTML <br> tags.
|
||||
---
|
||||
|
||||
Replaces every newline (`\n`) with an HTML line break (`<br>`).
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% capture string_with_newlines %}
|
||||
Hello
|
||||
there
|
||||
{% endcapture %}
|
||||
|
||||
{{ string_with_newlines | newline_to_br }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```html
|
||||
{% capture string_with_newlines %}
|
||||
Hello
|
||||
there
|
||||
{% endcapture %}
|
||||
|
||||
{{ string_with_newlines | newline_to_br }}
|
||||
```
|
||||
@@ -1,42 +0,0 @@
|
||||
---
|
||||
title: plus
|
||||
description: Liquid filter that adds a number to another number.
|
||||
---
|
||||
|
||||
Adds a number to another number.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 4 | plus: 2 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 4 | plus: 2 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 16 | plus: 4 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 16 | plus: 4 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 183.357 | plus: 12 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 183.357 | plus: 12 }}
|
||||
```
|
||||
@@ -1,36 +0,0 @@
|
||||
---
|
||||
title: prepend
|
||||
description: Liquid filter that prepends a string to the beginning of another string.
|
||||
---
|
||||
|
||||
Adds the specified string to the beginning of another string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "apples, oranges, and bananas" | prepend: "Some fruit: " }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "apples, oranges, and bananas" | prepend: "Some fruit: " }}
|
||||
```
|
||||
|
||||
You can also `prepend` variables:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign url = "liquidmarkup.com" %}
|
||||
|
||||
{{ "/index.html" | prepend: url }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign url = "liquidmarkup.com" %}
|
||||
|
||||
{{ "/index.html" | prepend: url }}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: remove
|
||||
description: Liquid filter that removes all occurences of a given substring from a string.
|
||||
---
|
||||
|
||||
Removes every occurrence of the specified substring from a string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "I strained to see the train through the rain" | remove: "rain" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "I strained to see the train through the rain" | remove: "rain" }}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: remove_first
|
||||
description: Liquid filter that removes the first occurence of a given substring from a string.
|
||||
---
|
||||
|
||||
Removes only the first occurrence of the specified substring from a string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "I strained to see the train through the rain" | remove_first: "rain" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "I strained to see the train through the rain" | remove_first: "rain" }}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: replace
|
||||
description: Liquid filter that replaces all occurences of a given substring in a string.
|
||||
---
|
||||
|
||||
Replaces every occurrence of an argument in a string with the second argument.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Take my protein pills and put my helmet on" | replace: "my", "your" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Take my protein pills and put my helmet on" | replace: "my", "your" }}
|
||||
```
|
||||
@@ -1,20 +0,0 @@
|
||||
---
|
||||
title: replace_first
|
||||
description: Liquid filter that replaces the first occurrence of a given substring in a string.
|
||||
---
|
||||
|
||||
Replaces only the first occurrence of the first argument in a string with the second argument.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_string = "Take my protein pills and put my helmet on" %}
|
||||
{{ my_string | replace_first: "my", "your" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_string = "Take my protein pills and put my helmet on" %}
|
||||
{{ my_string | replace_first: "my", "your" }}
|
||||
```
|
||||
@@ -1,36 +0,0 @@
|
||||
---
|
||||
title: reverse
|
||||
description: Liquid filter that reverses an array, or a string converted to an array.
|
||||
---
|
||||
|
||||
Reverses the order of the items in an array. `reverse` cannot reverse a string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array | reverse | join: ", " }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array | reverse | join: ", " }}
|
||||
```
|
||||
|
||||
`reverse` cannot be used directly on a string, but you can split a string into an array, reverse the array, and rejoin it by chaining together filters:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Ground control to Major Tom." | split: "" | reverse | join: "" }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Ground control to Major Tom." | split: "" | reverse | join: "" }}
|
||||
```
|
||||
@@ -1,42 +0,0 @@
|
||||
---
|
||||
title: round
|
||||
description: Liquid filter that rounds a number to the nearest integer.
|
||||
---
|
||||
|
||||
Rounds an input number to the nearest integer or, if a number is specified as an argument, to that number of decimal places.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 1.2 | round }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 1.2 | round }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 2.7 | round }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 2.7 | round }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 183.357 | round: 2 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 183.357 | round: 2 }}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: rstrip
|
||||
description: Liquid filter that removes all whitespace from the right side of a string.
|
||||
---
|
||||
|
||||
Removes all whitespace (tabs, spaces, and newlines) from the right side of a string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ " So much room for activities! " | rstrip }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ " So much room for activities! " | rstrip }}
|
||||
```
|
||||
@@ -1,44 +0,0 @@
|
||||
---
|
||||
title: size
|
||||
description: Liquid filter that returns the number of characters in a string or the number of items in an array.
|
||||
---
|
||||
|
||||
Returns the number of characters in a string or the number of items in an array. `size` can also be used with dot notation (for example, `{% raw %}{{ my_string.size }}{% endraw %}`). This allows you to use `size` inside tags such as conditionals.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Ground control to Major Tom." | size }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Ground control to Major Tom." | size }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array | size }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "apples, oranges, peaches, plums" | split: ", " %}
|
||||
|
||||
{{ my_array | size }}
|
||||
```
|
||||
|
||||
Using dot notation:
|
||||
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% if site.pages.size > 10 %}
|
||||
This is a big website!
|
||||
{% endif %}
|
||||
{% endraw %}
|
||||
```
|
||||
@@ -1,58 +0,0 @@
|
||||
---
|
||||
title: slice
|
||||
description: Liquid filter that returns a substring from a given position in a string.
|
||||
---
|
||||
|
||||
Returns a substring of 1 character beginning at the index specified by the argument passed in. An optional second argument specifies the length of the substring to be returned.
|
||||
|
||||
String indices are numbered starting from 0.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Liquid" | slice: 0 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Liquid" | slice: 0 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Liquid" | slice: 2 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Liquid" | slice: 2 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Liquid" | slice: 2, 5 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Liquid" | slice: 2, 5 }}
|
||||
```
|
||||
|
||||
If the first parameter is a negative number, the indices are counted from the end of the string:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Liquid" | slice: -3, 2 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Liquid" | slice: -3, 2 }}
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
---
|
||||
title: sort
|
||||
description: Liquid filter that sorts an array in case-sensitive order.
|
||||
---
|
||||
|
||||
Sorts items in an array by a property of an item in the array. The order of the sorted array is case-sensitive.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "zebra, octopus, giraffe, Sally Snake" | split: ", " %}
|
||||
|
||||
{{ my_array | sort | join: ", " }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "zebra, octopus, giraffe, Sally Snake" | split: ", " %}
|
||||
|
||||
{{ my_array | sort | join: ", " }}
|
||||
```
|
||||
@@ -1,20 +0,0 @@
|
||||
---
|
||||
title: sort_natural
|
||||
description: Liquid filter that sorts an array in case-insensitive order.
|
||||
---
|
||||
|
||||
Sorts items in an array by a property of an item in the array.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "zebra, octopus, giraffe, Sally Snake" | split: ", " %}
|
||||
|
||||
{{ my_array | sort_natural | join: ", " }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
giraffe, octopus, Sally Snake, zebra
|
||||
```
|
||||
@@ -1,26 +0,0 @@
|
||||
---
|
||||
title: split
|
||||
description: Liquid filter that splits a string into an array using separators.
|
||||
---
|
||||
|
||||
Divides an input string into an array using the argument as a separator. `split` is commonly used to convert comma-separated items from a string to an array.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign beatles = "John, Paul, George, Ringo" | split: ", " %}
|
||||
|
||||
{% for member in beatles %}
|
||||
{{ member }}
|
||||
{% endfor %}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign beatles = "John, Paul, George, Ringo" | split: ", " %}
|
||||
|
||||
{% for member in beatles %}
|
||||
{{ member }}
|
||||
{% endfor %}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: strip
|
||||
description: Liquid filter that removes whitespace from the left and right sides of a string.
|
||||
---
|
||||
|
||||
Removes all whitespace (tabs, spaces, and newlines) from both the left and right side of a string. It does not affect spaces between words.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ " So much room for activities! " | strip }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ " So much room for activities! " | strip }}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: strip_html
|
||||
description: Liquid filter that removes HTML tags from a string.
|
||||
---
|
||||
|
||||
Removes any HTML tags from a string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Have <em>you</em> read <strong>Ulysses</strong>?" | strip_html }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Have <em>you</em> read <strong>Ulysses</strong>?" | strip_html }}
|
||||
```
|
||||
@@ -1,28 +0,0 @@
|
||||
---
|
||||
title: strip_newlines
|
||||
description: Liquid filter that removes newline characters from a string.
|
||||
---
|
||||
|
||||
Removes any newline characters (line breaks) from a string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% capture string_with_newlines %}
|
||||
Hello
|
||||
there
|
||||
{% endcapture %}
|
||||
|
||||
{{ string_with_newlines | strip_newlines }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```html
|
||||
{% capture string_with_newlines %}
|
||||
Hello
|
||||
there
|
||||
{% endcapture %}
|
||||
|
||||
{{ string_with_newlines | strip_newlines }}
|
||||
```
|
||||
@@ -1,42 +0,0 @@
|
||||
---
|
||||
title: times
|
||||
description: Liquid filter that multiplies a number by another number.
|
||||
---
|
||||
|
||||
Multiplies a number by another number.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 3 | times: 2 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 3 | times: 2 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 24 | times: 7 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 24 | times: 7 }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ 183.357 | times: 12 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ 183.357 | times: 12 }}
|
||||
```
|
||||
@@ -1,52 +0,0 @@
|
||||
---
|
||||
title: truncate
|
||||
description: Liquid filter that truncates a string to a given number of characters.
|
||||
---
|
||||
|
||||
`truncate` shortens a string down to the number of characters passed as a parameter. If the number of characters specified is less than the length of the string, an ellipsis (...) is appended to the string and is included in the character count.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Ground control to Major Tom." | truncate: 20 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Ground control to Major Tom." | truncate: 20 }}
|
||||
```
|
||||
|
||||
### Custom ellipsis
|
||||
|
||||
`truncate` takes an optional second parameter that specifies the sequence of characters to be appended to the truncated string. By default this is an ellipsis (...), but you can specify a different sequence.
|
||||
|
||||
The length of the second parameter counts against the number of characters specified by the first parameter. For example, if you want to truncate a string to exactly 10 characters, and use a 3-character ellipsis, use **13** for the first parameter of `truncate`, since the ellipsis counts as 3 characters.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ "Ground control to Major Tom." | truncate: 25, ", and so on" }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ "Ground control to Major Tom." | truncate: 25, ", and so on" }}
|
||||
```
|
||||
|
||||
### No ellipsis
|
||||
|
||||
You can truncate to the exact number of characters specified by the first parameter and show no trailing characters by passing a blank string as the second parameter:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ "Ground control to Major Tom." | truncate: 20, "" }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ "Ground control to Major Tom." | truncate: 20, "" }}
|
||||
```
|
||||
@@ -1,50 +0,0 @@
|
||||
---
|
||||
title: truncatewords
|
||||
description: Liquid filter that truncates a string to the given number of words.
|
||||
---
|
||||
|
||||
Shortens a string down to the number of words passed as the argument. If the specified number of words is less than the number of words in the string, an ellipsis (...) is appended to the string.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Ground control to Major Tom." | truncatewords: 3 }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Ground control to Major Tom." | truncatewords: 3 }}
|
||||
```
|
||||
|
||||
### Custom ellipsis
|
||||
|
||||
`truncatewords` takes an optional second parameter that specifies the sequence of characters to be appended to the truncated string. By default this is an ellipsis (...), but you can specify a different sequence.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ "Ground control to Major Tom." | truncatewords: 3, "--" }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ "Ground control to Major Tom." | truncatewords: 3, "--" }}
|
||||
```
|
||||
|
||||
### No ellipsis
|
||||
|
||||
You can avoid showing trailing characters by passing a blank string as the second parameter:
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
{% raw %}
|
||||
``` liquid
|
||||
{{ "Ground control to Major Tom." | truncatewords: 3, "" }}
|
||||
```
|
||||
{% endraw %}
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
``` text
|
||||
{{ "Ground control to Major Tom." | truncatewords: 3, "" }}
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
---
|
||||
title: uniq
|
||||
description: Liquid filter that removes duplicate items from an array.
|
||||
---
|
||||
|
||||
Removes any duplicate elements in an array.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{% assign my_array = "ants, bugs, bees, bugs, ants" | split: ", " %}
|
||||
|
||||
{{ my_array | uniq | join: ", " }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{% assign my_array = "ants, bugs, bees, bugs, ants" | split: ", " %}
|
||||
|
||||
{{ my_array | uniq | join: ", " }}
|
||||
```
|
||||
@@ -1,30 +0,0 @@
|
||||
---
|
||||
title: upcase
|
||||
description: Liquid filter that capitalizes every character in a string.
|
||||
---
|
||||
|
||||
Makes each character in a string uppercase. It has no effect on strings which are already all uppercase.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Parker Moore" | upcase }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Parker Moore" | upcase }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "APPLE" | upcase }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "APPLE" | upcase }}
|
||||
```
|
||||
@@ -1,18 +0,0 @@
|
||||
---
|
||||
title: url_decode
|
||||
description: Liquid filter that decodes percent-encoded characters in a string.
|
||||
---
|
||||
|
||||
Decodes a string that has been encoded as a URL or by [`url_encode`]({{ '/filters/url_encode' | prepend: site.baseurl }}).
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "%27Stop%21%27+said+Fred" | url_decode }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
'Stop!' said Fred
|
||||
```
|
||||
@@ -1,30 +0,0 @@
|
||||
---
|
||||
title: url_encode
|
||||
description: Liquid filter that encodes URL-unsafe characters in a string.
|
||||
---
|
||||
|
||||
Converts any URL-unsafe characters in a string into percent-encoded characters.
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "john@liquid.com" | url_encode }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "john@liquid.com" | url_encode }}
|
||||
```
|
||||
|
||||
<p class="code-label">Input</p>
|
||||
```liquid
|
||||
{% raw %}
|
||||
{{ "Tetsuro Takara" | url_encode }}
|
||||
{% endraw %}
|
||||
```
|
||||
|
||||
<p class="code-label">Output</p>
|
||||
```text
|
||||
{{ "Tetsuro Takara" | url_encode }}
|
||||
```
|
||||
|
Before Width: | Height: | Size: 20 KiB |
|
Before Width: | Height: | Size: 9.0 KiB |
|
Before Width: | Height: | Size: 1.6 KiB |
|
Before Width: | Height: | Size: 3.9 KiB |
|
Before Width: | Height: | Size: 30 KiB |
|
Before Width: | Height: | Size: 27 KiB |
|
Before Width: | Height: | Size: 18 KiB |
@@ -1,14 +0,0 @@
|
||||
---
|
||||
layout: default
|
||||
description: Documentation for the Liquid template language, created by Shopify.
|
||||
---
|
||||
|
||||
{% include home-banner.html %}
|
||||
|
||||
Liquid is an open-source template language created by [Shopify](https://www.shopify.com) and written in Ruby. It is the backbone of Shopify themes and is used to load dynamic content on storefronts.
|
||||
|
||||
Liquid has been in production use at Shopify since 2006 and is now used by many other hosted web applications.
|
||||
|
||||
## Used by
|
||||
|
||||
{% include home-users-grid.html %}
|
||||
@@ -1,12 +0,0 @@
|
||||
$menuButton = $(".menu-button");
|
||||
$sidebar = $(".sidebar");
|
||||
$contentOverlay = $(".content__overlay");
|
||||
|
||||
|
||||
$(document).ready(function() {
|
||||
|
||||
$menuButton.add($contentOverlay).on("click", function() {
|
||||
$sidebar.toggleClass("sidebar--is-visible");
|
||||
$contentOverlay.toggleClass("content__overlay--is-active");
|
||||
});
|
||||
})
|
||||
@@ -0,0 +1,69 @@
|
||||
# Copyright (c) 2005 Tobias Luetke
|
||||
#
|
||||
# Permission is hereby granted, free of charge, to any person obtaining
|
||||
# a copy of this software and associated documentation files (the
|
||||
# "Software"), to deal in the Software without restriction, including
|
||||
# without limitation the rights to use, copy, modify, merge, publish,
|
||||
# distribute, sublicense, and/or sell copies of the Software, and to
|
||||
# permit persons to whom the Software is furnished to do so, subject to
|
||||
# the following conditions:
|
||||
#
|
||||
# The above copyright notice and this permission notice shall be
|
||||
# included in all copies or substantial portions of the Software.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
||||
# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||
# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||
# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
|
||||
module Liquid
|
||||
FilterSeparator = /\|/
|
||||
ArgumentSeparator = ','.freeze
|
||||
FilterArgumentSeparator = ':'.freeze
|
||||
VariableAttributeSeparator = '.'.freeze
|
||||
TagStart = /\{\%/
|
||||
TagEnd = /\%\}/
|
||||
VariableSignature = /\(?[\w\-\.\[\]]\)?/
|
||||
VariableSegment = /[\w\-]/
|
||||
VariableStart = /\{\{/
|
||||
VariableEnd = /\}\}/
|
||||
VariableIncompleteEnd = /\}\}?/
|
||||
QuotedString = /"[^"]*"|'[^']*'/
|
||||
QuotedFragment = /#{QuotedString}|(?:[^\s,\|'"]|#{QuotedString})+/o
|
||||
TagAttributes = /(\w+)\s*\:\s*(#{QuotedFragment})/o
|
||||
AnyStartingTag = /\{\{|\{\%/
|
||||
PartialTemplateParser = /#{TagStart}.*?#{TagEnd}|#{VariableStart}.*?#{VariableIncompleteEnd}/om
|
||||
TemplateParser = /(#{PartialTemplateParser}|#{AnyStartingTag})/om
|
||||
VariableParser = /\[[^\]]+\]|#{VariableSegment}+\??/o
|
||||
|
||||
singleton_class.send(:attr_accessor, :cache_classes)
|
||||
self.cache_classes = true
|
||||
end
|
||||
|
||||
require "liquid/version"
|
||||
require 'liquid/lexer'
|
||||
require 'liquid/parser'
|
||||
require 'liquid/i18n'
|
||||
require 'liquid/drop'
|
||||
require 'liquid/extensions'
|
||||
require 'liquid/errors'
|
||||
require 'liquid/interrupts'
|
||||
require 'liquid/strainer'
|
||||
require 'liquid/context'
|
||||
require 'liquid/tag'
|
||||
require 'liquid/block'
|
||||
require 'liquid/document'
|
||||
require 'liquid/variable'
|
||||
require 'liquid/file_system'
|
||||
require 'liquid/template'
|
||||
require 'liquid/standardfilters'
|
||||
require 'liquid/condition'
|
||||
require 'liquid/module_ex'
|
||||
require 'liquid/utils'
|
||||
|
||||
# Load all the tags of the standard library
|
||||
#
|
||||
Dir[File.dirname(__FILE__) + '/liquid/tags/*.rb'].each { |f| require f }
|
||||
@@ -0,0 +1,156 @@
|
||||
module Liquid
|
||||
class Block < Tag
|
||||
FullToken = /\A#{TagStart}\s*(\w+)\s*(.*)?#{TagEnd}\z/om
|
||||
ContentOfVariable = /\A#{VariableStart}(.*)#{VariableEnd}\z/om
|
||||
TAGSTART = "{%".freeze
|
||||
VARSTART = "{{".freeze
|
||||
|
||||
def blank?
|
||||
@blank
|
||||
end
|
||||
|
||||
def parse(tokens)
|
||||
@blank = true
|
||||
@nodelist ||= []
|
||||
@nodelist.clear
|
||||
|
||||
# All child tags of the current block.
|
||||
@children = []
|
||||
|
||||
while token = tokens.shift
|
||||
unless token.empty?
|
||||
case
|
||||
when token.start_with?(TAGSTART)
|
||||
if token =~ FullToken
|
||||
|
||||
# if we found the proper block delimiter just end parsing here and let the outer block
|
||||
# proceed
|
||||
if block_delimiter == $1
|
||||
end_tag
|
||||
return
|
||||
end
|
||||
|
||||
# fetch the tag from registered blocks
|
||||
if tag = Template.tags[$1]
|
||||
new_tag = tag.parse($1, $2, tokens, @options)
|
||||
@blank &&= new_tag.blank?
|
||||
@nodelist << new_tag
|
||||
@children << new_tag
|
||||
else
|
||||
# this tag is not registered with the system
|
||||
# pass it to the current block for special handling or error reporting
|
||||
unknown_tag($1, $2, tokens)
|
||||
end
|
||||
else
|
||||
raise SyntaxError.new(options[:locale].t("errors.syntax.tag_termination".freeze, :token => token, :tag_end => TagEnd.inspect))
|
||||
end
|
||||
when token.start_with?(VARSTART)
|
||||
new_var = create_variable(token)
|
||||
@nodelist << new_var
|
||||
@children << new_var
|
||||
@blank = false
|
||||
else
|
||||
@nodelist << token
|
||||
@blank &&= (token =~ /\A\s*\z/)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
# Make sure that it's ok to end parsing in the current block.
|
||||
# Effectively this method will throw an exception unless the current block is
|
||||
# of type Document
|
||||
assert_missing_delimitation!
|
||||
end
|
||||
|
||||
# warnings of this block and all sub-tags
|
||||
def warnings
|
||||
all_warnings = []
|
||||
all_warnings.concat(@warnings) if @warnings
|
||||
|
||||
(@children || []).each do |node|
|
||||
all_warnings.concat(node.warnings || [])
|
||||
end
|
||||
|
||||
all_warnings
|
||||
end
|
||||
|
||||
def end_tag
|
||||
end
|
||||
|
||||
def unknown_tag(tag, params, tokens)
|
||||
case tag
|
||||
when 'else'.freeze
|
||||
raise SyntaxError.new(options[:locale].t("errors.syntax.unexpected_else".freeze,
|
||||
:block_name => block_name))
|
||||
when 'end'.freeze
|
||||
raise SyntaxError.new(options[:locale].t("errors.syntax.invalid_delimiter".freeze,
|
||||
:block_name => block_name,
|
||||
:block_delimiter => block_delimiter))
|
||||
else
|
||||
raise SyntaxError.new(options[:locale].t("errors.syntax.unknown_tag".freeze, :tag => tag))
|
||||
end
|
||||
end
|
||||
|
||||
def block_name
|
||||
@tag_name
|
||||
end
|
||||
|
||||
def block_delimiter
|
||||
@block_delimiter ||= "end#{block_name}"
|
||||
end
|
||||
|
||||
def create_variable(token)
|
||||
token.scan(ContentOfVariable) do |content|
|
||||
return Variable.new(content.first, @options)
|
||||
end
|
||||
raise SyntaxError.new(options[:locale].t("errors.syntax.variable_termination".freeze, :token => token, :tag_end => VariableEnd.inspect))
|
||||
end
|
||||
|
||||
def render(context)
|
||||
render_all(@nodelist, context)
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
def assert_missing_delimitation!
|
||||
raise SyntaxError.new(options[:locale].t("errors.syntax.tag_never_closed".freeze, :block_name => block_name))
|
||||
end
|
||||
|
||||
def render_all(list, context)
|
||||
output = []
|
||||
context.resource_limits[:render_length_current] = 0
|
||||
context.resource_limits[:render_score_current] += list.length
|
||||
|
||||
list.each do |token|
|
||||
# Break out if we have any unhanded interrupts.
|
||||
break if context.has_interrupt?
|
||||
|
||||
begin
|
||||
# If we get an Interrupt that means the block must stop processing. An
|
||||
# Interrupt is any command that stops block execution such as {% break %}
|
||||
# or {% continue %}
|
||||
if token.is_a? Continue or token.is_a? Break
|
||||
context.push_interrupt(token.interrupt)
|
||||
break
|
||||
end
|
||||
|
||||
token_output = (token.respond_to?(:render) ? token.render(context) : token)
|
||||
context.increment_used_resources(:render_length_current, token_output)
|
||||
if context.resource_limits_reached?
|
||||
context.resource_limits[:reached] = true
|
||||
raise MemoryError.new("Memory limits exceeded".freeze)
|
||||
end
|
||||
unless token.is_a?(Block) && token.blank?
|
||||
output << token_output
|
||||
end
|
||||
rescue MemoryError => e
|
||||
raise e
|
||||
rescue ::StandardError => e
|
||||
output << (context.handle_error(e))
|
||||
end
|
||||
end
|
||||
|
||||
output.join
|
||||
end
|
||||
end
|
||||
end
|
||||