import test from "ava"

import { spy } from "sinon"

import { identity } from "ramda"
import { v4 } from "uuid"

import { sample } from "@/core"

import { BEFORE, PRIMARY, AFTER } from "~/share/constants/role"
import { LEFT, RIGHT } from "~/share/constants/direction"

import store from "~/client/store"

test("hideNavigation", t => {
  const state = { showNavigation: true }
  store.mutations.hideNavigation(state)
  t.false(state.showNavigation)
})

test("toggleNavigation", t => {
  const state = { showNavigation: true }

  store.mutations.toggleNavigation(state)
  t.false(state.showNavigation)

  store.mutations.toggleNavigation(state)
  t.true(state.showNavigation)
})

test("login", t => {
  const state = { user: null }

  const user = { }

  store.mutations.login(state, user)

  t.is(user, state.user)
})

test("logout", t => {
  const state = { user: { } }
  store.mutations.logout(state)
  t.falsy(state.user)
})

test("universe", t => {
  const state = { universe: null }

  const universe = { }
  const payload = { universe }

  store.mutations.universe(state, payload)

  t.is(universe, state.universe)
})

test("game: when not rotating accepts new game", t => {
  const state = { rotating: false, games: { } }

  const role = sample(BEFORE, PRIMARY, AFTER)
  const game = { }

  store.mutations.game(state, { role, game })

  t.is(game, state.games[role])
})

test("game: when rotating and role is BEFORE", t => {
  const state = {
    rotating: true,
    games: {
      [BEFORE]: BEFORE,
      [PRIMARY]: PRIMARY,
      [AFTER]: AFTER
    }
  }

  const role = BEFORE
  const game = { }

  store.mutations.game(state, { role, game })

  t.deepEqual(
    state.games,
    {
      [BEFORE]: game,
      [PRIMARY]: BEFORE,
      [AFTER]: PRIMARY
    }
  )
})

test("game: when rotating and role is AFTER", t => {
  const state = {
    rotating: true,
    games: {
      [BEFORE]: BEFORE,
      [PRIMARY]: PRIMARY,
      [AFTER]: AFTER
    }
  }

  const role = AFTER
  const game = { }

  store.mutations.game(state, { role, game })

  t.deepEqual(
    state.games,
    {
      [BEFORE]: PRIMARY,
      [PRIMARY]: AFTER,
      [AFTER]: game
    }
  )
})

test("game: when rotating stops rotation and inverts", t => {
  const role = sample(BEFORE, PRIMARY, AFTER)
  const flip = sample(true, false)

  const state = { rotating: true, flip }

  store.mutations.game(state, { role, game: { } })

  t.is(!flip, state.flip)
  t.false(state.rotating)
})

test("rotateLeft: when already rotating does nothing", t => {
  const send = spy()
  const state = { send, rotating: true }

  store.mutations.rotateLeft(state)

  t.true(send.notCalled)
})

test("rotateLeft: when after game exists", t => {
  const send = spy()
  const after = { uuid: v4() }
  const games = { after }

  const state = { send, games }

  store.mutations.rotateLeft(state)

  t.true(state.rotating)

  t.true(send.calledOnce)
  t.true(send.calledWithMatch({
    action: "rotate",
    direction: LEFT,
    of: games.after.uuid
  }))
})

test("rotateRight: when already rotating does nothing", t => {
  const send = spy()
  const state = { send, rotating: true }

  store.mutations.rotateRight(state)

  t.true(send.notCalled)
})

test("rotateRight: when before game exists", t => {
  const send = spy()
  const before = { uuid: v4() }
  const games = { before }

  const state = { send, games }

  store.mutations.rotateRight(state)

  t.true(state.rotating)

  t.true(send.calledOnce)
  t.true(send.calledWithMatch({
    action: "rotate",
    direction: RIGHT,
    of: games.before.uuid
  }))
})

test("actions: logout", async t => {
  const commit = identity
  const state = { fetch: identity }

  store.actions.logout({ commit, state })

  t.pass()
})

@@ -2346,16 +2346,27 @@
 ue, flip
+, games: %7B%7D
  %7D%0A%0A  st

fix intermittent test failures