SEBA-259
Added testing of username/password for xos

Change-Id: I9d2d3dd32d217d4f2c13bae843df427fddc631fb
diff --git a/api/abstract_olt_api.proto b/api/abstract_olt_api.proto
index 6604703..dd8fcea 100644
--- a/api/abstract_olt_api.proto
+++ b/api/abstract_olt_api.proto
@@ -25,14 +25,25 @@
 
 message AddChassisMessage{
    string CLLI =1;
-   string VCoreIP =2;
-   int32 VCorePort=3;
-   int32 Rack=4;
-   int32 Shelf=5;
+   string XOSIP =2;
+   int32 XOSPort=3;
+   string XOSUser=4;
+   string XOSPassword=5;
+   int32 Rack=6;
+   int32 Shelf=7;
 }
 message AddChassisReturn{
    string DeviceID = 1;
 }
+message ChangeXOSUserPasswordMessage{
+   string CLLI =1;
+   string XOSUser=2;
+   string XOSPassword=3;
+}
+message ChangeXOSUserPasswordReturn{
+   bool Success=1;
+}
+
 message AddOLTChassisMessage{
    string CLLI=1;
    string SlotIP=2;
@@ -100,6 +111,12 @@
 	 body:"*"
       };
    }
+   rpc ChangeXOSUserPassword(ChangeXOSUserPasswordMessage) returns(ChangeXOSUserPasswordReturn){
+      option(google.api.http)={
+        post:"/v1/ChangeXOSUserPassword"
+	body:"*"
+      };
+   }
    rpc CreateOLTChassis(AddOLTChassisMessage) returns (AddOLTChassisReturn) {
       option(google.api.http) = {
          post: "/v1/CreateOLTChassis"
diff --git a/api/handler.go b/api/handler.go
index 2e6b9cc..f6d4c5b 100644
--- a/api/handler.go
+++ b/api/handler.go
@@ -19,8 +19,10 @@
 import (
 	"errors"
 	"fmt"
+	"io/ioutil"
 	"log"
 	"net"
+	"net/http"
 	"os"
 	"strings"
 
@@ -52,14 +54,35 @@
 func (s *Server) CreateChassis(ctx context.Context, in *AddChassisMessage) (*AddChassisReturn, error) {
 	chassisMap := models.GetChassisMap()
 	clli := in.GetCLLI()
+
+	xosIP := net.ParseIP(in.GetXOSIP())
+	xosPort := int(in.GetXOSPort())
+	if xosIP == nil {
+		errStr := fmt.Sprintf("Invalid IP %s supplied for XOSIP", in.GetXOSIP())
+		return nil, errors.New(errStr)
+	}
+
+	xosAddress := net.TCPAddr{IP: xosIP, Port: xosPort}
+
+	xosUser := in.GetXOSUser()
+	xosPassword := in.GetXOSPassword()
+	if xosUser == "" || xosPassword == "" {
+		return nil, errors.New("Either XOSUser or XOSPassword supplied were empty")
+	}
+	loginWorked := testLogin(xosUser, xosPassword, xosIP, xosPort)
+	if !loginWorked {
+		return nil, errors.New("Unable to validate login not creating Abstract Chassis")
+	}
+	shelf := int(in.GetShelf())
+	rack := int(in.GetRack())
+
 	chassisHolder := (*chassisMap)[clli]
 	if chassisHolder != nil {
 		return &AddChassisReturn{DeviceID: chassisHolder.AbstractChassis.CLLI}, nil
 	}
 
 	abstractChassis := abstract.GenerateChassis(clli, int(in.GetRack()), int(in.GetShelf()))
-	phyChassis := physical.Chassis{CLLI: clli, VCoreAddress: net.TCPAddr{IP: net.ParseIP(in.GetVCoreIP()),
-		Port: int(in.GetVCorePort())}, Rack: int(in.GetRack()), Shelf: int(in.GetShelf())}
+	phyChassis := physical.Chassis{CLLI: clli, XOSAddress: xosAddress, Rack: rack, Shelf: shelf}
 
 	chassisHolder = &models.ChassisHolder{AbstractChassis: abstractChassis, PhysicalChassis: phyChassis}
 	if settings.GetDebug() {
@@ -72,6 +95,35 @@
 }
 
 /*
+ChangeXOSUserPassword - allows update of xos credentials
+*/
+func (s *Server) ChangeXOSUserPassword(ctx context.Context, in *ChangeXOSUserPasswordMessage) (*ChangeXOSUserPasswordReturn, error) {
+	clli := in.GetCLLI()
+	xosUser := in.GetXOSUser()
+	xosPassword := in.GetXOSPassword()
+	if xosUser == "" || xosPassword == "" {
+		return nil, errors.New("Either XOSUser or XOSPassword supplied were empty")
+	}
+	chassisMap := models.GetChassisMap()
+	chassisHolder := (*chassisMap)[clli]
+	if chassisHolder == nil {
+		errString := fmt.Sprintf("There is no chassis with CLLI of %s", clli)
+		return nil, errors.New(errString)
+	}
+	xosIP := chassisHolder.PhysicalChassis.XOSAddress.IP
+	xosPort := chassisHolder.PhysicalChassis.XOSAddress.Port
+	loginWorked := testLogin(xosUser, xosPassword, xosIP, xosPort)
+	if !loginWorked {
+		return nil, errors.New("Unable to validate login when changing password")
+	}
+
+	chassisHolder.PhysicalChassis.XOSUser = xosUser
+	chassisHolder.PhysicalChassis.XOSPassword = xosPassword
+	return &ChangeXOSUserPasswordReturn{Success: true}, nil
+
+}
+
+/*
 CreateOLTChassis adds an OLT chassis/line card to the Physical chassis
 */
 func (s *Server) CreateOLTChassis(ctx context.Context, in *AddOLTChassisMessage) (*AddOLTChassisReturn, error) {
@@ -152,3 +204,39 @@
 	return &OutputReturn{Success: true}, nil
 
 }
+func testLogin(xosUser string, xosPassword string, xosIP net.IP, xosPort int) bool {
+	var dummyYaml = `
+tosca_definitions_version: tosca_simple_yaml_1_0
+imports:
+  - custom_types/site.yaml
+description: anything
+topology_template:
+  node_templates:
+    mysite:
+      type: tosca.nodes.Site
+      properties:
+        must-exist: true
+        name: mysite
+`
+	client := &http.Client{}
+	requestList := fmt.Sprintf("http://%s:%d/run", xosIP, xosPort)
+	req, err := http.NewRequest("POST", requestList, strings.NewReader(dummyYaml))
+	req.Header.Add("xos-username", xosUser)
+	req.Header.Add("xos-password", xosPassword)
+	resp, err := client.Do(req)
+	log.Printf("testLogin resp:%v", resp)
+	if err != nil {
+		log.Printf("Unable to validate XOS Login Information %v", err)
+		return false
+	}
+	defer resp.Body.Close()
+
+	if resp.StatusCode == http.StatusOK {
+		bodyBytes, _ := ioutil.ReadAll(resp.Body)
+		bodyString := string(bodyBytes)
+		fmt.Println(bodyString)
+		return true
+	}
+	return false
+
+}