<commit_before>const socket = io("http://127.0.0.1:3001");

const wesh = console.log;

const exit = (code = 0) => process.exit(code);

const tileMapSize = 16;
const size = 40;
const windowSize = size * tileMapSize;

if (gup("id")) {
  const id = gup("id");
  const hubName = decodeURI(gup("hubname"));
  console.log("ONLY JOINING");

  socket.on("connect", () => {
    socket.emit("connectFront");
    wesh("I' am connected");
    //socket.emit('join', { hubName: 'hub1', team: 'ISSOU' })
    startGame();
  });

  const players = [];
  const createMap = () => {
      let arr = new Array(mapHeight)
      for (let i = 0; i < mapHeight; i++) {
          arr[i] = new Array()
          for (let j = 0; j < mapWidth; j++) {
            arr[i].push({
                food: 0,
                entity: null,
                deraumere: 0,
                linemate: 0,
                mendiane: 0,
                phiras: 0,
                sibur: 0,
                thystame: 0
            })
        }
    }
    return arr
  };
  const map = createMap();

  socket.on("dead", () => {
    wesh("I' dead");
    //exit();
  });

  socket.on(`update:${hubName}`, data => {
    wesh("I' m updated");
    wesh(data);
    parseHubData(data.hubInfo);
    parseClientsData(data.clients);
    clearEntities();
  });

  socket.on("disconnect", () => {
    wesh("I'm out");
    //exit()
  });

  socket.on("start", () => {
    wesh("Start play ");
    socket.emit("Right");
  });

  const createPlayer = data => {
    return Crafty.e("2D, Canvas, team1, Controls, Collision, SpriteAnimation")
      .attr({
        x: data.pos.x * tileMapSize,
        y: data.pos.y * tileMapSize,
        w: tileMapSize,
        h: tileMapSize
      })
      .reel("4", 100, [[0, 3], [1, 3], [2, 3]])
      .reel("2", 100, [[0, 1], [1, 1], [2, 1]])
      .reel("3", 100, [[0, 2], [1, 2], [2, 2]])
      .reel("1", 100, [[0, 0], [1, 0], [2, 0]])
      .bind("Update", function(data) {
        this.animate(data.orientation.toString());
        this.x = data.pos.x * tileMapSize;
        this.y = data.pos.y * tileMapSize;
      });
  };

  const parseClientsData = data => {
    for (let i = 0; i < data.length; i++) {
      if (
        players.some(function(e) {
          if (e.id == data[i].id) {
            e.pos = data[i].pos;
            e.orientation = data[i].orientation;
            wesh(e.pos, e.orientation);
            e.alive = true;
          }
          return e.id == data[i].id;
        })
      ) {
      } else {
        data[i].entity = createPlayer(data[i]);
        data[i].alive = true;
        players.push(data[i]);
      }
    }
  };

    const parseHubData = data => {
        for (let i = 0; i < data.map.length; i++) {
            for (let j = 0; j < data.map[i].length; j++) {
                map[i][j].food = data.map[i][j].food
                map[i][j].deraumere = data.map[i][j].deraumere
                map[i][j].linemate = data.map[i][j].linemate
                map[i][j].mendiane = data.map[i][j].mendiane
                map[i][j].phiras = data.map[i][j].phiras
                map[i][j].sibur = data.map[i][j].sibur
                map[i][j].thystame = data.map[i][j].thystame;
                if (map[i][j].food > 0 && !map[i][j].entity) {
                    map[i][j].entity = Crafty.e(`2D, Canvas, Mouse, flower`).attr({
                        x: i * tileMapSize,
                        y: j * tileMapSize
                    })
                        .bind("Click", function(data) {
                            wesh(data)
                            wesh(this.x / tileMapSize, this.y / tileMapSize)
                        });
                }
                else if (map[i][j].food <= 0 && map[i][j].entity) {
                    map[i][j].entity.destroy()
                }
            }
        }
    };

  const clearEntities = () => {
    for (let i = 0; i < players.length; i++) {
      if (players[i].alive) {
        players[i].entity.trigger("Update", players[i]);
        players[i].alive = false;
      } else {
        players[i].entity.destroy();
        players.slice(i, 1);
      }
    }
  };

  //randomy generate map
    const generateWorld = () => {
        for (let i = 0; i < mapHeight; ++i) {
            for (let j = 0; j < mapWidth; ++j) {
                grassType = Math.floor(Math.random() * 4 + 1);
                Crafty.e(`2D, Canvas, Color, grass${grassType}`).attr({
                    x: i * tileMapSize,
                    y: j * tileMapSize
                });
            }
        }
    };

  const startGame = () => {
    const WelcomeDiv = document.getElementById("welcome");
    WelcomeDiv.innerHTML = hubName;
    Crafty.init(windowSize, windowSize, document.getElementById("game"));
    Crafty.addEvent(this, "mousewheel", Crafty.mouseWheelDispatch);

    //Add audio for Gameplay
    //Crafty.audio.add("PokemonSounds", "/sounds/Bourvil.mp3");
    //Crafty.audio.play("PokemonSounds", 5, 1);

    //turn the sprite map into usable components
    Crafty.sprite(16, "/images/sprite.png", {
      grass1: [0, 0],
      grass2: [1, 0],
      grass3: [2, 0],
      grass4: [3, 0],
      flower: [0, 1]
    });

    Crafty.sprite(33, "/images/Pl.png", {
      team1: [0, 2],
      team2: [3, 2]
    });

    Crafty.sprite(
      28,
      "/images/Object.png",
      {
        //Sprite for Food object.
      }
    );
    generateWorld();
  };

  Crafty.extend({
    mouseWheelDispatch: function(e) {
      Crafty.trigger("MouseWheel", e);
    }
  });

  Crafty.bind("MouseWheel", function(e) {
        var delta= (e.wheelDelta? e.wheelDelta/120 : e.detail)/2;
        Crafty.viewport.zoom((delta>0) ? (delta+1) : 1/(-delta+1), e.clientX, e.clientY, 10);
});

  /*const zoom = Crafty.e("2D")

zoom.onMouseDown = e => {
  //For CraftyJS Middle === Left, I don't know why
  if (e.buttons === Crafty.mouseButtons.MIDDLE)
    Crafty.viewport.zoom(2, e.clientX, e.clientY, 500);
  else if (e.buttons === Crafty.mouseButtons.RIGHT)
    Crafty.viewport.zoom(0.5, e.clientX, e.clientY, 500);
};*/
} else {
  //TODO: make this dynamic
  const hubName = decodeURI(gup("hubname")) || "hub1";

  const mapWidth = parseInt(gup("width")) || 40;

  const mapHeight = parseInt(gup("height")) || 40;

  const teams = decodeURI(gup("team")).split("*") || ["ISSOU", "BITE"];

  const clientsPerTeam = parseInt(gup("number")) || 1;

  //Players and map infos
    const players = [];
    const createMap = () => {
        let arr = new Array(mapHeight)
        for (let i = 0; i < mapHeight; i++) {
            arr[i] = new Array()
            for (let j = 0; j < mapWidth; j++) {
                arr[i].push({
                    food: 0,
                    entity: null,
                    deraumere: 0,
                    linemate: 0,
                    mendiane: 0,
                    phiras: 0,
                    sibur: 0,
                    thystame: 0
                })
            }
        }
        return arr
    };
    const map = createMap();

  socket.on("connect", () => {
    socket.emit("connectFront");
    wesh("I' am connected");
    socket.emit("createHub", {
      hubName: hubName,
      mapWidth: mapWidth,
      mapHeight: mapHeight,
      teams: teams,
      clientsPerTeam: clientsPerTeam
    });
    //socket.emit('join', { hubName: 'hub1', team: 'ISSOU' })
    startGame();
  });

  socket.on("dead", () => {
    wesh("I' dead");
    //exit();
  });

  socket.on(`update:${hubName}`, data => {
    wesh("I' m updated");
    wesh(data);
    parseHubData(data.hubInfo);
    parseClientsData(data.clients);
    clearEntities();
  });

  socket.on("disconnect", () => {
    wesh("I'm out");
    //exit()
  });

  socket.on("start", () => {
    wesh("Start play ");
    socket.emit("Right");
  });

  const createPlayer = data => {
    return Crafty.e("2D, Canvas, team1, Controls, Collision, SpriteAnimation")
      .attr({
        x: data.pos.x * tileMapSize,
        y: data.pos.y * tileMapSize,
        w: tileMapSize,
        h: tileMapSize
      })
      .reel("2", 100, [[0, 3], [1, 3], [2, 3]])
      .reel("4", 100, [[0, 1], [1, 1], [2, 1]])
      .reel("3", 100, [[0, 2], [1, 2], [2, 2]])
      .reel("1", 100, [[0, 0], [1, 0], [2, 0]])
      .bind("Update", function(data) {
        this.animate(data.orientation.toString());
        this.x = data.pos.x * tileMapSize;
        this.y = data.pos.y * tileMapSize;
      });
  };

  const parseClientsData = data => {
    for (let i = 0; i < data.length; i++) {
      if (
        players.some(function(e) {
          if (e.id == data[i].id) {
            e.pos = data[i].pos;
            e.orientation = data[i].orientation;
            wesh(e.pos, e.orientation);
            e.alive = true;
          }
          return e.id == data[i].id;
        })
      ) {
      } else {
        data[i].entity = createPlayer(data[i]);
        data[i].alive = true;
        players.push(data[i]);
      }
    }
  };

    const parseHubData = data => {
        for (let i = 0; i < data.map.length; i++) {
            for (let j = 0; j < data.map[i].length; j++) {
                map[i][j].food = data.map[i][j].food
                map[i][j].deraumere = data.map[i][j].deraumere
                map[i][j].linemate = data.map[i][j].linemate
                map[i][j].mendiane = data.map[i][j].mendiane
                map[i][j].phiras = data.map[i][j].phiras
                map[i][j].sibur = data.map[i][j].sibur
                map[i][j].thystame = data.map[i][j].thystame;
                if (map[i][j].food > 0 && !map[i][j].entity) {
                    map[i][j].entity = Crafty.e(`2D, Canvas, Mouse, flower, ClickFocus`).attr({
                        x: i * tileMapSize,
                        y: j * tileMapSize
                    })
                    .bind("Click", function(data) {
                        wesh(data)
                        wesh(this.x / tileMapSize, this.y / tileMapSize)
                    });
                }
                else if (map[i][j].food <= 0 && map[i][j].entity) {
                    map[i][j].entity.destroy()
                }
            }
        }
    };

  const clearEntities = () => {
    for (let i = 0; i < players.length; i++) {
      if (players[i].alive) {
        players[i].entity.trigger("Update", players[i]);
        players[i].alive = false;
      } else {
        players[i].entity.destroy();
        players.slice(i, 1);
      }
    }
  };

  //randomy generate map
  const generateWorld = () => {
    for (let i = 0; i < mapHeight; ++i) {
      for (let j = 0; j < mapWidth; ++j) {
        grassType = Math.floor(Math.random() * 4 + 1);
        Crafty.e(`2D, Canvas, Color, grass${grassType}`).attr({
          x: i * tileMapSize,
          y: j * tileMapSize
        });
      }
    }
  };

  const startGame = () => {
    const WelcomeDiv = document.getElementById("welcome");
    WelcomeDiv.innerHTML = hubName;
    Crafty.init(windowSize, windowSize, document.getElementById("game"));
    Crafty.addEvent(this, "mousewheel", Crafty.mouseWheelDispatch);

    //Add audio for Gameplay
    //Crafty.audio.add("PokemonSounds", "/sounds/Bourvil.mp3");
    //Crafty.audio.play("PokemonSounds", 5, 1);

    //turn the sprite map into usable components
    Crafty.sprite(16, "/images/sprite.png", {
      grass1: [0, 0],
      grass2: [1, 0],
      grass3: [2, 0],
      grass4: [3, 0],
      flower: [0, 1]
    });

    Crafty.sprite(33, "/images/Pl.png", {
      team1: [0, 2],
      team2: [3, 2]
    });

    Crafty.sprite(
      28,
      "/images/Object.png",
      {
        //Sprite for Food object.
      }
    );
    generateWorld();
  };

  Crafty.extend({
    mouseWheelDispatch: function(e) {
      Crafty.trigger("MouseWheel", e);
    }
  });

  Crafty.bind("MouseWheel", function(e) {
        var delta= (e.wheelDelta? e.wheelDelta/120 : e.detail)/2;
        Crafty.viewport.zoom((delta>0) ? (delta+1) : 1/(-delta+1), e.clientX, e.clientY, 10);
});

  /*const zoom = Crafty.e("2D")

zoom.onMouseDown = e => {
  //For CraftyJS Middle === Left, I don't know why
  if (e.buttons === Crafty.mouseButtons.MIDDLE)
    Crafty.viewport.zoom(2, e.clientX, e.clientY, 500);
  else if (e.buttons === Crafty.mouseButtons.RIGHT)
    Crafty.viewport.zoom(0.5, e.clientX, e.clientY, 500);
};*/
}
<commit_msg>remove old code with id<commit_after>const socket = io("http://127.0.0.1:3001");

