const dedent = require('dedent')
const stylelint = require('stylelint')
const pluginPath = require.resolve('../plugins/colors')

const ruleName = 'primer/colors'
const configWithOptions = (...args) => ({
  plugins: [pluginPath],
  rules: {
    [ruleName]: args
  }
})

describe(ruleName, () => {
  it('reports color properties w/o variables', () => {
    return stylelint
      .lint({
        code: `.x { color: #f00; }`,
        config: configWithOptions(true)
      })
      .then(data => {
        expect(data).toHaveErrored()
        expect(data).toHaveWarningsLength(1)
        expect(data).toHaveWarnings([`Please use a text color variable instead of "#f00". (${ruleName})`])
      })
  })

  it('does not run when disabled', () => {
    return stylelint
      .lint({
        code: `.x { color: #f00; }`,
        config: configWithOptions(false)
      })
      .then(data => {
        expect(data).not.toHaveErrored()
        expect(data).toHaveWarningsLength(0)
      })
  })

  it('does not report color properties with allowed values', () => {
    return stylelint
      .lint({
        code: `.x { background-color: transparent; }`,
        config: configWithOptions(true)
      })
      .then(data => {
        expect(data).not.toHaveErrored()
        expect(data).toHaveWarningsLength(0)
      })
  })

  it('does not report color properties in at-rules', () => {
    return stylelint
      .lint({
        code: `
          @mixin foo() {
            .x { background-color: #123456; }
          }
        `,
        config: configWithOptions(true)
      })
      .then(data => {
        expect(data).not.toHaveErrored()
        expect(data).toHaveWarningsLength(0)
      })
  })

  it('reports properties with wrong variable usage', () => {
    return stylelint
      .lint({
        code: `.x { background-color: $red; }`,
        config: configWithOptions(true)
      })
      .then(data => {
        expect(data).toHaveErrored()
        expect(data).toHaveWarningsLength(1)
        expect(data).toHaveWarnings([`Please use a background color variable instead of "$red". (${ruleName})`])
      })
  })

  it('does not report properties with valid variables', () => {
    return stylelint
      .lint({
        code: `.x { background-color: $bg-red; }`,
        config: configWithOptions(true)
      })
      .then(data => {
        expect(data).not.toHaveErrored()
        expect(data).toHaveWarningsLength(0)
      })
  })

  it('does not report non-color values in background:', () => {
    return stylelint
      .lint({
        code: `.x { background: red url(derp.png) top right; }`,
        config: configWithOptions(true)
      })
      .then(data => {
        expect(data).toHaveErrored()
        expect(data).toHaveWarningsLength(1)
        expect(data).toHaveWarnings([`Please use a background color variable instead of "red". (${ruleName})`])
      })
  })

  describe('autofix', () => {
    it('fixes text colors', () => {
      return stylelint
        .lint({
          code: dedent`
            .x { color: $red-600; }
            .y { color: $purple; }
          `,
          config: configWithOptions(true),
          fix: true
        })
        .then(data => {
          expect(data).not.toHaveErrored()
          expect(data).toHaveWarningsLength(0)
          expect(data.output).toEqual(dedent`
            .x { color: $text-red; }
            .y { color: $text-purple; }
          `)
        })
    })

    it('fixes background colors', () => {
      return stylelint
        .lint({
          code: dedent`
            .x { background-color: $red-500; }
          `,
          config: configWithOptions(true, {verbose: true}),
          fix: true
        })
        .then(data => {
          expect(data).not.toHaveErrored()
          expect(data).toHaveWarningsLength(0)
          expect(data.output).toEqual(dedent`
            .x { background-color: $bg-red; }
          `)
        })
    })

    it('does not fix other properties', () => {
      return stylelint
        .lint({
          code: dedent`
            .x { border-color: $red-500; }
          `,
          config: configWithOptions(true, {verbose: true}),
          fix: true
        })
        .then(data => {
          expect(data).not.toHaveErrored()
          expect(data).toHaveWarningsLength(0)
          expect(data.output).toEqual(dedent`
            .x { border-color: $red-500; }
          `)
        })
    })
  })

  it('gets chatty with {verbose: true}', () => {
    return stylelint
      .lint({
        code: `.x { color: #f00; }`,
        config: configWithOptions(true, {verbose: true})
      })
      .then(data => {
        expect(data).toHaveErrored()
        expect(data).toHaveWarningsLength(1)
        expect(data).toHaveWarnings([`Please use a text color variable instead of "#f00". (${ruleName})`])
      })
  })

  it('can override via options.rules', () => {
    return stylelint
      .lint({
        code: `.x { color: #f00; }`,
        config: configWithOptions(true, {
          rules: {
            'text color': false
          }
        })
      })
      .then(data => {
        expect(data).not.toHaveErrored()
        expect(data).toHaveWarningsLength(0)
      })
  })
})

@@ -1496,32 +1496,182 @@
 6; %7D%0A          %7D
+%0A%0A          @each $color in $colors %7B%0A            @include breakpoint(sm) %7B%0A              .text-#%7B$color%7D %7B color: $color; %7D%0A            %7D%0A          %7D
 %0A        %60,%0A    
@@ -1697,32 +1697,56 @@
 ithOptions(true)
+,%0A        syntax: 'scss'
 %0A      %7D)%0A      

add scss test for avoiding mixins, other atrules