github/markup · error · GitHub::Markup::CommandError

stderr

Error message

stderr

What it means

Raised as GitHub::Markup::CommandError when an external rendering command exits with a non-zero status. CommandImplementation#execute runs the command registered for the markup (vendored scripts under lib/github/markup/commands/ such as rest2html or asciidoc, or a system binary) via Open3.capture3 and raises with the command's raw stderr as the message. So 'stderr' as a message means the message content is whatever the failed tool printed; the real cause is in that text. It indicates the command was invoked but the tool itself failed on the given input or environment.

Source

Thrown at lib/github/markup/command_implementation.rb:42

      end

    private
      def call_block(rendered, content)
        if block && block.arity == 2
          block.call(rendered, content)
        elsif block
          block.call(rendered)
        else
          rendered
        end
      end

      def execute(command, target)
        # capture3 blocks until both buffers are written to and the process terminates, but
        # it won't allow either buffer to fill up
        stdout, stderr, status = Open3.capture3(*command, stdin_data: target)

        raise CommandError.new(stderr) unless status.success?
        sanitize(stdout, target.encoding)
      end

      def sanitize(input, encoding)
        input.gsub("\r", '').force_encoding(encoding)
      end

    end
  end
end

View on GitHub (pinned to 76e2682193)

Solutions

  1. Inspect e.message - it is the failed command's stderr verbatim and names the actual failure (missing module, traceback, usage error).
  2. Reproduce manually: pipe the exact same content into the command shown by the registration (e.g. lib/github/markup/commands/rest2html) and observe its stderr.
  3. Install or repair the missing runtime dependency the stderr mentions (pip install docutils, apt install python3, gem/system deps for the tool).
  4. If the failure is input-specific, fix or sanitize the markup document rather than swallowing the error.
  5. Wrap render calls in rescue GitHub::Markup::CommandError to degrade gracefully (log stderr, show the raw content) when rendering third-party documents.

Example fix

// before
html = GitHub::Markup.render('README.rst', rst_content)
# => GitHub::Markup::CommandError: Traceback (most recent call last): ModuleNotFoundError: No module named 'docutils'

// after
begin
  html = GitHub::Markup.render('README.rst', rst_content)
rescue GitHub::Markup::CommandError => e
  Rails.logger.warn("rst render failed: #{e.message}")
  html = "<pre>#{ERB::Util.html_escape(rst_content)}</pre>"
end
Defensive patterns

Strategy: try-catch

Validate before calling

# Smoke-test the external renderer before trusting it with user content:
require 'open3'

def renderer_healthy?(command)
  out, err, status = Open3.capture3(*command, stdin_data: 'probe')
  status.success?
rescue Errno::ENOENT
  false
end

# command value as registered, e.g. File.dirname(GitHub::Markup.method(:render).source_location.first) + '/markup/commands/rest2html'
raise 'rst tooling missing' unless renderer_healthy?([HTML_PIPELINE_RST_CMD].compact)

Try / catch

begin
  html = GitHub::Markup.render(filename, content)
rescue GitHub::Markup::CommandError => e
  # e.message is the command's stderr - log it verbatim for diagnosis
  logger.error("markup command failed for #{filename}: #{e.message}")
  html = fallback_for(filename, content) # e.g. escaped <pre> of the source
end

Prevention

When it happens

Trigger: Calling GitHub::Markup.render('file.rst', content) when the bundled Python-based rest2html wrapper exits non-zero (e.g. docutils missing from the invoked interpreter, or a traceback on malformed input); rendering .adoc/.pod/.mediawiki whose external interpreter crashes; registering a custom renderer via GitHub::Markup.command whose command fails and writes to stderr; any pipeline where the tool's shebang interpreter or its runtime deps are absent.

Common situations: Server/container where python3, docutils, or asciidoctor were never installed although the gem is present; system Python upgraded so the vendored commands/* wrappers can no longer import docutils; malformed or pathological markup documents that crash the external tool; CI environments trimmed of runtime dependencies.

Related errors


AI-assisted analysis of github/markup@76e2682193 (2026-08-21). Data as JSON: /api/errors/9c04999cabf51daf. Report an issue: GitHub.