hashicorp/vagrant · error · Vagrant::Errors::BoxMetadataMalformed

The metadata for the box was malformed. The exact error is s

Error message

The metadata for the box was malformed. The exact error is shown below. Please contact the maintainer of the box so that this issue can be fixed.

%{error}

What it means

BoxMetadataMalformed is raised in BoxMetadata#initialize (lib/vagrant/box_metadata.rb:29) when JSON.load(io) on the catalog metadata raises JSON::ParserError. The parser's message is embedded, so the error shows exactly where the JSON is broken; it points at the metadata maintainer since the document is not valid JSON.

Source

Thrown at lib/vagrant/box_metadata.rb:29

    # The name that the box should be if it is added.
    #
    # @return [String]
    attr_accessor :name

    # The long-form human-readable description of a box.
    #
    # @return [String]
    attr_accessor :description

    # Loads the metadata associated with the box from the given
    # IO.
    #
    # @param [IO] io An IO object to read the metadata from.
    def initialize(io, **_)
      begin
        @raw = JSON.load(io)
      rescue JSON::ParserError => e
        raise Errors::BoxMetadataMalformed,
          error: e.to_s
      end

      @raw ||= {}
      @name = @raw["name"]
      @description = @raw["description"]
      @version_map = (@raw["versions"] || []).map do |v|
        begin
          [Gem::Version.new(v["version"]), Version.new(v)]
        rescue ArgumentError
          raise Errors::BoxMetadataMalformedVersion,
            version: v["version"].to_s
        end
      end
      @version_map = Hash[@version_map]
    end

    # Returns data about a single version that is included in this

View on GitHub (pinned to 35f3160f4a)

Solutions

  1. Fetch the exact URL with curl and inspect what is really returned: 'curl -sL -H "Accept: application/json" <metadata-url> | head'
  2. If you maintain the metadata, validate it (jq . metadata.json) and fix the reported JSON syntax error
  3. If a proxy/portal intercepts the request, whitelist the host or authenticate so JSON comes through
Defensive patterns

Strategy: validation

Validate before calling

require 'json'
require 'open-uri'
raw = URI.parse(metadata_url).open.read
JSON.parse(raw) # raises now, on your terms, if the catalog serves HTML/garbage

Prevention

When it happens

Trigger: BoxMetadata.new(io) is constructed from a downloaded or file-based metadata source (Box#load_metadata after download, or reading a catalog file) whose content is not parseable JSON — HTML login/error page, truncated body, trailing commas, BOM.

Common situations: Self-hosted catalog behind a proxy that returns an HTML block page; internal web server misconfigured to serve the URL as a directory listing; hand-edited metadata.json with a trailing comma; CDN serving partial content.

Understand the failure class

Related errors


AI-assisted analysis of hashicorp/vagrant@35f3160f4a (2026-08-21). Data as JSON: /api/errors/a990aad982bb4f2f. Report an issue: GitHub.