Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

mateog98's avatar

Why am i anot being able to generate a token with my Service?

I created a TokenGenerator class

<?php
    class TokenGenerator
    {
        private $authServiceUrl = ''; 
	    private $username = '';
	    private $password = '';
    
        # constructor
        function __construct($username, $pasword, $authServiceUrl) {
            $this->username = $username;
            $this->password = $pasword;
            $this->authServiceUrl = $authServiceUrl;
        }
    
	    public function loadToken()
	    {
		    $computedHash = base64_encode(hash_hmac ( 'md5' , $this->authServiceUrl , $this->password, true ));
		    $authorization = 'Authorization: Bearer '.$this->username.':'.$computedHash;
		
		    $curl = curl_init();
		    curl_setopt($curl, CURLOPT_POST, true);
		    curl_setopt($curl, CURLOPT_POSTFIELDS, '');
		    curl_setopt($curl, CURLOPT_HTTPHEADER, array('Content-Type: application/json' , $authorization ));
		    curl_setopt($curl, CURLOPT_URL, $this->authServiceUrl);
		    curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
		    curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);

		    $result = curl_exec($curl);
            $obj = json_decode($result);
            $info = curl_getinfo($curl);
            curl_close($curl);
        
            if ($info['http_code'] != '200') {
                throw new Exception('Failed to load token');
            }
        
           return $obj;
	    }
    }
?>

