Module: JekyllMermaidPrebuild::MmdcWrapper
- Defined in:
- lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb
Overview
Wrapper for mmdc (mermaid CLI) commands
Constant Summary collapse
- MMDC_COMMAND =
Check if mmdc is available in PATH
"mmdc"- ALLOWED_RENDER_THEMES =
Render mermaid source to SVG file
%i[default dark].freeze
Class Method Summary collapse
- .available? ⇒ Boolean
-
.check_status ⇒ Symbol
Check mmdc status (availability and Puppeteer).
-
.command_exists?(cmd) ⇒ Boolean
Check if a command exists in PATH (cross-platform).
-
.mermaid_fence_pattern ⇒ Regexp
Build regex pattern for mermaid fenced code blocks Supports both backtick (```) and tilde (~~~) fences with 3+ characters.
-
.render(mermaid_source, output_path, theme: :default) ⇒ Boolean
True if successful.
-
.reset_cache! ⇒ Object
Reset cached status (useful for testing).
-
.test_render ⇒ Symbol
Test mmdc with a minimal diagram to verify Puppeteer works.
-
.version ⇒ String?
Get mmdc version.
Class Method Details
.available? ⇒ Boolean
14 15 16 17 18 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 14 def self.available? return @available if instance_variable_defined?(:@available) @available = command_exists?(MMDC_COMMAND) end |
.check_status ⇒ Symbol
Check mmdc status (availability and Puppeteer)
51 52 53 54 55 56 57 58 59 60 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 51 def self.check_status return @check_status if instance_variable_defined?(:@check_status) unless available? @check_status = :not_found return @check_status end @check_status = test_render end |
.command_exists?(cmd) ⇒ Boolean
Check if a command exists in PATH (cross-platform)
24 25 26 27 28 29 30 31 32 33 34 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 24 def self.command_exists?(cmd) return false if cmd.nil? || cmd.empty? cmd_name = Gem.win_platform? ? "#{cmd}.exe" : cmd path_dirs = ENV.fetch("PATH", "").split(File::PATH_SEPARATOR) path_dirs.any? do |dir| executable = File.join(dir, cmd_name) File.file?(executable) && File.executable?(executable) end end |
.mermaid_fence_pattern ⇒ Regexp
Build regex pattern for mermaid fenced code blocks Supports both backtick (```) and tilde (~~~) fences with 3+ characters
129 130 131 132 133 134 135 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 129 def self.mermaid_fence_pattern / ^(`{3,}|~{3,})mermaid\s*\n # Opening fence: 3+ backticks or tildes, then 'mermaid' (.*?) # Content (captured, non-greedy) ^\1\s*$ # Closing fence: must match opening fence type and length /mx end |
.render(mermaid_source, output_path, theme: :default) ⇒ Boolean
Returns true if successful.
106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 106 def self.render(mermaid_source, output_path, theme: :default) raise ArgumentError, "unsupported mmdc theme #{theme.inspect}" unless ALLOWED_RENDER_THEMES.include?(theme) input_file = Tempfile.new(["mermaid", ".mmd"]) begin input_file.write(mermaid_source) input_file.close cmd = [MMDC_COMMAND, "-i", input_file.path, "-o", output_path, "-e", "svg"] cmd += ["-t", "dark"] if theme == :dark _stdout, _stderr, status = Open3.capture3(*cmd) status.success? ensure input_file.unlink end end |
.reset_cache! ⇒ Object
Reset cached status (useful for testing)
63 64 65 66 67 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 63 def self.reset_cache! remove_instance_variable(:@available) if instance_variable_defined?(:@available) remove_instance_variable(:@version) if instance_variable_defined?(:@version) remove_instance_variable(:@check_status) if instance_variable_defined?(:@check_status) end |
.test_render ⇒ Symbol
Test mmdc with a minimal diagram to verify Puppeteer works
72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 72 def self.test_render input = Tempfile.new(["", ".mmd"]) output = Tempfile.new(["", ".svg"]) begin input.write("graph TD\nA-->B") input.close output.close # Close before mmdc writes (Windows file locking) _stdout, stderr, status = Open3.capture3( MMDC_COMMAND, "-i", input.path, "-o", output.path, "-e", "svg" ) if status.success? :ok elsif stderr.include?("libgbm") || stderr.include?("browser process") :puppeteer_error else :unknown_error end ensure input.unlink output.unlink end end |
.version ⇒ String?
Get mmdc version
39 40 41 42 43 44 45 46 |
# File 'lib/jekyll-mermaid-prebuild/mmdc_wrapper.rb', line 39 def self.version return @version if instance_variable_defined?(:@version) output, status = Open3.capture2e(MMDC_COMMAND, "--version") @version = output.strip if status.success? rescue StandardError @version = nil end |