<commit_before>'use strict';

describe('Arrays', function () {

  /*Arrays*/
  /* An array is a data structure with automatically indexed positions*/
  it('Arrays can be accessed by indices', function () {
    //The brackets indicate to the compiler to make an array and to fill it with the comma-separated values between the brackets
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings[1]).toBe("StringOne");//We can access any location of the zero-based array
  });
  it('You can reference and change specific cells with indices', function () {
    var arrayOfStrings = [ "StringOne" , "StringOne" , "StringTwo"];
    arrayOfStrings[0] = "StringZero"; //You can change the value contained at any index
    expect(arrayOfStrings[0]).toBe("StringZero");
  });
  it('You can access the length of Arrays with the .length property', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings.length).toBe(3);
  });
  it('Pop() function removes a cell from the back of the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings.pop()).toBe("StringTwo");//Pop() function deletes the last position and retrieves its value
    expect(arrayOfStrings.length).toBe(2);//The array length automatically adjusts
  });
  it('shift() function removes a cell from the beginning of the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings.shift()).toBe("StringZero");//shift() function deletes the first position and retrieves its value
    expect(arrayOfStrings.length).toBe(2);//The array length automatically adjusts
  });
  it('Push() function adds a cell and its contents to the back of the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" ];
    arrayOfStrings.push('StringTwo');
    expect(arrayOfStrings[2]).toBe("StringTwo");//Push() will add a cell onto the back of the arrays
    expect(arrayOfStrings.length).toBe(3);//The array length automatically adjusts
  });

  it('splice() function removes elements from anywhere in the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    //The first argument is the index where you want to start
    //The second argument is the number of elements you want to remove
    arrayOfStrings.splice(1,1);
    expect(arrayOfStrings[1]).toBe("StringTwo");
    expect(arrayOfStrings.length).toBe(2);//The array length automatically adjusts
  });

  it('Arrays can hold different types of variables ', function () {
    var StringTwoVariable = "StringTwo";
    var arrayOfStrings = [ "StringZero" , 1 , StringTwoVariable];
    //When assigning variables to an entry of an array, the variable name is not used,
    //Instead, the internal value is retrieved
    expect(arrayOfStrings[2]).toBe("StringTwo");
  });
  it('Arrays can hold Arrays ', function () {
    var firstArrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    var secondArrayOfStrings = [ "StringThree" , "StringFour" , "StringFive"];
    var firstAndSecondArrays = [firstArrayOfStrings , secondArrayOfStrings];
    expect(typeof firstAndSecondArrays).toBe("object");//Arrays are treated as objects
    expect(firstAndSecondArrays[1][0]).toBe("StringThree");//You can access any index of the composed array
  });
  it('Arrays can hold undefined values ', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    arrayOfStrings[1] = undefined; //to make a cell empty. we can use the keyword 'undefined', which means 'NO CONTENTS'
    expect(arrayOfStrings[1]).toBeUndefined();
    expect(arrayOfStrings.length).toBe(3);//The array length does not change when some of the values are undefined
  });
  it('Arrays can be created with no values ', function () {
    var arrayOfStrings = [];
    expect(Array.isArray(arrayOfStrings)).toBe(true);
    //When you access an index of the array, but you haven't assigned a value, the array returns 'undefined'
    expect(arrayOfStrings[1]).toBeUndefined();
    expect(arrayOfStrings.length).toBe(0);
  });
});
<commit_msg>Remove extra space from unit test and fix semantic error<commit_after>'use strict';

describe('Arrays', function () {

  /*Arrays*/
  /* An array is a data structure with automatically indexed positions*/
  it('Arrays can be accessed by indices', function () {
    //The brackets indicate to the compiler to make an array and to fill it with the comma-separated values between the brackets
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings[1]).toBe("StringOne");//We can access any location of the zero-based array
  });
  it('You can reference and change specific cells with indices', function () {
    var arrayOfStrings = [ "StringOne" , "StringOne" , "StringTwo"];
    arrayOfStrings[0] = "StringZero"; //You can change the value contained at any index
    expect(arrayOfStrings[0]).toBe("StringZero");
  });
  it('You can access the length of Arrays with the .length property', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings.length).toBe(3);
  });
  it('Pop() function removes a cell from the back of the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings.pop()).toBe("StringTwo");//Pop() function deletes the last position and retrieves its value
    expect(arrayOfStrings.length).toBe(2);//The array length automatically adjusts
  });
  it('shift() function removes a cell from the beginning of the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    expect(arrayOfStrings.shift()).toBe("StringZero");//shift() function deletes the first position and retrieves its value
    expect(arrayOfStrings.length).toBe(2);//The array length automatically adjusts
  });
  it('Push() function adds a cell and its contents to the back of the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" ];
    arrayOfStrings.push('StringTwo');
    expect(arrayOfStrings[2]).toBe("StringTwo");//Push() will add a cell onto the back of the arrays
    expect(arrayOfStrings.length).toBe(3);//The array length automatically adjusts
  });

  it('splice() function removes elements from anywhere in the array', function () {
    var arrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    //The first argument is the index where you want to start
    //The second argument is the number of elements you want to remove
    arrayOfStrings.splice(1,1);
    expect(arrayOfStrings[1]).toBe("StringTwo");
    expect(arrayOfStrings.length).toBe(2);//The array length automatically adjusts
  });

  it('Arrays can hold different types of variables ', function () {
    var StringTwoVariable = "StringTwo";
    var arrayOfStrings = [ "StringZero" , 1 , StringTwoVariable];
    //When assigning variables to an entry of an array, the variable name is not used,
    //Instead, the internal value is retrieved
    expect(arrayOfStrings[2]).toBe("StringTwo");
  });
  it('Arrays can hold Arrays ', function () {
    var firstArrayOfStrings = [ "StringZero" , "StringOne" , "StringTwo"];
    var secondArrayOfStrings = [ "StringThree" , "StringFour" , "StringFive"];
    var firstAndSecondArrays = [firstArrayOfStrings , secondArrayOfStrings];
    expect(Array.isArray(firstAndSecondArrays)).toBe(true);// By combining Arrays, you create a new Array
    expect(firstAndSecondArrays[1][0]).toBe("StringThree");//You can access any index of the composed array
  });
  it('Arrays can hold undefined values ', function () {
    var arrayOfStrings = ["StringZero" , "StringOne" , "StringTwo"];
    arrayOfStrings[1] = undefined; //to make a cell empty. we can use the keyword 'undefined', which means 'NO CONTENTS'
    expect(arrayOfStrings[1]).toBeUndefined();
    expect(arrayOfStrings.length).toBe(3);//The array length does not change when some of the values are undefined
  });
  it('Arrays can be created with no values ', function () {
    var arrayOfStrings = [];
    expect(Array.isArray(arrayOfStrings)).toBe(true);
    //When you access an index of the array, but you haven't assigned a value, the array returns 'undefined'
    expect(arrayOfStrings[1]).toBeUndefined();
    expect(arrayOfStrings.length).toBe(0);
  });
});
<|endoftext|>


