@vituum/vite-plugin-latte 0.1.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (201) hide show
  1. package/README.md +39 -0
  2. package/handler.js +9 -0
  3. package/index.js +138 -0
  4. package/index.php +173 -0
  5. package/latte/AssetFilter.php +11 -0
  6. package/latte/FetchFunction.php +28 -0
  7. package/latte/IconFilter.php +14 -0
  8. package/latte/JsonTag.php +64 -0
  9. package/latte/PlaceholderFunction.php +11 -0
  10. package/latte/RandomColorFunction.php +14 -0
  11. package/latte/TelFilter.php +22 -0
  12. package/package.json +35 -0
  13. package/vendor/autoload.php +7 -0
  14. package/vendor/bin/latte-lint +107 -0
  15. package/vendor/composer/ClassLoader.php +572 -0
  16. package/vendor/composer/InstalledVersions.php +350 -0
  17. package/vendor/composer/LICENSE +21 -0
  18. package/vendor/composer/autoload_classmap.php +183 -0
  19. package/vendor/composer/autoload_namespaces.php +9 -0
  20. package/vendor/composer/autoload_psr4.php +9 -0
  21. package/vendor/composer/autoload_real.php +57 -0
  22. package/vendor/composer/autoload_static.php +193 -0
  23. package/vendor/composer/installed.json +93 -0
  24. package/vendor/composer/installed.php +32 -0
  25. package/vendor/composer/platform_check.php +26 -0
  26. package/vendor/latte/latte/bin/latte-lint +29 -0
  27. package/vendor/latte/latte/composer.json +53 -0
  28. package/vendor/latte/latte/license.md +60 -0
  29. package/vendor/latte/latte/ncs.php +14 -0
  30. package/vendor/latte/latte/ncs.xml +9 -0
  31. package/vendor/latte/latte/readme.md +21 -0
  32. package/vendor/latte/latte/src/Bridges/Tracy/BlueScreenPanel.php +114 -0
  33. package/vendor/latte/latte/src/Bridges/Tracy/LattePanel.php +99 -0
  34. package/vendor/latte/latte/src/Bridges/Tracy/templates/LattePanel.panel.phtml +98 -0
  35. package/vendor/latte/latte/src/Bridges/Tracy/templates/LattePanel.tab.phtml +15 -0
  36. package/vendor/latte/latte/src/Latte/Compiler/Block.php +44 -0
  37. package/vendor/latte/latte/src/Latte/Compiler/Escaper.php +244 -0
  38. package/vendor/latte/latte/src/Latte/Compiler/ExpressionBuilder.php +128 -0
  39. package/vendor/latte/latte/src/Latte/Compiler/Node.php +28 -0
  40. package/vendor/latte/latte/src/Latte/Compiler/NodeHelpers.php +132 -0
  41. package/vendor/latte/latte/src/Latte/Compiler/NodeTraverser.php +77 -0
  42. package/vendor/latte/latte/src/Latte/Compiler/Nodes/AreaNode.php +17 -0
  43. package/vendor/latte/latte/src/Latte/Compiler/Nodes/AuxiliaryNode.php +27 -0
  44. package/vendor/latte/latte/src/Latte/Compiler/Nodes/FragmentNode.php +59 -0
  45. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Html/AttributeNode.php +48 -0
  46. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Html/BogusTagNode.php +46 -0
  47. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Html/CommentNode.php +39 -0
  48. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Html/ElementNode.php +129 -0
  49. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Html/QuotedValue.php +53 -0
  50. package/vendor/latte/latte/src/Latte/Compiler/Nodes/NopNode.php +21 -0
  51. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/ArgumentNode.php +45 -0
  52. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/ComplexTypeNode.php +17 -0
  53. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ArrayAccessNode.php +41 -0
  54. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ArrayItemNode.php +52 -0
  55. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ArrayNode.php +94 -0
  56. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/AssignNode.php +39 -0
  57. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/AssignOpNode.php +45 -0
  58. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/BinaryOpNode.php +65 -0
  59. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/CastNode.php +43 -0
  60. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ClassConstantFetchNode.php +42 -0
  61. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/CloneNode.php +36 -0
  62. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ClosureNode.php +73 -0
  63. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ClosureUseNode.php +37 -0
  64. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ConstantFetchNode.php +37 -0
  65. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/EmptyNode.php +36 -0
  66. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/ErrorSuppressNode.php +36 -0
  67. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/FilterCallNode.php +39 -0
  68. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/FunctionCallNode.php +45 -0
  69. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/FunctionCallableNode.php +39 -0
  70. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/InRangeNode.php +42 -0
  71. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/InstanceofNode.php +40 -0
  72. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/IssetNode.php +40 -0
  73. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/MatchNode.php +49 -0
  74. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/MethodCallNode.php +50 -0
  75. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/MethodCallableNode.php +42 -0
  76. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/NewNode.php +45 -0
  77. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/NotNode.php +36 -0
  78. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/PostOpNode.php +43 -0
  79. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/PreOpNode.php +43 -0
  80. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/PropertyFetchNode.php +42 -0
  81. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/StaticCallNode.php +55 -0
  82. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/StaticCallableNode.php +47 -0
  83. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/StaticPropertyFetchNode.php +42 -0
  84. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/TernaryNode.php +50 -0
  85. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/UnaryOpNode.php +45 -0
  86. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Expression/VariableNode.php +40 -0
  87. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/ExpressionNode.php +17 -0
  88. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/FilterNode.php +67 -0
  89. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/IdentifierNode.php +36 -0
  90. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/IntersectionTypeNode.php +39 -0
  91. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/MatchArmNode.php +45 -0
  92. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/ModifierNode.php +107 -0
  93. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/NameNode.php +89 -0
  94. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/NullableTypeNode.php +35 -0
  95. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/ParameterNode.php +54 -0
  96. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Scalar/BooleanNode.php +30 -0
  97. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Scalar/EncapsedStringNode.php +80 -0
  98. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Scalar/EncapsedStringPartNode.php +30 -0
  99. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Scalar/FloatNode.php +63 -0
  100. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Scalar/IntegerNode.php +70 -0
  101. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Scalar/NullNode.php +29 -0
  102. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/Scalar/StringNode.php +40 -0
  103. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/ScalarNode.php +15 -0
  104. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/SuperiorTypeNode.php +29 -0
  105. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/UnionTypeNode.php +39 -0
  106. package/vendor/latte/latte/src/Latte/Compiler/Nodes/Php/VarLikeIdentifierNode.php +21 -0
  107. package/vendor/latte/latte/src/Latte/Compiler/Nodes/StatementNode.php +15 -0
  108. package/vendor/latte/latte/src/Latte/Compiler/Nodes/TemplateNode.php +34 -0
  109. package/vendor/latte/latte/src/Latte/Compiler/Nodes/TextNode.php +37 -0
  110. package/vendor/latte/latte/src/Latte/Compiler/PhpHelpers.php +227 -0
  111. package/vendor/latte/latte/src/Latte/Compiler/Position.php +43 -0
  112. package/vendor/latte/latte/src/Latte/Compiler/PrintContext.php +334 -0
  113. package/vendor/latte/latte/src/Latte/Compiler/Tag.php +117 -0
  114. package/vendor/latte/latte/src/Latte/Compiler/TagLexer.php +399 -0
  115. package/vendor/latte/latte/src/Latte/Compiler/TagParser.php +388 -0
  116. package/vendor/latte/latte/src/Latte/Compiler/TagParserData.php +580 -0
  117. package/vendor/latte/latte/src/Latte/Compiler/TemplateGenerator.php +206 -0
  118. package/vendor/latte/latte/src/Latte/Compiler/TemplateLexer.php +391 -0
  119. package/vendor/latte/latte/src/Latte/Compiler/TemplateParser.php +448 -0
  120. package/vendor/latte/latte/src/Latte/Compiler/TemplateParserHtml.php +506 -0
  121. package/vendor/latte/latte/src/Latte/Compiler/Token.php +259 -0
  122. package/vendor/latte/latte/src/Latte/Compiler/TokenStream.php +151 -0
  123. package/vendor/latte/latte/src/Latte/ContentType.php +22 -0
  124. package/vendor/latte/latte/src/Latte/Engine.php +591 -0
  125. package/vendor/latte/latte/src/Latte/Essential/Blueprint.php +160 -0
  126. package/vendor/latte/latte/src/Latte/Essential/CachingIterator.php +232 -0
  127. package/vendor/latte/latte/src/Latte/Essential/CoreExtension.php +232 -0
  128. package/vendor/latte/latte/src/Latte/Essential/Filters.php +591 -0
  129. package/vendor/latte/latte/src/Latte/Essential/Nodes/BlockNode.php +161 -0
  130. package/vendor/latte/latte/src/Latte/Essential/Nodes/CaptureNode.php +98 -0
  131. package/vendor/latte/latte/src/Latte/Essential/Nodes/ContentTypeNode.php +74 -0
  132. package/vendor/latte/latte/src/Latte/Essential/Nodes/DebugbreakNode.php +53 -0
  133. package/vendor/latte/latte/src/Latte/Essential/Nodes/DefineNode.php +134 -0
  134. package/vendor/latte/latte/src/Latte/Essential/Nodes/DoNode.php +49 -0
  135. package/vendor/latte/latte/src/Latte/Essential/Nodes/DumpNode.php +58 -0
  136. package/vendor/latte/latte/src/Latte/Essential/Nodes/EmbedNode.php +125 -0
  137. package/vendor/latte/latte/src/Latte/Essential/Nodes/ExtendsNode.php +60 -0
  138. package/vendor/latte/latte/src/Latte/Essential/Nodes/FirstLastSepNode.php +81 -0
  139. package/vendor/latte/latte/src/Latte/Essential/Nodes/ForNode.php +91 -0
  140. package/vendor/latte/latte/src/Latte/Essential/Nodes/ForeachNode.php +155 -0
  141. package/vendor/latte/latte/src/Latte/Essential/Nodes/IfChangedNode.php +141 -0
  142. package/vendor/latte/latte/src/Latte/Essential/Nodes/IfContentNode.php +82 -0
  143. package/vendor/latte/latte/src/Latte/Essential/Nodes/IfNode.php +180 -0
  144. package/vendor/latte/latte/src/Latte/Essential/Nodes/ImportNode.php +49 -0
  145. package/vendor/latte/latte/src/Latte/Essential/Nodes/IncludeBlockNode.php +140 -0
  146. package/vendor/latte/latte/src/Latte/Essential/Nodes/IncludeFileNode.php +81 -0
  147. package/vendor/latte/latte/src/Latte/Essential/Nodes/IterateWhileNode.php +94 -0
  148. package/vendor/latte/latte/src/Latte/Essential/Nodes/NAttrNode.php +105 -0
  149. package/vendor/latte/latte/src/Latte/Essential/Nodes/NClassNode.php +54 -0
  150. package/vendor/latte/latte/src/Latte/Essential/Nodes/NTagNode.php +79 -0
  151. package/vendor/latte/latte/src/Latte/Essential/Nodes/ParametersNode.php +84 -0
  152. package/vendor/latte/latte/src/Latte/Essential/Nodes/PrintNode.php +70 -0
  153. package/vendor/latte/latte/src/Latte/Essential/Nodes/RawPhpNode.php +46 -0
  154. package/vendor/latte/latte/src/Latte/Essential/Nodes/RollbackNode.php +37 -0
  155. package/vendor/latte/latte/src/Latte/Essential/Nodes/SkipNode.php +71 -0
  156. package/vendor/latte/latte/src/Latte/Essential/Nodes/SpacelessNode.php +62 -0
  157. package/vendor/latte/latte/src/Latte/Essential/Nodes/SwitchNode.php +118 -0
  158. package/vendor/latte/latte/src/Latte/Essential/Nodes/TemplatePrintNode.php +39 -0
  159. package/vendor/latte/latte/src/Latte/Essential/Nodes/TemplateTypeNode.php +38 -0
  160. package/vendor/latte/latte/src/Latte/Essential/Nodes/TraceNode.php +35 -0
  161. package/vendor/latte/latte/src/Latte/Essential/Nodes/TranslateNode.php +104 -0
  162. package/vendor/latte/latte/src/Latte/Essential/Nodes/TryNode.php +75 -0
  163. package/vendor/latte/latte/src/Latte/Essential/Nodes/VarNode.php +106 -0
  164. package/vendor/latte/latte/src/Latte/Essential/Nodes/VarPrintNode.php +40 -0
  165. package/vendor/latte/latte/src/Latte/Essential/Nodes/VarTypeNode.php +36 -0
  166. package/vendor/latte/latte/src/Latte/Essential/Nodes/WhileNode.php +81 -0
  167. package/vendor/latte/latte/src/Latte/Essential/Passes.php +115 -0
  168. package/vendor/latte/latte/src/Latte/Essential/RawPhpExtension.php +28 -0
  169. package/vendor/latte/latte/src/Latte/Essential/RollbackException.php +16 -0
  170. package/vendor/latte/latte/src/Latte/Essential/Tracer.php +117 -0
  171. package/vendor/latte/latte/src/Latte/Essential/TranslatorExtension.php +101 -0
  172. package/vendor/latte/latte/src/Latte/Extension.php +97 -0
  173. package/vendor/latte/latte/src/Latte/Helpers.php +96 -0
  174. package/vendor/latte/latte/src/Latte/Loader.php +37 -0
  175. package/vendor/latte/latte/src/Latte/Loaders/FileLoader.php +95 -0
  176. package/vendor/latte/latte/src/Latte/Loaders/StringLoader.php +76 -0
  177. package/vendor/latte/latte/src/Latte/Policy.php +24 -0
  178. package/vendor/latte/latte/src/Latte/PositionAwareException.php +50 -0
  179. package/vendor/latte/latte/src/Latte/Runtime/Block.php +24 -0
  180. package/vendor/latte/latte/src/Latte/Runtime/FilterExecutor.php +151 -0
  181. package/vendor/latte/latte/src/Latte/Runtime/FilterInfo.php +39 -0
  182. package/vendor/latte/latte/src/Latte/Runtime/Filters.php +234 -0
  183. package/vendor/latte/latte/src/Latte/Runtime/Html.php +35 -0
  184. package/vendor/latte/latte/src/Latte/Runtime/HtmlStringable.php +17 -0
  185. package/vendor/latte/latte/src/Latte/Runtime/Template.php +381 -0
  186. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/FunctionCallNode.php +30 -0
  187. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/FunctionCallableNode.php +29 -0
  188. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/MethodCallNode.php +32 -0
  189. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/MethodCallableNode.php +30 -0
  190. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/PropertyFetchNode.php +32 -0
  191. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/SandboxNode.php +73 -0
  192. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/StaticCallNode.php +31 -0
  193. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/StaticCallableNode.php +30 -0
  194. package/vendor/latte/latte/src/Latte/Sandbox/Nodes/StaticPropertyFetchNode.php +32 -0
  195. package/vendor/latte/latte/src/Latte/Sandbox/RuntimeChecker.php +116 -0
  196. package/vendor/latte/latte/src/Latte/Sandbox/SandboxExtension.php +132 -0
  197. package/vendor/latte/latte/src/Latte/Sandbox/SecurityPolicy.php +185 -0
  198. package/vendor/latte/latte/src/Latte/Strict.php +101 -0
  199. package/vendor/latte/latte/src/Latte/attributes.php +24 -0
  200. package/vendor/latte/latte/src/Latte/exceptions.php +69 -0
  201. package/vendor/latte/latte/src/Tools/Linter.php +175 -0
