"use-strict"

var Lexer = require("lexer");

var EmergencyCode = function(msg) {
  var hasCode = false;
  var satisfied = false;
  var lexer = new Lexer(function (char) {});
  
  this.isCancelled = false;
  this.color = "";
  this.team = "";
  this.room = "";
  
  var _this = this;
  
  // Parse color
  lexer.addRule(/code/i, function() {
    hasCode = true;
  }).addRule(/red/i, function() {
    if (hasCode) satisfied = true;
    _this.color = "RED";
  }).addRule(/blue/i, function() {
    if (hasCode) satisfied = true;
    _this.color = "BLUE";
  }).addRule(/orange/i, function() {
    if (hasCode) satisfied = true;
    _this.color = "ORANGE";
  }).addRule(/silver/i, function() {
    if (hasCode) satisfied = true;
    _this.color = "SILVER";
  }).addRule(/grey/i, function() {
    if (hasCode) satisfied = true;
    _this.color = "GREY";
  }).addRule(/clear/i, function() {
    if (hasCode) satisfied = true;
    _this.color = "CLEAR";
  }).addRule(/grey/i, function() {
    if (hasCode) satisfied = true;
    _this.color = "GREY";
  });
  
  // Check if it was cancelled
  lexer.addRule(/cancel/i, function() {
    _this.isCancelled = true;
  });
  
  // Check if there is a team
  var expectingTeam = false;
  lexer.addRule(/team/i, function() {
    expectingTeam = true;
  });
  
  // Check if there is a room
  var expectingRoom = false;
  lexer.addRule(/room/i, function() {
    expectingRoom = true;
  }).addRule(/room:/i, function() {
    expectingRoom = true;
  })
  
  lexer.addRule(/[0-9]+/, function(token) {
    if (expectingTeam) {
      _this.team = token;
      expectingTeam = false;
    } else if (expectingRoom) {
      _this.room = token;
    }
  });
  
  lexer.setInput(msg).lex();
  
  this.isSatisfied = function() {
    return satisfied;
  }
}

var BedRequest = function(msg) {
  this.subject = "";
  this.message = "";
  this.isSatisfied = function() {
    return this.message !== "" && this.subject !== "";
  }
  
  if (msg.toLowerCase().indexOf("bed request") == -1) {
    return;
  }
  const STATE_IDLE = 0;
  const EXPECTING_SUBJECT = 1;
  const EXPECTING_MSG = 2;
  
  var state = STATE_IDLE;
  var lexer = new Lexer(function (char) {});
  var _this = this;
  
  lexer.addRule(/subject:/i, function() {
    state = EXPECTING_SUBJECT;
  }).addRule(/message:/i, function() {
    state = EXPECTING_MSG;
  }).addRule(/bed/i, function() {
  }).addRule(/./, function(char) {
   if (state == EXPECTING_SUBJECT) {
     _this.subject += char;
   } else if (state == EXPECTING_MSG) {
     _this.message += char;
   }
  });
  
  lexer.setInput(msg).lex();
  this.subject = this.subject.trim();
  this.message = this.message.trim();
}

var TransportRequest = function(msg) {
  this.sequence = "Primary";
  this.origin = "";
  this.destination = "";
  this.mode = "";
  
  this.isSatisfied = function() {
    return this.origin !== "" && this.destination !== "" && this.mode !== "";
  }
  
  if (msg.toLowerCase().indexOf("transport request") == -1) {
    return;
  }
  const STATE_IDLE = 0;
  const EXPECTING_ORIGIN = 1;
  const EXPECTING_DESTINATION = 2;
  const EXPECTING_MODE = 3;
  const EXPECTING_REQUIREMENTS = 4;
  
  var state = STATE_IDLE;
  var lexer = new Lexer(function (char) {});
  var _this = this;
  
  lexer.addRule(/secondary/i, function() {
    _this.sequence = "Secondary"
  }).addRule(/origin:/i, function() {
    state = EXPECTING_ORIGIN;
  }).addRule(/destination:/i, function() {
    
    state = EXPECTING_DESTINATION;
  }).addRule(/requirements:/i, function() {
    state = EXPECTING_REQUIREMENTS;
  }).addRule(/mode:/i, function() {
    state = EXPECTING_MODE;
  }).addRule(/./, function(char) {
   if (state == EXPECTING_ORIGIN) {
     _this.origin += char;
   } else if (state == EXPECTING_DESTINATION) {
     _this.destination += char;
   } else if (state == EXPECTING_MODE) {
     _this.mode += char;
   }
  });
  
  lexer.setInput(msg).lex();
  this.origin = this.origin.trim();
  this.destination = this.destination.trim();
  this.mode = this.mode.trim();
}



var Message = function(msg) {
  var parser = new EmergencyCode(msg);
  this.category = "Message"
  if (parser.isSatisfied()) {
    this.category = "Emergency";
    this.text = "";
    if (parser.isCancelled) {
      this.text = "CANCELLED ";
    }
    this.text += "Code " + parser.color + " ";
    if (parser.team !== "") {
      this.text += "Team " + parser.team + " ";
    }
    if (parser.room !== "") {
      this.text += "Room " + parser.room + " ";
    }
    return;
  }
  
  parser = new BedRequest(msg);
  if (parser.isSatisfied()) {
    this.category = "Bed Request";
    this.text = parser.message;
    return;
  }
  
  parser = new TransportRequest(msg);
  if (parser.isSatisfied()) {
    this.category = "Transport Request";
    this.text = parser.sequence + " transport " + parser.mode + " from " + parser.origin + " to " + parser.destination; 
    return;
  }
  
  this.text = msg.substring(0, 50);
  this.text = this.text.trim() + " ...";
}

exports.Message = Message;