<commit_before>describe("M_bkNotebookCellModelManager", function() {
    function CodeCell (id) {
        this.type = "code";
        this.id = id;
    };
    function SectionCell (id, level) {
        this.type = "section";
        this.id = id;
        this.level = level; // for level, root is 0, h1 is 1, h2 is 2
    };
    var code01 = new CodeCell("code01");
    var code02 = new CodeCell("code02");
    var code03 = new CodeCell("code03");
    var code04 = new CodeCell("code04");
    var code05 = new CodeCell("code05");
    var code06 = new CodeCell("code06");
    var code07 = new CodeCell("code07");
    var code08 = new CodeCell("code08");
    var code09 = new CodeCell("code09");
    var code10 = new CodeCell("code10");
    var sect01 = new SectionCell("sect01", 2);
    var sect02 = new SectionCell("sect02", 1);
    var sect03 = new SectionCell("sect03", 2);
    var sect04 = new SectionCell("sect04", 3);
    var sect05 = new SectionCell("sect05", 2);
    var sect06 = new SectionCell("sect06", 3);
    var sect07 = new SectionCell("sect07", 2);
    var sect08 = new SectionCell("sect08", 1);
    var sect09 = new SectionCell("sect09", 3);
    var sect10 = new SectionCell("sect10", 2);

    var bkNotebookCellModelManager;
    beforeEach(module("M_bkNotebookCellModelManager"));
    beforeEach(inject(function (_bkNotebookCellModelManager_) {
        bkNotebookCellModelManager = _bkNotebookCellModelManager_;
    }));
    describe("bkNotebookCellModelManager", function () {
        it("should construct the tree from cells", function () {
            bkNotebookCellModelManager.reset([
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06 // h3
            ]);
            var theTree = bkNotebookCellModelManager._getTagMap();

            expect(theTree["root"].children).toEqual(["sect02"]);
            expect(theTree["code04"].children).toEqual([]);
            expect(theTree["sect03"].children).toEqual(["code05", "sect04"]);
            expect(theTree["sect04"].children).toEqual(["code06"]);
            expect(theTree["sect05"].children).toEqual(["sect06"]);
        });
        it("should get a cell from id", function () {
            bkNotebookCellModelManager.reset([code01]);
            expect(bkNotebookCellModelManager.getCell("code01")).toBe(code01);
        });
        it("should get a cell from index", function () {
            bkNotebookCellModelManager.reset([code01]);
            expect(bkNotebookCellModelManager.getCellAtIndex(0)).toBe(code01);
            expect(bkNotebookCellModelManager.getCellAtIndex(-1)).toBe(undefined);
        });
        it("should get the type of a cell", function () {
            bkNotebookCellModelManager.reset([code01]);
            expect(bkNotebookCellModelManager.getCellType("code01")).toBe("code");
        });
        it("should get the index of a cell in cells list", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03]);
            expect(bkNotebookCellModelManager.getIndex("code01")).toBe(0);
            expect(bkNotebookCellModelManager.getIndex("code02")).toBe(1);
            expect(bkNotebookCellModelManager.getIndex("code03")).toBe(2);
        });
        it("should get the parent of a cell", function () {
            var cells = [
                code01,
                sect01, // h2
                    code02,
                    code03,
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06, // h3
                    sect07, // h2
                        code07,
                sect08, // h1
                    sect09, //h3
                    sect10, //h2
                        code08,
                        code09
            ];
            bkNotebookCellModelManager.reset(cells);
            expect(bkNotebookCellModelManager.getParent("code01")).toBeUndefined();
            expect(bkNotebookCellModelManager.getParent("code02")).toBe(sect01);
            expect(bkNotebookCellModelManager.getParent("code06")).toBe(sect04);
        });
        it("should get children of a cell", function () {
            var cells = [
                code01,
                sect01, // h2
                    code02,
                    code03,
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06, // h3
                    sect07, // h2
                        code07,
                sect08, // h1
                    sect09, //h3
                    sect10, //h2
                        code08,
                        code09
            ];
            bkNotebookCellModelManager.reset(cells);
            expect(bkNotebookCellModelManager.getChildren("code01")).toEqual([]);
            expect(bkNotebookCellModelManager.getChildren("sect01")).toEqual([code02, code03]);
            expect(bkNotebookCellModelManager.getChildren("sect05")).toEqual([sect06]);
            expect(bkNotebookCellModelManager.getChildren("sect02")).toEqual([code04, sect03, sect05, sect07]);
            expect(bkNotebookCellModelManager.getChildren("sect08")).toEqual([sect09, sect10]);
        });
        it("should get all descendants of a cell", function () {
            var cells = [
                code01,
                sect01, // h2
                    code02,
                    code03,
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06, // h3
                    sect07, // h2
                        code07,
                sect08, // h1
                    sect09, //h3
                    sect10, //h2
                        code08,
                        code09
            ];
            bkNotebookCellModelManager.reset(cells);
            expect(bkNotebookCellModelManager.getAllDescendants("code01")).toEqual([]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect01")).toEqual([code02, code03]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect05")).toEqual([sect06]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect02")).toEqual([code04, sect03, code05, sect04, code06, sect05, sect06, sect07, code07]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect08")).toEqual([sect09, sect10, code08, code09]);
        });
        it("should delete cell", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03, code04]);
            bkNotebookCellModelManager.delete("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code03, code04]);
            bkNotebookCellModelManager.delete("code01");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code03, code04]);
            bkNotebookCellModelManager.delete("code04");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code03]);
            bkNotebookCellModelManager.delete("code05");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code03]);
        });
        it("should insert cell - before", function () {
            bkNotebookCellModelManager.reset([code01, code03]);
            bkNotebookCellModelManager.insertBefore("code03", code02);
            bkNotebookCellModelManager.insertBefore("code01", code04);
            expect(bkNotebookCellModelManager.getCells()).toEqual([code04, code01, code02, code03]);

            expect(function () { bkNotebookCellModelManager.insertBefore("code00", code04) })
                .toThrow("target cell code00 was not found");
        });
        it("should insert cell - after", function () {
            bkNotebookCellModelManager.reset([code01, code03]);
            bkNotebookCellModelManager.insertAfter("code01", code02);
            bkNotebookCellModelManager.insertAfter("code03", code04);
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code02, code03, code04]);

            expect(function () { bkNotebookCellModelManager.insertAfter("code00", code04) })
                .toThrow("target cell code00 was not found");
        });
        it("should move a cell up", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03]);
            bkNotebookCellModelManager.moveUp("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code02, code01, code03]);
            bkNotebookCellModelManager.moveUp("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code02, code01, code03]);
        });
        it("should move a cell down", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03]);
            bkNotebookCellModelManager.moveDown("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code03, code02]);
            bkNotebookCellModelManager.moveDown("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code03, code02]);
        });
        it("should delete a section", function () {
            bkNotebookCellModelManager.reset([
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06 // h3
            ]);
            expect(function () { bkNotebookCellModelManager.deleteSection("code04") })
                .toThrow("target cell code04 is not a section cell");
            bkNotebookCellModelManager.deleteSection("sect03");
            expect(bkNotebookCellModelManager.getCells()).toEqual([sect02, code04, sect05, sect06]);
            bkNotebookCellModelManager.deleteSection("sect02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([]);
            expect(function () { bkNotebookCellModelManager.deleteSection("sect02") })
                .toThrow("target cell sect02 was not found");
        });
        it("should get code cells", function () {
            bkNotebookCellModelManager.reset([
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06 // h3
            ]);
            expect(bkNotebookCellModelManager.getAllCodeCells("sect02")).toEqual([code04, code05, code06]);
        })
    });
});<commit_msg>Minor<commit_after>describe("M_bkNotebookCellModelManager", function() {
    function CodeCell (id) {
        this.type = "code";
        this.id = id;
    };
    function SectionCell (id, level) {
        this.type = "section";
        this.id = id;
        this.level = level; // root is 0, h1 is 1, h2 is 2
    };
    var code01 = new CodeCell("code01");
    var code02 = new CodeCell("code02");
    var code03 = new CodeCell("code03");
    var code04 = new CodeCell("code04");
    var code05 = new CodeCell("code05");
    var code06 = new CodeCell("code06");
    var code07 = new CodeCell("code07");
    var code08 = new CodeCell("code08");
    var code09 = new CodeCell("code09");
    var code10 = new CodeCell("code10");
    var sect01 = new SectionCell("sect01", 2);
    var sect02 = new SectionCell("sect02", 1);
    var sect03 = new SectionCell("sect03", 2);
    var sect04 = new SectionCell("sect04", 3);
    var sect05 = new SectionCell("sect05", 2);
    var sect06 = new SectionCell("sect06", 3);
    var sect07 = new SectionCell("sect07", 2);
    var sect08 = new SectionCell("sect08", 1);
    var sect09 = new SectionCell("sect09", 3);
    var sect10 = new SectionCell("sect10", 2);

    var bkNotebookCellModelManager;
    beforeEach(module("M_bkNotebookCellModelManager"));
    beforeEach(inject(function (_bkNotebookCellModelManager_) {
        bkNotebookCellModelManager = _bkNotebookCellModelManager_;
    }));
    describe("bkNotebookCellModelManager", function () {
        it("should construct the tree from cells", function () {
            bkNotebookCellModelManager.reset([
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06 // h3
            ]);
            var theTree = bkNotebookCellModelManager._getTagMap();

            expect(theTree["root"].children).toEqual(["sect02"]);
            expect(theTree["code04"].children).toEqual([]);
            expect(theTree["sect03"].children).toEqual(["code05", "sect04"]);
            expect(theTree["sect04"].children).toEqual(["code06"]);
            expect(theTree["sect05"].children).toEqual(["sect06"]);
        });
        it("should get a cell from id", function () {
            bkNotebookCellModelManager.reset([code01]);
            expect(bkNotebookCellModelManager.getCell("code01")).toBe(code01);
        });
        it("should get a cell from index", function () {
            bkNotebookCellModelManager.reset([code01]);
            expect(bkNotebookCellModelManager.getCellAtIndex(0)).toBe(code01);
            expect(bkNotebookCellModelManager.getCellAtIndex(-1)).toBe(undefined);
        });
        it("should get the type of a cell", function () {
            bkNotebookCellModelManager.reset([code01]);
            expect(bkNotebookCellModelManager.getCellType("code01")).toBe("code");
        });
        it("should get the index of a cell in cells list", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03]);
            expect(bkNotebookCellModelManager.getIndex("code01")).toBe(0);
            expect(bkNotebookCellModelManager.getIndex("code02")).toBe(1);
            expect(bkNotebookCellModelManager.getIndex("code03")).toBe(2);
        });
        it("should get the parent of a cell", function () {
            var cells = [
                code01,
                sect01, // h2
                    code02,
                    code03,
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06, // h3
                    sect07, // h2
                        code07,
                sect08, // h1
                    sect09, //h3
                    sect10, //h2
                        code08,
                        code09
            ];
            bkNotebookCellModelManager.reset(cells);
            expect(bkNotebookCellModelManager.getParent("code01")).toBeUndefined();
            expect(bkNotebookCellModelManager.getParent("code02")).toBe(sect01);
            expect(bkNotebookCellModelManager.getParent("code06")).toBe(sect04);
        });
        it("should get children of a cell", function () {
            var cells = [
                code01,
                sect01, // h2
                    code02,
                    code03,
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06, // h3
                    sect07, // h2
                        code07,
                sect08, // h1
                    sect09, //h3
                    sect10, //h2
                        code08,
                        code09
            ];
            bkNotebookCellModelManager.reset(cells);
            expect(bkNotebookCellModelManager.getChildren("code01")).toEqual([]);
            expect(bkNotebookCellModelManager.getChildren("sect01")).toEqual([code02, code03]);
            expect(bkNotebookCellModelManager.getChildren("sect05")).toEqual([sect06]);
            expect(bkNotebookCellModelManager.getChildren("sect02")).toEqual([code04, sect03, sect05, sect07]);
            expect(bkNotebookCellModelManager.getChildren("sect08")).toEqual([sect09, sect10]);
        });
        it("should get all descendants of a cell", function () {
            var cells = [
                code01,
                sect01, // h2
                    code02,
                    code03,
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06, // h3
                    sect07, // h2
                        code07,
                sect08, // h1
                    sect09, //h3
                    sect10, //h2
                        code08,
                        code09
            ];
            bkNotebookCellModelManager.reset(cells);
            expect(bkNotebookCellModelManager.getAllDescendants("code01")).toEqual([]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect01")).toEqual([code02, code03]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect05")).toEqual([sect06]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect02")).toEqual([code04, sect03, code05, sect04, code06, sect05, sect06, sect07, code07]);
            expect(bkNotebookCellModelManager.getAllDescendants("sect08")).toEqual([sect09, sect10, code08, code09]);
        });
        it("should delete cell", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03, code04]);
            bkNotebookCellModelManager.delete("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code03, code04]);
            bkNotebookCellModelManager.delete("code01");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code03, code04]);
            bkNotebookCellModelManager.delete("code04");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code03]);
            bkNotebookCellModelManager.delete("code05");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code03]);
        });
        it("should insert cell - before", function () {
            bkNotebookCellModelManager.reset([code01, code03]);
            bkNotebookCellModelManager.insertBefore("code03", code02);
            bkNotebookCellModelManager.insertBefore("code01", code04);
            expect(bkNotebookCellModelManager.getCells()).toEqual([code04, code01, code02, code03]);

            expect(function () { bkNotebookCellModelManager.insertBefore("code00", code04) })
                .toThrow("target cell code00 was not found");
        });
        it("should insert cell - after", function () {
            bkNotebookCellModelManager.reset([code01, code03]);
            bkNotebookCellModelManager.insertAfter("code01", code02);
            bkNotebookCellModelManager.insertAfter("code03", code04);
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code02, code03, code04]);

            expect(function () { bkNotebookCellModelManager.insertAfter("code00", code04) })
                .toThrow("target cell code00 was not found");
        });
        it("should move a cell up", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03]);
            bkNotebookCellModelManager.moveUp("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code02, code01, code03]);
            bkNotebookCellModelManager.moveUp("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code02, code01, code03]);
        });
        it("should move a cell down", function () {
            bkNotebookCellModelManager.reset([code01, code02, code03]);
            bkNotebookCellModelManager.moveDown("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code03, code02]);
            bkNotebookCellModelManager.moveDown("code02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([code01, code03, code02]);
        });
        it("should delete a section", function () {
            bkNotebookCellModelManager.reset([
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06 // h3
            ]);
            expect(function () { bkNotebookCellModelManager.deleteSection("code04") })
                .toThrow("target cell code04 is not a section cell");
            bkNotebookCellModelManager.deleteSection("sect03");
            expect(bkNotebookCellModelManager.getCells()).toEqual([sect02, code04, sect05, sect06]);
            bkNotebookCellModelManager.deleteSection("sect02");
            expect(bkNotebookCellModelManager.getCells()).toEqual([]);
            expect(function () { bkNotebookCellModelManager.deleteSection("sect02") })
                .toThrow("target cell sect02 was not found");
        });
        it("should get code cells", function () {
            bkNotebookCellModelManager.reset([
                sect02, // h1
                    code04,
                    sect03, // h2
                        code05,
                        sect04, // h3
                            code06,
                    sect05, // h2
                        sect06 // h3
            ]);
            expect(bkNotebookCellModelManager.getAllCodeCells("sect02")).toEqual([code04, code05, code06]);
        })
    });
});<|endoftext|>


