/* eslint-disable max-len */
import { test } from '@japa/runner'
import { DOMParser } from '@xmldom/xmldom'
import { ApiSchemaGenerator } from '../../../src/amf/ApiSchemaGenerator.js'
import { IAmfDocument } from '../../../src/amf/definitions/Amf.js'
import { IApiAnyShape } from '../../../src/amf/definitions/Shapes.js'
import { AmfLoader } from './AmfLoader.js'

test.group('APIC-690', (group) => {
  const loader = new AmfLoader()
  const xmlMime = 'application/xml'
  const apiFile = 'APIC-690'
  let model: IAmfDocument

  group.setup(async () => {
    model = await loader.getGraph(apiFile)
  })

  test('generates xml examples for an array body', ({ assert }) => {
    const payload = loader.getResponsePayloads(model, '/customers', 'get', '200')[0]
    const anyShape = payload.schema as IApiAnyShape
    const result = ApiSchemaGenerator.asExample(anyShape, xmlMime, {
      renderExamples: true,
    })!

    assert.typeOf(result, 'object', 'generates the example')
    assert.typeOf(result.renderValue, 'string', 'has the value')

    const parser = new DOMParser()
    const schema = parser.parseFromString(`<root>${result.renderValue}</root>`, xmlMime)

    const root = schema.getElementsByTagName('root')[0]!

    // this version of the library does not add "schema" to the shape generated from the payload type
    // The problem is that there is not wrapping object when including a schema directly to the body.
    // In the previous version this was wrapping the object with <schema> but it is not correct.

    const customers = root.getElementsByTagName('customerID')!
    assert.equal(customers.length, 2, 'has both customerID')
    assert.equal(customers[0].textContent!.trim(), '1fe1c22s-3d3a-9n3v', 'has the customerID')

    const firstNames = root.getElementsByTagName('firstName')!
    assert.equal(firstNames.length, 2, 'has both firstName')
    assert.equal(firstNames[0].textContent!.trim(), 'Molly', 'has the firstName')

    const displayNames = root.getElementsByTagName('displayName')!
    assert.equal(displayNames.length, 2, 'has both displayName')
    assert.equal(displayNames[0].textContent!.trim(), 'Molly the Mule', 'has the displayName')

    const phones = root.getElementsByTagName('phone')!
    assert.equal(phones.length, 2, 'has both phone')
    assert.equal(phones[0].textContent!.trim(), '415-000-0000', 'has the phone')

    const emails = root.getElementsByTagName('email')!
    assert.equal(emails.length, 2, 'has both email')
    assert.equal(emails[0].textContent!.trim(), 'molly@mulesoft.com', 'has the email')

    const ssns = root.getElementsByTagName('ssn')!
    assert.equal(ssns.length, 2, 'has both ssn')
    assert.equal(ssns[0].textContent!.trim(), '321-654-0987', 'has the ssn')

    const dateOfBirths = root.getElementsByTagName('dateOfBirth')!
    assert.equal(dateOfBirths.length, 2, 'has both dateOfBirth')
    assert.equal(dateOfBirths[0].textContent!.trim(), '1990-09-04', 'has the dateOfBirth')

    const addresses = root.getElementsByTagName('address')!
    assert.equal(addresses.length, 2, 'has both addresses')

    // const nodes = root.getElementsByTagName('schema')!;

    // assert.equal(nodes.length, 2, 'has both examples generated');
    // const testNode = nodes[1]!;

    // assert.equal(testNode.getElementsByTagName('customerID')!.textContent!.trim(), '1fe1c22s-3d3a-9n3v', 'has the customerID');
    // assert.equal(testNode.getElementsByTagName('firstName')!.textContent!.trim(), 'Molly', 'has the firstName');
    // assert.equal(testNode.getElementsByTagName('lastName')!.textContent!.trim(), 'Mule', 'has the lastName');
    // assert.equal(testNode.getElementsByTagName('displayName')!.textContent!.trim(), 'Molly the Mule', 'has the displayName');
    // assert.equal(testNode.getElementsByTagName('phone')!.textContent!.trim(), '415-000-0000', 'has the phone');
    // assert.equal(testNode.getElementsByTagName('email')!.textContent!.trim(), 'molly@mulesoft.com', 'has the email');
    // assert.equal(testNode.getElementsByTagName('ssn')!.textContent!.trim(), '321-654-0987', 'has the ssn');
    // assert.equal(testNode.getElementsByTagName('dateOfBirth')!.textContent!.trim(), '1990-09-04', 'has the dateOfBirth');

    // const address = testNode.getElementsByTagName('address')!;
    // assert.ok(address, 'has the address node');

    // assert.equal(address.getElementsByTagName('addressLine1')!.textContent!.trim(), '123 Street', 'has the address.addressLine1');
    // assert.equal(address.getElementsByTagName('addressLine2')!.textContent!.trim(), 'Apt.#3D', 'has the address.addressLine2');
    // assert.equal(address.getElementsByTagName('city')!.textContent!.trim(), 'San Francisco', 'has the address.city');
    // assert.equal(address.getElementsByTagName('state')!.textContent!.trim(), 'California', 'has the address.state');
    // assert.equal(address.getElementsByTagName('zipCode')!.textContent!.trim(), '94110', 'has the address.zipCode');
    // assert.equal(address.getElementsByTagName('country')!.textContent!.trim(), 'United States', 'has the address.country');
  })
})
