trmnl_preview 0.31.0 → 0.31.2

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 549b443e84d37972c94d74e4db9559deb402ce49f526e52ad1625ba704db50d5
4
- data.tar.gz: c0588a1cd534aa350c525efd02410635cd095ccd17974eb6180812e4ae5ca25f
3
+ metadata.gz: 19c7a981cfdf1ef495dcc4aaa724fd21e111a307899062e9231ebc3b9dc5e702
4
+ data.tar.gz: f2e39cc80825f4f828cc999ca945d21076be53f0323d48ad56dda5e4249cbdb7
5
5
  SHA512:
6
- metadata.gz: d66bb390b64ab86df09562ab6a789d58973b1510cc0adbfe72dd6a853e7382ea869ee45d8a96b11004148fc2f392047f4b0bc649b0b772bfc258647938f157cf
7
- data.tar.gz: d805eb40ec0b503e85b724f0ee6ce4a267ac4aa396882144e123221318f585920be6cd09b858720428702152846954cda8ccca5413bbf2da95b438c7b1f9c802
6
+ metadata.gz: 72bce8abf4d3d92eaa82685ea0a7ae1e0ee1330526b152e589737bc5c058ef354c16f1601944a63f4e10fbb60db17b19244cb9d6dfdc19f7f1c94b07720c6ddf
7
+ data.tar.gz: 4cfdbc78ca03b8fffefe5552b82c956f3ff0bfdd96ab041c6415795b3c575634af8c1616b892233cf365467f7f186004d8c21cea74f23665d0b0c1e69e87946e
data/CHANGELOG.md CHANGED
@@ -1,6 +1,18 @@
1
1
 
2
2
  # Changelog
3
3
 
4
+ ## 0.31.2
5
+
6
+ - A transform whose `serverless_language` is not `node`, `python`, `ruby` or `php`, such as `javascript`, runs as node, as on TRMNL. Before, trmnlp looked for an interpreter by that name and failed with "No such file or directory @ rb_check_realpath_internal".
7
+
8
+ ## 0.31.1
9
+
10
+ - A view with no `.liquid` file draws the shared markup alone, as TRMNL does when a recipe keeps all of its markup in shared. Before, trmnlp drew "Missing template" there, so `trmnlp test` showed a blank screen for a recipe that draws on TRMNL. A view with no file and no shared markup still says "Missing template".
11
+
12
+ - `trmnlp test` mocks the HTTPS requests of a Python transform on Python 3.13 and newer, which the Docker image ships. Before, Python 3.13 refused the test proxy's certificate ("Missing Authority Key Identifier"), so every request failed and the screens showed the transform's error path.
13
+
14
+ - A Python transform can `import requests`, as on TRMNL, where it is installed. When the Python on your PATH does not have it, trmnlp makes a virtual environment with it in `~/.cache/trmnl/python` the first time and runs Python transforms there. Before, such a transform failed with `No module named 'requests'` and `trmnlp test` drew its error screen. The Docker image now has it installed.
15
+
4
16
  ## 0.31.0
5
17
 
6
18
  - `trmnlp test`'s publishable recipe draws the full view with each boolean field on and off, as `"true"` and `"false"`, the strings TRMNL saves. Before, only select fields were drawn with each option, so a recipe that breaks or goes blank with a switch off passed.
@@ -1,6 +1,6 @@
1
1
  # Mirrored from the TRMNL design-system source.
2
2
  # Refresh with `rake framework:sync` — do not edit manually.
3
- latest: 3.4.2
3
+ latest: 3.4.3
4
4
  versions:
5
5
  - number: 0.0.1
6
6
  released_at: '2024-06-22'
@@ -98,3 +98,5 @@ versions:
98
98
  released_at: '2026-10-14'
99
99
  - number: 3.4.2
100
100
  released_at: '2026-10-14'
101
+ - number: 3.4.3
102
+ released_at: '2026-10-15'
@@ -11,6 +11,8 @@ require_relative '../select_field_choices'
11
11
  module TRMNLP
12
12
  class Config
13
13
  class Plugin
14
+ TRANSFORM_LANGUAGES = %w[node python ruby php].freeze
15
+
14
16
  def initialize(paths, project_config)
15
17
  @paths = paths
16
18
  @project_config = project_config
@@ -83,9 +85,12 @@ module TRMNLP
83
85
  # stores it on the plugin_setting record. The scaffold emits
84
86
  # `serverless_language: ''`, so empty strings collapse to nil here
85
87
  # to let the `||` in the pipeline fall through to the inferred value.
88
+ # TRMNL runs any other value (like `javascript`) as node.
86
89
  def serverless_language
87
90
  value = @config['serverless_language']
88
- value unless value.to_s.empty?
91
+ return if value.to_s.empty?
92
+
93
+ TRANSFORM_LANGUAGES.include?(value) ? value : 'node'
89
94
  end
90
95
 
91
96
  # The TRMNL design-system version this plugin renders against.
