require_relative "../helpers"

require "json_pointer"

class InteragentRenderTest < Minitest::Test
  def test_render_for_valid_schema
    markdown = render

    assert_match(/An app in our PaaS ecosystem./, markdown)
  end

  def test_render_for_schema_with_property_defined_with_anyOf
    pointer("#/definitions/app").merge!({
      "properties" => {
        "version" => {
          "anyOf" => [
            { "type" => "string", "example" => "v10.9.rc1", "minLength" => 1 },
            { "type" => "number", "minimum" => 0 },
          ],
        },
      },
    })
    markdown = render
    assert_match(/version.*v10\.9\.rc1/, markdown)
  end

  def test_render_for_schema_with_property_defined_with_oneOf
    markdown = render

    assert_match(/\*\*options\/\[OPTION1\]\.type\*\*/, markdown)
    assert_match(/\*\*options\/\[OPTION2\]\.type\*\*/, markdown)
  end

  def test_render_for_toc
    schema = Prmd::Schema.new(data)
    template = File.expand_path(File.join(File.dirname(__FILE__), "..", "..", "lib", "prmd", "templates"))
    markdown = Prmd.render(schema, template: template, doc: { toc: true })

    assert_match(/^## The table of contents/, markdown)
    assert_match '<a href="#resource-app"', markdown
    assert_match '- <a href="#link-POST-app-/apps">POST /apps', markdown
    assert_match '<a name="link-POST-app-/apps"></a>', markdown
  end

  def test_render_for_example_as_an_array
    # matches -d '[{...}]' taking into account line breaks and spacing
    expression = /-d '\[[\s\n]+\{[\n\s]+"name": "EXAMPLE",[\n\s]+"value": "example"[\s\n]+\}[\n\s]+\]/
    markdown = render
    assert_match expression, markdown
  end

  def test_render_for_regex_patterns_with_pipes
    expression = /<pre>\^&lbrack;a-z\]\(\?:&lbrack;a&vert;b\]\)&ast;&lbrack;a-z]&ast;\$/
    markdown = render
    assert_match expression, markdown
  end

  private

  def data
    @data ||= {
      "$schema" => "http://interagent.github.io/interagent-hyper-schema",
      "description" => "My simple example API.",
      "id" => "http://example.com/schema",
      "title" => "Example API",
      "definitions" => {
        "app" => {
          "description" => "An app in our PaaS ecosystem.",
          "title" => "App",
          "type" => "object",
          "definitions" => {
            "identity" => {
              "anyOf" => [
                {
                  "$ref" => "#/definitions/app/definitions/name",
                },
              ],
            },
            "name" => {
              "description" => "The app's name.",
              "type" => "string",
            },
          },
          "links" => [
            {
              "description" => "Create a new app.",
              "href" => "/apps",
              "method" => "POST",
              "rel" => "create",
              "title" => "Create App",
            },
          ],
          "properties" => {},
        },
        "config-var" => {
          "description" => "A configuration variable for an app.",
          "title" => "Config-var",
          "type" => "object",
          "definitions" => {
            "name" => {
              "description" => "The config-var's name.",
              "type" => "string",
              "example" => "EXAMPLE",
            },
            "value" => {
              "description" => "The config-var's value.",
              "type" => "string",
              "example" => "example",
            },
            "option-type1" => {
              "type" => "string",
              "example" => "OPTION1",
              "enum" => "OPTION1",
            },
            "option-type2" => {
              "type" => "string",
              "example" => "OPTION2",
              "enum" => "OPTION2",
            },
            "patterned-string" => {
              "description" => "A string with a regex pattern applied to it.",
              "type" => "string",
              "example" => "second",
              "pattern" => "^[a-z](?:[a|b])*[a-z]*$",
            },
            "option1" => {
              "properties" => {
                "type" => {
                  "$ref" => "#/definitions/config-var/definitions/option-type1",
                },
              },
            },
            "option2" => {
              "properties" => {
                "type" => {
                  "$ref" => "#/definitions/config-var/definitions/option-type2",
                },
              },
            },
            "options" => {
              "items" => {
                "example" => "CHOICE1",
                "oneOf" => [
                  {
                    "$ref" => "#/definitions/config-var/definitions/option1",
                  },
                  {
                    "$ref" => "#/definitions/config-var/definitions/option2",
                  },
                ],
              },
            },
          },
          "links" => [
            {
              "description" => "Create many config-vars.",
              "href" => "/config-vars",
              "method" => "PATCH",
              "rel" => "instances",
              "title" => "Create Config-var",
              "schema" => {
                "type" => [
                  "array",
                ],
                "items" => {
                  "name" => {
                    "$ref" => "#/definitions/config-var/definitions/name",
                  },
                  "value" => {
                    "$ref" => "#/definitions/config-var/definitions/value",
                  },
                  "example" => [
                    { "name" => "EXAMPLE", "value" => "example" },
                  ],
                },
              },
            },
          ],
          "properties" => {
            "name" => {
              "$ref" => "#/definitions/config-var/definitions/name",
            },
            "value" => {
              "$ref" => "#/definitions/config-var/definitions/value",
            },
            "options" => {
              "$ref" => "#/definitions/config-var/definitions/options",
            },
            "patterned-string" => {
              "$ref" => "#/definitions/config-var/definitions/patterned-string",
            },
          },
        },
      },
      "links" => [
        {
          "href" => "https://example.com",
          "rel" => "self",
        },
      ],
      "properties" => {
        "app" => {
          "$ref" => "#/definitions/app",
        },
        "config-var" => {
          "$ref" => "#/definitions/config-var",
        },
      },
      "type" => "object",
    }
  end

  def pointer(path)
    JsonPointer.evaluate(data, path)
  end

  def render
    schema = Prmd::Schema.new(data)

    template = File.expand_path(File.join(File.dirname(__FILE__), "..", "..", "lib", "prmd", "templates"))

    Prmd.render(schema, template: template)
  end
end