And this is my ApiMedicService.php

  <?php

    namespace App\Services;

    use GuzzleHttp\Client;
    use App\Services\TokenGenerator;
    use App\Services\DiagnosisClient;

    class ApiMedicService
    {
        protected $diagnosisClient;

        public function __construct($language)
        {
              $tokenGenerator = new TokenGenerator(
                env('APIMEDIC_USERNAME'),
                env('APIMEDIC_PASSWORD'),
                env('AUTH_SERVICE_URL')
            );
           $token = $tokenGenerator->loadToken();
    
            if ($token) {
                $this->diagnosisClient = new DiagnosisClient($language, $token->Token, $healthServiceUrl);
            } else {
                throw new Exception('Failed to load API token');
            }
        }

        public function loadSymptoms()
        {
            return $this->diagnosisClient->loadSymptoms();
        }       

        public function loadDiagnosis($selectedSymptoms, $gender, $yearOfBirth)
       {
           return $this->diagnosisClient->loadDiagnosis($selectedSymptoms, $gender, $yearOfBirth);
       }

   

    

And this is a fragment from my DiagnosisClient.php

			<?php

			namespace App\Services;

			use Illuminate\Support\Facades\Config;
			use Illuminate\Support\Facades\Http;

			class DiagnosisClient { 

				private $healthServiceUrl; 
				private $language;
				private $token;
				private $validThrough;

			 # constructor
			 function __construct($language, $token, $healthServiceUrl) {
   				 $this->token = $token->{'Token'};
   				 $this->validThrough = $this->getTokenValidThrough();
    				$this->healthServiceUrl = $healthServiceUrl;
    				$this->language = $language;
				}

			 # <summary>
			 # Generic api get call to load data from webservice
				# </summary>
				# <param name="$action">common url parameters for each call</param>
			 # <returns>Returns deserialized result from webservice</returns>
				private function _loadFromWebserice($action)
				{
    				$extraArgs = 'token='.$this->token.'&format=json&language='.$this->language;
   				 $extraChar = strpos($action, '?') ? '&' : '?';
   				 $url = $this->healthServiceUrl.'/'.$action.$extraChar.$extraArgs;

    				var_dump($url);
    				$response = Http::get($url);
    				$result = $response->body();
   				 $obj = json_decode($result, true);

    				if ($response->status() != 200) {
        				// Handle error from the server
        				// You can throw an exception or return an appropriate response
        				return null;
    				}

    				return $obj;
			}

For some reasons my token is not being generated or being pass correctly becuase i get the following error message in my DiagnosisClient.php

"message": "Unresolvable dependency resolving [Parameter #1 [ <required> $token ]] in class App\\Services\\DiagnosisClient", "exception": "Illuminate\\Contracts\\Container\\BindingResolutionException",

0 likes
5 replies
krisi_gjika's avatar

@mateog98 can you show the full stack trace of your crash? It sound like you are trying to auto resolve your DiagnosisClient somewhere, but the container can't do so.

mateog98's avatar

@krisi_gjika

This is my TokenGenerator.php provided by the apimedic api at https://github.com/priaid-eHealth/symptomchecker

<?php
	class TokenGenerator
	{
    	private $authServiceUrl = ''; 
		private $username = '';
		private $password = '';
    
    	# constructor
    	function __construct($username, $pasword, $authServiceUrl) {
        	$this->username = $username;
        	$this->password = $pasword;
        	$this->authServiceUrl = $authServiceUrl;
    	}
    
		# <summary>
    	# loadToken function. Gets a token from $authServiceUrl.
    	# </summary>
    	# <param name="$username">api user username</param>
    	# <param name="$password">api user password</param>
    	# <param name="$authServiceUrl">priaid login url (https://authservice.priaid.ch/login)</param>
    	# <returns>Returns deserialized token object. It has 2 properties: 'Token' and 'ValidThrough'</returns>
		public function loadToken()
		{
			$computedHash = base64_encode(hash_hmac ( 'md5' , $this->authServiceUrl , $this->password, true 	));
			$authorization = 'Authorization: Bearer '.$this->username.':'.$computedHash;
		
			$curl = curl_init();
			curl_setopt($curl, CURLOPT_POST, true);
			curl_setopt($curl, CURLOPT_POSTFIELDS, '');
			curl_setopt($curl, CURLOPT_HTTPHEADER, array('Content-Type: application/json' , $authorization ));
			curl_setopt($curl, CURLOPT_URL, $this->authServiceUrl);
			curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
			curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);

			$result = curl_exec($curl);
        	$obj = json_decode($result);
        	$info = curl_getinfo($curl);
        	curl_close($curl);
        
        	if ($info['http_code'] != '200') {
            	throw new Exception('Failed to load token');
        	}
        
        	return $obj;
		}
	}
?>

This is my DiagnosisClient.php

<?php

namespace App\Services;

use Illuminate\Support\Facades\Config;
 use Illuminate\Support\Facades\Http;

class DiagnosisClient { 

    private $healthServiceUrl; 
    private $language;
    private $token;
    private $validThrough;

    # constructor
    function __construct($language) {
        $this->token = Config::get('services.apimedic_key');
        $this->validThrough = $this->getTokenValidThrough();
        $this->healthServiceUrl = Config::get('services.health_service_url');
        $this->language = $language;
    }


	private function _loadFromWebserice($action)
	{
    	$extraArgs = 'token='.$this->token.'&format=json&language='.$this->language;
    	$extraChar = strpos($action, '?') ? '&' : '?';
    	$url = $this->healthServiceUrl.'/'.$action.$extraChar.$extraArgs;

    	var_dump($url);
    	$response = Http::get($url);
    	$result = $response->body();
    	$obj = json_decode($result, true);

    	if ($response->status() != 200) {
        // Handle error from the server
        // You can throw an exception or return an appropriate response
       	 return null;
    	}

    	return $obj;
	}		

	private function getTokenValidThrough()
	{
    	$tokenParts = explode('.', $this->token);
    	if (count($tokenParts) !== 3) {
        	return null;
    	}

    	$payload = base64_decode($tokenParts[1]);
    	$data = json_decode($payload, true);
    	return $data['ValidThrough'] ?? null;
	}


	public function loadSymptoms() { 
    	return $this->_loadFromWebserice('symptoms'); 
	} 


	public function loadIssues() { 
    	return $this->_loadFromWebserice('issues'); 
	} 


	public function loadIssueInfo($issueId) { 
    	return $this->_loadFromWebserice('issues/'.$issueId.'/info'); 
	} 


	public function loadDiagnosis($selectedSymptoms, $gender, $yearOfBirth) { 
    	return $this->_loadFromWebserice('diagnosis?symptoms='.json_encode($selectedSymptoms).'&	gender='.$gender.'&year_of_birth='.$yearOfBirth); 
	} 


 public function loadSpecialisations($selectedSymptoms, $gender, $yearOfBirth) { 
    	return 	$this->_loadFromWebserice('diagnosis/specialisations?symptoms='.json_encode($selectedSymptoms).'&	gender='.$gender.'&year_of_birth='.$yearOfBirth); 
	} 


  public function loadBodyLocations() { 
    	return $this->_loadFromWebserice('body/locations'); 
	}
  
	public function loadBodySublocations($bodyLocationId) { 
    	return $this->_loadFromWebserice('body/locations/'.$bodyLocationId); 
	}


	public function loadSublocationSymptoms($sublocationId, $selectedSelectorStatus) { 
    	return $this->_loadFromWebserice('symptoms/'.$sublocationId.'/'.$selectedSelectorStatus); 
	}


 public function loadProposedSymptoms($selectedSymptoms, $gender, $yearOfBirth) { 
    	return 	$this->_loadFromWebserice('symptoms/proposed?symptoms='.json_encode($selectedSymptoms).'&	gender='.$gender.'&year_of_birth='.$yearOfBirth); 
	} 


	public function loadRedFlag($symptomId) { 
    	return $this->_loadFromWebserice('redflag?symptomId='.$symptomId); 
	} 
}

This is my ApiMedicService.php

<?php

namespace App\Services;

use GuzzleHttp\Client;
use App\Http\Services\TokenGenerator;

class ApiMedicService
{
    protected $diagnosisClient;

    public function __construct($language)
    {
        $this->diagnosisClient = new DiagnosisClient($language);
    }

public function loadSymptoms()
					}
  					  return $this->diagnosisClient->loadSymptoms();
					}

					public function loadIssues()
					{
					    return $this->diagnosisClient->loadIssues();
					}

					public function loadIssueInfo($issueId)
					{
    					return $this->diagnosisClient->loadIssueInfo($issueId);
					}

					public function loadDiagnosis($selectedSymptoms, $gender, $yearOfBirth)
					{
    					return $this->diagnosisClient->loadDiagnosis($selectedSymptoms, $gender, $yearOfBirth);
					}

					public function loadSpecialisations($selectedSymptoms, $gender, $yearOfBirth)
					{
   					 return $this->diagnosisClient->loadSpecialisations($selectedSymptoms, $gender, $yearOfBirth);
					}

					public function loadBodyLocations()
					{
    					return $this->diagnosisClient->loadBodyLocations();
					}

					public function loadBodySublocations($bodyLocationId)
					{
    					return $this->diagnosisClient->loadBodySublocations($bodyLocationId);
					}

				 public function loadSublocationSymptoms($sublocationId, $selectedSelectorStatus)
					{
   					 return $this->diagnosisClient->loadSublocationSymptoms($sublocationId, $selectedSelectorStatus);
					}

					public function loadProposedSymptoms($selectedSymptoms, $gender, $yearOfBirth)
					{
    					return $this->diagnosisClient->loadProposedSymptoms($selectedSymptoms, $gender, $yearOfBirth);
					}

					public function loadRedFlag($symptomId)
					{
    					return $this->diagnosisClient->loadRedFlag($symptomId);
					}
				}

