///////////////////////////////////////////////////////////////////////////////
//
// Copyright (c) 2000-2018 Ericsson Telecom AB
//
// All rights reserved. This program and the accompanying materials
// are made available under the terms of the Eclipse Public License v2.0
// which accompanies this distribution, and is available at
// https://www.eclipse.org/org/documents/epl-2.0/EPL-2.0.html
///////////////////////////////////////////////////////////////////////////////
//  File:               IFW_HTTP_Client_Functions.ttcn
//  Description:
//  Rev:                R1A
//  Prodnr:             LPA 108 661
//  Updated:            2017-09-01
//  Contact:            http://ttcn.ericsson.se
///////////////////////////////////////////////////////////////////////////////
module IFW_HTTP_Client_Functions
{
    import from IFW_HTTP_Client_Definitions all;
	import from HTTPmsg_Types all;
	import from IPL4asp_Types all;
	import from IPL4asp_PortType all;
	import from IFW_Common all;
	import from TCCMessageHandling_Functions all;
import from HTTPmsg_MessageLen all;

	
	modulepar
	{
		float tsp_HTTP_Client_maxResponseTime := 0.0;
    }

	function f_HTTP_Client_init() runs on IFW_HTTP_Client_CT
    {
		log(%definitionId, " started");
		var Result vl_result;
    
		log("Mapping started");
		map(self:IPL4_PCO,system:IPL4_PCO);
		var f_IPL4_getMsgLen vl_f := refers(f_HTTP_Client_getMessageLength);
		f_IPL4_setGetMsgLen(IPL4_PCO, -1, vl_f, {});
    
		log("Connecting the socket to the remote");
		vl_result := f_IPL4_connect(IPL4_PCO, ctx.remoteHost, ctx.remotePort, ctx.localHost, ctx.localPort, -1, {tcp := {}}, {{reuseAddress := {enable := true}}});
		f_checkResult(vl_result);
		ctx.connId := vl_result.connId;
		
		log(%definitionId, " finished");
	}
	
	function f_HTTP_Client_cleanUp() runs on IFW_HTTP_Client_CT
    {
		log(%definitionId, " started");
		var Result vl_result;
    
		log("Closing connection");
		if (ctx.connId >= 0)
		{
		  vl_result := f_IPL4_close(IPL4_PCO, ctx.connId, {tcp := {}});
		  //f_checkResult(vl_result);		  
		}
	
		log(%definitionId, " finished");
	}
	
	function f_HTTP_Client_getContext() runs on IFW_HTTP_Client_CT
	return HttpClientContext
	{
		return ctx;
	}
	
	function f_HTTP_Client_setContext(in HttpClientContext p_ctx) runs on IFW_HTTP_Client_CT
	{
	  ctx := p_ctx;
	}
	
	function f_HTTP_Client_setMessageToSend(in HTTPMessage p_msg) runs on IFW_HTTP_Client_CT
	{
	  msgToSend := p_msg;
	  
	  if (ischosen(msgToSend.request))
	  {
  	    for (var integer i:=0; i<sizeof(ctx.requestHeaders); i:=i+1)
	    {
	      if (f_HTTP_lookupHeader(ctx.requestHeaders[i].header_name, msgToSend.request.header) == -1)
	      {
	        msgToSend.request.header[sizeof(msgToSend.request.header)] := ctx.requestHeaders[i];
	      }
	      else
	      {
	        log("HTTP Client: Didn't add request header because a header with the same name is already there ", ctx.requestHeaders[i]);
	      }
	    }
      }
	}	
	
    function f_HTTP_Client_send() runs on IFW_HTTP_Client_CT
	{
	  	var octetstring v_encoded;
	  	
	  	v_encoded := enc_HTTPMessage(msgToSend);
	  
	  	var ASP_SendTo vl_send;

		vl_send.connId := ctx.connId;
		vl_send.remName := ctx.remoteHost;
		vl_send.remPort := ctx.remotePort;
		vl_send.proto := {tcp := {}}

		vl_send.msg := v_encoded;

		log("HTTP PDU: ", msgToSend);
		IPL4_PCO.send(vl_send);
	}
	
	function f_HTTP_Client_receive() runs on IFW_HTTP_Client_CT
	{
	  // Activate default
	  
	  timer t_Timeout := tsp_HTTP_Client_maxResponseTime;
	  if (tsp_HTTP_Client_maxResponseTime > 0.0) { t_Timeout.start; }
	  
	  var ASP_RecvFrom v_ipl4Recv;
	  var ASP_Event v_ipl4Event;
	  
	  alt
	  {
	    [] IPL4_PCO.receive(ASP_RecvFrom:?) -> value v_ipl4Recv
	    {
	      log("Received: ", v_ipl4Recv);
	      
	      var HTTPMessage v_httpMsg;
	      dec_HTTPMessage(v_ipl4Recv.msg, v_httpMsg);
	      
          lastReceived := v_httpMsg;
          log("HTTP PDU: ", lastReceived);          
	    }
	    [] IPL4_PCO.receive(ASP_Event:?) -> value v_ipl4Event
	    {
	      log("Received: ", v_ipl4Event);
	      repeat;
	    }
	    [] t_Timeout.timeout
	    {
	      lastReceived := c_HTTPMessage_empty;
	    }
	    
	    // Deactivate default
	  }
	}
	
	function f_HTTP_Client_check(in template HTTPMessage p_expected) runs on IFW_HTTP_Client_CT
	return ReturnBoolean
	{
	  if (not match(lastReceived, p_expected)) 
	  {
		  log("CHECK: last received is not matching with expected template");
		  return false;
	  }
		
		log("CHECK: return true");
		return true;
	}
	
	function f_HTTP_Client_getMessageLength(in octetstring stream, inout ro_integer args)
    return integer
    {
//      return f_TCCMessageHandling_getMessageLength(stream)
return f_HTTPMessage_len(stream);

    }
    
    function f_HTTP_lookupHeader(charstring p_headerName, in HeaderLines p_headers)
    return integer
    {
      for (var integer i:=0; i<sizeof(p_headers); i:=i+1)
      {
        if (p_headers[i].header_name == p_headerName) { return i; }
      }
      return -1;
    }
}