package/README.md ADDED
@@ -0,0 +1,39 @@
1
+ <a href="https://npmjs.com/package/vite-plugin-latte"><img src="https://img.shields.io/npm/v/vite-plugin-latte.svg" alt="npm package"></a>
2
+ <a href="https://nodejs.org/en/about/releases/"><img src="https://img.shields.io/node/v/vite-plugin-latte.svg" alt="node compatility"></a>
3
+
4
+ # ⚡️☕ ViteLatte
5
+
6
+ ```js
7
+ export default {
8
+ plugins: [
9
+ latte({
10
+ bin: 'php', // php or docker or your own binary path
11
+ filters: {
12
+ icon: 'latte/IconFilter.php',
13
+ nbsp: () => {}
14
+ },
15
+ functions: {},
16
+ tags: {},
17
+ globals: {
18
+ template: 'playground/templates/Layout/Main.latte'
19
+ }
20
+ })
21
+ ]
22
+ }
23
+ ```
24
+
25
+ ```html
26
+ <!-- index.html -->
27
+ <script type="application/json">
28
+ {
29
+ "template": "path/to/template.latte",
30
+ "title": "Hello world"
31
+ }
32
+ </script>
33
+ ```
34
+
35
+ ### Requirements
36
+
37
+ - [Node.js LTS (16.x)](https://nodejs.org/en/download/)
38
+ - [NPM (8.x)](https://www.npmjs.com/package/npm) or [Yarn (2.x)](https://yarnpkg.com/)
39
+ - [PHP (8.x)](https://www.php.net/) or [Docker PHP (8.x)](https://hub.docker.com/_/php)
package/handler.js ADDED
@@ -0,0 +1,9 @@
1
+ import { resolve } from 'path'
2
+
3
+ const vite = (await import(resolve(process.cwd(), 'vite.config.js'))).default
4
+ const params = JSON.parse(process.argv[2])
5
+ const name = params[0]
6
+
7
+ params.shift()
8
+
9
+ vite.plugins.filter(({ name }) => name === 'vite-plugin-latte')[0]._params.filters[name](...params)
package/index.js ADDED
@@ -0,0 +1,138 @@
1
+ import { extname, resolve, dirname } from 'path'
2
+ import { fileURLToPath } from 'url'
3
+ import fs from 'fs'
4
+ import process from 'node:process'
5
+ import * as childProcess from 'child_process'
6
+ import FastGlob from 'fast-glob'
7
+ import lodash from 'lodash'
8
+
9
+ const defaultParams = {
10
+ bin: 'php',
11
+ filters: {},
12
+ functions: {},
13
+ tags: {},
14
+ globals: {},
15
+ data: '',
16
+ isStringFilter: undefined
17
+ }
18
+
19
+ const execSync = (cmd) => {
20
+ try {
21
+ return {
22
+ output: childProcess.execSync(cmd).toString()
23
+ }
24
+ } catch ({ output }) {
25
+ return {
26
+ error: true,
27
+ output: output[1].toString()
28
+ }
29
+ }
30
+ }
31
+
32
+ const renderTemplate = (path, params, content) => {
33
+ if (params.data) {
34
+ params.data = FastGlob.sync(params.data).map(entry => resolve(process.cwd(), entry))
35
+ }
36
+
37
+ Object.keys(params.filters).forEach(key => {
38
+ if (typeof params.filters[key] === 'function') {
39
+ params.filters[key] = params.filters[key].toString().match(/\(\s*([^)]+?)\s*\)/)[1].replace(/\s/g, '').split(',')
40
+ }
41
+ })
42
+
43
+ Object.keys(params.functions).forEach(key => {
44
+ if (typeof params.functions[key] === 'function') {
45
+ params.functions[key] = params.functions[key].toString().match(/\(\s*([^)]+?)\s*\)/)[1].replace(/\s/g, '').split(',')
46
+ }
47
+ })
48
+
49
+ if (params.isString) {
50
+ const timestamp = Math.floor(Date.now() * Math.random())
51
+
52
+ params.contentTimestamp = timestamp
53
+
54
+ if (!fs.existsSync(resolve(params.packageRoot, 'temp'))) {
55
+ fs.mkdirSync(resolve(params.packageRoot, 'temp'))
56
+ }
57
+
58
+ fs.writeFileSync(resolve(params.packageRoot, `temp/${timestamp}.html`), content)
59
+ }
60
+
61
+ return execSync(`${params.bin} ${params.packageRoot}/index.php ${params.root + path} ${JSON.stringify(JSON.stringify(params))}`)
62
+ }
63
+
64
+ const latte = (params = {}) => {
65
+ params.cwd = process.cwd()
66
+
67
+ params = lodash.merge(defaultParams, params)
68
+
69
+ params.packageRoot = dirname((fileURLToPath(import.meta.url)))
70
+
71
+ if (fs.existsSync(resolve(params.packageRoot, 'temp'))) {
72
+ fs.rmSync(resolve(params.packageRoot, 'temp'), { recursive: true, force: true })
73
+ }
74
+
75
+ if (params.bin === 'docker') {
76
+ params.bin = `docker run --rm --name index -v "${process.cwd()}":/usr/src/app -w /usr/src/app php:8-cli php`
77
+ }
78
+
79
+ return {
80
+ _params: params,
81
+ name: 'vite-plugin-latte',
82
+ config: ({ root }) => {
83
+ params.root = root
84
+ },
85
+ transformIndexHtml: {
86
+ enforce: 'pre',
87
+ async transform(content, { path, filename, server }) {
88
+ if (
89
+ !path.endsWith('.json.html') &&
90
+ !path.endsWith('.latte.html') &&
91
+ !path.endsWith('.json') &&
92
+ !path.endsWith('.latte') &&
93
+ !content.startsWith('<script type="application/json"')
94
+ ) {
95
+ return content
96
+ }
97
+
98
+ if (content.startsWith('<script type="application/json"') && !content.includes('data-format="latte"')) {
99
+ return content
100
+ }
101
+
102
+ if (typeof params.isStringFilter === 'function' && params.isStringFilter(filename)) {
103
+ params.isString = true
104
+ } else {
105
+ params.isString = false
106
+ }
107
+
108
+ const renderLatte = renderTemplate(path, params, content)
109
+
110
+ if (renderLatte.error) {
111
+ if (!server) {
112
+ console.error(renderLatte.output)
113
+ return
114
+ }
115
+
116
+ server.ws.send({
117
+ type: 'error',
118
+ err: {
119
+ message: renderLatte.output,
120
+ plugin: 'vite-plugin-latte'
121
+ }
122
+ })
123
+
124
+ return
125
+ }
126
+
127
+ return renderLatte.output
128
+ }
129
+ },
130
+ handleHotUpdate({ file, server }) {
131
+ if (extname(file) === '.latte' || extname(file) === '.html' || extname(file) === '.json') {
132
+ server.ws.send({ type: 'full-reload' })
133
+ }
134
+ }
135
+ }
136
+ }
137
+
138
+ export default latte
package/index.php ADDED
@@ -0,0 +1,173 @@
1
+ <?php
2
+
3
+ declare(strict_types=1);
4
+
5
+ ini_set('log_errors', "0");
6
+ ini_set('display_errors', "1");
7
+
8
+ require __DIR__ . '/vendor/autoload.php';
9
+
10
+ $latte = new Latte\Engine;
11
+ $file = $argv[1] ?? null;
12
+ $config = $argv[2] ?? null;
13
+
14
+ if ($config) {
15
+ try {
16
+ $config = json_decode($config, false, 512, JSON_THROW_ON_ERROR);
17
+ } catch (JsonException $e) {
18
+ throw new Error($e->getMessage());
19
+ }
20
+ }
21
+
22
+ $isDocker = str_starts_with($config->bin, 'docker');
23
+
24
+ if ($isDocker) {
25
+ define("ROOT_DIR", '/usr/src/app/');
26
+ } else {
27
+ define("ROOT_DIR", $config->cwd . '/');
28
+ }
29
+
30
+ define("PACKAGE_DIR", str_replace($config->cwd, ROOT_DIR, $config->packageRoot));
31
+
32
+ /**
33
+ * @throws JsonException
34
+ */
35
+ function NodeHandler($name, ...$params) : string {
36
+ array_unshift($params, $name);
37
+
38
+ exec('node '. PACKAGE_DIR .'/handler.js ' . json_encode(json_encode($params, JSON_THROW_ON_ERROR), JSON_THROW_ON_ERROR), $output);
39
+
40
+ return $output[0] ?? $params[1];
41
+ }
42
+
43
+ if (!file_exists(__DIR__ . '/temp') && !mkdir($concurrentDirectory = __DIR__ . '/temp') && !is_dir($concurrentDirectory)) {
44
+ throw new Error(sprintf('Directory "%s" was not created', $concurrentDirectory));
45
+ }
46
+
47
+ $latte->setTempDirectory(__DIR__ . '/temp');
48
+
49
+ $params = [(array)$config->globals];
50
+
51
+ foreach ($config->data as $dataPath) {
52
+ $dataPath = str_replace($config->cwd, ROOT_DIR, $dataPath);
53
+
54
+ if (!file_exists($dataPath)) {
55
+ throw new Error('File not found ' . $dataPath);
56
+ }
57
+
58
+ try {
59
+ $params[] = json_decode(file_get_contents($dataPath), true, 512, JSON_THROW_ON_ERROR);
60
+ } catch (JsonException $e) {
61
+ throw new Error('Error parsing params');
62
+ }
63
+ }
64
+
65
+ $file = str_replace($config->cwd, ROOT_DIR, $file);
66
+ $withoutTemplate = false;
67
+
68
+ if (!file_exists($file)) {
69
+ throw new Error('File not found ' . $file);
70
+ }
71
+
72
+ if (!str_ends_with($file, '.json.html') && !str_ends_with($file, '.json') && !str_ends_with($file, '.latte.html') && !str_ends_with($file, '.latte')) {
73
+ preg_match('/<script\b[^>]*>([\s\S]+)<\/script>/', file_get_contents($file), $fileContents);
74
+
75
+ $fileContents = $fileContents[1];
76
+
77
+ } else if (str_ends_with($file, '.latte.html')) {
78
+ if (file_exists(str_replace('.latte.html', '.latte.json', $file))) {
79
+ $fileContents = file_get_contents(str_replace('.latte.html', '.latte.json', $file));
80
+ }
81
+
82
+ $withoutTemplate = true;
83
+ } else if (str_ends_with($file, '.latte')) {
84
+ if (file_exists(str_replace('.latte', '.latte.json', $file))) {
85
+ $fileContents = file_get_contents(str_replace('.latte', '.latte.json', $file));
86
+ }
87
+
88
+ $withoutTemplate = true;
89
+ } else {
90
+ $fileContents = file_get_contents($file);
91
+ }
92
+
93
+ if (isset($fileContents)) {
94
+ try {
95
+ $params[] = json_decode($fileContents, true, 512, JSON_THROW_ON_ERROR);
96
+ } catch (JsonException $e) {
97
+ throw new Error('Error parsing params');
98
+ }
99
+ }
100
+
101
+ $params = array_replace_recursive(...$params);
102
+
103
+ try {
104
+ $params = json_encode($params, JSON_THROW_ON_ERROR);
105
+ $params = json_decode($params, false, 512, JSON_THROW_ON_ERROR);
106
+ } catch (JsonException $e) {
107
+ throw new Error('Error parsing params');
108
+ }
109
+
110
+ if ($withoutTemplate) {
111
+ $params->template = $file;
112
+ }
113
+
114
+ foreach (['tel', 'asset'] as $filter) {
115
+ require PACKAGE_DIR . '/latte/' . ucfirst($filter) . 'Filter.php';
116
+ $latte->addFilter($filter, 'App\Latte\\' . ucfirst($filter) . 'Filter::execute');
117
+ }
118
+
119
+ foreach (['fetch', 'placeholder', 'randomColor'] as $function) {
120
+ require PACKAGE_DIR . '/latte/' . ucfirst($function) . 'Function.php';
121
+ $latte->addFunction($function, 'App\Latte\\' . ucfirst($function) . 'Function::execute');
122
+ }
123
+
124
+ foreach ($config->filters as $filter => $path) {
125
+ if (is_string($path)) {
126
+ require ROOT_DIR . $path;
127
+ $latte->addFilter($filter, 'App\Latte\\' . ucfirst($filter) . 'Filter::execute');
128
+ } elseif (!$isDocker) {
129
+ $latte->addFilter($filter, function (...$params) use ($filter) : string {
130
+ return NodeHandler($filter, ...$params);
131
+ });
132
+ }
133
+ }
134
+
135
+ foreach ($config->functions as $function => $path) {
136
+ if (is_string($path)) {
137
+ require ROOT_DIR . $path;
138
+ $latte->addFunction($function, 'App\Latte\\' . ucfirst($function) . 'Function::execute');
139
+ } elseif (!$isDocker) {
140
+ $latte->addFunction($function, function (...$params) use ($function) : string {
141
+ return NodeHandler($function, ...$params);
142
+ });
143
+ }
144
+ }
145
+
146
+ $tag = 'json';
147
+ require PACKAGE_DIR . '/latte/' . ucfirst($tag) . 'Tag.php';
148
+ eval('$latte->addExtension(new App\Latte\\' . ucfirst($tag) . 'Extension);');
149
+
150
+ foreach ($config->tags as $tag => $path) {
151
+ require ROOT_DIR . $path;
152
+ eval('$latte->addExtension(new App\Latte\\' . ucfirst($tag) . 'Extension);');
153
+ }
154
+
155
+ if (!file_exists(str_replace($config->cwd, ROOT_DIR, $params->template))) {
156
+ throw new Error('File not found ' . str_replace($config->cwd, ROOT_DIR, $params->template));
157
+ }
158
+
159
+ if (isset($config->isString) && $config->isString) {
160
+ if (isset($config->contentTimestamp)) {
161
+ $content = file_get_contents(__DIR__ . '/temp/' . $config->contentTimestamp . '.html');
162
+ unlink(__DIR__ . '/temp/' . $config->contentTimestamp . '.html');
163
+ } else {
164
+ $content = '';
165
+ }
166
+
167
+ $latte->setLoader(new Latte\Loaders\StringLoader([
168
+ str_replace($config->cwd, ROOT_DIR, $params->template) => $content
169
+ ]));
170
+ }
171
+
172
+ echo $latte->renderToString(str_replace($config->cwd, ROOT_DIR, $params->template), $params);
173
+
@@ -0,0 +1,11 @@
1
+ <?php
2
+
3
+ namespace App\Latte;
4
+
5
+ class AssetFilter
6
+ {
7
+ public static function execute($source): string
8
+ {
9
+ return $source;
10
+ }
11
+ }
@@ -0,0 +1,28 @@
1
+ <?php
2
+
3
+ namespace App\Latte;
4
+
5
+ class FetchFunction {
6
+ public static function execute($file): string {
7
+ $hashPath = __DIR__ . '../temp' . md5($file);
8
+
9
+ if (!str_starts_with($file, 'http')) {
10
+ if (!file_exists(ROOT_DIR . $file)) {
11
+ trigger_error(ROOT_DIR . $file . ' cannot be fetched');
12
+ return '';
13
+ }
14
+
15
+ $content = file_get_contents(ROOT_DIR . $file);
16
+ } elseif (file_exists($hashPath)) {
17
+ $content = file_get_contents($hashPath);
18
+ } else {
19
+ $content = @file_get_contents($file);
20
+
21
+ if ($content) {
22
+ file_put_contents($hashPath, $content);
23
+ }
24
+ }
25
+
26
+ return $content;
27
+ }
28
+ }
@@ -0,0 +1,14 @@
1
+ <?php
2
+
3
+ namespace App\Latte;
4
+
5
+ class IconFilter
6
+ {
7
+
8
+ public static function execute($value, $icon = null, $style = null): \Latte\Runtime\Html
9
+ {
10
+ $i = $icon ?? 'icon';
11
+
12
+ return new \Latte\Runtime\Html("<svg class='{$i} {$value}' style='{$style}'><use href='#{$value}'/></svg>");
13
+ }
14
+ }
@@ -0,0 +1,64 @@
1
+ <?php
2
+
3
+ declare(strict_types=1);
4
+
5
+ namespace App\Latte;
6
+
7
+ use Latte\Compiler\Nodes\AreaNode;
8
+ use Latte\Compiler\Nodes\StatementNode;
9
+ use Latte\Compiler\PrintContext;
10
+ use Latte\Compiler\Tag;
11
+ use Latte\ContentType;
12
+
13
+
14
+ /**
15
+ * {spaceless}
16
+ */
17
+ class JsonTag extends StatementNode
18
+ {
19
+ public AreaNode $content;
20
+
21
+
22
+ /**
23
+ * @param Tag $tag
24
+ * @return \Generator<int, ?array, array{AreaNode, ?Tag}, static>
25
+ */
26
+ public static function create(Tag $tag): \Generator
27
+ {
28
+ $node = new static;
29
+ [$node->content] = yield;
30
+ return $node;
31
+ }
32
+
33
+
34
+ public function print(PrintContext $context): string
35
+ {
36
+ return $context->format(
37
+ <<<'XX'
38
+ ob_start('Latte\Essential\Filters::%raw', 4096) %line;
39
+ try {
40
+ %node
41
+ } finally {
42
+ ob_end_flush();
43
+ }
44
+ XX,
45
+ $context->getEscaper()->getContentType() === ContentType::Html
46
+ ? 'spacelessHtmlHandler'
47
+ : 'spacelessText',
48
+ $this->position,
49
+ $this->content,
50
+ );
51
+ }
52
+
53
+
54
+ public function &getIterator(): \Generator
55
+ {
56
+ yield $this->content;
57
+ }
58
+ }
59
+
60
+ class JsonExtension extends \Latte\Extension {
61
+ public function getTags(): array {
62
+ return ['json' => [JsonTag::class, 'create']];
63
+ }
64
+ }
@@ -0,0 +1,11 @@
1
+ <?php
2
+
3
+ namespace App\Latte;
4
+
5
+ class PlaceholderFunction {
6
+
7
+ public static function execute($width, $height): string {
8
+ $colors = ["333", "444", "666", "222", "777", "888", "111"];
9
+ return 'https://via.placeholder.com/' . $width . 'x' . $height . '/' . $colors[array_rand($colors)];
10
+ }
11
+ }
@@ -0,0 +1,14 @@
1
+ <?php
2
+
3
+ namespace App\Latte;
4
+
5
+ use Exception;
6
+
7
+ class RandomColorFunction {
8
+ /**
9
+ * @throws Exception
10
+ */
11
+ public static function execute(): string {
12
+ return sprintf('#%06X', random_int(0, 0xFFFFFF));
13
+ }
14
+ }
@@ -0,0 +1,22 @@
1
+ <?php
2
+
3
+ namespace App\Latte;
4
+
5
+ class TelFilter
6
+ {
7
+ public static function execute($source): string
8
+ {
9
+ $phone = preg_replace('/\D/', '', $source);
10
+
11
+ $addPus = true;
12
+ if (str_starts_with($phone, '00')) {
13
+ $addPus = false;
14
+ }
15
+
16
+ if (strlen($phone) === 9) {
17
+ $addPus = false;
18
+ }
19
+
20
+ return ($addPus ? '+' : '') . $phone;
21
+ }
22
+ }
package/package.json ADDED
@@ -0,0 +1,35 @@
1
+ {
2
+ "name": "@vituum/vite-plugin-latte",
3
+ "version": "0.1.8",
4
+ "type": "module",
5
+ "main": "index.js",
6
+ "scripts": {
7
+ "dev": "vite dev",
8
+ "build": "vite build && mv public/views/* public && rm -rf public/views",
9
+ "preview": "vite preview"
10
+ },
11
+ "dependencies": {
12
+ "fast-glob": "^3.2.11",
13
+ "lodash": "^4.17.21"
14
+ },
15
+ "devDependencies": {
16
+ "vite": "^3.0.4",
17
+ "eslint": "^8.21.0",
18
+ "eslint-config-standard": "^17.0.0"
19
+ },
20
+ "files": [
21
+ "index.js",
22
+ "handler.js",
23
+ "index.php",
24
+ "latte",
25
+ "vendor"
26
+ ],
27
+ "engines": {
28
+ "node": ">=16.0.0",
29
+ "npm": ">=8.0.0"
30
+ },
31
+ "repository": {
32
+ "type": "git",
33
+ "url": "git+https://github.com/lubomirblazekcz/vite-plugin-latte.git"
34
+ }
35
+ }
@@ -0,0 +1,7 @@
1
+ <?php
2
+
3
+ // autoload.php @generated by Composer
4
+
5
+ require_once __DIR__ . '/composer/autoload_real.php';
6
+
7
+ return ComposerAutoloaderInit19cfb30b66a778b432af39bbd1e78bca::getLoader();
@@ -0,0 +1,107 @@
1
+ #!/usr/bin/env php
2
+ <?php
3
+
4
+ /**
5
+ * Proxy PHP file generated by Composer
6
+ *
7
+ * This file includes the referenced bin path (../latte/latte/bin/latte-lint)
8
+ * using a stream wrapper to prevent the shebang from being output on PHP<8
9
+ *
10
+ * @generated
11
+ */
12
+
13
+ namespace Composer;
14
+
15
+ $GLOBALS['_composer_bin_dir'] = __DIR__;
16
+ $GLOBALS['_composer_autoload_path'] = __DIR__ . '/..'.'/autoload.php';
17
+
18
+ if (PHP_VERSION_ID < 80000) {
19
+ if (!class_exists('Composer\BinProxyWrapper')) {
20
+ /**
21
+ * @internal
22
+ */
23
+ final class BinProxyWrapper
24
+ {
25
+ private $handle;
26
+ private $position;
27
+ private $realpath;
28
+
29
+ public function stream_open($path, $mode, $options, &$opened_path)
30
+ {
31
+ // get rid of phpvfscomposer:// prefix for __FILE__ & __DIR__ resolution
32
+ $opened_path = substr($path, 17);
33
+ $this->realpath = realpath($opened_path) ?: $opened_path;
34
+ $opened_path = $this->realpath;
35
+ $this->handle = fopen($this->realpath, $mode);
36
+ $this->position = 0;
37
+
38
+ return (bool) $this->handle;
39
+ }
40
+
41
+ public function stream_read($count)
42
+ {
43
+ $data = fread($this->handle, $count);
44
+
45
+ if ($this->position === 0) {
46
+ $data = preg_replace('{^#!.*\r?\n}', '', $data);
47
+ }
48
+
49
+ $this->position += strlen($data);
50
+
51
+ return $data;
52
+ }
53
+
54
+ public function stream_cast($castAs)
55
+ {
56
+ return $this->handle;
57
+ }
58
+
59
+ public function stream_close()
60
+ {
61
+ fclose($this->handle);
62
+ }
63
+
64
+ public function stream_lock($operation)
65
+ {
66
+ return $operation ? flock($this->handle, $operation) : true;
67
+ }
68
+
69
+ public function stream_tell()
70
+ {
71
+ return $this->position;
72
+ }
73
+
74
+ public function stream_eof()
75
+ {
76
+ return feof($this->handle);
77
+ }
78
+
79
+ public function stream_stat()
80
+ {
81
+ return array();
82
+ }
83
+
84
+ public function stream_set_option($option, $arg1, $arg2)
85
+ {
86
+ return true;
87
+ }
88
+
89
+ public function url_stat($path, $flags)
90
+ {
91
+ $path = substr($path, 17);
92
+ if (file_exists($path)) {
93
+ return stat($path);
94
+ }
95
+
96
+ return false;
97
+ }
98
+ }
99
+ }
100
+
101
+ if (function_exists('stream_wrapper_register') && stream_wrapper_register('phpvfscomposer', 'Composer\BinProxyWrapper')) {
102
+ include("phpvfscomposer://" . __DIR__ . '/..'.'/latte/latte/bin/latte-lint');
103
+ exit(0);
104
+ }
105
+ }
106
+
107
+ include __DIR__ . '/..'.'/latte/latte/bin/latte-lint';