<?php 
header("Access-Control-Allow-Origin: *");
class FFL_Rest_API extends WP_REST_Controller{
	function __construct(){
		$this->namespace = 'v1';
		$this->rest_base = 'ffl-dealers';
	}
	public function register_routes(){
		register_rest_route(
			$this->namespace,
			'/'.$this->rest_base,
			[
				[
					'methods' => WP_REST_Server::READABLE,
					'callback'=> [$this,'get_items'],
					'permission_callback'=>[$this,'get_items_permissions_check'],
					'args'=> $this->get_collection_params()
				],
				[
					'methods' 				=> WP_REST_Server::CREATABLE,
					'callback'				=> [$this,'get_items'],
					'permission_callback'	=>[$this,'get_items_permissions_check'],
					'args'               	=> $this->get_endpoint_args_for_item_schema( WP_REST_Server::CREATABLE ),
				],
				'schema'=> [$this,'get_item_schema']
			]
		);
	}
	public function get_items_permissions_check($request){
		
		return true;
	}
	/**
	* Retrives a list of dealers
	*
	*/
	public function get_items($request){
		$args =[];
		$params = $this->get_collection_params();
		foreach($params as $key => $value){
			if(isset($request[$key])){
				$args[$key] = $request[$key];
			}
		}
		$args['zipcode'] = $request['zipcode'];
		$args['radius'] = $request['radius'];
		
		unset($args['per_page']);
		unset($args['page']);
		$data = [];
		if(isset($request['radius']) && $request['radius'] <=100){
				$dealer_array_data	= all_dealer_data_array();
				
				$ffl_dealers		= $this->get_dealers_list($args);
				
				if($ffl_dealers){
					foreach($ffl_dealers as $ffl_dealer){
						 $response = $this->prepare_item_for_response( $ffl_dealer, $request );
						$data[]   = $this->prepare_response_for_collection( $response );
					}
				}else{
					$data = array(
						'headers'=>array(),
						'original'=>array(
							"message"=> "Not a valid ZipCode!",
							"status"=> 400
						),
						"exception"=>null
					);
				}
		}else{
			$data = array(
						'headers'=>array(),
						'original'=>array(
							"message"=> "The radius must be between 1 and 100",
							"status"=> 400
						),
						"exception"=>null
					);
		}
		
		$response = rest_ensure_response( $data );
		return $response;
	}
	public function prepare_item_for_response($item,$request){
		$data = [];
		$fields = $this->get_fields_for_response($request);
		if(in_array('id',$fields,true)){
			$data['id'] = (int) $item['id'];
		}
		if(in_array('license_number',$fields,true)){
			$data['license_number'] = (string) $item['license_number'];
		}
		if(in_array('short_lic',$fields,true)){
			$data['short_lic'] = (string) $item['short_lic'];
		}
		if(in_array('license_name',$fields,true)){
			$data['license_name'] = (string) $item['license_name'];
		}
		if(in_array('business_name',$fields,true)){
			$data['business_name'] = (string) $item['business_name'];
		}
		if(in_array('premise_street',$fields,true)){
			$data['premise_street'] = (string) $item['premise_street'];
		}
		if(in_array('premise_city',$fields,true)){
			$data['premise_city'] = (string) $item['premise_city'];
		}
		if(in_array('premise_state',$fields,true)){
			$data['premise_state'] = (string) $item['premise_state'];
		}
		if(in_array('premise_zip_code',$fields,true)){
			$data['premise_zip_code'] = (string) $item['premise_zip_code'];
		}
		if(in_array('lat',$fields,true)){
			$data['lat'] = (string) $item['lat'];
		}
		if(in_array('lng',$fields,true)){
			$data['lng'] = (string) $item['lng'];
		}
		if(in_array('voice_phone',$fields,true)){
			$data['voice_phone'] = (string) $item['voice_phone'];
		}
		
		$context = !empty($request['context'])?$request['context']:'view';
		$data = $this->filter_response_by_context($data,$context);

		$response = rest_ensure_response( $data );
        $response->add_links( $this->prepare_links( $item ) );

        return $response;
	}
	/**
	* Retrives the dealers schema
	*/
	public function get_item_schema(){
		if($this->schema){
			return $this->add_additional_fields_schema($this->schema);
		};
		$schema = [
			'$schema' => 'http://json-schema.org/draft-04/schema#',
			'title'   =>'contact',
			'type'    =>'object',
			'properties'=>[
				'id'=>[
					'description'=>__('Unique identifier for the objects'),
					'type'=>'integer',
					'context'=> ['view'],
					'readonly'=> true
				],
				'license_number'=>[
					'description'=>__('Unique license_number for the objects'),
					'type'=>'string',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'short_lic'=>[
					'description'=>__('Unique short_lic for the objects'),
					'type'=>'string',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'license_name'=>[
					'description'=>__('Unique license_name for the objects'),
					'type'=>'string',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'business_name'=>[
					'description'=>__('Unique business_name for the objects'),
					'type'=>'string',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'premise_street'=>[
					'description'=>__('Unique premise_street for the objects'),
					'type'=>'string',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'premise_city'=>[
					'description'=>__('Unique identifier for the objects'),
					'type'=>'string',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
						]
				],
				'premise_state'=>[
					'description'=>__('Unique premise_state for the objects'),
					'type'=>'string',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'premise_zip_code'=>[
					'description'=>__('Unique premise_zip_code for the objects'),
					'type'=>'integer',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'lat'=>[
					'description'=>__('Unique lat for the objects'),
					'type'=>'integer',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'lng'=>[
					'description'=>__('Unique lng for the objects'),
					'type'=>'integer',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				],
				'voice_phone'=>[
					'description'=>__('Unique voice_phone for the objects'),
					'type'=>'integer',
					'context'=> ['view'],
					'arg_options' =>[
						'sanitize_callback' =>'sanitize_text_field'
					]
				]
			]
		];
		$this->schema = $schema;
		return $this->add_additional_fields_schema($this->schema);
	}
	public function get_collection_params(){
		$params = parent::get_collection_params();
		unset($params['search']);
		return $params;
	}
	protected function prepare_links( $item ) {
        $base = sprintf( '%s/%s', $this->namespace, $this->rest_base );

        $links = [
            'self' => [
                'href' => rest_url( trailingslashit( $base ) . $item->id ),
            ],
            'collection' => [
                'href' => rest_url( $base ),
            ],
        ];

        return $links;
    }
	public function get_dealers_list($args ) {
		
		if(is_array($args) && !empty($args)){
			
			$zipcode = (string)$args['zipcode'];
			$radius = $args['radius'];
			
			$lat_lang_by_zip = $this->get_zipcode($zipcode);
	
			if($lat_lang_by_zip){
				$ffl_dealers = $this->get_ffl_dealers_by_radius($lat_lang_by_zip, $radius);
				if($ffl_dealers){
					return $ffl_dealers;
				}
			}
		}
	}
	public function get_zipcode($zipCode){
		$locations = all_dealer_data_array();
		if(!empty($locations)){
			foreach ($locations as $location) {
				if ($location['premise_zip_code'] == $zipCode) {
					return $location;
				}
			}
		}
		return null;
	}
	public function get_ffl_dealers_by_radius($zip_search, $radius = 5){
		
		if($radius && !empty($zip_search)){
			$radius_km 	= $radius;
			$latitude 	= $zip_search['lat'];
			$longitude 	= $zip_search['lng'];
			$zipCode 	= $zip_search['premise_zip_code'];
			
			$result_by_radius =  get_all_dealers_by_radius($zipCode,$latitude,$longitude,$radius_km);
			return $result_by_radius;
		}else{
			return $zip_search;
		}
	}
}