const test = require('tape')
const noop = function () {}
const noopStore = function (commit) {
  commit(() => '')

  return function () {
    commit(function () {
      return ''
    })
  }
}
const raf = function (callback) {
  process.nextTick(function () { callback() })
}
const initialElement = Symbol('initial target')
const newElement = Symbol('new target')
const initialState = Symbol('initial state')
const newState = Symbol('new state')
const dispatchArgumnt = Symbol('dispatch argument')

test('init to render', function (t) {
  t.plan(14)

  require('./main.js')({
    target: initialElement,
    store: function (commit) {
      t.equal(commit.name, 'commit')

      t.equal(typeof commit, 'function')

      commit(() => initialState)

      return function (arg) {
        t.equal(arg, dispatchArgumnt)

        commit(function (state) {
          t.equal(state, initialState)

          return newState
        })
      }
    },
    component: function (app) {
      t.deepEqual(Object.keys(app).length, 3)

      t.equal(app.dispatch.name, 'dispatch')

      t.equal(typeof app.dispatch, 'function')

      t.equal(app.next.name, 'next')

      t.equal(typeof app.next, 'function')

      t.equal(app.state, newState)

      return newElement
    },
    diff: function (target, newElement) {
      t.equal(target, initialElement)

      t.deepEqual(newElement, newElement)
    },
    raf
  })(function (dispatch) {
    t.equal(dispatch.name, 'dispatch')

    t.equal(typeof dispatch, 'function')

    dispatch(dispatchArgumnt)
  })
})

test('using next', function (t) {
  t.plan(1)

  require('./main.js')({
    target: initialElement,
    store: noopStore,
    component: function ({next}) {
      next(function (target) {
        t.equal(target, initialElement)
      })

      return newElement
    },
    diff: noop,
    raf
  })
})

test('using dispatch', function (t) {
  t.plan(2)

  require('./main.js')({
    target: initialElement,
    store: function (commit) {
      commit(() => initialState)

      return function (arg) {
        t.equal(arg, dispatchArgumnt)

        commit(function (state) {
          t.equal(state, initialState)

          return newState
        })
      }
    },
    component: function ({dispatch, state}) {
      if (state === initialState) {
        process.nextTick(function () {
          dispatch(dispatchArgumnt)
        })
      }

      return newElement
    },
    diff: noop,
    raf
  })
})

test('dispatch multiple', function (t) {
  t.plan(2)

  require('./main.js')({
    target: initialElement,
    store: function (commit) {
      commit(() => '')

      return function (arg) {
        t.equal(arg, dispatchArgumnt)

        commit(function (state) {
          return newState
        })
      }
    },
    component: function (app) {
      t.equal(app.state, newState)

      return newElement
    },
    diff: noop,
    raf
  })(function (dispatch) {
    dispatch()

    dispatch(dispatchArgumnt)
  })
})

@@ -601,34 +601,24 @@
 t,%0A    store
-: function
  (commit) %7B%0A
@@ -613,24 +613,24 @@
  (commit) %7B%0A
+
       t.equa
@@ -935,34 +935,24 @@
    component
-: function
  (app) %7B%0A   
@@ -1246,26 +1246,16 @@
     diff
-: function
  (target
@@ -1649,26 +1649,16 @@
 omponent
-: function
  (%7Bnext%7D
@@ -1915,34 +1915,24 @@
 t,%0A    store
-: function
  (commit) %7B%0A
@@ -2173,26 +2173,16 @@
 omponent
-: function
  (%7Bdispa
@@ -2507,26 +2507,16 @@
    store
-: function
  (commit
@@ -2690,32 +2690,32 @@
 %0A      %7D%0A    %7D,%0A
+
     component: f
@@ -2715,18 +2715,8 @@
 nent
-: function
  (ap

Enforce consistency with functions