<commit_before>"use strict";

var _ = require('lodash'),
    App = require('../app'),
    router = require('../router').router,
    views = require('./views'),
    modelingModels = require('../modeling/models.js'),
    modelingControls = require('../modeling/controls');

var CompareController = {
    compare: function(projectId) {
        var first = null,
            aoi_census = null;

        if (App.currentProject) {
            first = App.currentProject.get('scenarios').first();
            if (first) {
                aoi_census = first.get('aoi_census');
            }

            setupProjectCopy(aoi_census);
            addForestCoverScenario(aoi_census);
            showCompareWindow();
        } else if (projectId) {
            App.currentProject = new modelingModels.ProjectModel({
                id: projectId
            });

            first = App.currentProject.get('scenarios').first();
            if (first) {
                aoi_census = first.get('aoi_census');
            }

            App.currentProject
                .fetch()
                .done(function() {
                    setupProjectCopy(aoi_census);
                    addForestCoverScenario(aoi_census);
                    showCompareWindow();
                });
        }
        // else -- this case is caught by the backend and raises a 404

    },

    compareCleanUp: function() {
        App.user.off('change:guest', saveAfterLogin);
        App.origProject.off('change:id', updateUrl);

        // Switch back to the origProject so any changes are discarded.
        App.currentProject.off();
        App.currentProject = App.origProject;
        if (!App.map.get('areaOfInterest')) {
            App.map.set('areaOfInterest', App.currentProject.get('area_of_interest'));
        }

        App.rootView.footerRegion.empty();
    }
};

function setupProjectCopy(aoi_census) {
    /*
    Create a copy of the project so that:
      -Changes to the results and inputs are not saved to the server
      -Changes to the results and inputs are not present after hitting the back button (and project is unsaved).
       When the user is logged in as a guest, the only copy of the original inputs and results
       are in App.currentProject, and modifying these values in the compare views will result in those new
       values being back in the modeling views, which is not what we want.
      -The original project (without changes) is saved when logging in. If the user is a guest,
       goes into the compare views, and then logs in, the project should be saved with the inputs
       and results that were present before going to the compare views. This is to enforce the
       constraint that inputs and results entered in the compare views should never be saved.
       Without holding onto the original copies of these values, it's not possible to do this.
     */
    App.origProject = App.currentProject;
    App.currentProject = copyProject(App.origProject, aoi_census);

    App.user.on('change:guest', saveAfterLogin);
    App.origProject.on('change:id', updateUrl);
}

// Creates a special-purpose copy of the project
// for the compare views, since creating a true deep
// clone is more difficult and unnecessary.
function copyProject(project, aoi_census) {
    var scenariosCopy = new modelingModels.ScenariosCollection();
    project.get('scenarios').forEach(function(scenario) {
        var scenarioCopy = new modelingModels.ScenarioModel({});
        scenarioCopy.set({
            name: scenario.get('name'),
            is_current_conditions: scenario.get('is_current_conditions'),
            modifications: scenario.get('modifications'),
            modification_hash: scenario.get('modification_hash'),
            modification_censuses: scenario.get('modification_censuses'),
            results: new modelingModels.ResultCollection(scenario.get('results').toJSON()),
            inputs: new modelingModels.ModificationsCollection(scenario.get('inputs').toJSON()),
            inputmod_hash: scenario.get('inputmod_hash'),
            allow_save: false
        });
        if (aoi_census) {
            scenarioCopy.set('aoi_census', aoi_census);
        }
        scenarioCopy.get('inputs').on('add', _.debounce(_.bind(scenarioCopy.fetchResults, scenarioCopy), 500));
        scenariosCopy.add(scenarioCopy);
    });
    return new modelingModels.ProjectModel({
        name: App.origProject.get('name'),
        area_of_interest: App.origProject.get('area_of_interest'),
        model_package: App.origProject.get('model_package'),
        scenarios: scenariosCopy,
        allow_save: false
    });
}

// Adds special 100% Forest Cover Scenario for the Compare View
function addForestCoverScenario(aoi_census) {
    var project = App.currentProject,
        forestCoverScenario = new modelingModels.ScenarioModel({}),
        currentConditions = project.get('scenarios').findWhere({ is_current_conditions: true });

    forestCoverScenario.set({
        name: '100% Forest Cover',
        is_current_conditions: false,
        is_pre_columbian: true,
        modifications: currentConditions.get('modifications'),
        modification_hash: currentConditions.get('modification_hash'),
        results: new modelingModels.ResultCollection(currentConditions.get('results').toJSON()),
        inputs: new modelingModels.ModificationsCollection(currentConditions.get('inputs').toJSON()),
        inputmod_hash: currentConditions.get('inputmod_hash'),
        allow_save: false
    });
    if (aoi_census) {
        forestCoverScenario.set('aoi_census', aoi_census);
    }
    forestCoverScenario.get('inputs').on('add', _.debounce(_.bind(forestCoverScenario.fetchResults, forestCoverScenario), 500));
    project.get('scenarios').add(forestCoverScenario, { at: 0 });
}

function saveAfterLogin(user, guest) {
    if (!guest && App.origProject.isNew()) {
        var user_id = user.get('id');
        App.origProject.set('user_id', user_id);
        App.origProject.get('scenarios').each(function(scenario) {
            scenario.set('user_id', user_id);
        });
        // Save the origProject (as opposed to the currentProject)
        // to not include changes to inputs and results.
        App.origProject.saveProjectAndScenarios();
    }
}

function updateUrl() {
    // Use replace: true, so that the back button will work as expected.
    router.navigate(App.origProject.getCompareUrl(), { replace: true });
}

function showCompareWindow() {
    var compareWindow = new views.CompareWindow({
            model: App.currentProject
        });
    App.rootView.footerRegion.show(compareWindow);
}

module.exports = {
    CompareController: CompareController
};
<commit_msg>Remove 100% Forest Cover Column From Compare View<commit_after>"use strict";

var _ = require('lodash'),
    App = require('../app'),
    router = require('../router').router,
    views = require('./views'),
    modelingModels = require('../modeling/models.js'),
    modelingControls = require('../modeling/controls');

var CompareController = {
    compare: function(projectId) {
        var first = null,
            aoi_census = null;

        if (App.currentProject) {
            first = App.currentProject.get('scenarios').first();
            if (first) {
                aoi_census = first.get('aoi_census');
            }

            setupProjectCopy(aoi_census);
            showCompareWindow();
        } else if (projectId) {
            App.currentProject = new modelingModels.ProjectModel({
                id: projectId
            });

            first = App.currentProject.get('scenarios').first();
            if (first) {
                aoi_census = first.get('aoi_census');
            }

            App.currentProject
                .fetch()
                .done(function() {
                    setupProjectCopy(aoi_census);
                    showCompareWindow();
                });
        }
        // else -- this case is caught by the backend and raises a 404

    },

    compareCleanUp: function() {
        App.user.off('change:guest', saveAfterLogin);
        App.origProject.off('change:id', updateUrl);

        // Switch back to the origProject so any changes are discarded.
        App.currentProject.off();
        App.currentProject = App.origProject;
        if (!App.map.get('areaOfInterest')) {
            App.map.set('areaOfInterest', App.currentProject.get('area_of_interest'));
        }

        App.rootView.footerRegion.empty();
    }
};

function setupProjectCopy(aoi_census) {
    /*
    Create a copy of the project so that:
      -Changes to the results and inputs are not saved to the server
      -Changes to the results and inputs are not present after hitting the back button (and project is unsaved).
       When the user is logged in as a guest, the only copy of the original inputs and results
       are in App.currentProject, and modifying these values in the compare views will result in those new
       values being back in the modeling views, which is not what we want.
      -The original project (without changes) is saved when logging in. If the user is a guest,
       goes into the compare views, and then logs in, the project should be saved with the inputs
       and results that were present before going to the compare views. This is to enforce the
       constraint that inputs and results entered in the compare views should never be saved.
       Without holding onto the original copies of these values, it's not possible to do this.
     */
    App.origProject = App.currentProject;
    App.currentProject = copyProject(App.origProject, aoi_census);

    App.user.on('change:guest', saveAfterLogin);
    App.origProject.on('change:id', updateUrl);
}

// Creates a special-purpose copy of the project
// for the compare views, since creating a true deep
// clone is more difficult and unnecessary.
function copyProject(project, aoi_census) {
    var scenariosCopy = new modelingModels.ScenariosCollection();
    project.get('scenarios').forEach(function(scenario) {
        var scenarioCopy = new modelingModels.ScenarioModel({});
        scenarioCopy.set({
            name: scenario.get('name'),
            is_current_conditions: scenario.get('is_current_conditions'),
            modifications: scenario.get('modifications'),
            modification_hash: scenario.get('modification_hash'),
            modification_censuses: scenario.get('modification_censuses'),
            results: new modelingModels.ResultCollection(scenario.get('results').toJSON()),
            inputs: new modelingModels.ModificationsCollection(scenario.get('inputs').toJSON()),
            inputmod_hash: scenario.get('inputmod_hash'),
            allow_save: false
        });
        if (aoi_census) {
            scenarioCopy.set('aoi_census', aoi_census);
        }
        scenarioCopy.get('inputs').on('add', _.debounce(_.bind(scenarioCopy.fetchResults, scenarioCopy), 500));
        scenariosCopy.add(scenarioCopy);
    });
    return new modelingModels.ProjectModel({
        name: App.origProject.get('name'),
        area_of_interest: App.origProject.get('area_of_interest'),
        model_package: App.origProject.get('model_package'),
        scenarios: scenariosCopy,
        allow_save: false
    });
}