const wesh = console.log;

const exit = (code = 0) => process.exit(code);

const tileMapSize = 16;
const size = 40;
const windowSize = size * tileMapSize;

//TODO: make this dynamic
const hubName = decodeURI(gup("hubname")) || "hub1";

const mapWidth = parseInt(gup("width")) || 40;

const mapHeight = parseInt(gup("height")) || 40;

const teams = decodeURI(gup("team")).split("*") || ["ISSOU", "BITE"];

const clientsPerTeam = parseInt(gup("number")) || 1;

//Players and map infos
const players = [];
const createMap = () => {
  let arr = new Array(mapHeight);
  for (let i = 0; i < mapHeight; i++) {
    arr[i] = new Array();
    for (let j = 0; j < mapWidth; j++) {
      arr[i].push({
        food: 0,
        entity: null,
        deraumere: 0,
        linemate: 0,
        mendiane: 0,
        phiras: 0,
        sibur: 0,
        thystame: 0
      });
    }
  }
  return arr;
};
const map = createMap();

socket.on("connect", () => {
  socket.emit("connectFront");
  wesh("I' am connected");
  socket.emit("createHub", {
    hubName: hubName,
    mapWidth: mapWidth,
    mapHeight: mapHeight,
    teams: teams,
    clientsPerTeam: clientsPerTeam
  });
  //socket.emit('join', { hubName: 'hub1', team: 'ISSOU' })
  startGame();
});

socket.on("dead", () => {
  wesh("I' dead");
  //exit();
});

socket.on(`update:${hubName}`, data => {
  wesh("I' m updated");
  wesh(data);
  parseHubData(data.hubInfo);
  parseClientsData(data.clients);
  clearEntities();
});

socket.on("disconnect", () => {
  wesh("I'm out");
  //exit()
});

socket.on("start", () => {
  wesh("Start play ");
  socket.emit("Right");
});

const createPlayer = data => {
  return Crafty.e("2D, Canvas, team1, Controls, Collision, SpriteAnimation")
    .attr({
      x: data.pos.x * tileMapSize,
      y: data.pos.y * tileMapSize,
      w: tileMapSize,
      h: tileMapSize
    })
    .reel("2", 100, [[0, 3], [1, 3], [2, 3]])
    .reel("4", 100, [[0, 1], [1, 1], [2, 1]])
    .reel("3", 100, [[0, 2], [1, 2], [2, 2]])
    .reel("1", 100, [[0, 0], [1, 0], [2, 0]])
    .bind("Update", function(data) {
      this.animate(data.orientation.toString());
      this.x = data.pos.x * tileMapSize;
      this.y = data.pos.y * tileMapSize;
    });
};

const parseClientsData = data => {
  for (let i = 0; i < data.length; i++) {
    if (
      players.some(function(e) {
        if (e.id == data[i].id) {
          e.pos = data[i].pos;
          e.orientation = data[i].orientation;
          wesh(e.pos, e.orientation);
          e.alive = true;
        }
        return e.id == data[i].id;
      })
    ) {
    } else {
      data[i].entity = createPlayer(data[i]);
      data[i].alive = true;
      players.push(data[i]);
    }
  }
};

const parseHubData = data => {
  for (let i = 0; i < data.map.length; i++) {
    for (let j = 0; j < data.map[i].length; j++) {
      map[i][j].food = data.map[i][j].food;
      map[i][j].deraumere = data.map[i][j].deraumere;
      map[i][j].linemate = data.map[i][j].linemate;
      map[i][j].mendiane = data.map[i][j].mendiane;
      map[i][j].phiras = data.map[i][j].phiras;
      map[i][j].sibur = data.map[i][j].sibur;
      map[i][j].thystame = data.map[i][j].thystame;
      if (map[i][j].food > 0 && !map[i][j].entity) {
        map[i][j].entity = Crafty.e(`2D, Canvas, Mouse, flower, ClickFocus`)
          .attr({
            x: i * tileMapSize,
            y: j * tileMapSize
          })
          .bind("Click", function(data) {
            wesh(data);
            wesh(this.x / tileMapSize, this.y / tileMapSize);
          });
      } else if (map[i][j].food <= 0 && map[i][j].entity) {
        map[i][j].entity.destroy();
      }
    }
  }
};

const clearEntities = () => {
  for (let i = 0; i < players.length; i++) {
    if (players[i].alive) {
      players[i].entity.trigger("Update", players[i]);
      players[i].alive = false;
    } else {
      players[i].entity.destroy();
      players.slice(i, 1);
    }
  }
};

//randomy generate map
const generateWorld = () => {
  for (let i = 0; i < mapHeight; ++i) {
    for (let j = 0; j < mapWidth; ++j) {
      grassType = Math.floor(Math.random() * 4 + 1);
      Crafty.e(`2D, Canvas, Color, grass${grassType}`).attr({
        x: i * tileMapSize,
        y: j * tileMapSize
      });
    }
  }
};

const startGame = () => {
  const WelcomeDiv = document.getElementById("welcome");
  WelcomeDiv.innerHTML = hubName;
  Crafty.init(windowSize, windowSize, document.getElementById("game"));
  Crafty.addEvent(this, "mousewheel", Crafty.mouseWheelDispatch);

  //Add audio for Gameplay
  //Crafty.audio.add("PokemonSounds", "/sounds/Bourvil.mp3");
  //Crafty.audio.play("PokemonSounds", 5, 1);

  //turn the sprite map into usable components
  Crafty.sprite(16, "/images/sprite.png", {
    grass1: [0, 0],
    grass2: [1, 0],
    grass3: [2, 0],
    grass4: [3, 0],
    flower: [0, 1]
  });

  Crafty.sprite(33, "/images/Pl.png", {
    team1: [0, 2],
    team2: [3, 2]
  });

  Crafty.sprite(
    28,
    "/images/Object.png",
    {
      //Sprite for Food object.
    }
  );
  generateWorld();
};

Crafty.extend({
  mouseWheelDispatch: function(e) {
    Crafty.trigger("MouseWheel", e);
  }
});

Crafty.bind("MouseWheel", function(e) {
  var delta = (e.wheelDelta ? e.wheelDelta / 120 : e.detail) / 2;
  Crafty.viewport.zoom(
    delta > 0 ? delta + 1 : 1 / (-delta + 1),
    e.clientX,
    e.clientY,
    10
  );
});

/*const zoom = Crafty.e("2D")

zoom.onMouseDown = e => {
  //For CraftyJS Middle === Left, I don't know why
  if (e.buttons === Crafty.mouseButtons.MIDDLE)
    Crafty.viewport.zoom(2, e.clientX, e.clientY, 500);
  else if (e.buttons === Crafty.mouseButtons.RIGHT)
    Crafty.viewport.zoom(0.5, e.clientX, e.clientY, 500);
};*/
<|endoftext|>


<commit_before>// info gather
var name = prompt("what is your name?")
var classmessage = alert("Availiable classes are: Paladin, Mage, Marksman")
var userclass = prompt("Please choose your class.")

// creating players
var player = function(health, attack, defense, specialattack, specialdefense){
    this.health = health;
    this.attack = attack;
    this.defense = defense;
    this.specialattack = specialattack;
    this.specialdefense = specialdefense;
}
var move = function(damage, accuracy){
    this.damage = damage;
    this.accuracy = accuracy;
}
var healmove = function(range, accuracy){
    this.rang = range;
    this.accuracy = accuracy;
}
// creating the skills
var punch = new move(10,100)
var kick = new move(15,85)
var wisp = new move(12,100)
var minorheal = new healmove(5,100)
// class creation
if (userclass == "Paladin"){
    var user = new player(100, 12, 10, 5, 6)
    var skills = [punch, kick]
}
else if (userclass == "Mage"){
    var user = new player(100, 6, 6, 14, 11)
    var skills = [wisp, minorheal]
}

// attack script
var attack = prompt("???")
if (attack == "Punch"){
  punch(damage) + attack
}
<commit_msg>created enemies<commit_after>// info gather
var name = prompt("what is your name?")
var classmessage = alert("Availiable classes are: Paladin, Mage, Marksman")
var userclass = prompt("Please choose your class.")

// creating players
var player = function(health, attack, defense, specialattack, specialdefense){
    this.health = health;
    this.attack = attack;
    this.defense = defense;
    this.specialattack = specialattack;
    this.specialdefense = specialdefense;
}
// moves
var move = function(damage, accuracy){
    this.damage = damage;
    this.accuracy = accuracy;
}
var healmove = function(range, accuracy){
    this.rang = range;
    this.accuracy = accuracy;
}
// creating enemies
var enemy = function(health, attack, defense, specialattack, specialdefense){
    this.health = health;
    this.attack = attack;
    this.defense = defense;
    this.specialattack = specialattack;
    this.specialdefense = specialdefense;
}
var evilcat = new enemy(40, 3, 4, 3, 4)
// creating the skills
var punch = new move(10,100)
var kick = new move(15,85)
var wisp = new move(12,100)
var minorheal = new healmove(5,100)
// class creation
if (userclass == "Paladin"){
    var user = new player(100, 12, 10, 5, 6)
    var skills = [punch, kick]
}
else if (userclass == "Mage"){
    var user = new player(100, 6, 6, 14, 11)
    var skills = [wisp, minorheal]
}

// attack script
var attack = prompt("???")
if (attack == "Punch"){
  punch(damage) + attack
}
<|endoftext|>


<commit_before>"use strict";
const request = require('request');

/**
 * A Husqvarna mower
 * @param {object} mower - Object parsed from API response
 * @param {string} trackUrl - API Url for interacting with the mower
 * @param {object} headers - Headers with authentication data for interacting with the API
 * @constructor
 */
