/* global Twitch */
import DeprecatedStreamModel from 'web-client/models/deprecated-stream';
import moduleForComponent from 'web-client/tests/helpers/module-for-component';
import { test } from 'ember-qunit';
import hbs from 'htmlbars-inline-precompile';

const RealPlayer = Twitch.embed.Player;

function createStream(name) {
  let streamModel = DeprecatedStreamModel.create({
    channel: {
      name,
      logo: '',
      display_name: 'neil youngs hits'
    },
    game: 'csgo',
    title: 'rocking in the free world',
    text: 'comes a time'
  });
  return {
    stream: streamModel,
    index: 0
  };
}

moduleForComponent('front-page/carousel-player', 'Integration | Component | front page/carousel player', {
  afterEach() {
    Twitch.embed.Player = RealPlayer;
  }
});

test('player starts when data comes in after render', function(assert) {
  assert.expect(8);

  let channelNameA = 'day9tv';
  let channelNameB = 'yohsfault';
  let streamA = createStream(channelNameA);
  let streamB = createStream(channelNameB);

  let hasCreatedPlayer = false;
  let hasSetChannel = null;
  let setCount = 0;

  class FakeFrontPagePlayer {
    constructor(div, { channel }) {
      hasCreatedPlayer = true;
      this.listeners = {};

      if (channel) {
        this.setChannel(channel);
      }
    }

    setChannel(name) {
      hasSetChannel = name;
      setCount++;
    }

    addEventListener(eventName, fn) {
      let eventListeners = this.listeners[eventName];
      if (!eventListeners) {
        eventListeners = this.listeners[eventName] = [];
      }

      eventListeners.push(fn);
    }

    removeEventListener(eventName, fn) {
      let eventListeners = this.listeners[eventName];
      if (eventListeners) {
        this.listeners[eventName] = eventListeners.without(fn);
      }
    }

    destroy() {
      /* invoked upon `willDestroyElement` */
    }
  }
  Twitch.embed.Player = FakeFrontPagePlayer;

  this.render(hbs`{{front-page/carousel-player selectedStream=selectedStream}}`);

  assert.ok(hasCreatedPlayer, 'player has booted');
  assert.equal(setCount, 0, 'player has not set channel');

  this.set('selectedStream', streamA);

  assert.equal(hasSetChannel, channelNameA, 'player has set a channel');
  assert.equal(setCount, 1, 'player has set once');

  this.set('selectedStream', streamB);

  assert.equal(hasSetChannel, channelNameB, 'player has set a channel');
  assert.equal(setCount, 2, 'player has set twice');

  this.set('selectedStream', streamB);

  assert.equal(hasSetChannel, channelNameB, 'player channel remains');
  assert.equal(setCount, 2, 'player has still only set twice');
});

test('player starts when data comes in before render', function(assert) {
  assert.expect(2);

  let channelName = 'day9tv';
  let stream = createStream(channelName);

  let hasCreatedPlayer = false;
  let hasSetChannelOnInit = null;

  class FakeFrontPagePlayer {
    constructor(id, options) {
      hasCreatedPlayer = true;
      this.listeners = {};
      hasSetChannelOnInit = options.channel;
    }

    addEventListener(eventName, fn) {
      let eventListeners = this.listeners[eventName];
      if (!eventListeners) {
        eventListeners = this.listeners[eventName] = [];
      }

      eventListeners.push(fn);
    }

    removeEventListener(eventName, fn) {
      let eventListeners = this.listeners[eventName];
      if (eventListeners) {
        this.listeners[eventName] = eventListeners.without(fn);
      }
    }

    destroy() {
      /* invoked upon `willDestroyElement` */
    }
  }
  Twitch.embed.Player = FakeFrontPagePlayer;

  this.set('selectedStream', stream);
  this.render(hbs`{{front-page/carousel-player selectedStream=selectedStream}}`);

  assert.ok(hasCreatedPlayer, 'player has booted');
  assert.equal(hasSetChannelOnInit, channelName, 'player has set a channel');
});