function saveAfterLogin(user, guest) {
    if (!guest && App.origProject.isNew()) {
        var user_id = user.get('id');
        App.origProject.set('user_id', user_id);
        App.origProject.get('scenarios').each(function(scenario) {
            scenario.set('user_id', user_id);
        });
        // Save the origProject (as opposed to the currentProject)
        // to not include changes to inputs and results.
        App.origProject.saveProjectAndScenarios();
    }
}

function updateUrl() {
    // Use replace: true, so that the back button will work as expected.
    router.navigate(App.origProject.getCompareUrl(), { replace: true });
}

function showCompareWindow() {
    var compareWindow = new views.CompareWindow({
            model: App.currentProject
        });
    App.rootView.footerRegion.show(compareWindow);
}

module.exports = {
    CompareController: CompareController
};
<|endoftext|>


<commit_before>const getPropertyValue = require('./utility').getPropertyValue;
const Cookies          = require('../../lib/js-cookie');

const isStorageSupported = function(storage) {
    if (typeof storage === 'undefined') {
        return false;
    }

    const testKey = 'test';
    try {
        storage.setItem(testKey, '1');
        storage.removeItem(testKey);
        return true;
    } catch (e) {
        return false;
    }
};

const Store = function(storage) {
    this.storage = storage;
};

Store.prototype = {
    get: function(key) {
        return this.storage.getItem(key) || undefined;
    },
    set: function(key, value) {
        if (typeof value !== 'undefined') {
            this.storage.setItem(key, value);
        }
    },
    remove: function(key) {
        this.storage.removeItem(key);
    },
    clear: function() {
        this.storage.clear();
    },
};

const InScriptStore = function(object) {
    this.store = typeof object !== 'undefined' ? object : {};
};

InScriptStore.prototype = {
    get: function(key) {
        return getPropertyValue(this.store, key);
    },
    set: function(key, value) {
        let obj = this.store;
        if (Array.isArray(key)) {
            key.forEach(function(k) {
                if (k in obj) obj = obj[k];
                else key = k;
            });
        }
        obj[key] = value;
    },
    remove: function(key)        { delete this.store[key]; },
    clear : function()           { this.store = {}; },
    has   : function(key)        { return this.get(key) !== undefined; },
    keys  : function()           { return Object.keys(this.store); },
};

const State = new InScriptStore();
State.set('response', {});

const CookieStorage = function (cookie_name, cookie_domain) {
    this.initialized = false;
    this.cookie_name = cookie_name;
    const hostname = window.location.hostname;
    this.domain = cookie_domain || (/\.binary\.com/i.test(hostname) ? '.' + hostname.split('.').slice(-2).join('.') : hostname);
    this.path = '/';
    this.expires = new Date('Thu, 1 Jan 2037 12:00:00 GMT');
    this.value = {};
};

CookieStorage.prototype = {
    read: function() {
        const cookie_value = Cookies.get(this.cookie_name);
        try {
            this.value = cookie_value ? JSON.parse(cookie_value) : {};
        } catch (e) {
            this.value = {};
        }
        this.initialized = true;
    },
    write: function(value, expireDate, isSecure) {
        if (!this.initialized) this.read();
        this.value = value;
        if (expireDate) this.expires = expireDate;
        Cookies.set(this.cookie_name, this.value, {
            expires: this.expires,
            path   : this.path,
            domain : this.domain,
            secure : !!isSecure,
        });
    },
    get: function(key) {
        if (!this.initialized) this.read();
        return this.value[key];
    },
    set: function(key, value) {
        if (!this.initialized) this.read();
        this.value[key] = value;
        Cookies.set(this.cookie_name, this.value, {
            expires: new Date(this.expires),
            path   : this.path,
            domain : this.domain,
        });
    },
    remove: function() {
        Cookies.remove(this.cookie_name, {
            path  : this.path,
            domain: this.domain,
        });
    },
};

let SessionStore,
    LocalStore;
if (typeof window !== 'undefined' && isStorageSupported(window.localStorage)) {
    LocalStore = new Store(window.localStorage);
}

if (typeof window !== 'undefined' && isStorageSupported(window.sessionStorage)) {
    if (!LocalStore) {
        LocalStore = new Store(window.sessionStorage);
    }
    SessionStore = new Store(window.sessionStorage);
}

if (!SessionStore || !LocalStore) {
    if (!LocalStore) {
        LocalStore = new InScriptStore();
    }
    if (!SessionStore) {
        SessionStore = new InScriptStore();
    }
}

module.exports = {
    isStorageSupported: isStorageSupported,
    Store             : Store,
    InScriptStore     : InScriptStore,
    CookieStorage     : CookieStorage,
    State             : State,
    SessionStore      : SessionStore,
    LocalStore        : LocalStore,
};
<commit_msg>update key correctly for overwriting values in store<commit_after>const getPropertyValue = require('./utility').getPropertyValue;
const objectNotEmpty   = require('./utility').objectNotEmpty;
const Cookies          = require('../../lib/js-cookie');

const isStorageSupported = function(storage) {
    if (typeof storage === 'undefined') {
        return false;
    }

    const testKey = 'test';
    try {
        storage.setItem(testKey, '1');
        storage.removeItem(testKey);
        return true;
    } catch (e) {
        return false;
    }
};

const Store = function(storage) {
    this.storage = storage;
};

Store.prototype = {
    get: function(key) {
        return this.storage.getItem(key) || undefined;
    },
    set: function(key, value) {
        if (typeof value !== 'undefined') {
            this.storage.setItem(key, value);
        }
    },
    remove: function(key) {
        this.storage.removeItem(key);
    },
    clear: function() {
        this.storage.clear();
    },
};

const InScriptStore = function(object) {
    this.store = typeof object !== 'undefined' ? object : {};
};

InScriptStore.prototype = {
    get: function(key) {
        return getPropertyValue(this.store, key);
    },
    set: function(key, value, obj = this.store) {
        if (!Array.isArray(key)) key = [key];
        if (key.length > 1) {
            if (!(key[0] in obj) || !objectNotEmpty(obj[key[0]])) obj[key[0]] = {};
            this.set(key.slice(1), value, obj[key[0]]);
        } else {
            obj[key[0]] = value;
        }
    },
    remove: function(key)        { delete this.store[key]; },
    clear : function()           { this.store = {}; },
    has   : function(key)        { return this.get(key) !== undefined; },
    keys  : function()           { return Object.keys(this.store); },
};

const State = new InScriptStore();
State.set('response', {});

const CookieStorage = function (cookie_name, cookie_domain) {
    this.initialized = false;
    this.cookie_name = cookie_name;
    const hostname = window.location.hostname;
    this.domain = cookie_domain || (/\.binary\.com/i.test(hostname) ? '.' + hostname.split('.').slice(-2).join('.') : hostname);
    this.path = '/';
    this.expires = new Date('Thu, 1 Jan 2037 12:00:00 GMT');
    this.value = {};
};

CookieStorage.prototype = {
    read: function() {
        const cookie_value = Cookies.get(this.cookie_name);
        try {
            this.value = cookie_value ? JSON.parse(cookie_value) : {};
        } catch (e) {
            this.value = {};
        }
        this.initialized = true;
    },
    write: function(value, expireDate, isSecure) {
        if (!this.initialized) this.read();
        this.value = value;
        if (expireDate) this.expires = expireDate;
        Cookies.set(this.cookie_name, this.value, {
            expires: this.expires,
            path   : this.path,
            domain : this.domain,
            secure : !!isSecure,
        });
    },
    get: function(key) {
        if (!this.initialized) this.read();
        return this.value[key];
    },
    set: function(key, value) {
        if (!this.initialized) this.read();
        this.value[key] = value;
        Cookies.set(this.cookie_name, this.value, {
            expires: new Date(this.expires),
            path   : this.path,
            domain : this.domain,
        });
    },
    remove: function() {
        Cookies.remove(this.cookie_name, {
            path  : this.path,
            domain: this.domain,
        });
    },
};

let SessionStore,
    LocalStore;
if (typeof window !== 'undefined' && isStorageSupported(window.localStorage)) {
    LocalStore = new Store(window.localStorage);
}

if (typeof window !== 'undefined' && isStorageSupported(window.sessionStorage)) {
    if (!LocalStore) {
        LocalStore = new Store(window.sessionStorage);
    }
    SessionStore = new Store(window.sessionStorage);
}

if (!SessionStore || !LocalStore) {
    if (!LocalStore) {
        LocalStore = new InScriptStore();
    }
    if (!SessionStore) {
        SessionStore = new InScriptStore();
    }
}

module.exports = {
    isStorageSupported: isStorageSupported,
    Store             : Store,
    InScriptStore     : InScriptStore,
    CookieStorage     : CookieStorage,
    State             : State,
    SessionStore      : SessionStore,
    LocalStore        : LocalStore,
};
<|endoftext|>


<commit_before>// @flow

import { Record } from 'immutable'

const props = (def: any) => {
  const p: TodosFilterModelSchema = {
    priority: 0,
    sortType: 0,
    order: 1,
    ...def
  }
  return p
}

export const TodosFilterModel = (def: any) => class extends Record(props(def)) {
  getPriority (): string {
    return this.get('priority')
  }
  getSortType (): string {
    return this.get('sortType')
  }
  getOrder (): string {
    return this.get('order')
  }
  getTodosFilterJS (): any {
    return this.toJS()
  }
  // setter

  restoreTodosFilter (src: any): TodosModel {
    if (src === null) return this
    return this.setPriority(src.priority).setSortType(src.sortType).setOrder(src.order)
  }
  setPriority (index: number): TodosModel {
    return this.set('priority', index)
  }
  setSortType (index: number): TodosViewModel {
    return this.set('sortType', index)
  }
  setOrder (order: number): TodosViewModel {
    return this.set('order', order)
  }
}
<commit_msg>fix lint error<commit_after>// @flow

import { Record } from 'immutable'

const props = (def: any) => {
  const p: TodosFilterModelSchema = {
    priority: 0,
    sortType: 0,
    order: 1,
    ...def
  }
  return p
}