function HMower(mower, trackUrl, headers) {
    this.trackUrl = trackUrl;
    this.headers = headers;
    this.mower = mower;
    this.command = {
        park: 'PARK',
        stop: 'STOP',
        start: 'START'
    };
    this.status = {
        error: 'ERROR',
        cutting: 'OK_CUTTING',
        manualCutting: 'OK_CUTTING_NOT_AUTO',
        parked: 'PARKED_TIMER',
        manualParked: 'PARKED_PARKED_SELECTED',
        paused: 'PAUSED',
        searching: 'OK_SEARCHING', // Going home.
    };
    this.currentStatus = null;
}

/**
 * Is the mower currently cutting?
 * @returns {boolean}
 */
HMower.prototype.isCutting = function () {
    return [
        this.status.cutting,
        this.status.manualCutting
    ].indexOf(this.currentStatus) !== -1;
};

/**
 * Is the mower currently stopped or errored outside of the docking station?
 * @returns {boolean}
 */
HMower.prototype.isStopped = function () {
    return [
        this.status.error,
        this.status.paused
    ].indexOf(this.currentStatus) !== -1;

};

/**
 * Is the mower parked in the docking station?
 * @returns {boolean}
 */
HMower.prototype.isParked = function () {
    return [
        this.status.parked,
        this.status.manualParked
    ].indexOf(this.currentStatus) !== -1;
};

/**
 * Is the mower looking for its charging station?
 * @returns {boolean}
 */
HMower.prototype.isParking = function () {
    return this.currentStatus === this.status.searching;
};

/**
 * Is the mower in an errored state?
 * @returns {boolean}
 */
HMower.prototype.isErrored = function () {
    return this.currentStatus === this.status.error;
};

/**
 * Gets the status of the mower and returns the API response to a callback.
 * On success, the third parameter is an object with the status information.
 * @callback requestCallback
 */
HMower.prototype.getStatus = function (callback) {
    request({
        url: this.trackUrl + 'mowers/' + this.mower.id + '/status',
        method: "GET",
        headers: this.headers
    }, function (error, response, body) {
        let status = null;
        if (error || response.statusCode !== 200) {
            callback(error, response);
        } else {
            status = JSON.parse(body);
            this.currentStatus = status.mowerStatus; // TODO store as const
            callback(error, response, status);
        }
    });
};

/**
 * Gets the geo fence status with geolocation history and current location
 * @callback requestCallback
 */
HMower.prototype.getGeoStatus = function (callback) {
    request({
        url: this.trackUrl + 'mowers/' + this.mower.id + '/geofence',
        method: "GET",
        headers: this.headers
    }, function (error, response, body) {
        if (error || response.statusCode !== 200) {
            callback(error, response);
        } else {
            callback(error, response, JSON.parse(body));
        }
    });
};

/**
 * Sends a command to the mower
 * @param {string} action       An action as defined in HMower.command
 * @callback requestCallback    (boolean) Error, (String) Error Message
 * @returns {boolean} Success
 */
HMower.prototype.sendCommand = function (action, callback) {
    // Polyfill Object.values
    if (typeof Object.values !== 'function') {
        Object.values = function(obj) {
            var vals = [];
            for (var i in obj) {
                if (obj.hasOwnProperty(i)) {
                    vals.push(obj[i]);
                }
            }
            return vals;
        };
    }

    if (Object.values(this.command).indexOf(action) === -1) {
        callback(true, 'Unknown Command: ' + action);
        return false;
    }

    if (this.isErrored()) {
        callback(true, 'Cannot perform actions while mower is in error state');
        return false;
    }
    if (action === this.command.park && ( this.isParked() || this.isParking() )) {
        callback(true, 'Already in state: ' + this.currentStatus);
        return false;
    }

    if (action === this.command.start && this.isCutting()) {
        callback(true, 'Already in state: ' + this.currentStatus);
        return false;
    }

    console.log(this.command[action]);
    request({
        url: this.trackUrl + 'mowers/' + this.mower.id + '/control',
        method: "POST",
        headers: this.headers,
        json: true,
        body: {
            action: action
        }
    }, (error, response, body) => {
        if (error || response.statusCode !== 200) {
            console.log(body);
            callback(error, response);
        } else {
            console.log(body);
            callback(false);
        }
    });
};

/**
 *
 * @returns {int}   Battery power from 0-100 (percent)
 */
HMower.prototype.getBatteryPower = function () {
    return this.mower.status.batteryPercent;
};

module.exports = HMower;<commit_msg>Remove some debug console logging<commit_after>"use strict";
const request = require('request');

/**
 * A Husqvarna mower
 * @param {object} mower - Object parsed from API response
 * @param {string} trackUrl - API Url for interacting with the mower
 * @param {object} headers - Headers with authentication data for interacting with the API
 * @constructor
 */
function HMower(mower, trackUrl, headers) {
    this.trackUrl = trackUrl;
    this.headers = headers;
    this.mower = mower;
    this.command = {
        park: 'PARK',
        stop: 'STOP',
        start: 'START'
    };
    this.status = {
        error: 'ERROR',
        cutting: 'OK_CUTTING',
        manualCutting: 'OK_CUTTING_NOT_AUTO',
        parked: 'PARKED_TIMER',
        manualParked: 'PARKED_PARKED_SELECTED',
        paused: 'PAUSED',
        searching: 'OK_SEARCHING', // Going home.
    };
    this.currentStatus = null;
}

/**
 * Is the mower currently cutting?
 * @returns {boolean}
 */
HMower.prototype.isCutting = function () {
    return [
        this.status.cutting,
        this.status.manualCutting
    ].indexOf(this.currentStatus) !== -1;
};

/**
 * Is the mower currently stopped or errored outside of the docking station?
 * @returns {boolean}
 */
HMower.prototype.isStopped = function () {
    return [
        this.status.error,
        this.status.paused
    ].indexOf(this.currentStatus) !== -1;

};

/**
 * Is the mower parked in the docking station?
 * @returns {boolean}
 */
HMower.prototype.isParked = function () {
    return [
        this.status.parked,
        this.status.manualParked
    ].indexOf(this.currentStatus) !== -1;
};

/**
 * Is the mower looking for its charging station?
 * @returns {boolean}
 */
HMower.prototype.isParking = function () {
    return this.currentStatus === this.status.searching;
};

/**
 * Is the mower in an errored state?
 * @returns {boolean}
 */
HMower.prototype.isErrored = function () {
    return this.currentStatus === this.status.error;
};

/**
 * Gets the status of the mower and returns the API response to a callback.
 * On success, the third parameter is an object with the status information.
 * @callback requestCallback
 */
HMower.prototype.getStatus = function (callback) {
    request({
        url: this.trackUrl + 'mowers/' + this.mower.id + '/status',
        method: "GET",
        headers: this.headers
    }, function (error, response, body) {
        let status = null;
        if (error || response.statusCode !== 200) {
            callback(error, response);
        } else {
            status = JSON.parse(body);
            this.currentStatus = status.mowerStatus; // TODO store as const
            callback(error, response, status);
        }
    });
};

/**
 * Gets the geo fence status with geolocation history and current location
 * @callback requestCallback
 */
HMower.prototype.getGeoStatus = function (callback) {
    request({
        url: this.trackUrl + 'mowers/' + this.mower.id + '/geofence',
        method: "GET",
        headers: this.headers
    }, function (error, response, body) {
        if (error || response.statusCode !== 200) {
            callback(error, response);
        } else {
            callback(error, response, JSON.parse(body));
        }
    });
};

/**
 * Sends a command to the mower
 * @param {string} action       An action as defined in HMower.command
 * @callback requestCallback    (boolean) Error, (String) Error Message
 * @returns {boolean} Success
 */
HMower.prototype.sendCommand = function (action, callback) {
    // Polyfill Object.values
    if (typeof Object.values !== 'function') {
        Object.values = function(obj) {
            var vals = [];
            for (var i in obj) {
                if (obj.hasOwnProperty(i)) {
                    vals.push(obj[i]);
                }
            }
            return vals;
        };
    }

    if (Object.values(this.command).indexOf(action) === -1) {
        callback(true, 'Unknown Command: ' + action);
        return false;
    }

    if (this.isErrored()) {
        callback(true, 'Cannot perform actions while mower is in error state');
        return false;
    }
    if (action === this.command.park && ( this.isParked() || this.isParking() )) {
        callback(true, 'Already in state: ' + this.currentStatus);
        return false;
    }

    if (action === this.command.start && this.isCutting()) {
        callback(true, 'Already in state: ' + this.currentStatus);
        return false;
    }

    request({
        url: this.trackUrl + 'mowers/' + this.mower.id + '/control',
        method: "POST",
        headers: this.headers,
        json: true,
        body: {
            action: action
        }
    }, (error, response, body) => {
        if (error || response.statusCode !== 200) {
            callback(error, response);
        } else {
            callback(false);
        }
    });
};

/**
 *
 * @returns {int}   Battery power from 0-100 (percent)
 */
HMower.prototype.getBatteryPower = function () {
    return this.mower.status.batteryPercent;
};

module.exports = HMower;<|endoftext|>


<commit_before>/**
 * Controller: Migration
 * - Prepares all external services for integration with the app; this includes, but
 *   is not limited to, creating mailchimp custom fields, registering webhook callbacks,
 *   creating indices and prepared data structures in dynamodb, &c.
 */

var config = require('../libs/config');
var civicinfo = require('../libs/google').civicinfo('v2');
var civicinfo_utils = require('../libs/civicinfo_utils');
var mailchimp = require('../libs/mailchimp');
var AWS = require('aws-sdk');

AWS.config.update({
  region: process.env.AWS_REGION
});

var docClient = new AWS.DynamoDB.DocumentClient();

const expected_merge_fields = {
  H_NAME:    { display_order: 11, name: 'House Rep. Name',        required: false, tag: 'H_NAME',   type: 'text' },
  H_PHOTO:   { display_order: 12, name: 'House Rep. Photo',       required: false, tag: 'H_PHOTO',  type: 'imageurl'},
  H_PHONE:   { display_order: 13, name: 'House Rep. Phone',       required: false, tag: 'H_PHONE',  type: 'phone',   options: { phone_format: 'US' } },
  S1_NAME:   { display_order: 14, name: 'Senate Rep. 1\'s Name',  required: false, tag: 'S1_NAME',  type: 'text' },
  S1_PHOTO:  { display_order: 15, name: 'Senate Rep. 1\'s Photo', required: false, tag: 'S1_PHOTO', type: 'imageurl'},
  S1_PHONE:  { display_order: 16, name: 'Senate Rep. 1\'s Phone', required: false, tag: 'S1_PHONE', type: 'phone',   options: { phone_format: 'US' } },
  S2_NAME:   { display_order: 17, name: 'Senate Rep. 2\'s Name',  required: false, tag: 'S2_NAME',  type: 'text' },
  S2_PHOTO:  { display_order: 18, name: 'Senate Rep. 2\'s Photo', required: false, tag: 'S2_PHOTO', type: 'imageurl'},
  S2_PHONE:  { display_order: 19, name: 'Senate Rep. 2\'s Phone', required: false, tag: 'S2_PHONE', type: 'phone',   options: { phone_format: 'US' } }
};

