/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */
import chai from 'chai'
const { expect } = chai

import * as util from '../../../../frameworks/legacy/util'

describe('Util', () => {
  describe('isReserved', () => {
    it('should be first char is $ or _', () => {
      expect(util.isReserved('$isReserved')).eql(true)
      expect(util.isReserved('_isReserved')).eql(true)
      expect(util.isReserved('isReserved$')).eql(false)
      expect(util.isReserved('is$Reserved')).eql(false)
      expect(util.isReserved('isReserved')).eql(false)
    })
  })

  describe('camelize', () => {
    it('should be camelize a hyphen-delmited string', () => {
      expect(util.camelize('mini-camelize')).eql('miniCamelize')
      expect(util.camelize('mini-camelize-test')).eql('miniCamelizeTest')
    })
  })

  describe('toArray', () => {
    it('should be convert an Array-like object to a real Array', () => {
      const mockup = {
        '0': 1,
        '1': 2,
        '2': 3,
        length: 3
      }

      expect(util.toArray(mockup)).eql([1, 2, 3])
      expect(util.toArray(mockup, 2)).eql([3])
    })
  })

  describe('extend', () => {
    it('should be extend object', () => {
      const mockup = {
        a: 1,
        b: 2
      }

      expect(util.extend(mockup, { b: 4, c: 5 })).eql({
        a: 1,
        b: 4,
        c: 5
      })

      expect(util.extend(mockup, { c: 5 })).eql({
        a: 1,
        b: 4,
        c: 5
      })

      expect(util.extend(mockup, { c: 5 }, { d: 6 }, { e: 7 })).eql({
        a: 1,
        b: 4,
        c: 5,
        d: 6,
        e: 7
      })
    })

    it('polyfill Object.assign', () => {
      const _assign = Object.assign
      Object.assign = undefined

      const mockup = {
        a: 1,
        b: 2
      }

      expect(util.extend(mockup, { b: 4, c: 5 })).eql({
        a: 1,
        b: 4,
        c: 5
      })

      expect(util.extend(mockup, { c: 5 })).eql({
        a: 1,
        b: 4,
        c: 5
      })

      expect(util.extend(mockup, { c: 5 }, { d: 6 }, { e: 7 })).eql({
        a: 1,
        b: 4,
        c: 5,
        d: 6,
        e: 7
      })

      Object.assign = _assign
    })
  })

  describe('isObject', () => {
    it('should be an array or object', () => {
      expect(util.isObject({})).eql(true)
      expect(util.isObject([])).eql(true)
      expect(util.isObject('a')).eql(false)
      expect(util.isObject(1)).eql(false)
      expect(util.isObject(true)).eql(false)
      expect(util.isObject(null)).eql(false)
      expect(util.isObject(undefined)).eql(false)
      expect(util.isObject(function () {})).eql(false)
      expect(util.isObject(/\w*/)).eql(true) // regexp is object
      expect(util.isObject(new Date())).eql(true)
    })
  })

  describe('isPlainObject', () => {
    it('should be an real object', () => {
      expect(util.isPlainObject({})).eql(true)
      expect(util.isPlainObject([])).eql(false)
      expect(util.isPlainObject('a')).eql(false)
      expect(util.isPlainObject(1)).eql(false)
      expect(util.isPlainObject(true)).eql(false)
      expect(util.isPlainObject(null)).eql(false)
      expect(util.isPlainObject(undefined)).eql(false)
      expect(util.isPlainObject(function () {})).eql(false)
      expect(util.isPlainObject(/\w*/)).eql(false)
      expect(util.isPlainObject(new Date())).eql(false)
    })
  })

  describe('typof', () => {
    it('should be real type', () => {
      expect(util.typof({})).eql('object')
      expect(util.typof([])).eql('array')
      expect(util.typof('a')).eql('string')
      expect(util.typof(1)).eql('number')
      expect(util.typof(true)).eql('boolean')
      expect(util.typof(null)).eql('null')
      expect(util.typof(undefined)).eql('undefined')
      expect(util.typof(function () {})).eql('function')
      expect(util.typof(/\w*/)).eql('regexp')
      expect(util.typof(new Date())).eql('date')
    })
  })

  describe('def', () => {
    it('should be define a non-enumerable property', () => {
      const obj = {}
      util.def(obj, 'a', 1, true)
      expect(obj).eql({ a: 1 })

      util.def(obj, 'b', 1, false)
      expect(obj).eql({ a: 1 })

      util.def(obj, 'c', 1, true)
      expect(obj).eql({ a: 1, c: 1 })

      util.def(obj, 'd', 1)
      expect(obj).eql({ a: 1, c: 1 })
    })
  })

  describe('hyphenate', () => {
    it('should hyphenate a camelCase string', () => {
      const str = 'helloWorldWeex'
      expect(util.hyphenate(str)).eql('hello-world-weex')
    })
  })
})