export const TodosFilterModel = (def: any) => class extends Record(props(def)) {
  getPriority (): string {
    return this.get('priority')
  }
  getSortType (): string {
    return this.get('sortType')
  }
  getOrder (): string {
    return this.get('order')
  }
  getTodosFilterJS (): any {
    return this.toJS()
  }
  // setter

  restoreTodosFilter (src: any): TodosModel {
    if (src === null) return this
    return this.setPriority(src.priority).setSortType(src.sortType).setOrder(src.order)
  }
  setPriority (index: number): TodosModel {
    return this.set('priority', index)
  }
  setSortType (index: number): TodosViewModel {
    return this.set('sortType', index)
  }
  setOrder (order: number): TodosViewModel {
    return this.set('order', order)
  }
}
<|endoftext|>


<commit_before>import Util from "../helpers/Util";

// Default values for the config form editor
export const AppConfigFormDefaultValues = Util.deepFreeze({
  id: "",
  cmd: "",
  cpus: 1,
  mem: 128,
  disk: 0,
  instances: 1
});

// Default values for an 'empty' app config, or the JSON editor
export const AppConfigDefaultValues = Util.deepFreeze({
  id: null,
  cmd: null,
  cpus: 1,
  mem: 128,
  disk: 0,
  instances: 1
});

// Complete app configuration with default values
export const AllAppConfigDefaultValues = Util.deepFreeze(
  Object.assign({}, AppConfigDefaultValues, {
    args: null,
    env: {},
    executor: "",
    constraints: [],
    uris: [],
    fetch: [],
    storeUrls: [],
    requirePorts: false,
    backoffSeconds: 1,
    backoffFactor: 1.15,
    maxLaunchDelaySeconds: 3600,
    container: null,
    healthChecks: [],
    dependencies: [],
    upgradeStrategy: {
      minimumHealthCapacity: 1,
      maximumOverCapacity: 1
    },
    labels: {},
    acceptedResourceRoles: null,
    portDefinitions: [{
      "labels": {},
      "port": 0,
      "protocol": "tcp"
    }],
    readinessChecks: [],
    user: null,
    taskKillGracePeriodSeconds: null
  })
);
<commit_msg>Including "secrets" in known variables<commit_after>import Util from "../helpers/Util";

// Default values for the config form editor
export const AppConfigFormDefaultValues = Util.deepFreeze({
  id: "",
  cmd: "",
  cpus: 1,
  mem: 128,
  disk: 0,
  instances: 1
});

// Default values for an 'empty' app config, or the JSON editor
export const AppConfigDefaultValues = Util.deepFreeze({
  id: null,
  cmd: null,
  cpus: 1,
  mem: 128,
  disk: 0,
  instances: 1
});

// Complete app configuration with default values
export const AllAppConfigDefaultValues = Util.deepFreeze(
  Object.assign({}, AppConfigDefaultValues, {
    args: null,
    env: {},
    executor: "",
    constraints: [],
    uris: [],
    fetch: [],
    storeUrls: [],
    requirePorts: false,
    backoffSeconds: 1,
    backoffFactor: 1.15,
    maxLaunchDelaySeconds: 3600,
    container: null,
    healthChecks: [],
    dependencies: [],
    upgradeStrategy: {
      minimumHealthCapacity: 1,
      maximumOverCapacity: 1
    },
    labels: {},
    acceptedResourceRoles: null,
    portDefinitions: [{
      "labels": {},
      "port": 0,
      "protocol": "tcp"
    }],
    readinessChecks: [],
    user: null,
    taskKillGracePeriodSeconds: null,
    secrets: {}
  })
);
<|endoftext|>