function list_field_migrate() {
  // default is 10, but with FNAME and LNAME already available by default, lets just go to 50 and call it a day
  const field_url = `/lists/${process.env.MAILCHIMP_LIST_ID}/merge-fields?count=50`;
  console.log(`Fetching fields from ${field_url}`);

  return mailchimp.get(field_url)
  .then(fields => {
    const existing_field_tags = new Map(fields.merge_fields.map(f => [f.tag, f]));
    console.log('Existing fields: ' + JSON.stringify(Array.from(existing_field_tags.keys())));

    const missing_fields = Object.keys(expected_merge_fields)
      .filter(tag => !existing_field_tags.has(tag))
      .map(tag => expected_merge_fields[tag]);
    console.log('Missing merge fields: ' + JSON.stringify(missing_fields));

    const missing_fields_promises = missing_fields
      .map(missing_field => mailchimp.post(`/lists/${process.env.MAILCHIMP_LIST_ID}/merge-fields`, missing_field));

    const modified_fields = Object.keys(expected_merge_fields)
      .filter(tag => existing_field_tags.has(tag))
      .map(tag => expected_merge_fields[tag])
      .filter(f => existing_field_tags.get(f.tag).name          !== f.name         ||
                   existing_field_tags.get(f.tag).type          !== f.type         ||
                   existing_field_tags.get(f.tag).required      !== f.required     ||
                   existing_field_tags.get(f.tag).display_order !== f.display_order)
    console.log('Modified merge fields: ' + JSON.stringify(modified_fields));

    const modified_fields_promises = modified_fields
      .map(modified_field => mailchimp.patch(`/lists/${process.env.MAILCHIMP_LIST_ID}/merge-fields/${existing_field_tags.get(modified_field.tag).merge_id}`, modified_field));

    return Promise.all(missing_fields_promises.concat(modified_fields_promises))
      .catch(error => console.log('There was an error during merge fields: ' + JSON.stringify(error)));
  });
}

const expected_webhooks = [
  {
    url: `${config.api_hostname[process.env.STAGE]}/mailchimp/hook/subscribe`,
    sources: { user: true, admin: true, api: true },
    events: { subscribe: true }
  },
  {
    url: `${config.api_hostname[process.env.STAGE]}/mailchimp/hook/unsubscribe`,
    sources: { user: true, admin: true, api: true },
    events: { unsubscribe: true }
  }
];

function list_webhook_register() {
  const webhook_url = `/lists/${process.env.MAILCHIMP_LIST_ID}/webhooks`;
  console.log(`Fetching webhooks from ${webhook_url}`);
  return mailchimp.get(webhook_url)
  .then(existing_hooks => {
    console.log('Existing webhooks: ' + JSON.stringify(existing_hooks));

    const existing_hook_urls = new Map(existing_hooks.webhooks.map(hook => [hook.url, hook]));
    console.log('Existing webhook urls: ' + JSON.stringify(Array.from(existing_hook_urls.keys())));

    const missing_hooks = expected_webhooks
      .filter(hook => !existing_hook_urls.has(hook.url));
    console.log('Missing webhooks: ' + JSON.stringify(missing_hooks));

    const missing_hooks_promises = missing_hooks
      .map(missing_hook => mailchimp.post(`/lists/${process.env.MAILCHIMP_LIST_ID}/webhooks`, missing_hook));

    return Promise.all(missing_hooks_promises)
      .catch(error => console.log('There was an error during web hooks: ' + JSON.stringify(error)));
  });
}

function docClientPut(doc) {
  return new Promise((resolve, reject) => {
    docClient.put(civicinfo_utils.removeEmptyStringElements(doc), (err, data) => {
      if (err) reject(err);
      else resolve(data);
    })
  });
}

function repopulate_reps_table() {
  return new Promise((resolve, reject) => {
    docClient.scan({
      TableName: 'subscribers',
      Select: 'SPECIFIC_ATTRIBUTES',
      AttributesToGet: [
        'email',
        'street',
        'city',
        'state',
        'zip'
      ]
    }, function(err, data) {
      if(err) reject(err);
      else resolve(data);
    })
  })

  .then(all_subscribers => {
    return Promise.all(all_subscribers.Items.map(subscriber => {
      var representativeObj = {
        TableName: 'representatives',
        Item: {
          district: '',
          senate1name: '',
          senate1number: '',
          senate2name: '',
          senate2number: '',
          repname: '',
          repnumber: ''
        }
      };

      return new Promise((resolve, reject) => {
        civicinfo.representatives.representativeInfoByAddress({
          address: `${subscriber.street} ${subscriber.city} ${subscriber.state} ${subscriber.zip}`,
          levels: ['country'],
          roles: ['legislatorLowerBody', 'legislatorUpperBody'],
          fields: 'normalizedInput,officials(name,phones,photoUrl),offices(name, roles, officialIndices)'
        }, function(err, data) {
          if (err) reject(err);
          else resolve(data);
        })
      })
      .then(civic => {
        const res = civicinfo_utils.representativeProcessing(civic);

        representativeObj.Item.district = res.district;
        representativeObj.Item.senate1name = res.senators[0].name;
        representativeObj.Item.senate1number = civicinfo_utils.normalizePhoneNumber(res.senators[0].phones);
        representativeObj.Item.senate2name = res.senators[1].name;
        representativeObj.Item.senate2number = civicinfo_utils.normalizePhoneNumber(res.senators[1].phones);
        representativeObj.Item.repname = res.representative.name;
        representativeObj.Item.repnumber = civicinfo_utils.normalizePhoneNumber(res.representative.phones);

        console.log('Rep: ' + JSON.stringify(representativeObj));
      })

      .then(() => docClientPut(representativeObj))
      .catch(error => console.log('CIVIC Parsing error:' + JSON.stringify(error)));
    }));
  });
}

module.exports.handler = (event, context, callback) => {
  Promise.all([
    list_field_migrate(),
    list_webhook_register(),
    repopulate_reps_table()
  ]).then(values => {
    callback(null, { values: values });
  })

  .catch(error => {
    if (error.error) {
      console.log(error.code + ': ' + error.error);
    } else {
      console.log('There was an error performing migrations!');
    }
    callback(JSON.stringify({
      message: 'There was an error!',
      error: error
    }));
  });

};
<commit_msg>Disable one-time migration<commit_after>/**
 * Controller: Migration
 * - Prepares all external services for integration with the app; this includes, but
 *   is not limited to, creating mailchimp custom fields, registering webhook callbacks,
 *   creating indices and prepared data structures in dynamodb, &c.
 */

var config = require('../libs/config');
var civicinfo = require('../libs/google').civicinfo('v2');
var civicinfo_utils = require('../libs/civicinfo_utils');
var mailchimp = require('../libs/mailchimp');
var AWS = require('aws-sdk');

AWS.config.update({
  region: process.env.AWS_REGION
});

var docClient = new AWS.DynamoDB.DocumentClient();

const expected_merge_fields = {
  H_NAME:    { display_order: 11, name: 'House Rep. Name',        required: false, tag: 'H_NAME',   type: 'text' },
  H_PHOTO:   { display_order: 12, name: 'House Rep. Photo',       required: false, tag: 'H_PHOTO',  type: 'imageurl'},
  H_PHONE:   { display_order: 13, name: 'House Rep. Phone',       required: false, tag: 'H_PHONE',  type: 'phone',   options: { phone_format: 'US' } },
  S1_NAME:   { display_order: 14, name: 'Senate Rep. 1\'s Name',  required: false, tag: 'S1_NAME',  type: 'text' },
  S1_PHOTO:  { display_order: 15, name: 'Senate Rep. 1\'s Photo', required: false, tag: 'S1_PHOTO', type: 'imageurl'},
  S1_PHONE:  { display_order: 16, name: 'Senate Rep. 1\'s Phone', required: false, tag: 'S1_PHONE', type: 'phone',   options: { phone_format: 'US' } },
  S2_NAME:   { display_order: 17, name: 'Senate Rep. 2\'s Name',  required: false, tag: 'S2_NAME',  type: 'text' },
  S2_PHOTO:  { display_order: 18, name: 'Senate Rep. 2\'s Photo', required: false, tag: 'S2_PHOTO', type: 'imageurl'},
  S2_PHONE:  { display_order: 19, name: 'Senate Rep. 2\'s Phone', required: false, tag: 'S2_PHONE', type: 'phone',   options: { phone_format: 'US' } }
};

function list_field_migrate() {
  // default is 10, but with FNAME and LNAME already available by default, lets just go to 50 and call it a day
  const field_url = `/lists/${process.env.MAILCHIMP_LIST_ID}/merge-fields?count=50`;
  console.log(`Fetching fields from ${field_url}`);

  return mailchimp.get(field_url)
  .then(fields => {
    const existing_field_tags = new Map(fields.merge_fields.map(f => [f.tag, f]));
    console.log('Existing fields: ' + JSON.stringify(Array.from(existing_field_tags.keys())));

    const missing_fields = Object.keys(expected_merge_fields)
      .filter(tag => !existing_field_tags.has(tag))
      .map(tag => expected_merge_fields[tag]);
    console.log('Missing merge fields: ' + JSON.stringify(missing_fields));

    const missing_fields_promises = missing_fields
      .map(missing_field => mailchimp.post(`/lists/${process.env.MAILCHIMP_LIST_ID}/merge-fields`, missing_field));

    const modified_fields = Object.keys(expected_merge_fields)
      .filter(tag => existing_field_tags.has(tag))
      .map(tag => expected_merge_fields[tag])
      .filter(f => existing_field_tags.get(f.tag).name          !== f.name         ||
                   existing_field_tags.get(f.tag).type          !== f.type         ||
                   existing_field_tags.get(f.tag).required      !== f.required     ||
                   existing_field_tags.get(f.tag).display_order !== f.display_order)
    console.log('Modified merge fields: ' + JSON.stringify(modified_fields));

    const modified_fields_promises = modified_fields
      .map(modified_field => mailchimp.patch(`/lists/${process.env.MAILCHIMP_LIST_ID}/merge-fields/${existing_field_tags.get(modified_field.tag).merge_id}`, modified_field));

    return Promise.all(missing_fields_promises.concat(modified_fields_promises))
      .catch(error => console.log('There was an error during merge fields: ' + JSON.stringify(error)));
  });
}

const expected_webhooks = [
  {
    url: `${config.api_hostname[process.env.STAGE]}/mailchimp/hook/subscribe`,
    sources: { user: true, admin: true, api: true },
    events: { subscribe: true }
  },
  {
    url: `${config.api_hostname[process.env.STAGE]}/mailchimp/hook/unsubscribe`,
    sources: { user: true, admin: true, api: true },
    events: { unsubscribe: true }
  }
];

function list_webhook_register() {
  const webhook_url = `/lists/${process.env.MAILCHIMP_LIST_ID}/webhooks`;
  console.log(`Fetching webhooks from ${webhook_url}`);
  return mailchimp.get(webhook_url)
  .then(existing_hooks => {
    console.log('Existing webhooks: ' + JSON.stringify(existing_hooks));

    const existing_hook_urls = new Map(existing_hooks.webhooks.map(hook => [hook.url, hook]));
    console.log('Existing webhook urls: ' + JSON.stringify(Array.from(existing_hook_urls.keys())));

    const missing_hooks = expected_webhooks
      .filter(hook => !existing_hook_urls.has(hook.url));
    console.log('Missing webhooks: ' + JSON.stringify(missing_hooks));

    const missing_hooks_promises = missing_hooks
      .map(missing_hook => mailchimp.post(`/lists/${process.env.MAILCHIMP_LIST_ID}/webhooks`, missing_hook));

    return Promise.all(missing_hooks_promises)
      .catch(error => console.log('There was an error during web hooks: ' + JSON.stringify(error)));
  });
}

