"use strict";

var assert = require("assert");
var proxyquire = require("proxyquire").noCallThru();
var sinon = require("sinon");

describe("isMap factory", function () {
  beforeEach(function () {
    this.fakeActualMessageValues = "a4bf1905-489e-4f10-a47e-5b79b7cf173a";

    this.factory = proxyquire("./is-map", {
      "../actual-message-values": this.fakeActualMessageValues,
    });

    this.fakeReferee = {
      add: sinon.fake(),
    };

    this.factory(this.fakeReferee);

    this.options = this.fakeReferee.add.args[0][1];
  });

  it("calls referee.add with 'isMap' as name", function () {
    assert(this.fakeReferee.add.calledWith("isMap"));
  });

  describe(".assert", function () {
    describe("when actual is an instance of Map", function () {
      it("returns true", function () {
        var result = this.options.assert(new Map());

        assert.equal(result, true);
      });
    });

    describe("when actual is not an instance of Map", function () {
      it("returns false", function () {
        var t = this;

        [
          Map,
          WeakMap,
          Set,
          // eslint-disable-next-line ie11/no-weak-collections
          new WeakMap(),
          [],
          {},
          "apple pie",
          123,
          new Date(),
        ].forEach(function (value) {
          var result = t.options.assert(value);

          assert.equal(result, false);
        });
      });
    });
  });

  describe(".assertMessage", function () {
    it("is '${customMessage}Expected ${actual} to be a Map'", function () {
      assert.equal(
        this.options.assertMessage,
        "${customMessage}Expected ${actual} to be a Map"
      );
    });
  });

  describe(".refuteMessage", function () {
    it("is '${customMessage}Expected ${actual} not to be a Map'", function () {
      assert.equal(
        this.options.refuteMessage,
        "${customMessage}Expected ${actual} not to be a Map"
      );
    });
  });

  describe(".expectation", function () {
    it("is 'toBeMap'", function () {
      assert.equal(this.options.expectation, "toBeMap");
    });
  });

  describe(".values", function () {
    it("delegates to '../actual-message-values'", function () {
      assert.equal(this.options.values, this.fakeActualMessageValues);
    });
  });
});