<commit_before>/*
EditableController: attached to editable element
TODO: this file should be refactored to work more clear without closures!
*/
angular.module('xeditable').factory('editableController', ['$q', function($q) {

  //EditableController function
  EditableController.$inject = ['$scope', '$attrs', '$element', '$parse', 'editableThemes', 'editableOptions', '$rootScope', '$compile', '$q'];
  function EditableController($scope, $attrs, $element, $parse, editableThemes, editableOptions, $rootScope, $compile, $q) {
    var valueGetter;

    //if control is disabled - it does not participate in waiting process
    var inWaiting;

    var self = this;

    self.scope = $scope;
    self.elem = $element;
    self.attrs = $attrs;
    self.inputEl = null;
    self.editorEl = null;
    self.single = true;
    self.error = '';
    self.theme =  editableThemes[editableOptions.theme] || editableThemes['default'];
    self.parent = {};

    //to be overwritten
    self.inputTpl = '';
    self.directiveName = '';

    //init
    self.init = function(single) {
      self.single = single;

      self.name = $attrs.eName || $attrs[self.directiveName];
      /*
      if(!$attrs[directiveName] && !$attrs.eNgModel && ($attrs.eValue === undefined)) {
        throw 'You should provide value for `'+directiveName+'` or `e-value` in editable element!';
      }
      */
      if($attrs[self.directiveName]) {
        valueGetter = $parse($attrs[self.directiveName]);
      } else {
        throw 'You should provide value for `'+self.directiveName+'` in editable element!';
      }

      // hide buttons for non-single
      if (!self.single) {
        self.attrs.buttons = 'no';
      }

      //moved to show()
      //self.render();

      //if name defined --> watch changes and update $data in form
      if($attrs.eName) {
        self.scope.$watch('$data', function(newVal){
          self.scope.$form.$data[$attrs.eName] = newVal;
        });
      }

      //onshow
      if($attrs.onshow) {
        self.onshow = function() {
          return self.catchError($parse($attrs.onshow)($scope));
        };
      }

      //onbeforesave
      if ($attrs.onbeforesave) {
        self.onbeforesave = function() {
          return self.catchError($parse($attrs.onbeforesave)($scope));
        };
      }

      //onaftersave
      if ($attrs.onaftersave) {
        self.onaftersave = function() {
          return self.catchError($parse($attrs.onaftersave)($scope));
        };
      }

      // watch change of model to update editable element
      // now particulary add/remove `editable-empty` class
      $scope.$parent.$watch($attrs[self.directiveName], function(newVal, oldVal) {
        if (newVal !== oldVal) {
          self.handleEmpty();
        }
      });
      // handle initial value for empty
      self.handleEmpty();
    };

    self.render = function() {
      var theme = self.theme;

      //build input
      self.inputEl = angular.element(self.inputTpl);

      //build controls
      self.controlsEl = angular.element(theme.controlsTpl);
      self.controlsEl.append(self.inputEl);

      //build buttons
      if(self.attrs.buttons !== 'no') {
        self.buttonsEl = angular.element(theme.buttonsTpl);
        self.submitEl = angular.element(theme.submitTpl);
        self.cancelEl = angular.element(theme.cancelTpl);
        self.buttonsEl.append(self.submitEl).append(self.cancelEl);
        self.controlsEl.append(self.buttonsEl);

        self.inputEl.addClass('editable-has-buttons');
      }

      //build error
      self.errorEl = angular.element(theme.errorTpl);
      self.controlsEl.append(self.errorEl);

      //build editor
      self.editorEl = angular.element(self.single ? theme.formTpl : theme.noformTpl);
      self.editorEl.append(self.controlsEl);

      //transfer `e-*` attributes
      for(var k in $attrs.$attr) {
        if(k === 'eForm' || k === 'eNgSubmit') {
          continue;
        }
        if (k.substring(0, 1) === 'e' && k.substring(1, 2) === k.substring(1, 2).toUpperCase()) {
          //cut "e-"
          var v = $attrs.$attr[k].substring(2);
          //workaround for attributes without value (e.g. `multiple = "multiple"`)
          var attrValue = ($attrs[k] === '') ? v : $attrs[k];
          self.inputEl.attr(v, attrValue);
        }
      }

      self.inputEl.addClass('editable-input');

      self.inputEl.attr('ng-model', '$data');

      if(self.single) {
        self.editorEl.attr('editable-form', '$form');
      }

      //apply `postrender` method of theme
      if(angular.isFunction(theme.postrender)) {
        theme.postrender.call(self);
      }

    };

    //show
    self.show = function() {
      // set value
      self.scope.$data = angular.copy(valueGetter($scope.$parent));

      /*
      Originally render() was inside init() method, but some directives polluting editorEl,
      so it is broken on second openning.
      Cloning is not a solution as jqLite can not clone with event handler's.
      */
      self.render();

      // compile and insert into DOM (compile needed to attach ng-* events from markup)
      $element.after($compile(self.editorEl)($scope));

      // attach listeners (`escape`, autosubmit, etc)
      self.addListeners();

      // hide element
      $element.addClass('editable-hide');

      //onshow
      return self.onshow();
    };

    //hide
    self.hide = function() {
      //console.log('editable hide', self.name);
      self.editorEl.remove();
      $element.removeClass('editable-hide');
      // todo: to think is it really needed or not
      /*
      if($element[0].tagName === 'A') {
        $element[0].focus();
      }
      */
    };

    /*
    Called after show to attach listeners
    */
    self.addListeners = function() {
      //bind keyup
      self.inputEl.bind('keyup', function(e) {
          if(!self.single) {
            return;
          }

          switch(e.keyCode) {
            // hide on `escape` press
            case 27:
              self.scope.$form.$hide();
            break;
          }
      });

      //autosubmit when no buttons
      if (self.single && self.attrs.buttons === 'no') {
        self.autosubmit();
      }
    };

    //setWaiting
    self.setWaiting = function(value) {
      if (value) {
        //participate in waiting only if not disabled
        inWaiting = !self.inputEl.attr('disabled');
        if (inWaiting) {
          self.inputEl.attr('disabled', 'disabled');
          if(self.buttonsEl) {
            self.buttonsEl.find('button').attr('disabled', 'disabled');
          }
        }
      } else {
        if (inWaiting) {
          self.inputEl.removeAttr('disabled');
          if (self.buttonsEl) {
            self.buttonsEl.find('button').removeAttr('disabled');
          }
        }
      }
    };

    self.activate = function() {
      setTimeout(function() {
        self.inputEl[0].focus();
      }, 0);
    };

    self.setError = function(msg) {
      if(!angular.isObject(msg)) {
        $scope.$error = msg;
        self.error = msg;
      }
    };

    /*
    Checks that result is string or promise returned string and shows it as error message
    Applied to onshow, onbeforesave, onaftersave
    */
    self.catchError = function(result, noPromise) {
      if (angular.isObject(result) && noPromise !== true) {
        $q.when(result).then(
          //success and fail handlers are equal
          angular.bind(this, function(r) {
            this.catchError(r, true);
          }),
          angular.bind(this, function(r) {
            this.catchError(r, true);
          })
        );
      //check $http error
      } else if (noPromise && angular.isObject(result) && result.status &&
        (result.status !== 200) && result.data && angular.isString(result.data)) {
        this.setError(result.data);
        //set result to string: to let form know that there was error
        result = result.data;
      } else if (angular.isString(result)) {
        this.setError(result);
      }
      return result;
    };

    self.save = function() {
      valueGetter.assign($scope.$parent, angular.copy(self.scope.$data));

      // no need to call handleEmpty here as we are watching change of model value
      // self.handleEmpty();
    };

    /*
    attach/detach `editable-empty` class to element
    */
    self.handleEmpty = function() {
      var val = valueGetter($scope.$parent);
      var isEmpty = val === null || val === undefined || val === "" || (angular.isArray(val) && val.length === 0);
      $element.toggleClass('editable-empty', isEmpty);
    };

    /*
    Called when `buttons = "no"` to submit automatically
    */
    self.autosubmit = angular.noop;

    self.onshow = angular.noop;
    self.onbeforesave = angular.noop;
    self.onaftersave = angular.noop;
  }

  return EditableController;
}]);
<commit_msg>simplify watch of model<commit_after>/*
EditableController: attached to editable element
TODO: this file should be refactored to work more clear without closures!
*/
angular.module('xeditable').factory('editableController', ['$q', function($q) {

  //EditableController function
  EditableController.$inject = ['$scope', '$attrs', '$element', '$parse', 'editableThemes', 'editableOptions', '$rootScope', '$compile', '$q'];
  function EditableController($scope, $attrs, $element, $parse, editableThemes, editableOptions, $rootScope, $compile, $q) {
    var valueGetter;

    //if control is disabled - it does not participate in waiting process
    var inWaiting;

    var self = this;

    self.scope = $scope;
    self.elem = $element;
    self.attrs = $attrs;
    self.inputEl = null;
    self.editorEl = null;
    self.single = true;
    self.error = '';
    self.theme =  editableThemes[editableOptions.theme] || editableThemes['default'];
    self.parent = {};

    //to be overwritten
    self.inputTpl = '';
    self.directiveName = '';

    //init
    self.init = function(single) {
      self.single = single;

      self.name = $attrs.eName || $attrs[self.directiveName];
      /*
      if(!$attrs[directiveName] && !$attrs.eNgModel && ($attrs.eValue === undefined)) {
        throw 'You should provide value for `'+directiveName+'` or `e-value` in editable element!';
      }
      */
      if($attrs[self.directiveName]) {
        valueGetter = $parse($attrs[self.directiveName]);
      } else {
        throw 'You should provide value for `'+self.directiveName+'` in editable element!';
      }

      // hide buttons for non-single
      if (!self.single) {
        self.attrs.buttons = 'no';
      }

      //moved to show()
      //self.render();

      //if name defined --> watch changes and update $data in form
      if($attrs.eName) {
        self.scope.$watch('$data', function(newVal){
          self.scope.$form.$data[$attrs.eName] = newVal;
        });
      }

      //onshow
      if($attrs.onshow) {
        self.onshow = function() {
          return self.catchError($parse($attrs.onshow)($scope));
        };
      }

      //onbeforesave
      if ($attrs.onbeforesave) {
        self.onbeforesave = function() {
          return self.catchError($parse($attrs.onbeforesave)($scope));
        };
      }

      //onaftersave
      if ($attrs.onaftersave) {
        self.onaftersave = function() {
          return self.catchError($parse($attrs.onaftersave)($scope));
        };
      }

      // watch change of model to update editable element
      // now only add/remove `editable-empty` class.
      // Initially this method called with newVal = undefined, oldVal = undefined
      // so no need initially call handleEmpty() explicitly
      $scope.$parent.$watch($attrs[self.directiveName], function(newVal, oldVal) {
        self.handleEmpty();
      });
    };

    self.render = function() {
      var theme = self.theme;

      //build input
      self.inputEl = angular.element(self.inputTpl);

      //build controls
      self.controlsEl = angular.element(theme.controlsTpl);
      self.controlsEl.append(self.inputEl);

      //build buttons
      if(self.attrs.buttons !== 'no') {
        self.buttonsEl = angular.element(theme.buttonsTpl);
        self.submitEl = angular.element(theme.submitTpl);
        self.cancelEl = angular.element(theme.cancelTpl);
        self.buttonsEl.append(self.submitEl).append(self.cancelEl);
        self.controlsEl.append(self.buttonsEl);

        self.inputEl.addClass('editable-has-buttons');
      }

      //build error
      self.errorEl = angular.element(theme.errorTpl);
      self.controlsEl.append(self.errorEl);

      //build editor
      self.editorEl = angular.element(self.single ? theme.formTpl : theme.noformTpl);
      self.editorEl.append(self.controlsEl);

      //transfer `e-*` attributes
      for(var k in $attrs.$attr) {
        if(k === 'eForm' || k === 'eNgSubmit') {
          continue;
        }
        if (k.substring(0, 1) === 'e' && k.substring(1, 2) === k.substring(1, 2).toUpperCase()) {
          //cut "e-"
          var v = $attrs.$attr[k].substring(2);
          //workaround for attributes without value (e.g. `multiple = "multiple"`)
          var attrValue = ($attrs[k] === '') ? v : $attrs[k];
          self.inputEl.attr(v, attrValue);
        }
      }

      self.inputEl.addClass('editable-input');

      self.inputEl.attr('ng-model', '$data');

      if(self.single) {
        self.editorEl.attr('editable-form', '$form');
      }

      //apply `postrender` method of theme
      if(angular.isFunction(theme.postrender)) {
        theme.postrender.call(self);
      }

    };

    //show
    self.show = function() {
      // set value
      self.scope.$data = angular.copy(valueGetter($scope.$parent));

      /*
      Originally render() was inside init() method, but some directives polluting editorEl,
      so it is broken on second openning.
      Cloning is not a solution as jqLite can not clone with event handler's.
      */
      self.render();

      // compile and insert into DOM (compile needed to attach ng-* events from markup)
      $element.after($compile(self.editorEl)($scope));

      // attach listeners (`escape`, autosubmit, etc)
      self.addListeners();

      // hide element
      $element.addClass('editable-hide');

      //onshow
      return self.onshow();
    };

    //hide
    self.hide = function() {
      //console.log('editable hide', self.name);
      self.editorEl.remove();
      $element.removeClass('editable-hide');
      // todo: to think is it really needed or not
      /*
      if($element[0].tagName === 'A') {
        $element[0].focus();
      }
      */
    };

    /*
    Called after show to attach listeners
    */
    self.addListeners = function() {
      //bind keyup
      self.inputEl.bind('keyup', function(e) {
          if(!self.single) {
            return;
          }

          switch(e.keyCode) {
            // hide on `escape` press
            case 27:
              self.scope.$form.$hide();
            break;
          }
      });

      //autosubmit when no buttons
      if (self.single && self.attrs.buttons === 'no') {
        self.autosubmit();
      }
    };

    //setWaiting
    self.setWaiting = function(value) {
      if (value) {
        //participate in waiting only if not disabled
        inWaiting = !self.inputEl.attr('disabled');
        if (inWaiting) {
          self.inputEl.attr('disabled', 'disabled');
          if(self.buttonsEl) {
            self.buttonsEl.find('button').attr('disabled', 'disabled');
          }
        }
      } else {
        if (inWaiting) {
          self.inputEl.removeAttr('disabled');
          if (self.buttonsEl) {
            self.buttonsEl.find('button').removeAttr('disabled');
          }
        }
      }
    };

    self.activate = function() {
      setTimeout(function() {
        self.inputEl[0].focus();
      }, 0);
    };

    self.setError = function(msg) {
      if(!angular.isObject(msg)) {
        $scope.$error = msg;
        self.error = msg;
      }
    };

    /*
    Checks that result is string or promise returned string and shows it as error message
    Applied to onshow, onbeforesave, onaftersave
    */
    self.catchError = function(result, noPromise) {
      if (angular.isObject(result) && noPromise !== true) {
        $q.when(result).then(
          //success and fail handlers are equal
          angular.bind(this, function(r) {
            this.catchError(r, true);
          }),
          angular.bind(this, function(r) {
            this.catchError(r, true);
          })
        );
      //check $http error
      } else if (noPromise && angular.isObject(result) && result.status &&
        (result.status !== 200) && result.data && angular.isString(result.data)) {
        this.setError(result.data);
        //set result to string: to let form know that there was error
        result = result.data;
      } else if (angular.isString(result)) {
        this.setError(result);
      }
      return result;
    };

    self.save = function() {
      valueGetter.assign($scope.$parent, angular.copy(self.scope.$data));

      // no need to call handleEmpty here as we are watching change of model value
      // self.handleEmpty();
    };

    /*
    attach/detach `editable-empty` class to element
    */
    self.handleEmpty = function() {
      var val = valueGetter($scope.$parent);
      var isEmpty = val === null || val === undefined || val === "" || (angular.isArray(val) && val.length === 0);
      $element.toggleClass('editable-empty', isEmpty);
    };

    /*
    Called when `buttons = "no"` to submit automatically
    */
    self.autosubmit = angular.noop;

    self.onshow = angular.noop;
    self.onbeforesave = angular.noop;
    self.onaftersave = angular.noop;
  }

  return EditableController;
}]);
<|endoftext|>


<commit_before>'use strict';