function docClientPut(doc) {
  return new Promise((resolve, reject) => {
    docClient.put(civicinfo_utils.removeEmptyStringElements(doc), (err, data) => {
      if (err) reject(err);
      else resolve(data);
    })
  });
}

function repopulate_reps_table() {
  return new Promise((resolve, reject) => {
    docClient.scan({
      TableName: 'subscribers',
      Select: 'SPECIFIC_ATTRIBUTES',
      AttributesToGet: [
        'email',
        'street',
        'city',
        'state',
        'zip'
      ]
    }, function(err, data) {
      if(err) reject(err);
      else resolve(data);
    })
  })

  .then(all_subscribers => {
    return Promise.all(all_subscribers.Items.map(subscriber => {
      var representativeObj = {
        TableName: 'representatives',
        Item: {
          district: '',
          senate1name: '',
          senate1number: '',
          senate2name: '',
          senate2number: '',
          repname: '',
          repnumber: ''
        }
      };

      return new Promise((resolve, reject) => {
        civicinfo.representatives.representativeInfoByAddress({
          address: `${subscriber.street} ${subscriber.city} ${subscriber.state} ${subscriber.zip}`,
          levels: ['country'],
          roles: ['legislatorLowerBody', 'legislatorUpperBody'],
          fields: 'normalizedInput,officials(name,phones,photoUrl),offices(name, roles, officialIndices)'
        }, function(err, data) {
          if (err) reject(err);
          else resolve(data);
        })
      })
      .then(civic => {
        const res = civicinfo_utils.representativeProcessing(civic);

        representativeObj.Item.district = res.district;
        representativeObj.Item.senate1name = res.senators[0].name;
        representativeObj.Item.senate1number = civicinfo_utils.normalizePhoneNumber(res.senators[0].phones);
        representativeObj.Item.senate2name = res.senators[1].name;
        representativeObj.Item.senate2number = civicinfo_utils.normalizePhoneNumber(res.senators[1].phones);
        representativeObj.Item.repname = res.representative.name;
        representativeObj.Item.repnumber = civicinfo_utils.normalizePhoneNumber(res.representative.phones);

        console.log('Rep: ' + JSON.stringify(representativeObj));
      })

      .then(() => docClientPut(representativeObj))
      .catch(error => console.log('CIVIC Parsing error:' + JSON.stringify(error)));
    }));
  });
}

module.exports.handler = (event, context, callback) => {
  Promise.all([
    list_field_migrate(),
    list_webhook_register()
    // repopulate_reps_table() NOT INTENDED FOR EVERY-SINGLE_DEPLOY!
  ]).then(values => {
    callback(null, { values: values });
  })

  .catch(error => {
    if (error.error) {
      console.log(error.code + ': ' + error.error);
    } else {
      console.log('There was an error performing migrations!');
    }
    callback(JSON.stringify({
      message: 'There was an error!',
      error: error
    }));
  });

};
<|endoftext|>


