import { selected as reducer } from '../../../pages/homepage/reducers/selected.js';

import * as actions from '../../../pages/homepage/actions/selected.js';
import * as categoryActions from '../../../pages/homepage/actions/categories.js';
import * as postActions from '../../../pages/homepage/actions/posts.js';
import * as ruleActions from '../../../pages/homepage/actions/rules.js';
import * as constants from '../../../pages/homepage/constants.js';

const defaultState = { item: {}, next: false, lastReached: false, post: {} };

describe('selected reducer', () => {
  it('should return state', () => {
    expect(reducer(undefined, {})).toEqual(defaultState);
  });

  it('should return state after selecting a category', () => {
    const category = { id: 9, name: 'Tech', unread: 291 };

    const action = {
      type: categoryActions.SELECT_CATEGORY,
      section: category,
    };

    const expectedState = {
      ...defaultState,
      item: { ...category, clicks: 1 },
    };

    expect(reducer(undefined, action)).toEqual(expectedState);
  });

  it('should return state after selecting a rule', () => {
    const rule = {
      id: 1,
      name: 'Test rule',
      unread: 100,
      category: 9,
      url: 'http://feeds.arstechnica.com/arstechnica/index?fmt=xml',
      favicon: 'https://cdn.arstechnica.net/favicon.ico',
    };

    const action = {
      type: ruleActions.SELECT_RULE,
      section: rule,
    };

    const expectedState = {
      ...defaultState,
      item: { ...rule, clicks: 1 },
    };

    expect(reducer(undefined, action)).toEqual(expectedState);
  });

  it('should return state after selecting saved items', () => {
    const action = {
      type: actions.SELECT_SAVED,
    };

    const expectedState = {
      ...defaultState,
      item: { type: constants.SAVED_TYPE },
    };

    expect(reducer(undefined, action)).toEqual(expectedState);
  });

  it('should return state after selecting a category twice', () => {
    const category = { id: 9, name: 'Tech', unread: 291 };

    const action = {
      type: categoryActions.SELECT_CATEGORY,
      section: category,
    };

    const state = {
      ...defaultState,
      item: { ...category, clicks: 1 },
    };

    const expectedState = {
      ...defaultState,
      item: { ...category, clicks: 2 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after selecting a rule twice', () => {
    const rule = {
      id: 1,
      name: 'Test rule',
      unread: 100,
      category: 9,
      url: 'http://feeds.arstechnica.com/arstechnica/index?fmt=xml',
      favicon: 'https://cdn.arstechnica.net/favicon.ico',
    };

    const action = {
      type: ruleActions.SELECT_RULE,
      section: rule,
    };

    const state = {
      ...defaultState,
      item: { ...rule, clicks: 1 },
    };

    const expectedState = {
      ...defaultState,
      item: { ...rule, clicks: 2 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after selecting a category the third time', () => {
    const category = { id: 9, name: 'Tech', unread: 291 };

    const action = {
      type: categoryActions.SELECT_CATEGORY,
      section: category,
    };

    const state = {
      ...defaultState,
      item: { ...category, clicks: 2 },
    };

    const expectedState = {
      ...defaultState,
      item: { ...category, clicks: 1 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after selecting a rule the third time', () => {
    const rule = {
      id: 1,
      name: 'Test rule',
      unread: 100,
      category: 9,
      url: 'http://feeds.arstechnica.com/arstechnica/index?fmt=xml',
      favicon: 'https://cdn.arstechnica.net/favicon.ico',
    };

    const action = {
      type: ruleActions.SELECT_RULE,
      section: rule,
    };

    const state = {
      ...defaultState,
      item: { ...rule, clicks: 2 },
    };

    const expectedState = {
      ...defaultState,
      item: { ...rule, clicks: 1 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after selecting different (rule) section type', () => {
    const category = { id: 9, name: 'Tech', unread: 291 };

    const rule = {
      id: 1,
      name: 'Test rule',
      unread: 100,
      category: 9,
      url: 'http://feeds.arstechnica.com/arstechnica/index?fmt=xml',
      favicon: 'https://cdn.arstechnica.net/favicon.ico',
    };

    const action = {
      type: ruleActions.SELECT_RULE,
      section: rule,
    };

    const state = {
      ...defaultState,
      item: { ...category, clicks: 1 },
    };

    const expectedState = {
      ...defaultState,
      item: { ...rule, clicks: 1 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after selecting different (category) section type', () => {
    const category = { id: 9, name: 'Tech', unread: 291 };

    const rule = {
      id: 1,
      name: 'Test rule',
      unread: 100,
      category: 9,
      url: 'http://feeds.arstechnica.com/arstechnica/index?fmt=xml',
      favicon: 'https://cdn.arstechnica.net/favicon.ico',
    };

    const action = {
      type: categoryActions.SELECT_CATEGORY,
      section: category,
    };

    const state = {
      ...defaultState,
      item: { ...rule, clicks: 1 },
    };

    const expectedState = {
      ...defaultState,
      item: { ...category, clicks: 1 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after receiving posts', () => {
    const posts = [
      {
        id: 2067,
        remoteIdentifier: 'https://arstechnica.com/?p=1648607',
        title:
          'This amazing glitch puts Star Fox 64 ships in an unmodified Zelda cartridge',
        body:
          '"Stale-reference manipulation," 300-character file names, and a clash between worlds.',
        author: 'Kyle Orland',
        publicationDate: '2020-01-24T19:50:12Z',
        url: 'https://arstechnica.com/?p=1648607',
        rule: 4,
        read: false,
      },
      {
        id: 2141,
        remoteIdentifier: 'https://arstechnica.com/?p=1648757',
        title: 'The most complete brain map ever is here: A fly’s “connectome”',
        body:
          'It took 12 years and at least $40 million to chart a region about 250µm across.',
        author: 'WIRED',
        publicationDate: '2020-01-25T11:06:46Z',
        url: 'https://arstechnica.com/?p=1648757',
        rule: 4,
        read: false,
      },
    ];

    const action = {
      type: postActions.RECEIVE_POSTS,
      next: 'https://durp.com/api/rules/4/posts/?page=2',
      posts,
    };

    const expectedState = {
      ...defaultState,
      next: 'https://durp.com/api/rules/4/posts/?page=2',
      lastReached: false,
    };

    expect(reducer(undefined, action)).toEqual(expectedState);
  });

  it('should return state after receiving a post which is selected', () => {
    const post = {
      id: 2067,
      remoteIdentifier: 'https://arstechnica.com/?p=1648607',
      title:
        'This amazing glitch puts Star Fox 64 ships in an unmodified Zelda cartridge',
      body:
        '"Stale-reference manipulation," 300-character file names, and a clash between worlds.',
      author: 'Kyle Orland',
      publicationDate: '2020-01-24T19:50:12Z',
      url: 'https://arstechnica.com/?p=1648607',
      rule: 4,
      read: false,
    };

    const action = {
      type: postActions.RECEIVE_POST,
      post: { ...post, rule: 6 },
    };

    const state = { ...defaultState, post };
    const expectedState = { ...defaultState, post: { ...post, rule: 6 } };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after receiving a post with none selected', () => {
    const post = {
      id: 2067,
      remoteIdentifier: 'https://arstechnica.com/?p=1648607',
      title:
        'This amazing glitch puts Star Fox 64 ships in an unmodified Zelda cartridge',
      body:
        '"Stale-reference manipulation," 300-character file names, and a clash between worlds.',
      author: 'Kyle Orland',
      publicationDate: '2020-01-24T19:50:12Z',
      url: 'https://arstechnica.com/?p=1648607',
      rule: 4,
      read: false,
    };

    const action = {
      type: postActions.RECEIVE_POST,
      post: { ...post, rule: 6 },
    };

    const state = { ...defaultState, post: {} };
    const expectedState = { ...defaultState, post: {} };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after selecting a post', () => {
    const post = {
      id: 2067,
      remoteIdentifier: 'https://arstechnica.com/?p=1648607',
      title:
        'This amazing glitch puts Star Fox 64 ships in an unmodified Zelda cartridge',
      body:
        '"Stale-reference manipulation," 300-character file names, and a clash between worlds.',
      author: 'Kyle Orland',
      publicationDate: '2020-01-24T19:50:12Z',
      url: 'https://arstechnica.com/?p=1648607',
      rule: 4,
      read: false,
    };

    const action = {
      type: postActions.SELECT_POST,
      post,
    };

    const expectedState = { ...defaultState, post };

    expect(reducer(undefined, action)).toEqual(expectedState);
  });

  it('should return state after unselecting a post', () => {
    const post = {
      id: 2067,
      remoteIdentifier: 'https://arstechnica.com/?p=1648607',
      title:
        'This amazing glitch puts Star Fox 64 ships in an unmodified Zelda cartridge',
      body:
        '"Stale-reference manipulation," 300-character file names, and a clash between worlds.',
      author: 'Kyle Orland',
      publicationDate: '2020-01-24T19:50:12Z',
      url: 'https://arstechnica.com/?p=1648607',
      rule: 4,
      read: false,
    };

    const action = {
      type: postActions.UNSELECT_POST,
      post,
    };

    const state = { ...defaultState, post };
    const expectedState = { ...defaultState, post: {} };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after marking a post read', () => {
    const post = {
      id: 2067,
      remoteIdentifier: 'https://arstechnica.com/?p=1648607',
      title:
        'This amazing glitch puts Star Fox 64 ships in an unmodified Zelda cartridge',
      body:
        '"Stale-reference manipulation," 300-character file names, and a clash between worlds.',
      author: 'Kyle Orland',
      publicationDate: '2020-01-24T19:50:12Z',
      url: 'https://arstechnica.com/?p=1648607',
      rule: 4,
      read: false,
    };

    const rule = {
      id: 4,
      name: 'Ars Technica',
      unread: 100,
      category: 1,
      url: 'http://feeds.arstechnica.com/arstechnica/index?fmt=xml',
      favicon: 'https://cdn.arstechnica.net/favicon.ico',
    };

    const action = {
      type: postActions.MARK_POST_READ,
      section: rule,
      post,
    };

    const state = {
      ...defaultState,
      item: rule,
    };
    const expectedState = {
      ...defaultState,
      item: { ...rule, unread: 99 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });

  it('should return state after marking a section read', () => {
    const rule = {
      id: 4,
      name: 'Ars Technica',
      unread: 100,
      category: 1,
      url: 'http://feeds.arstechnica.com/arstechnica/index?fmt=xml',
      favicon: 'https://cdn.arstechnica.net/favicon.ico',
    };

    const action = {
      section: { ...rule },
      type: actions.MARK_SECTION_READ,
    };

    const state = { ...defaultState, item: { ...rule, clicks: 2 } };
    const expectedState = {
      ...defaultState,
      item: { ...rule, unread: 0, clicks: 0 },
    };

    expect(reducer(state, action)).toEqual(expectedState);
  });
});