var Eventbus = (function () {
    var eventbus;

    function Eventbus() {
        eventbus = {};
    }

    /*
    * TODO Take subsscibe ID for multiple subscribing
    * */
    Eventbus.prototype.subscribe = function (event, callback) {
        if (arguments.length === 2) {
            var event = arguments[0];
            var callback = arguments[1];

            return _fillSubscribers(event, callback);

        } else if (arguments.length === 1) {
            var subscriberList = arguments[0];

            var _subscribers = [];

            subscriberList.forEach(function (subscriber) {
                var event = subscriber.event;
                var listener = subscriber.listener;

                _subscribers.push(_fillSubscribers(event, listener));
            });

            return _subscribers;
        } else {
            throw 'Error : Event parameter can not be null.'
        }
    };

    /*
    * TODO 1 : Trigger order of events(round robin algorithm ? Order or weight properties?)
    * */

    // Eventbus.prototype.;

    function _publish() {
        if (arguments.length === 2) {
            var event = arguments[0];
            var state = arguments[1];

            _fillPublishers(event, state);

        } else if (arguments.length === 1) {
            var publisherList = arguments[0];

            publisherList.forEach(function (publisher) {
                var event = publisher.event;
                var state = publisher.state;

                _fillPublishers(event, state);
            });

        } else {
            throw 'Error : Event parameter can not be null.'
        }
    }

    Eventbus.prototype.listen = function () {
        return _listenEventbus();
    };

    Eventbus.prototype.fire = function () {
        if (!arguments.length) {
            for (var i in eventbus) {
                var event = eventbus[i];

                event.callbacks.forEach(function (callback) {
                    callback(event.state === undefined ? {} : event.state);
                });
            }

            return;
        }

        var event = arguments[0];
        var eventState = _listenEventbus()[event].state;
        var callBacks = _listenEventbus()[event].callbacks;

        callBacks.forEach(function (callback) {
            callback(eventState === undefined ? {} : eventState)
        })
    };

    Eventbus.prototype.mute = function () {
        if (!arguments.length) {
            for (var i in eventbus) {
                var event = eventbus[i];

                event.callbacks = [];
            }
        }
    };

    Eventbus.prototype.clean = function () {
        eventbus = {};
    };

    Eventbus.prototype.publisher = {
        register: _publish
    };

    Eventbus.prototype.subscriber = {
        register: function () {
            console.log('registered subcriber');
        }
    };

    function _fillPublishers(event, state) {
        if (!eventbus.hasOwnProperty(event)) {
            eventbus[event] = {};
        }

        eventbus[event].state = state;

        if (eventbus[event].callbacks === undefined) {
            eventbus[event].callbacks = [];
            return;
        }

        eventbus[event].callbacks.forEach(function (callback) {
            callback(state === undefined ? {} : state);
        });
    }

    function _fillSubscribers(event, callback) {
        if (!eventbus.hasOwnProperty(event)) {
            throw 'Event is not defined.';
        }

        var eventIndex = eventbus[event].callbacks.push(callback) - 1;

        eventbus[event].callbacks[eventIndex](eventbus[event].state);

        return {
            unsubscribe: function () {
                eventbus[event]['callbacks'].splice(eventIndex, 1);
            }
        };
    }

    function _listenEventbus() {
        return eventbus;
    }

    return Eventbus;
})();

var Publisher = (function () {
    var _event;
    var _state;

    function Publisher(event, state) {
        _event = event || null;
        _state = state || null;
    }

    Publisher.prototype.event = function () {
        if (arguments.length) {
            _event = arguments[0];
        }

        return _event;
    };

    Publisher.prototype.state = function () {
        if (arguments[0] instanceof Object) {
            _state = arguments[0];
        } else if (arguments[0] === undefined) {
            return _state;
        }
    };

    return Publisher;
})();

var Subscriber = (function () {
    var _event;
    var _callback;

    function Subscriber(event, callback) {
        _event = event || null;

        if (callback instanceof Function) {
            _callback = callback || null;
        } else {
            throw 'Contructor should take a callback function.'
        }
    }

    Subscriber.prototype.event = function () {
        if (arguments.length) {
            _event = arguments[0];
        }

        return _event;
    };

    Subscriber.prototype.callback = function () {
        if (arguments[0] instanceof Function) {
            _callback = arguments[0];
        } else if (arguments[0] === undefined) {
            return _callback;
        }
    };

    return Subscriber;
})();<commit_msg>publish single and mult,ple publishers<commit_after>'use strict';

var Eventbus = (function () {
    var eventbus;

    function Eventbus() {
        eventbus = {};
    }

    /*
    * TODO Take subsscibe ID for multiple subscribing
    * */
    Eventbus.prototype.subscribe = function (event, callback) {
        if (arguments.length === 2) {
            var event = arguments[0];
            var callback = arguments[1];

            return _fillSubscribers(event, callback);

        } else if (arguments.length === 1) {
            var subscriberList = arguments[0];

            var _subscribers = [];

            subscriberList.forEach(function (subscriber) {
                var event = subscriber.event;
                var listener = subscriber.listener;

                _subscribers.push(_fillSubscribers(event, listener));
            });

            return _subscribers;
        } else {
            throw 'Error : Event parameter can not be null.'
        }
    };

    /*
    * TODO 1 : Trigger order of events(round robin algorithm ? Order or weight properties?)
    * */

    Eventbus.prototype.publisher = {
        register: _register,
        multipleRegister: _multipleRegister
        // register: function () {
        //     console.log('publisher was register')
        // }
    };

    Eventbus.prototype.subscriber = {
        register: function () {
            console.log('subscriber was register');
        }
    };

    function _register() {
        for (var i in arguments) {
            var publisher = arguments[i];

            var event = publisher.event();
            var state = publisher.state();

            _fillPublishers(event, state);
        }
    }

    function _multipleRegister() {

        // debugger;
        // var publishers = arguments[0];
        //
        // publishers.forEach(function (publisher) {
        //     var event = publisher.event();
        //     var state = publisher.state();
        //
        //     _fillPublishers(event, state);
        // });
    }

    Eventbus.prototype.listen = function () {
        return _listenEventbus();
    };

    Eventbus.prototype.fire = function () {
        if (!arguments.length) {
            for (var i in eventbus) {
                var event = eventbus[i];

                event.callbacks.forEach(function (callback) {
                    callback(event.state === undefined ? {} : event.state);
                });
            }

            return;
        }

        var event = arguments[0];
        var eventState = _listenEventbus()[event].state;
        var callBacks = _listenEventbus()[event].callbacks;

        callBacks.forEach(function (callback) {
            callback(eventState === undefined ? {} : eventState)
        })
    };

    Eventbus.prototype.mute = function () {
        if (!arguments.length) {
            for (var i in eventbus) {
                var event = eventbus[i];

                event.callbacks = [];
            }
        }
    };

    Eventbus.prototype.clean = function () {
        eventbus = {};
    };

    function _fillPublishers(event, state) {
        if (!eventbus.hasOwnProperty(event)) {
            eventbus[event] = {};
        }

        eventbus[event].state = state;

        if (eventbus[event].callbacks === undefined) {
            eventbus[event].callbacks = [];
            return;
        }

        eventbus[event].callbacks.forEach(function (callback) {
            callback(state === undefined ? {} : state);
        });
    }

    function _fillSubscribers(event, callback) {
        if (!eventbus.hasOwnProperty(event)) {
            throw 'Event is not defined.';
        }

        var eventIndex = eventbus[event].callbacks.push(callback) - 1;

        eventbus[event].callbacks[eventIndex](eventbus[event].state);

        return {
            unsubscribe: function () {
                eventbus[event]['callbacks'].splice(eventIndex, 1);
            }
        };
    }

    function _listenEventbus() {
        return eventbus;
    }

    return Eventbus;
})();

var Publisher = (function () {
    function Publisher(event, state) {
        this._event = event || null;
        this._state = state || null;
    }

    Publisher.prototype.event = function () {
        if (arguments.length) {
            this._event = arguments[0];
        }

        return this._event;
    };

    Publisher.prototype.state = function () {
        if (arguments[0] instanceof Object) {
            this._state = arguments[0];
        } else if (arguments[0] === undefined) {
            return this._state;
        }
    };

    Publisher.prototype.toString = function () {
        return "Event : " + this._event + " " + " State : " + this._state;
    };

    return Publisher;
})();

var Subscriber = (function () {
    function Subscriber(event, callback) {
        this._event = event || null;

        if (callback instanceof Function) {
            this._callback = callback || null;
        } else {
            throw 'Contructor should take a callback function.'
        }
    }

    Subscriber.prototype.event = function () {
        if (arguments.length) {
            this._event = arguments[0];
        }

        return this._event;
    };

    Subscriber.prototype.callback = function () {
        if (arguments[0] instanceof Function) {
            this._callback = arguments[0];
        } else if (arguments[0] === undefined) {
            return this._callback;
        }
    };

    return Subscriber;
})();<|endoftext|>


<commit_before>import React from 'react';
import { connect } from 'react-redux';

import { classNames } from '../utillities';
import config from '../config';
import actions from '../actions';
import BlockUser from '../components/components.block-user';

class ChatSettings extends React.Component {

  constructor(props) {
    super(props);

    this.state = {
      search: false,
      query: '',
      selectedUsers: [],
    };
  }

  componentWillMount() {
    if (!this.props.contactsState.receivedAt) {
      this.props.fetchContacts();
    }
  }

  render() {
    let groupName,
        participants,
        container,
        heading,
        icon,
        styles,
        input;

    groupName = this.props.groupName ? this.props.groupName : 'Group name';

    participants = renderParticipants(this.props);

    if (this.props.participants.length === 0) {
      heading = 'Tap on the right icon above to start adding participants.';
    } else {
      heading = 'Participants';
    }

    if (!!this.props.groupImage) {
      styles = { backgroundImage: `url(${ this.props.groupImage })` };
    } else {
      icon = (

      );
    }

    if (!!this.state.search) {
      input = (

            <button className="c-input-group__addon" onClick={ this.hideSearch.bind(this) }>

            </button>
            <input type="text"
              className="c-input-group__field"
              placeholder="Add participants"
              onKeyUp={ this.onKeyUp.bind(this) }
              ref={ input => this.participantsInput = input } />
            <button className="c-input-group__addon submit" onClick={ this.addParticipants.bind(this) }></button>

      );

      container = (
        this.getContacts().map((user, index) => {
          return (
            <BlockUser
              key={ index }
              id={ user.id}
              name={ user.firstName }
              description={ user.description }
              lastMessage={ user.lastMessage }
              image={ user.image }
              lastSeenAt={ user.lastSeenAt }
              lastMessageAt={ user.lastMessageAt }
              unreadMessagesCount={ user.unreadMessagesCount }
              isActive={ this.state.selectedUsers.indexOf(user) >= 0 }
              onClick={ () => this.toggleUserSelection(user) }
            />
          );
        })
      );
    } else {
      container = (

{ groupName }

            { icon }

{ heading }

          { participants }

      );
    }

    return (

                  <button className="sign-out" onClick={ this.leaveGroup.bind(this) }>

                    Leave group
                  </button>

                  <button onClick={ this.editGroupName.bind(this) }>

                  </button>

                  <button onClick={ this.addGroupImage.bind(this) }>

                  </button>

                  <button onClick={ this.showSearch.bind(this) }>

                  </button>

              { input }

          { container }

    );
  }

  onKeyUp() {
    this.setState({
      query: this.participantsInput.value,
    });
  }

  toggleUserSelection(user) {
    let selectedUsers = this.state.selectedUsers.slice();
    if ( selectedUsers.indexOf(user) >= 0 ) {
      selectedUsers.splice(selectedUsers.indexOf(user), 1);
    } else {
      selectedUsers.push(user);
    }
    this.setState({selectedUsers});
  }

  getContacts() {
    const contacts = this.props.contactsState.contacts;
    return Object.keys(contacts).map((id) => contacts[id]).filter((contact) => {
      let fullName = `${contact.firstName} ${contact.lastName}`;
      return (this.state.selectedUsers.indexOf(contact) >= 0) ||
        (fullName.toLowerCase().indexOf(this.state.query.toLowerCase()) >= 0);
    });
  }