<commit_before>var HTMLCS = new function()
{
    var _standards    = {};
    var _sniffs       = [];
    var _tags         = {};
    var _standard     = null;
    var _currentSniff = null;

    var _messages     = [];
    var _msgOverrides = {};

    /*
        Message type constants.
    */
    this.ERROR   = 1;
    this.WARNING = 2;
    this.NOTICE  = 3;

    /**
     * Loads the specifid standard and run the sniffs.
     *
     * @param {string}         standard The name of the standard to load.
     * @param {string|DOMNode} An HTML string or a DOMNode.
     * @param {function}       The function that will be called when the testing is completed.
     */
    this.process = function(standard, content, callback) {
        if (!content) {
            return false;
        }

        if (_standards[_getStandardPath(standard)]) {
            HTMLCS.run(callback, content);
        } else {
            this.loadStandard(standard, function() {
                HTMLCS.run(callback, content);
            });
        }
    };

    /**
     * Loads the specified standard and its sniffs.
     *
     * @param {string}   standard The name of the standard to load.
     * @param {function} callback The function to call once the standard is loaded.
     *
     * @return void
     */
    this.loadStandard = function(standard, callback) {
        if (!standard) {
            return false;
        }

        _includeStandard(standard, function() {
            _standard = standard;
            callback.call(this);
        });
    };

    /**
     * Runs the sniffs for the loaded standard.
     *
     * @param {function}       callback The function to call once all sniffs are completed.
     * @param {string|DOMNode} content  An HTML string or a DOMNode.
     *
     * @return void
     */
    this.run = function(callback, content) {
        var element = null;
        if (typeof content === 'string') {
            element = document.createElement('div');
            element.innerHTML = content;
        } else {
            element = content;
        }

        if (!element) {
            callback.call(this);
            return;
        }

        callback  = callback || function() {};
        _messages = [];

        // Get all the elements in the element.
        var elements = _getAllTags(element);

        // Run the sniffs.
        _run(elements, callback);
    };

    /**
     * Adds a message.
     *
     * @param {integer} type The type of the message.
     * @param {DOMNode} element The element that the message is related to.
     * @param {string}  msg     The message string.
     * @param {string}  code    Unique code for the message.
     * @param {object}  data    Extra data to store for the message.
     */
    this.addMessage = function(type, element, msg, code, data) {
        code = _getMessageCode(code);

        _messages.push({
            type: type,
            element: element,
            msg: _msgOverrides[code] || msg,
            code: code,
            data: data
        });
    };

    /**
     * Returns all the messages for the last run.
     *
     * @return {array} Array of message objects.
     */
    this.getMessages = function() {
        return _messages;
    };

    /**
     * Runs the sniffs in the loaded standard for the specified element.
     *
     * @param {DOMNode}  element  The element to test.
     * @param {function} callback The function to call once all tests are run.
     */
    var _run = function(elements, callback) {
        if (elements.length === 0) {
            callback.call(this);
            return;
        }

        var element = elements.shift();
        var tagName = element.tagName.toLowerCase();
        if (_tags[tagName] && _tags[tagName].length > 0) {
            _processSniffs(element, _tags[tagName].concat([]), function() {
                _run(elements, callback);
            });
        } else {
            _run(elements, callback);
        }
    };

    /**
     * Process the sniffs.
     *
     * @param {DOMNode}  element  The element to test.
     * @param {array}    sniffs   Array of sniffs.
     * @param {function} callback The function to call once the processing is completed.
     */
    var _processSniffs = function(element, sniffs, callback) {
        if (sniffs.length === 0) {
            callback.call(this);
            return;
        }

        var sniff     = sniffs.shift();
        _currentSniff = sniff;

        if (sniff.useCallback === true) {
            // If the useCallback property is set to true then wait for process method
            // to call the function and then continue processing sniffs.
            sniff.process(element, function() {
                _processSniffs(element, sniffs, callback);
            });
        } else {
            // Process the sniff.
            sniff.process(element);

            // Continue processing the rest of the sniffs.
            _processSniffs(element, sniffs, callback);
        }
    };

    /**
     * Includes the specified standard file.
     *
     * @param {string}   standard The name of the standard.
     * @param {function} callback The function to call once the standard is included.
     * @param {object}   options  The options for the standard (e.g. exclude sniffs).
     */
    var _includeStandard = function(standard, callback, options) {
        if (standard.indexOf('http') !== 0) {
            standard = _getStandardPath(standard);
        }//end id

        // Include the standard's ruleset JS file.
        _includeScript(standard, function() {
            // Script is included now register the standard.
            _registerStandard(standard, callback, options);
        });
    };

    /**
     * Registers the specified standard and its sniffs.
     *
     * @param {string}   standard The name of the standard.
     * @param {function} callback The function to call once the standard is registered.
     * @param {object}   options  The options for the standard (e.g. exclude sniffs).
     */
    var _registerStandard = function(standard, callback, options) {
        // Get the object name.
        var parts = standard.split('/');

        // Get the ruleset object.
        var ruleSet = window['HTMLCS_' + parts[(parts.length - 2)]];
        if (!ruleSet) {
            return false;
        }

        _standards[standard] = ruleSet;

        // Process the options.
        if (options) {
            if (options.include && options.include.length > 0) {
                // Included sniffs.
                ruleSet.sniffs = options.include;
            } else if (options.exclude) {
                // Excluded sniffs.
                for (var i = 0; i < options.exclude.length; i++) {
                    var index = ruleSet.sniffs.find(options.exclude[i]);
                    if (index >= 0) {
                        ruleSet.sniffs.splice(index, 1);
                    }
                }
            }
        }//end if

        // Register the sniffs for this standard.
        _registerSniffs(standard, ruleSet.sniffs, callback);
    };

    /**
     * Registers the sniffs for the specified standard.
     *
     * @param {string}   standard The name of the standard.
     * @param {array}    sniffs   List of sniffs to register.
     * @param {function} callback The function to call once the sniffs are registered.
     */
    var _registerSniffs = function(standard, sniffs, callback) {
        if (sniffs.length === 0) {
            callback.call(this);
            return;
        }

        // Include and register sniffs.
        var sniff = sniffs.shift();
        _loadSniffFile(standard, sniff, function() {
            _registerSniffs(standard, sniffs, callback);
        });
    };

    /**
     * Includes the sniff's JS file and registers it.
     *
     * @param {string}        standard The name of the standard.
     * @param {string|object} sniff    The sniff to register, can be a string or
     *                                 and object specifying another standard.
     * @param {function}      callback The function to call once the sniff is included and registered.
     */
    var _loadSniffFile = function(standard, sniff, callback) {
        if (typeof sniff === 'string') {
            _includeScript(_getSniffPath(standard, sniff), function() {
                _registerSniff(standard, sniff);
                callback.call(this);
            });
        } else {
            // Including a whole other standard.
            _includeStandard(sniff.standard, function() {
                if (sniff.messages) {
                    // Add message overrides.
                    for (var msg in sniff.messages) {
                        _msgOverrides[msg] = sniff.messages[msg];
                    }
                }

                callback.call(this);
            }, {
                exclude: sniff.exclude,
                include: sniff.include
            });
        }
    };

    /**
     * Registers the specified sniff.
     *
     * @param {string} standard The name of the standard.
     * @param {string} sniff    The name of the sniff.
     */
    var _registerSniff = function(standard, sniff) {
        // Get the sniff object.
        var sniffObj = _getSniff(standard, sniff);
        if (!sniffObj) {
            return false;
        }

        // Call the register method of the sniff, it should return an array of tags.
        var watchedTags = sniffObj.register();
        if (watchedTags && watchedTags.length > 0) {
            for (var i = 0; i < watchedTags.length; i++) {
                if (!_tags[watchedTags[i]]) {
                    _tags[watchedTags[i]] = [];
                }

                _tags[watchedTags[i]].push(sniffObj);
            }
        }

        _sniffs.push(sniffObj);
    };

    /**
     * Returns the path to the sniff file.
     *
     * @param {string} standard The name of the standard.
     * @param {string} sniff    The name of the sniff.
     *
     * @return {string} The path to the JS file of the sniff.
     */
    var _getSniffPath = function(standard, sniff) {
        var parts = standard.split('/');
        parts.pop();

        return parts.join('/') + '/Sniffs/' + sniff.replace('.', '/', 'g') + '.js';
    };

    /**
     * Returns the path to a local standard.
     *
     * @param {string} standard The name of the standard.
     *
     * @return {string} The path to the local standard.
     */
    var _getStandardPath = function(standard)
    {
        // Get the include path of a local standard.
        var scripts = document.getElementsByTagName('script');
        var path    = null;

        // Loop through all the script tags that exist in the document and find the one
        // that has included this file.
        for (var i = 0; i < scripts.length; i++) {
            if (scripts[i].src) {
                if (scripts[i].src.match(/HTMLCS\.js/)) {
                    // We have found our appropriate <script> tag that includes
                    // this file, we can extract the path.
                    path = scripts[i].src.replace(/HTMLCS\.js/,'');
                    break;
                }
            }
        }

        return path + 'Standards/' + standard + '/ruleset.js';

    };

    /**
     * Returns the sniff object.
     *
     * @param {string} standard The name of the standard.
     * @param {string} sniff    The name of the sniff.
     *
     * @return {object} The sniff object.
     */
    var _getSniff = function(standard, sniff) {
        var name = 'HTMLCS_';
        name    += _standards[standard].name + '_Sniffs_';
        name    += sniff.split('.').join('_');

        if (!window[name]) {
            return null;
        }

        window[name]._name = sniff;
        return window[name];
    };

    /**
     * Returns the full message code.
     *
     * A full message code includes the standard name, the sniff name and the given code.
     *
     * @return {string} The full message code.
     */
    var _getMessageCode = function(code) {
        code = _standard + '.' + _currentSniff._name + '.' + code;
        return code;
    };

    /**
     * Includes the specified JS file.
     *
     * @param {string}   src      The URL to the JS file.
     * @param {function} callback The function to call once the script is loaded.
     */
    var _includeScript = function(src, callback) {
        var script    = document.createElement('script');
        script.onload = function() {
            callback.call(this);
        };

        script.src = src;
        document.head.appendChild(script);
    };

    /**
     * Returns all the child elements in the given element.
     *
     * @param {DOMNode} element The parent element.
     *
     * @return {array} Array of DOMNode.
     */
    var _getAllTags = function(element) {
        element      = element || document;
        var elements = element.getElementsByTagName('*');

        // Conver to array.
        elements = [].slice.call(elements, 0);

        return elements;
    };

};
<commit_msg>Fixed regex for Chrome<commit_after>var HTMLCS = new function()
{
    var _standards    = {};
    var _sniffs       = [];
    var _tags         = {};
    var _standard     = null;
    var _currentSniff = null;

    var _messages     = [];
    var _msgOverrides = {};

    /*
        Message type constants.
    */
    this.ERROR   = 1;
    this.WARNING = 2;
    this.NOTICE  = 3;

    /**
     * Loads the specifid standard and run the sniffs.
     *
     * @param {string}         standard The name of the standard to load.
     * @param {string|DOMNode} An HTML string or a DOMNode.
     * @param {function}       The function that will be called when the testing is completed.
     */
    this.process = function(standard, content, callback) {
        if (!content) {
            return false;
        }

        if (_standards[_getStandardPath(standard)]) {
            HTMLCS.run(callback, content);
        } else {
            this.loadStandard(standard, function() {
                HTMLCS.run(callback, content);
            });
        }
    };

    /**
     * Loads the specified standard and its sniffs.
     *
     * @param {string}   standard The name of the standard to load.
     * @param {function} callback The function to call once the standard is loaded.
     *
     * @return void
     */
    this.loadStandard = function(standard, callback) {
        if (!standard) {
            return false;
        }

        _includeStandard(standard, function() {
            _standard = standard;
            callback.call(this);
        });
    };

    /**
     * Runs the sniffs for the loaded standard.
     *
     * @param {function}       callback The function to call once all sniffs are completed.
     * @param {string|DOMNode} content  An HTML string or a DOMNode.
     *
     * @return void
     */
    this.run = function(callback, content) {
        var element = null;
        if (typeof content === 'string') {
            element = document.createElement('div');
            element.innerHTML = content;
        } else {
            element = content;
        }

        if (!element) {
            callback.call(this);
            return;
        }

        callback  = callback || function() {};
        _messages = [];

        // Get all the elements in the element.
        var elements = _getAllTags(element);

        // Run the sniffs.
        _run(elements, callback);
    };

    /**
     * Adds a message.
     *
     * @param {integer} type The type of the message.
     * @param {DOMNode} element The element that the message is related to.
     * @param {string}  msg     The message string.
     * @param {string}  code    Unique code for the message.
     * @param {object}  data    Extra data to store for the message.
     */
    this.addMessage = function(type, element, msg, code, data) {
        code = _getMessageCode(code);

        _messages.push({
            type: type,
            element: element,
            msg: _msgOverrides[code] || msg,
            code: code,
            data: data
        });
    };

    /**
     * Returns all the messages for the last run.
     *
     * @return {array} Array of message objects.
     */
    this.getMessages = function() {
        return _messages;
    };

    /**
     * Runs the sniffs in the loaded standard for the specified element.
     *
     * @param {DOMNode}  element  The element to test.
     * @param {function} callback The function to call once all tests are run.
     */
    var _run = function(elements, callback) {
        if (elements.length === 0) {
            callback.call(this);
            return;
        }

        var element = elements.shift();
        var tagName = element.tagName.toLowerCase();
        if (_tags[tagName] && _tags[tagName].length > 0) {
            _processSniffs(element, _tags[tagName].concat([]), function() {
                _run(elements, callback);
            });
        } else {
            _run(elements, callback);
        }
    };

    /**
     * Process the sniffs.
     *
     * @param {DOMNode}  element  The element to test.
     * @param {array}    sniffs   Array of sniffs.
     * @param {function} callback The function to call once the processing is completed.
     */
    var _processSniffs = function(element, sniffs, callback) {
        if (sniffs.length === 0) {
            callback.call(this);
            return;
        }

        var sniff     = sniffs.shift();
        _currentSniff = sniff;

        if (sniff.useCallback === true) {
            // If the useCallback property is set to true then wait for process method
            // to call the function and then continue processing sniffs.
            sniff.process(element, function() {
                _processSniffs(element, sniffs, callback);
            });
        } else {
            // Process the sniff.
            sniff.process(element);

            // Continue processing the rest of the sniffs.
            _processSniffs(element, sniffs, callback);
        }
    };

    /**
     * Includes the specified standard file.
     *
     * @param {string}   standard The name of the standard.
     * @param {function} callback The function to call once the standard is included.
     * @param {object}   options  The options for the standard (e.g. exclude sniffs).
     */
    var _includeStandard = function(standard, callback, options) {
        if (standard.indexOf('http') !== 0) {
            standard = _getStandardPath(standard);
        }//end id

        // Include the standard's ruleset JS file.
        _includeScript(standard, function() {
            // Script is included now register the standard.
            _registerStandard(standard, callback, options);
        });
    };

    /**
     * Registers the specified standard and its sniffs.
     *
     * @param {string}   standard The name of the standard.
     * @param {function} callback The function to call once the standard is registered.
     * @param {object}   options  The options for the standard (e.g. exclude sniffs).
     */
    var _registerStandard = function(standard, callback, options) {
        // Get the object name.
        var parts = standard.split('/');

        // Get the ruleset object.
        var ruleSet = window['HTMLCS_' + parts[(parts.length - 2)]];
        if (!ruleSet) {
            return false;
        }

        _standards[standard] = ruleSet;

        // Process the options.
        if (options) {
            if (options.include && options.include.length > 0) {
                // Included sniffs.
                ruleSet.sniffs = options.include;
            } else if (options.exclude) {
                // Excluded sniffs.
                for (var i = 0; i < options.exclude.length; i++) {
                    var index = ruleSet.sniffs.find(options.exclude[i]);
                    if (index >= 0) {
                        ruleSet.sniffs.splice(index, 1);
                    }
                }
            }
        }//end if

        // Register the sniffs for this standard.
        _registerSniffs(standard, ruleSet.sniffs, callback);
    };

    /**
     * Registers the sniffs for the specified standard.
     *
     * @param {string}   standard The name of the standard.
     * @param {array}    sniffs   List of sniffs to register.
     * @param {function} callback The function to call once the sniffs are registered.
     */
    var _registerSniffs = function(standard, sniffs, callback) {
        if (sniffs.length === 0) {
            callback.call(this);
            return;
        }

        // Include and register sniffs.
        var sniff = sniffs.shift();
        _loadSniffFile(standard, sniff, function() {
            _registerSniffs(standard, sniffs, callback);
        });
    };

    /**
     * Includes the sniff's JS file and registers it.
     *
     * @param {string}        standard The name of the standard.
     * @param {string|object} sniff    The sniff to register, can be a string or
     *                                 and object specifying another standard.
     * @param {function}      callback The function to call once the sniff is included and registered.
     */
    var _loadSniffFile = function(standard, sniff, callback) {
        if (typeof sniff === 'string') {
            _includeScript(_getSniffPath(standard, sniff), function() {
                _registerSniff(standard, sniff);
                callback.call(this);
            });
        } else {
            // Including a whole other standard.
            _includeStandard(sniff.standard, function() {
                if (sniff.messages) {
                    // Add message overrides.
                    for (var msg in sniff.messages) {
                        _msgOverrides[msg] = sniff.messages[msg];
                    }
                }

                callback.call(this);
            }, {
                exclude: sniff.exclude,
                include: sniff.include
            });
        }
    };

    /**
     * Registers the specified sniff.
     *
     * @param {string} standard The name of the standard.
     * @param {string} sniff    The name of the sniff.
     */
    var _registerSniff = function(standard, sniff) {
        // Get the sniff object.
        var sniffObj = _getSniff(standard, sniff);
        if (!sniffObj) {
            return false;
        }

        // Call the register method of the sniff, it should return an array of tags.
        var watchedTags = sniffObj.register();
        if (watchedTags && watchedTags.length > 0) {
            for (var i = 0; i < watchedTags.length; i++) {
                if (!_tags[watchedTags[i]]) {
                    _tags[watchedTags[i]] = [];
                }

                _tags[watchedTags[i]].push(sniffObj);
            }
        }

        _sniffs.push(sniffObj);
    };

    /**
     * Returns the path to the sniff file.
     *
     * @param {string} standard The name of the standard.
     * @param {string} sniff    The name of the sniff.
     *
     * @return {string} The path to the JS file of the sniff.
     */
    var _getSniffPath = function(standard, sniff) {
        var parts = standard.split('/');
        parts.pop();
        var path = parts.join('/') + '/Sniffs/' + sniff.replace(/\./g, '/') + '.js';
        return path;
    };

    /**
     * Returns the path to a local standard.
     *
     * @param {string} standard The name of the standard.
     *
     * @return {string} The path to the local standard.
     */
    var _getStandardPath = function(standard)
    {
        // Get the include path of a local standard.
        var scripts = document.getElementsByTagName('script');
        var path    = null;

        // Loop through all the script tags that exist in the document and find the one
        // that has included this file.
        for (var i = 0; i < scripts.length; i++) {
            if (scripts[i].src) {
                if (scripts[i].src.match(/HTMLCS\.js/)) {
                    // We have found our appropriate <script> tag that includes
                    // this file, we can extract the path.
                    path = scripts[i].src.replace(/HTMLCS\.js/,'');
                    break;
                }
            }
        }

        return path + 'Standards/' + standard + '/ruleset.js';

    };

    /**
     * Returns the sniff object.
     *
     * @param {string} standard The name of the standard.
     * @param {string} sniff    The name of the sniff.
     *
     * @return {object} The sniff object.
     */
    var _getSniff = function(standard, sniff) {
        var name = 'HTMLCS_';
        name    += _standards[standard].name + '_Sniffs_';
        name    += sniff.split('.').join('_');

        if (!window[name]) {
            return null;
        }

        window[name]._name = sniff;
        return window[name];
    };

    /**
     * Returns the full message code.
     *
     * A full message code includes the standard name, the sniff name and the given code.
     *
     * @return {string} The full message code.
     */
    var _getMessageCode = function(code) {
        code = _standard + '.' + _currentSniff._name + '.' + code;
        return code;
    };

    /**
     * Includes the specified JS file.
     *
     * @param {string}   src      The URL to the JS file.
     * @param {function} callback The function to call once the script is loaded.
     */
    var _includeScript = function(src, callback) {
        var script    = document.createElement('script');
        script.onload = function() {
            callback.call(this);
        };

        script.src = src;
        document.head.appendChild(script);
    };

    /**
     * Returns all the child elements in the given element.
     *
     * @param {DOMNode} element The parent element.
     *
     * @return {array} Array of DOMNode.
     */
    var _getAllTags = function(element) {
        element      = element || document;
        var elements = element.getElementsByTagName('*');

        // Conver to array.
        elements = [].slice.call(elements, 0);

        return elements;
    };

};
<|endoftext|>


