<?
/**
 * VoiceOne Webservices Interface
 *
 * @package voiceone_webservices
 * @subpackage  Extensions
 */

//******************************************************************************
//******************           Virtual Extensions            *******************
//******************************************************************************
/**
* FUNCTION: getVirtualExtension
* Get Virtual Extension defined on the system that match to id. If no id is passed
* to the function, it returns all virtual extensions.
* @param id:int -> Virtual Extension's id used to retireve data
* @return:VirtualExtensionArray -> Array of structure contains entities data
*/
function getVirtualExtension($id){
	global $db;
  $ret=array();
  //check input values
  if((!isset($id))||(trim($id)=="")) $id=0;
  //get virtual extensions
  if($id!=0) $where="WHERE `id`='".$id."' "; else $where="";
  $qry="SELECT * FROM `cw_virtual` ".$where." ORDER BY `extension` ";
  $res=$db->Execute($qry);
  if($res===false) return 0;
  while($arr=$res->FetchRow()){
  	$virtual=array();
  	//general info ("id","name","surname","extension","id_application")
  	$virtual=$arr;
    //login info ("username","password","language")
   	$virtual["username"]="";
   	$virtual["password"]="";
   	$virtual["language"]="";
    $qry="SELECT * FROM `cw_user` WHERE `entity_id`='".$virtual["id"]."' ";
		$user_res=$db->Execute($qry);
		if($user_res!==false){
    	$user=$user_res->FetchRow();
      if(is_array($user)){
    		$virtual["username"]=$user["username"];
      	$virtual["password"]=$user["password"];
      	$virtual["language"]=$user["lang"];
      }
    }
    //linked client array ("linked_clients")
    $linked_clients=array();
    $qry="SELECT * FROM `cw_virtual_client` WHERE `id_virtual`='".$virtual["id"]."' ";
		$clients_res=$db->Execute($qry);
		if($clients_res!==false){
    	while($client=$clients_res->FetchRow()) $linked_clients[]=$client["id_client"];
    }
    $virtual["linked_clients"]=$linked_clients;
    //group array ("groups")
    if(trim($virtual["groups"])!=""){
      $virtual["groups"]=explode("|",$virtual["groups"]);
    }else $virtual["groups"]=array();
    //cid structureArr ("cid")
    $virtual["cid"]=array();
    $cidArr=getCid(0,$virtual["id"]);
    if(is_array($cidArr)){
      $virtual["cid"]=$cidArr;
    }else $virtual["cid"]==array();
    //voicemail structure ("voicemail")
    $voicemail=getVoiceMail($virtual["extension"]);
   	$virtual["voicemail"]=$voicemail[0];
    //create return
    $ret[]=$virtual;
  }
  //return structure
  return $ret;
}
/**
* FUNCTION: putVirtualExtension
* Save or Modify a Virtual Extension
* @param virtual:VirtualExtension -> Structure contains Virtual Extension data
* @return:int -> If success it return entity id, else return zero
*/
function putVirtualExtension($virtual){
	global $db;
  /**
   * TODO: check input values
   */
  //if virtual extension already exists, delete it
  if((isset($virtual["id"]))&&($virtual["id"]!="")){
  	//get user info
    $qry="SELECT * FROM `cw_user` WHERE `entity_id`='".$virtual["id"]."' ";
		$user_res=$db->Execute($qry);
		if($res!==false){
    	$user=$user_res->FetchRow();
      if(is_array($user)){
    		$user_id=$user["id"];
      	$user_type=$user["type"];
      }
    }
    //remove linked clients from groups and cid table
    if(is_array($virtual["linked_clients"])){
    	foreach($virtual["linked_clients"] as $client_id){
      	if((trim($client_id)!="")&&($client_id!=0)){
        	removeEntityFromGroup($client_id);
          delCid(0,$client_id);
        }
      }
    }
    //get related agent
    $old_agent=getAgent(getAgentFromEntity($virtual["id"]));
    $agent["id"]=$old_agent[0]["id"];
    $agent["joined_queues"]=$old_agent[0]["joined_queues"];
    //delete old virtual extension
		delVirtualExtension($virtual["id"],false);
  	$entity["id"]=$virtual["id"];
  }else{
  	$user_id="";
  	$user_type=USER_STANDARD;
    $joinedQueueArr=array();
  }
  //create a new entity
  $entity["type"]=VIRTUAL_EXTENSION;
  $entity_id=putEntity($entity);
  if((is_object($entity_id))||($entity_id==0)) return 0;
  //create a new application
  $app_id="";
	//get macro
	$macro=0;
  $ret=getMacroByName("virtualexten");
  if((is_array($ret))&&(is_array($ret[0]))) $macro=$ret[0]["id"];
  if($macro==0) return 0;
	//prepare extension list
  $extension_list="";
  if(is_array($virtual["linked_clients"])){
  	foreach($virtual["linked_clients"] as $client){
      $channel=getChannel(getChannelFromEntity($client),0);
      if((is_array($channel))&&(is_array($channel[0]))){
        $extension_list.=$channel[0]["name"]."&";
      }
    }
    if(trim($extension_list)!="") $extension_list=substr($extension_list,0,-1);
  }
  //put application
  $app_name="virtual_extension_".$entity_id;
  if(($virtual["id_application"]!="")&&($virtual["id_application"]!=0)) $app_id=$virtual["id_application"];
  $application=array(
      'id'          => $app_id,
      'name'        => $app_name,
      'label'       => "Virtual_extension_".$entity_id,
      'description' => "Virtual Extension for client ".$virtual["name"]." ".$virtual["surname"]." (".$virtual["extension"].")",
      'extension'   => $virtual["extension"],
      'code'        => "",
      'macro'       => $macro,
      'parameter'   => "dest=".$extension_list."|rule=",
      'groups'      => array()
  	);
  $ret=putApplication($application);
  if($ret==0) return 0;
  //get application id
  if(trim($app_id)==""){
  	$ret=getApplicationByName($app_name);
  	if((is_array($ret))&&(is_array($ret[0]))){
			$app_id=trim($ret[0]["id"]);
    }
  }
  if(!is_numeric($app_id)) return 0;
  //implode grouplist
  $groupList="";
  if((is_array($virtual["groups"]))&&(count($virtual["groups"])>0)){
    $groupList=implode("|",$virtual["groups"]);
  }
  //save virtual extension on db
  $qry="INSERT INTO `cw_virtual`(`id`,`name`,`surname`,`extension`,`rule`,`id_application`,`groups`,`location`,`area_code`) ";
  $qry.="VALUES ($entity_id,'".string2sql($virtual['name'])."','".string2sql($virtual['surname'])."','".string2sql($virtual['extension'])."',";
  $qry.="'".string2sql($virtual["rule"])."','".string2sql($app_id)."','".string2sql($groupList)."','".string2sql($virtual['location'])."','".string2sql($virtual['area_code'])."')";
  $res=$db->Execute($qry);
  if($res===false) return 0;
  //save linked clients
  if(is_array($virtual["linked_clients"])){
  	foreach($virtual["linked_clients"] as $client){
    	$qry="INSERT INTO `cw_virtual_client`(`id_virtual`,`id_client`) ";
  		$qry.="VALUES ('".string2sql($entity_id)."','".string2sql($client)."') ";
  		$res=$db->Execute($qry);
    	if($res===false) return 0;
    }
  }
  //create user
  $userArr=array(
  		"id" => $user_id,
      "username" => $virtual["extension"],
      "password" => $virtual["password"],
      "lang" => $virtual["language"],
      "type" => $user_type,
      "entity_id" => $entity_id
    );
  $user_id=putUser($userArr);
  if($ret==0) return 0;
  //put voicemail
  if(isset($virtual["voicemail"])){
  	$ret=putVoiceMail($virtual["voicemail"]);
    if($ret==0) return 0;
  }
  //put rule
  if(is_array($virtual["linked_clients"])){
  	//get rule name
    $ruleArr=getRule($virtual["rule"],0);
    if((is_array($ruleArr))&&(is_array($ruleArr[0]))){
    	$rulename=$ruleArr[0]["name"];
      $callerid=$virtual["name"]." ".$virtual["surname"]." <".$virtual["extension"].">";
      //modify clients
    	foreach($virtual["linked_clients"] as $client){
     		$clientArr=getClient($client,0);
        if((is_array($clientArr))&&(is_array($clientArr[0]))){
        	$client=$clientArr[0];
          //delete client voicemail
          delVoiceMail($client["extension"]);
          //set outgoing context in client's tech options
          if($client["technology"]==SIP) $tech="SIP";
          else if($client["technology"]==IAX2) $tech="IAX2";
          else continue;
          $ret=getConfOption("",$tech,SECTION_DEFAULT);
          if((is_array($ret))&&(is_array($client["options"]))){
            foreach($ret as $o){
              if($o["name"]=="context"){
                for($i=0;$i<count($client["options"]);$i++){
                	if($client["options"][$i]["key"]==$o["id"]){
                  	$client["options"][$i]["value"]=$rulename;
                    $client["options"][$i]["name"]="context";
                  }
                }
                continue;
              }
              if($o["name"]=="callerid"){
              	$callerid_set=false;
                for($i=0;$i<count($client["options"]);$i++){
                	if($client["options"][$i]["key"]==$o["id"]){
                  	$client["options"][$i]["value"]=$callerid;
                    $client["options"][$i]["name"]="callerid";
                    $callerid_set=true;
                  }
                }
                if($callerid_set===false) $client["options"][]=array("key"=>$o["id"],"value"=>$callerid);
                continue;
              }
            }
            //add voiceomail to client otheroptions
            $client["voicemail"]=$virtual["voicemail"];
            //put entity
            delEntityOption($client["id"],$client["technology"]);
            putEntityOption(array_merge($client["options"]), $client["technology"], $client["id"], $client);
            //update client channel location settings
            $qry="UPDATE `cw_channel` SET `location`='".$virtual["location"]."',`area_code`='".$virtual["area_code"]."' WHERE `key`='".$client["id"]."' LIMIT 1;";
            $db->Execute($qry);
          }
      	}
      }
    }
  }
  //put groups
  if(is_array($virtual["linked_clients"])){
  	foreach($virtual["linked_clients"] as $client){
    	removeEntityFromGroup($client);
  		$res=addEntityToGroup($client,$virtual["groups"]);
		  if($res===false) return 0;
    }
  }
  //map all linked client's private contact as property of virtual extension's user 
  if(is_array($virtual["linked_clients"])){
    $contactArr=array();
  	foreach($virtual["linked_clients"] as $client){
      $cu_id=getUserIdFromEntity($client);
      if($cu_id!=0){
    	  //save contact with virtual extension's user_id
        $ccArr=getContact(0,$cu_id,1);
        if(is_array($ccArr)){
          foreach($ccArr as $c){
            $c["id_user"]=$user_id;
            putContact($c,$cu_id);
          }
        }
        //disable linked extension login
        activateDeactivateUser($cu_id,0); 
  		}
    }
  }
  //create associated agent
  if($ret>0){
    $agent["client"]=$entity_id;
    $agent["extension"]=$virtual['extension'];
    $agent["username"]="";
    $agent["password"]="";
    $ret=putAgent($agent);
  }
  //put cid
  $ret=putCid($entity_id,$virtual["cid"]);
  if($ret==0) return 0;
  if(is_array($virtual["linked_clients"])){
  	foreach($virtual["linked_clients"] as $client){
  		$ret=putCid($client,$virtual["cid"]);
      if($ret==0) return 0;
  	}
  }
  //refresh asterisk proxy manager
  ast_writeProxyUsers();
  //refresh asterisk-stat users
  if(function_exists(ast_writeStatUsers)){
    ast_writeStatUsers();
  }
  //return entity id
  return $entity_id;
}
/**
* FUNCTION: delVirtualExtension
* Delete a Virtual Extension
* @param id:int -> Id of the Virtual Extension to delete
* @return:int -> If success it return deleted entity id, else return zero
*/
function delVirtualExtension($id,$reload=true){
	global $db;
  //check input values
  if((!isset($id))||(trim($id)=="")||($id==0)) return 0;
  $virtual=getVirtualExtension($id);
  $virtual=$virtual[0];
  $virtual["user_id"]=getUserIdFromEntity($virtual["id"]);
  $virtual["contacts"]=getContact(0,$virtual["user_id"],1);
  if(!is_array($virtual)) return 0;
  //delete virtual extension from db
	$qry="DELETE FROM `cw_virtual` WHERE `id`='".$virtual["id"]."' LIMIT 1 ";
	$res=$db->Execute($qry);
  if($res===false) return 0;
  //delete linked clients
  $qry="DELETE FROM `cw_virtual_client` WHERE `id_virtual`='".$virtual["id"]."' ";
	$res=$db->Execute($qry);
  if($res===false) return 0;
  //delete application
  delApplication($virtual["id_application"]);
  //delete entity
  delEntity($virtual["id"]);
	//delete the VoiceMail
  delVoiceMail($virtual["extension"]);
  //delete associated agent
  $ret=delAgent(getAgentFromEntity($virtual["id"]));
  //delete cid settings
  delCid(0,$virtual["id"]);
  //refresh asterisk proxy manager
  ast_writeProxyUsers();
  //refresh asterisk-stat users
  if(function_exists(ast_writeStatUsers)){
    ast_writeStatUsers();
  }
  //enable linked extension login
  if(is_array($virtual["linked_clients"])){
  	foreach($virtual["linked_clients"] as $client){
      $cu_id=getUserIdFromEntity($client);
      if($cu_id!=0){
        activateDeactivateUser($cu_id,1);
      }
    }
  }
  if($reload===true){
    //assign contact list to the first linked extension
    if(is_array($virtual["contacts"])){
      $first_user=getUserIdFromEntity($virtual["linked_clients"][0]);
      foreach($virtual["contacts"] as $c){
        $c["id_user"]=$first_user;
        putContact($c,$virtual["user_id"]);
      }
    }
    //grant fax accesses to linked extension
    if(function_exists("addFaxtoClient")){
      $faxes=getFaxFromClient($id);
      if((is_array($faxes))&&(is_array($virtual["linked_clients"]))){
      	foreach($virtual["linked_clients"] as $client){
          addFaxtoClient($client,$faxes);
        }
      }
    }
    //delete user
    delUser($virtual["user_id"]);
  }else{
    delUser($virtual["user_id"],false);
  }
	//return
  return $virtual["id"];
}
/**
* FUNCTION: getVirtualExtensionFromClient
* Get Virtual Extension defined on the system that contains passed client. If no id is passed
* to the function, it returns zero.
* @param id:int -> Client's id used to retireve data
* @return:VirtualExtension -> Structure contains Virtual Extension data
*/
function getVirtualExtensionFromClient($id_client){
	global $db;
  $ret=array();
  //check input values
  if((!isset($id_client))||(trim($id_client)=="")||($id_client==0)) return 0;
  //get virtual extensions
  $qry="SELECT v.* ";
  $qry.="FROM `cw_virtual` AS v ";
  $qry.="JOIN `cw_virtual_client` AS vc ON vc.`id_virtual`=v.`id` ";
  $qry.="WHERE vc.`id_client`='".$id_client."' ";
  $qry.="LIMIT 1 ";
  $res=$db->Execute($qry);
  if($res===false) return 0;
  $q=$res->RecordCount();
  if(($q>0)&&($arr=$res->FetchRow())){
  	$virtual=array();
  	//general info ("id","name","surname","extension","id_application")
  	$virtual=$arr;
    //login info ("username","password","language")
   	$virtual["username"]="";
   	$virtual["password"]="";
   	$virtual["language"]="";
    $qry="SELECT * FROM `cw_user` WHERE `entity_id`='".$virtual["id"]."' ";
		$user_res=$db->Execute($qry);
		if($res!==false){
    	$user=$user_res->FetchRow();
      if(is_array($user)){
    		$virtual["username"]=$user["username"];
      	$virtual["password"]=$user["password"];
      	$virtual["language"]=$user["lang"];
      }
    }
    //linked client array ("linked_clients")
    $linked_clients=array();
    $qry="SELECT * FROM `cw_virtual_client` WHERE `id_virtual`='".$virtual["id"]."' ";
		$clients_res=$db->Execute($qry);
		if($res!==false){
    	while($client=$clients_res->FetchRow()) $linked_clients[]=$client["id_client"];
    }
    $virtual["linked_clients"]=$linked_clients;
    //group array ("groups")
    if(trim($virtual["groups"])!=""){
      $virtual["groups"]=explode("|",$virtual["groups"]);
    }else $virtual["groups"]=array();
    //cid structureArr ("cid")
    $virtual["cid"]=array();
    $cidArr=getCid(0,$virtual["id"]);
    if(is_array($cidArr)){
      $virtual["cid"]=$cidArr;
    }else $virtual["cid"]==array();
    //voicemail structure ("voicemail")
    $voicemail=getVoiceMail($extension);
   	$virtual["voicemail"]=$voicemail[0];
    //return structure
  	return $virtual;
  }
  //return
  return 0;
}
// ---- getVirtualExtensionFromExtension(extension:string):VirtualExtension ----
function getVirtualExtensionFromExtension($extension) {
  global $db;
  $ret=0;
  $virtuals=getVirtualExtension(0);
  if((is_array($virtuals))&&(count($virtuals)>0)){
    foreach($virtuals as $virtual){
      if($extension==$virtual["extension"]){
  		  $ret=$virtual;
        break;
      }
    }
  }
  return $ret;
}
?>