And this is my SymptomsController.php

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use GuzzleHttp\Client;
use App\Services\DiagnosisClient;
use Carbon\Carbon;


 class SymptomsController extends Controller
							{
								protected $diagnosisClient;

							 public function __construct()
								{
   								 $language = 'en-gb';
   								 $this->diagnosisClient = app()->make(DiagnosisClient::class, ['language' => $language]);
								}

							 public function getAllSymptoms()
							 {
   								 $symptoms = $this->diagnosisClient->loadSymptoms();

    								return response()->json($symptoms);
							 }

								public function getIssues()
							 {
    								$issues = $this->diagnosisClient->loadIssues();

    								return response()->json($issues);
								}

							 public function getDiagnoses(Request $request)
								{
    								$this->validate($request, [
        								'symptoms' => 'required|array',
        								'symptoms.*' => 'numeric',
    								]);

    								$symptoms = $request->input('symptoms');
    								$user = Auth::user();
    								$gender = $user->gender;
    								$birth_date = Carbon::parse($user->birth_date)->format('Y');

    								$diagnoses = $this->diagnosisClient->loadDiagnosis($symptoms, $gender, $birth_date);

    								return response()->json($diagnoses);
								}


							}

The code works fine, the issue is that the token that is being sent in the url to make a request changes through time and it is a hash of the password and the authservicel url. So my code works by manually copy and pasting the token in my .env file everytime it changes.

So now i want to implement the TokenGenerator.php functionalities to my code for the token to be generated automatically with each request.

In my env file i have the following keys

HEALTH_SERVICE_URL=https://sandbox-healthservice.priaid.ch AUTH_SERVICE_URL=https://authservice.priaid.ch/login APIMEDIC_USERNAME= APIMEDIC_PASSWORD=

krisi_gjika's avatar

@mateog98 try replacing

$this->diagnosisClient = app()->make(DiagnosisClient::class, ['language' => $language]);

with:

$this->diagnosisClient = new DiagnosisClient($language);

Please or to participate in this conversation.