<commit_before>$(document).ready(function(){
    var nofinv = 1;
    $('#id_invoicenumber').addClass('invoice'+' '+nofinv);
    $('#id_invoicestatus').addClass('invoiceadditional'+' '+nofinv);
    $('#id_paidon').addClass('paid'+' '+nofinv);
    $('#id_rejectreason').addClass('reject'+' '+nofinv);
    $("#id_amount").addClass("amount"+" "+nofinv);
    $("#id_currency").addClass("currency"+" "+nofinv);
    $("#id_reasonother").addClass("other"+" "+nofinv);
    $('.addhiddendata:first').find('#id_invoicenumber').attr('id', 'id_invoicenumber'+nofinv);
    $('.addhiddendata:first').find('#id_invoicestatus').attr('id', 'id_invoicestatus'+nofinv);
    $('.addhiddendata:first').find('#id_paidon').attr('id', 'id_paidon'+nofinv);
    $('.addhiddendata:first').find('#id_rejectreason').attr('id', 'id_rejectreason'+nofinv);
    $(".addhiddendata:first").find("#id_amount").attr("id", "id_amount"+nofinv);
    $(".addhiddendata:first").find("#id_currency").attr("id", "id_currency"+nofinv);
    $("#id_reasonother").attr("id", "id_reasonother"+nofinv);

    $('#trbutton').on('click', function(){
	$('#trbutton').fadeOut('slow', function(){
	    $('#trform').fadeIn('slow');
	    $('#ptrack').html('Please fill in all the fields.');
	});
    });

    $('#id_reminderdate').datepicker({
	dateFormat: 'yy-mm-dd',
	constrainInput: false
    });
    $('.paid:first').datepicker({
	dateFormat: 'yy-mm-dd',
	constrainInput: false
    });

    var $name = $('#vclerk').attr('value');
    $('#id_clerk').val($name);

    $('#id_clerk').attr('readonly', true);
    $('#id_actiondate').attr('readonly', true);

    $('#id_market').on('change', function(){
	//show the ccode choice if is hidden
	if ($('#id_ccode').is(':hidden')) {$('#id_ccode').show()};

	$('#id_ccode option').each(function(){
	    $(this).show();
	});

	var market = $('#id_market').val();
	if (market == 'IT') {
	    var marketArray = ['', '11', '13', '15', '16'];
	} else if (market == 'DE') {
	    var marketArray = ['', '13', '52', '55', '60', '64', '66'];
	} else if (market == 'PT' || market == 'PL' || market == 'NL' || market == 'NO') {
	    var marketArray = ['', '10'];
	} else if (market == 'BE') {
	    var marketArray = ['', '12', '14', '18', '31'];
	} else if (market == 'SE') {
	    var marketArray = ['', '16'];
	} else if (market == 'FI') {
	    var marketArray = ['', '11'];
	} else if (market == 'DK') {
	    var marketArray = ['', '12'];
	} else {
	    var marketArray = [''];
	}

	$('#id_ccode option').each(function(){
	    var ccodeOpt = $(this).val();
	    if ($.inArray(ccodeOpt, marketArray) > -1){
		;
	    } else {
		$(this).hide();
	    }
	});

    });

    $(document).on('change', '.status', function() {
	var status = $(this).val();
	var nextform = $(this).parent().parent().parent().next();

	if (nextform.is(':hidden')){
	    ;
	} else {
	    nextform.hide();
	    if (nextform.find('.paid').is(':hidden')) {nextform.find('.paid').show()};
	    if (nextform.find('.other').is(':hidden')) {nextform.find('.other').show()};
	    if (nextform.find('.reject').is(':hidden')) {nextform.find('.reject').show()};
	    nextform.find('label').show();
	}

	if (status == 'RJ'){
	    nextform.find('.paid').hide();
	    nextform.find('label:last').hide();
	    nextform.fadeIn('slow');
	} else if (status == 'PD') {
	    nextform.find('.reject').hide();
	    nextform.find(".other").hide();
	    nextform.find('label:first').hide();
	    nextform.find('label:first').next().next("label").hide();
	    nextform.fadeIn('slow');
	};
    });

    $('#addbutt').on('click', function() {
	var formToApp = $('.addhiddendata:first').clone();
	formToApp.find('button').remove();
	formToApp.find('.paid').removeClass('hasDatepicker');
	formToApp.find('.paid').val('');
	formToApp.find('#id_invoicenumber1').removeClass('invoice'+' '+nofinv);
	formToApp.find('#id_invoicestatus1').removeClass('invoiceadditional'+' '+nofinv);
	formToApp.find('#id_paidon1').removeClass('paid'+' '+nofinv);
	formToApp.find('#id_rejectreason1').removeClass('reject'+' '+nofinv);
	formToApp.find("#id_amount1").removeClass("amount"+" "+nofinv);
	formToApp.find("#id_currency1").removeClass("currency"+" "+nofinv);
	formToApp.find("#id_reasonother1").removeClass("other"+" "+nofinv);
	nofinv = nofinv + 1;
	formToApp.find('#id_rejectreason1').addClass('reject'+' '+nofinv);
	formToApp.find('#id_rejectreason1').attr('name', 'reject'+nofinv);
	formToApp.find('#id_rejectreason1').attr('id', 'id_rejectreason'+nofinv);
	formToApp.find('#id_paidon1').addClass('paid'+' '+nofinv);
	formToApp.find('#id_paidon1').attr('name', 'paid'+nofinv);
	formToApp.find('#id_paidon1').attr('id', 'id_paidon'+nofinv);
	formToApp.find('#id_invoicenumber1').addClass('invoice'+' '+nofinv);
	formToApp.find('#id_invoicenumber1').attr('name', 'invoicenumber'+nofinv);
	formToApp.find('#id_invoicenumber1').attr('id', 'id_invoicenumber'+nofinv);
	formToApp.find('#id_invoicestatus1').addClass('invoiceadditional'+' '+nofinv);
	formToApp.find('#id_invoicestatus1').attr('name', 'invoicestatus'+nofinv);
	formToApp.find('#id_invoicestatus1').attr('id', 'id_invoicestatus'+nofinv);
	formToApp.find("#id_amount1").addClass("amount"+" "+nofinv);
	formToApp.find("#id_amount1").attr("name", "amount"+nofinv);
	formToApp.find("#id_amount1").attr("id", "id_amount"+nofinv);
	formToApp.find("#id_currency1").addClass("currency"+" "+nofinv);
	formToApp.find("#id_currency1").attr("name", "currency"+nofinv);
	formToApp.find("#id_currency1").attr("id", "id_currency"+nofinv);
	formToApp.find('#id_reasonother1').addClass('other'+' '+nofinv);
	formToApp.find('#id_reasonother1').attr('name', 'reasonother'+nofinv);
	formToApp.find('#id_reasonother1').attr('id', 'id_reasonother'+nofinv);
	$('#vendorform').before(formToApp);
	formToApp.find('.paid').datepicker({
	    dateFormat: 'yy-mm-dd',
	    constrainInput: false
	});
    });

    $('#rembutt').on('click', function() {
	//Remove additional invoices if there are at least 2 of them.
	if ($('.invoice').length == 1) {
	    ;
	} else {
	    $('.addhiddendata:last').remove();
	};
    });

    $('#id_reminderdate').on('change', function() {
	var rdate = $(this).val().split('-');
	var market = $('#id_market').val();
	$('#id_remindernumber').val('');
	$('#id_remindernumber').val(market+rdate[0]+rdate[1]+rdate[2]+'/');
    });

    function DunningTrack() {
	// get the total number of invoices.
	var invo = $('.invoice').length;

	var data = new Array()

	//loop through the invoice to create our data to post
	for (x = 1; x <= invo; x++) {
	    var formn = 'form'+x;
	    var obj = {
		market: $('#id_market').val(),
		ccode: $('#id_ccode').val(),
		clerk: $('#id_clerk').val(),
		actiondate: $('#id_actiondate').val(),
		reminderdate: $('#id_actiondate').val(),
		level: $('#id_level').val(),
		amount: $("#id_amount"+x).val(),
		currency: $("#id_currency"+x).val(),
		remindernumber: $('#id_remindernumber').val(),
		vendor: $('#id_vendor').val(),
		mailvendor: $('#id_mailvendor').val(),
		invoicenumber: $('#id_invoicenumber'+x).val(),
		invoicestatus: $('#id_invoicestatus'+x).val(),
		actiontaken: actionArray(),
		rejectreason: $('#id_rejectreason'+x).val(),
		paidon: $('#id_paidon'+x).val()
		//attachment:
	    };
	    data.push(obj);
	}

	//setup the AJAX request
	$.ajaxSetup({
	    type: 'POST',
	    dataType: 'json'
	});

	//the real AJAX request
	$.ajax({
	    url: '/ajax/',
	    data: {
		form_type: 'multi',
		mass_data: JSON.stringify(data)
	    },
	    success: window.location.replace("/main/"),
	    error: function (ajaxObj, textStatus, error) {
		alert(error);
	    }
	});
	return true;
    };

    $('#trackbutton').on('click', ValidateForm);
    $("#trform :input").on("change", function() {
	if ( $(this).val() != "" ) {
	    if ( $(this).parent().parent().hasClass("has-error") ) {
		$(this).parent().parent().removeClass("has-error");
	    }
	}
    });

    function ValidateForm() {
	DunningTrack();
    };
});