  addParticipants() {
    let participantIds = this.state.selectedUsers.map((user) => user.id);
    this.props.update({'participants': participantIds});
    this.hideSearch();
  }

  leaveGroup() {
    console.info('Leave group chat.');
  }

  editGroupName() {
    this.props.update({'groupName': prompt('Group name')});
  }

  addGroupImage() {
    this.props.update({'groupImage': prompt('Group image')});
  }

  showSearch() {
    this.setState({
      search: true,
    });
  }

  hideSearch() {
    this.setState({
      search: false,
      query: '',
    });
  }
}

ChatSettings.propTypes = {
  groupName: React.PropTypes.string,
  groupImage: React.PropTypes.string,
  participants: React.PropTypes.array,
  update: React.PropTypes.func,
};

function renderParticipants(props) {
  if (props.participants.length > 0) {
    return props.participants.map(p => props.contactsState.contacts[p.id])
      .filter(x => x)
      .map((user, index) => (
      <BlockUser
        key={ index }
        name={ user.firstName }
        description={ user.description }
        imageSource={ user.imageSource }
        lastSeenDate={ user.lastSeenDate }
        openChat={ () => props.openChat(user.id) }
      />
    ));
  } else {
    return [];
  }
}

const mapStateToProps = (state, ownProps) => state[config.stateName];

const mapDispatchToProps = (dispatch, ownProps) => {
  return {
    fetchContacts: () => {
      dispatch(actions.contacts.fetchContacts());
    },
  };
};

const ChatSettingsConnect = connect(mapStateToProps, mapDispatchToProps)(ChatSettings);
export default ChatSettingsConnect;
<commit_msg>Remove current user from the list of potential contacts when selecting participants.<commit_after>import React from 'react';
import { connect } from 'react-redux';

import { classNames } from '../utillities';
import config from '../config';
import actions from '../actions';
import BlockUser from '../components/components.block-user';

class ChatSettings extends React.Component {

  constructor(props) {
    super(props);

    this.state = {
      search: false,
      query: '',
      selectedUsers: [],
    };
  }

  componentWillMount() {
    if (!this.props.contactsState.receivedAt) {
      this.props.fetchContacts();
    }
  }

  render() {
    let groupName,
        participants,
        container,
        heading,
        icon,
        styles,
        input;

    groupName = this.props.groupName ? this.props.groupName : 'Group name';

    participants = renderParticipants(this.props);

    if (this.props.participants.length === 0) {
      heading = 'Tap on the right icon above to start adding participants.';
    } else {
      heading = 'Participants';
    }

    if (!!this.props.groupImage) {
      styles = { backgroundImage: `url(${ this.props.groupImage })` };
    } else {
      icon = (

      );
    }

    if (!!this.state.search) {
      input = (

            <button className="c-input-group__addon" onClick={ this.hideSearch.bind(this) }>

            </button>
            <input type="text"
              className="c-input-group__field"
              placeholder="Add participants"
              onKeyUp={ this.onKeyUp.bind(this) }
              ref={ input => this.participantsInput = input } />
            <button className="c-input-group__addon submit" onClick={ this.addParticipants.bind(this) }></button>

      );

      container = (
        this.getContacts().map((user, index) => {
          return (
            <BlockUser
              key={ index }
              id={ user.id}
              name={ user.firstName }
              description={ user.description }
              lastMessage={ user.lastMessage }
              image={ user.image }
              lastSeenAt={ user.lastSeenAt }
              lastMessageAt={ user.lastMessageAt }
              unreadMessagesCount={ user.unreadMessagesCount }
              isActive={ this.state.selectedUsers.indexOf(user) >= 0 }
              onClick={ () => this.toggleUserSelection(user) }
            />
          );
        })
      );
    } else {
      container = (

{ groupName }

            { icon }

{ heading }

          { participants }

      );
    }

    return (

                  <button className="sign-out" onClick={ this.leaveGroup.bind(this) }>

                    Leave group
                  </button>

                  <button onClick={ this.editGroupName.bind(this) }>

                  </button>

                  <button onClick={ this.addGroupImage.bind(this) }>

                  </button>

                  <button onClick={ this.showSearch.bind(this) }>

                  </button>

              { input }

          { container }

    );
  }

  onKeyUp() {
    this.setState({
      query: this.participantsInput.value,
    });
  }

  toggleUserSelection(user) {
    let selectedUsers = this.state.selectedUsers.slice();
    if ( selectedUsers.indexOf(user) >= 0 ) {
      selectedUsers.splice(selectedUsers.indexOf(user), 1);
    } else {
      selectedUsers.push(user);
    }
    this.setState({selectedUsers});
  }

  getContacts() {
    const contacts = this.props.contactsState.contacts;
    delete contacts[this.props.meState.me.id];
    return Object.keys(contacts).map((id) => contacts[id]).filter((contact) => {
      let fullName = `${contact.firstName} ${contact.lastName}`;
      return (this.state.selectedUsers.indexOf(contact) >= 0) ||
        (fullName.toLowerCase().indexOf(this.state.query.toLowerCase()) >= 0);
    });
  }

  addParticipants() {
    let participantIds = this.state.selectedUsers.map((user) => user.id);
    this.props.update({'participants': participantIds});
    this.hideSearch();
  }

  leaveGroup() {
    console.info('Leave group chat.');
  }

  editGroupName() {
    this.props.update({'groupName': prompt('Group name')});
  }

  addGroupImage() {
    this.props.update({'groupImage': prompt('Group image')});
  }

  showSearch() {
    this.setState({
      search: true,
    });
  }

  hideSearch() {
    this.setState({
      search: false,
      query: '',
    });
  }
}

ChatSettings.propTypes = {
  groupName: React.PropTypes.string,
  groupImage: React.PropTypes.string,
  participants: React.PropTypes.array,
  update: React.PropTypes.func,
};

function renderParticipants(props) {
  if (props.participants.length > 0) {
    return props.participants.map(p => props.contactsState.contacts[p.id])
      .filter(x => x)
      .map((user, index) => (
      <BlockUser
        key={ index }
        name={ user.firstName }
        description={ user.description }
        imageSource={ user.imageSource }
        lastSeenDate={ user.lastSeenDate }
        openChat={ () => props.openChat(user.id) }
      />
    ));
  } else {
    return [];
  }
}

const mapStateToProps = (state, ownProps) => state[config.stateName];

const mapDispatchToProps = (dispatch, ownProps) => {
  return {
    fetchContacts: () => {
      dispatch(actions.contacts.fetchContacts());
    },
  };
};

const ChatSettingsConnect = connect(mapStateToProps, mapDispatchToProps)(ChatSettings);
export default ChatSettingsConnect;
<|endoftext|>


<commit_before>let self;
class GamesController {
    /*@ngInject*/
    constructor($location, preScreenLoadingInterceptorsCallerService, constants, gamesService, booksService) {
        self = this;
        self.constants = constants;
        preScreenLoadingInterceptorsCallerService.intercept();
        self.$location = $location;
        self.gamesService = gamesService;
        self.booksService = booksService;

        self.gamesService.addGame(self.buildGame('warlock-firetop-mountain', 'Pascal', '0'));
        self.gamesService.addGame(self.buildGame('warlock-firetop-mountain', 'Pascal 2nd try', '12'));
        self.gamesService.addGame(self.buildGame('creature-from-chaos', 'François', '187'));

        this.rows = self.gamesService.getGamesAsCopy();
        self.completeBookName(this.rows);
    }

    buildGame(bookUrlName, playerName, paragraphNr) {
        // TODO remove
        let timestamp = new Date().getTime();
        let game = {
            id : timestamp,
            playerName : playerName,
            bookUrlName : bookUrlName,
            currentParagraphNr : paragraphNr
        };
        return game;
    }

    completeBookName(games) {
        for (var i = 0; i < games.length; i++) {
            let book = self.booksService.getBook(games[i].bookUrlName);
            if (!!book) {
                games[i].bookName = book.name;
            } else {
                games[i].bookName = games[i].bookUrlName;
            }
        }
    }

    select(row) {
        for (var i = 0; i < self.rows.length; i++) {
            self.rows[i].selected = false;
        }
        row.selected = true;
    }

    startNewGame() {
        self.$location.url(self.constants.url.selectBookForNewGame)
    }

    isContinueAllowed() {
        for (var i = 0; i < self.rows.length; i++) {
            if (!!self.rows[i].selected) {
                return true;
            }
        }
        return false;
    }

    continueGame() {
        self.$location.url(self.constants.url.inGame)
    }
}

export default GamesController;<commit_msg>use gamesService in games screen<commit_after>let self;
class GamesController {
    /*@ngInject*/
    constructor($location, preScreenLoadingInterceptorsCallerService, constants, gamesService, booksService) {
        self = this;
        self.constants = constants;
        preScreenLoadingInterceptorsCallerService.intercept();
        self.$location = $location;
        self.gamesService = gamesService;
        self.booksService = booksService;

        self.gamesService.addGame(self.buildGame('warlock-firetop-mountain', 'Pascal', '0'));
        self.gamesService.addGame(self.buildGame('warlock-firetop-mountain', 'Pascal 2nd try', '12'));
        self.gamesService.addGame(self.buildGame('creature-from-chaos', 'François', '187'));

        this.rows = self.gamesService.getGamesAsCopy();
        self.completeBookName(this.rows);
    }

    buildGame(bookUrlName, playerName, paragraphNr) {
        // TODO remove
        let timestamp = new Date().getTime();
        let game = {
            id : timestamp,
            playerName : playerName,
            bookUrlName : bookUrlName,
            currentParagraphNr : paragraphNr
        };
        return game;
    }

    completeBookName(games) {
        for (var i = 0; i < games.length; i++) {
            let book = self.booksService.getBook(games[i].bookUrlName);
            if (!!book) {
                games[i].bookName = book.name;
            } else {
                games[i].bookName = games[i].bookUrlName;
            }
        }
    }

    select(row) {
        for (var i = 0; i < self.rows.length; i++) {
            self.rows[i].selected = false;
        }
        row.selected = true;
    }

    startNewGame() {
        self.$location.url(self.constants.url.selectBookForNewGame)
    }

    continueGame() {
        let nextUrl = self.gamesService.getUrlOfGame(self.getSelectedRow().id);
        self.$location.url(nextUrl);
    }

    isContinueAllowed() {
        return !!self.getSelectedRow();
    }

    getSelectedRow() {
        for (var i = 0; i < self.rows.length; i++) {
            if (!!self.rows[i].selected) {
                return self.rows[i];
            }
        }
        return null;
    }
}

export default GamesController;<|endoftext|>