@@ -63,7 +63,9 @@ module TRMNLP
63
63
  # of 500-ing. Anything that's not a RenderError bubbles up as a bug.
64
64
  def render_liquid_template(view, device: {})
65
65
  template_path = paths.template(view)
66
- raise RenderError, "Missing template: #{template_path}" unless template_path.exist?
66
+ unless template_path.exist? || paths.shared_template.exist?
67
+ raise RenderError, "Missing template: #{template_path}"
68
+ end
67
69
 
68
70
  parse_and_render(template_path, device:)
69
71
  end
@@ -89,8 +91,7 @@ module TRMNLP
89
91
  end
90
92
 
91
93
  def full_markup(template_path)
92
- shared = paths.shared_template
93
- shared.exist? ? shared.read + template_path.read : template_path.read
94
+ [paths.shared_template, template_path].select(&:exist?).map(&:read).join
94
95
  end
95
96
 
96
97
  def liquid_environment
@@ -57,6 +57,8 @@ module TRMNLP
57
57
 
58
58
  def add_extensions(certificate, authority, host)
59
59
  factory = OpenSSL::X509::ExtensionFactory.new(authority ? certificate : @certificate, certificate)
60
+ certificate.add_extension(factory.create_extension('subjectKeyIdentifier', 'hash'))
61
+ certificate.add_extension(factory.create_extension('authorityKeyIdentifier', 'keyid:always'))
60
62
  if authority
61
63
  certificate.add_extension(factory.create_extension('basicConstraints', 'CA:TRUE', true))
62
64
  certificate.add_extension(factory.create_extension('keyUsage', 'keyCertSign,cRLSign', true))
@@ -0,0 +1,37 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'xdg'
4
+
5
+ module TRMNLP
6
+ module TransformBackend
7
+ # TRMNL's serverless Python has requests installed. A Python without it runs transforms from a
8
+ # virtual environment in the cache that has it, made once; if that fails, the Python runs as it is.
9
+ module Python
10
+ module_function
11
+
12
+ def interpreter(python, venv_dir: XDG.new.cache_home.join('trmnl', 'python'))
13
+ resolved[python] ||= imports_requests?(python) ? python : venv_python(python, venv_dir)
14
+ end
15
+
16
+ def venv_python(python, venv_dir)
17
+ venv_dir.dirname.mkpath
18
+ venv = venv_dir.join(Gem.win_platform? ? 'Scripts/python.exe' : 'bin/python').to_s
19
+ created = File.open("#{venv_dir}.lock", File::RDWR | File::CREAT) do |lock|
20
+ lock.flock(File::LOCK_EX)
21
+ imports_requests?(venv) || created_venv?(python, venv_dir, venv)
22
+ end
23
+ created ? venv : python
24
+ end
25
+
26
+ def created_venv?(python, venv_dir, venv)
27
+ succeeds?(python, '-m', 'venv', '--clear', venv_dir.to_s) && succeeds?(venv, '-m', 'pip', 'install', 'requests')
28
+ end
29
+
30
+ def imports_requests?(python) = succeeds?(python, '-c', 'import requests')
31
+
32
+ def succeeds?(*command) = system(*command, out: File::NULL, err: File::NULL) == true
33
+
34
+ def resolved = @resolved ||= {}
35
+ end
36
+ end
37
+ end
@@ -4,6 +4,7 @@ require 'open3'
4
4
  require 'tmpdir'
5
5
 
6
6
  require_relative '../transform_client'
7
+ require_relative 'python'
7
8
  require_relative 'which'
8
9
  require_relative 'wrapper'
9
10
 
@@ -52,7 +53,9 @@ module TRMNLP
52
53
  output_path = File.join(dir, 'output.json')
53
54
  src_path = File.join(dir, "transform.#{spec[:ext]}")
54
55
  File.write(src_path, Wrapper.for(language, code, sink_for(language, output_path)))
55
- run_process(Which.resolve(spec[:cmds]), src_path, stdin, timeout_seconds, output_path)
56
+ command = Which.resolve(spec[:cmds])
57
+ command = Python.interpreter(command) if language == 'python'
58
+ run_process(command, src_path, stdin, timeout_seconds, output_path)
56
59
  end
57
60
  rescue Errno::ENOENT, Errno::EACCES => e
58
61
  failure("interpreter not available: #{e.message}")
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module TRMNLP
4
- VERSION = '0.31.0'
4
+ VERSION = '0.31.2'
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: trmnl_preview
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.31.0
4
+ version: 0.31.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Rockwell Schrock
@@ -500,6 +500,7 @@ files:
500
500
  - lib/trmnlp/testing/snapshot.rb
501
501
  - lib/trmnlp/testing/text_ink.rb
502
502
  - lib/trmnlp/transform_backend/http.rb
503
+ - lib/trmnlp/transform_backend/python.rb
503
504
  - lib/trmnlp/transform_backend/subprocess.rb
504
505
  - lib/trmnlp/transform_backend/which.rb
505
506
  - lib/trmnlp/transform_backend/wrapper.rb