function SuccessfulTracking() {
    $('#trform *').filter(':input').each(function() {
	$(this).val('');
    });

function isValidEmailAddress(emailAddress) {
    var pattern = new RegExp(/^(("[\w-+\s]+")|([\w-+]+(?:\.[\w-+]+)*)|("[\w-+\s]+")([\w-+]+(?:\.[\w-+]+)*))(@((?:[\w-+]+\.)*\w[\w-+]{0,66})\.([a-z]{2,6}(?:\.[a-z]{2})?)$)|(@\[?((25[0-5]\.|2[0-4][\d]\.|1[\d]{2}\.|[\d]{1,2}\.))((25[0-5]|2[0-4][\d]|1[\d]{2}|[\d]{1,2})\.){2}(25[0-5]|2[0-4][\d]|1[\d]{2}|[\d]{1,2})\]?$)/i);
    return pattern.test(emailAddress);
};

function isInteger(value) {
    var intPattern = new RegExp(/^[0-9]+$/)
    return intPattern.test(value);
};
<commit_msg>This will be hold the final message after an item passed JS check and DB check. If the JS check is passed the item will be sent to our DB and if we get a JSON response like {"success": "true"} we will be sure that the item has been saved into our DB.<commit_after>$(document).ready(function(){
    var nofinv = 1;
    $('#id_invoicenumber').addClass('invoice'+' '+nofinv);
    $('#id_invoicestatus').addClass('invoiceadditional'+' '+nofinv);
    $('#id_paidon').addClass('paid'+' '+nofinv);
    $('#id_rejectreason').addClass('reject'+' '+nofinv);
    $("#id_amount").addClass("amount"+" "+nofinv);
    $("#id_currency").addClass("currency"+" "+nofinv);
    $("#id_reasonother").addClass("other"+" "+nofinv);
    $('.addhiddendata:first').find('#id_invoicenumber').attr('id', 'id_invoicenumber'+nofinv);
    $('.addhiddendata:first').find('#id_invoicestatus').attr('id', 'id_invoicestatus'+nofinv);
    $('.addhiddendata:first').find('#id_paidon').attr('id', 'id_paidon'+nofinv);
    $('.addhiddendata:first').find('#id_rejectreason').attr('id', 'id_rejectreason'+nofinv);
    $(".addhiddendata:first").find("#id_amount").attr("id", "id_amount"+nofinv);
    $(".addhiddendata:first").find("#id_currency").attr("id", "id_currency"+nofinv);
    $("#id_reasonother").attr("id", "id_reasonother"+nofinv);

    $('#trbutton').on('click', function(){
	$('#trbutton').fadeOut('slow', function(){
	    $('#trform').fadeIn('slow');
	    $('#ptrack').html('Please fill in all the fields.');
	});
    });

    $('#id_reminderdate').datepicker({
	dateFormat: 'yy-mm-dd',
	constrainInput: false
    });
    $('.paid:first').datepicker({
	dateFormat: 'yy-mm-dd',
	constrainInput: false
    });

    var $name = $('#vclerk').attr('value');
    $('#id_clerk').val($name);

    $('#id_clerk').attr('readonly', true);
    $('#id_actiondate').attr('readonly', true);

    $('#id_market').on('change', function(){
	//show the ccode choice if is hidden
	if ($('#id_ccode').is(':hidden')) {$('#id_ccode').show()};

	$('#id_ccode option').each(function(){
	    $(this).show();
	});

	var market = $('#id_market').val();
	if (market == 'IT') {
	    var marketArray = ['', '11', '13', '15', '16'];
	} else if (market == 'DE') {
	    var marketArray = ['', '13', '52', '55', '60', '64', '66'];
	} else if (market == 'PT' || market == 'PL' || market == 'NL' || market == 'NO') {
	    var marketArray = ['', '10'];
	} else if (market == 'BE') {
	    var marketArray = ['', '12', '14', '18', '31'];
	} else if (market == 'SE') {
	    var marketArray = ['', '16'];
	} else if (market == 'FI') {
	    var marketArray = ['', '11'];
	} else if (market == 'DK') {
	    var marketArray = ['', '12'];
	} else {
	    var marketArray = [''];
	}

	$('#id_ccode option').each(function(){
	    var ccodeOpt = $(this).val();
	    if ($.inArray(ccodeOpt, marketArray) > -1){
		;
	    } else {
		$(this).hide();
	    }
	});

    });

    $(document).on('change', '.status', function() {
	var status = $(this).val();
	var nextform = $(this).parent().parent().parent().next();

	if (nextform.is(':hidden')){
	    ;
	} else {
	    nextform.hide();
	    if (nextform.find('.paid').is(':hidden')) {nextform.find('.paid').show()};
	    if (nextform.find('.other').is(':hidden')) {nextform.find('.other').show()};
	    if (nextform.find('.reject').is(':hidden')) {nextform.find('.reject').show()};
	    nextform.find('label').show();
	}

	if (status == 'RJ'){
	    nextform.find('.paid').hide();
	    nextform.find('label:last').hide();
	    nextform.fadeIn('slow');
	} else if (status == 'PD') {
	    nextform.find('.reject').hide();
	    nextform.find(".other").hide();
	    nextform.find('label:first').hide();
	    nextform.find('label:first').next().next("label").hide();
	    nextform.fadeIn('slow');
	};
    });

    $('#addbutt').on('click', function() {
	var formToApp = $('.addhiddendata:first').clone();
	formToApp.find('button').remove();
	formToApp.find('.paid').removeClass('hasDatepicker');
	formToApp.find('.paid').val('');
	formToApp.find('#id_invoicenumber1').removeClass('invoice'+' '+nofinv);
	formToApp.find('#id_invoicestatus1').removeClass('invoiceadditional'+' '+nofinv);
	formToApp.find('#id_paidon1').removeClass('paid'+' '+nofinv);
	formToApp.find('#id_rejectreason1').removeClass('reject'+' '+nofinv);
	formToApp.find("#id_amount1").removeClass("amount"+" "+nofinv);
	formToApp.find("#id_currency1").removeClass("currency"+" "+nofinv);
	formToApp.find("#id_reasonother1").removeClass("other"+" "+nofinv);
	nofinv = nofinv + 1;
	formToApp.find('#id_rejectreason1').addClass('reject'+' '+nofinv);
	formToApp.find('#id_rejectreason1').attr('name', 'reject'+nofinv);
	formToApp.find('#id_rejectreason1').attr('id', 'id_rejectreason'+nofinv);
	formToApp.find('#id_paidon1').addClass('paid'+' '+nofinv);
	formToApp.find('#id_paidon1').attr('name', 'paid'+nofinv);
	formToApp.find('#id_paidon1').attr('id', 'id_paidon'+nofinv);
	formToApp.find('#id_invoicenumber1').addClass('invoice'+' '+nofinv);
	formToApp.find('#id_invoicenumber1').attr('name', 'invoicenumber'+nofinv);
	formToApp.find('#id_invoicenumber1').attr('id', 'id_invoicenumber'+nofinv);
	formToApp.find('#id_invoicestatus1').addClass('invoiceadditional'+' '+nofinv);
	formToApp.find('#id_invoicestatus1').attr('name', 'invoicestatus'+nofinv);
	formToApp.find('#id_invoicestatus1').attr('id', 'id_invoicestatus'+nofinv);
	formToApp.find("#id_amount1").addClass("amount"+" "+nofinv);
	formToApp.find("#id_amount1").attr("name", "amount"+nofinv);
	formToApp.find("#id_amount1").attr("id", "id_amount"+nofinv);
	formToApp.find("#id_currency1").addClass("currency"+" "+nofinv);
	formToApp.find("#id_currency1").attr("name", "currency"+nofinv);
	formToApp.find("#id_currency1").attr("id", "id_currency"+nofinv);
	formToApp.find('#id_reasonother1').addClass('other'+' '+nofinv);
	formToApp.find('#id_reasonother1').attr('name', 'reasonother'+nofinv);
	formToApp.find('#id_reasonother1').attr('id', 'id_reasonother'+nofinv);
	$('#vendorform').before(formToApp);
	formToApp.find('.paid').datepicker({
	    dateFormat: 'yy-mm-dd',
	    constrainInput: false
	});
    });

    $('#rembutt').on('click', function() {
	//Remove additional invoices if there are at least 2 of them.
	if ($('.invoice').length == 1) {
	    ;
	} else {
	    $('.addhiddendata:last').remove();
	};
    });

    $('#id_reminderdate').on('change', function() {
	var rdate = $(this).val().split('-');
	var market = $('#id_market').val();
	$('#id_remindernumber').val('');
	$('#id_remindernumber').val(market+rdate[0]+rdate[1]+rdate[2]+'/');
    });

    function DunningTrack() {
	// get the total number of invoices.
	var invo = $('.invoice').length;

	var data = new Array()

	//loop through the invoice to create our data to post
	for (x = 1; x <= invo; x++) {
	    var formn = 'form'+x;
	    var obj = {
		market: $('#id_market').val(),
		ccode: $('#id_ccode').val(),
		clerk: $('#id_clerk').val(),
		actiondate: $('#id_actiondate').val(),
		reminderdate: $('#id_actiondate').val(),
		level: $('#id_level').val(),
		amount: $("#id_amount"+x).val(),
		currency: $("#id_currency"+x).val(),
		remindernumber: $('#id_remindernumber').val(),
		vendor: $('#id_vendor').val(),
		mailvendor: $('#id_mailvendor').val(),
		invoicenumber: $('#id_invoicenumber'+x).val(),
		invoicestatus: $('#id_invoicestatus'+x).val(),
		actiontaken: actionArray(),
		rejectreason: $('#id_rejectreason'+x).val(),
		paidon: $('#id_paidon'+x).val()
		//attachment:
	    };
	    data.push(obj);
	}

	//setup the AJAX request
	$.ajaxSetup({
	    type: 'POST',
	    dataType: 'json'
	});

	//the real AJAX request
	$.ajax({
	    url: '/ajax/',
	    data: {
		form_type: 'multi',
		mass_data: JSON.stringify(data)
	    },
	    success: window.location.replace("/main/"),
	    error: function (ajaxObj, textStatus, error) {
		alert(error);
	    }
	});
	return true;
    };

    $('#trackbutton').on('click', ValidateForm);
    $("#trform :input").on("change", function() {
	if ( $(this).val() != "" ) {
	    if ( $(this).parent().parent().hasClass("has-error") ) {
		$(this).parent().parent().removeClass("has-error");
	    }
	}
    });

    function ValidateForm() {
	DunningTrack();
    };
});

function SuccessfulTracking() {
    alert("Item correctly tracked");
};
    });

function isValidEmailAddress(emailAddress) {
    var pattern = new RegExp(/^(("[\w-+\s]+")|([\w-+]+(?:\.[\w-+]+)*)|("[\w-+\s]+")([\w-+]+(?:\.[\w-+]+)*))(@((?:[\w-+]+\.)*\w[\w-+]{0,66})\.([a-z]{2,6}(?:\.[a-z]{2})?)$)|(@\[?((25[0-5]\.|2[0-4][\d]\.|1[\d]{2}\.|[\d]{1,2}\.))((25[0-5]|2[0-4][\d]|1[\d]{2}|[\d]{1,2})\.){2}(25[0-5]|2[0-4][\d]|1[\d]{2}|[\d]{1,2})\]?$)/i);
    return pattern.test(emailAddress);
};

function isInteger(value) {
    var intPattern = new RegExp(/^[0-9]+$/)
    return intPattern.test(value);
};
<|endoftext|>