Web Service
Nishchay provides web service features apart form RESTful route. Route allow us to create SEO friendly URL which can also used to create RESTful API. Using allowed method type we can create GET, POST, PUT or other service to provide various operation on same route. Using response type we can create JSON/XML response.
Apart from route path and HTTP method, Nishchay provides various features like defining error and success response structure, filtering response, token based service and many other.
Create Service
To make route a service, declare Nishchay\Attributes\Controller\Method\Service
on controller method.
NOTE: When route act as service it must have response type JSON or XML.
Service
attributes has following parameters.
Name | Description |
---|---|
fields | Enable or disable field demand or specify list of allowed fields demand in array |
token | Enable or disable token for the service |
supported | List of supported fields |
always | List of fields which will always be returned |
Make whole application serve as Service
To make whole application serve as Service, update setting to TRUE of enable config in service.php file. This will make all routes a service. We don't need to declare Service
attribute on each route but we can still declare it if want to configure something for service.
Filter service response/Fields demand
Service responds various fields but in some case does not want all fiends sent by service. If service consumer passes fields parameter then nishchay filters out fields before sending it to consumer. This fields parameter must be GET parameter.
#[Service]
#[Route(path: 'user/{userId}')]
#[Placeholder(['userId' => 'int'])]
#[Response(type: 'json')]
public function userProfile($userId = "@Segment(index='userId')") {
return [
'name'=>'Bhavik Patel',
'age'=>28,
'gender'=>'Male',
'accountType'=>'Developer'
];
}
If we call above service by user/1234 it will respond with all fields returned by route method. If we request same service with fields
GET parameter it will be filtered based on fields received. For request user/1234?fields=name,age, it will respond with only two fields name and age.
In fields parameter, multiple fields should separated by comma.
Force fields demand
By default demanding fields is optional. Omitting it will respond with everything. But we can make fields demand required by setting fields
parameter of Service
attribute to null.
#[Service(fields: null)]
In this case, when consumer calls service without fields, it responds with error.
Disable fields demand
Setting fields to FALSE, disables fields demand for service. Requesting fields on this service results in an error.
#[Service(fields: false)]
Specify default fields demand
If value of fields parameter is array, it will act as default fields demand. If this is set and consumer passes fields GET parameter then it overrides default demand.
#[Service(fields: ['name', 'age', 'gender', 'accountType'])]
Point to note for fields demand
If route method does not return requested fields then those fields will be added with default value as specified in service config. Nishchay add those fields with default only if its present in always and supported. Same will result in an error if its doesn't exist in route response, always and supported parameter of Service
attribute.
#[Service(always: ['name', 'gender'], supported: ['name', 'email', 'age', 'gender', 'accountType'])]
#[Route(path: 'user/{userId}')]
#[Placeholder(['userId' => 'int'])]
#[Response(type: 'json')]
public function userProfile($userId = "@Segment(index='userId')") {
return [
'name'=>'Bhavik Patel',
'age'=>28,
'gender'=>'Male',
'accountType'=>'Developer'
];
}
For above request user/1234?fields=name,gender,email
will respond all requested fields but for email field default value will be applied. Because email
is supported by service but not returned by route method.
If user/1234?fields=name,email,birthDate
then it will result in an error because birthDate not supported by service and also its not returned from route method.
Define supported fields
Defining supported fields for service will make sure service should respond with only supported fields. If in case method respond with fields which are not specified in supported list, then it will be removed by Nishchay service post processor.
#[Service(supported: ['name', 'email', 'age', 'accountType'])]
#[Route(path: 'user/{userId}')]
#[Placeholder(['userId' => 'int'])]
#[Response(type: 'json')]
public function userProfile($userId = "@Segment(index='userId')") {
return [
'name'=>'Bhavik Patel',
'age'=>28,
'gender'=>'Male',
'accountType'=>'Developer'
];
}
For above gender
field will be removed as its not supported by service.
Always returning fields
We can make service to always respond with fields. Even if fields demand does not request fields specified in always list, it will still be responded.
#[Service(always: ['name', 'gender'])]
#[Route(path: 'user/{userId}')]
#[Placeholder(['userId' => 'int'])]
#[Response(type: 'json')]
public function userProfile($userId = "@Segment(index='userId')") {
return [
'name'=>'Bhavik Patel',
'age'=>28,
'gender'=>'Male',
'accountType'=>'Developer'
];
}
For request user/1234?fields=age
will respond with name,age and gender fields. name
, gender
fields are not demanded but are still responds as its set to always respond.
Secure Service
Services are considered as secured if it requires to token to access it. Some service requires authentication to access it. To access those service consumer might need to send username and password in header/GET parameter to access it. Nishchay web service provides very familiar feature. We should implement non secure service, where user can pass credential. Once user verified we can generate token and respond to user so that user can use this token to access secure service.
By default all services are secured, we can make specific service non secure by setting token = true
of Service
attribute. We can also make all service secure or non secure by setting token in service.php config file.
Where token should be passed
Consumer can send token in header or GET parameter. This location is configurable to header and GET parameter only from token.where config in service.php setting file.
What should be token name
By default token is configured to be sent in header with X-Service-Token name. As mentioned above we can change token location to GET, in this case we might need to change token name. If we set token.name in service.php setting to token, then token should be passed like this user/1234?token={token}.
Service Token
Generate
There's two ways to create service token.
- OAuth
- Custom
For OAuth use Nishchay::getOAuth2()
to generate its token. Configuration related to this type of token is located in service.php setting file. When you want to use this token set verifyCallback = 'oauth'. This is default setting.
Below example demonstrate how we can generate oauth token.
$userId = 1;
$scopes = ['account', 'notes'];
$token = Nishchay::getOAuth2()->generateUserCredentialToken($userId, $scopes);
Here first parameter should be logged in user's userId and second parameter should be list scope names (As defined on route).
Custom
Another is one custom token, which you can generate on your own. How this token will be verified, please read next section.
Verification
If you are using Nishchay's OAuth token then you don't have to do anything as nishchay verifies this token for secure service. It also verifies scope.
When you generate OAuth token you also list of scope names. This will make token to be valid for given scopes. Upon requesting secure service, if it has scope defined on called route then nischay will check scope mentioned on route does exists in OAuth token.
For above example(See section Generate), token will be valid of account and notes scope.
Custom verification
If you are not using Nishchay OAuth token then you can specify callback method in token.verifyCallback of service.php setting file. When this setting has callback function set, then this function called with token received from request. Within this function you can verify your custom token.
This method must return true if token verification has been passed.
Service class
Using Service class we can know if the field is requested by consumer or not.
Service instance
Instance of service class is assigned to controller class property by declaring Nishchay\Attributes\Controller\Property\Service
attribute on it.
#[Service]
private $service;
Before calling route method, Nishchay will create instance of Service
class and assigns to $service
property. Here we can have any name for property, Nishchay assigns instance based on attribute declared on property.
Check if field is demanded
Checking if field is requested by consumer or not.
$this->service->getNeed()->isFirstName()
Any field can checked by is{fieldName}
, here first character of fieldName should be upper case. So for above, FirstName
will be checked as firstName
.
Save token to session
Saving service token.
$this->service->setToken('TOKEN')
Get service token
Getting service token.
$this->service->getToken()
Notes
Notes are visible to you only and its for your use only. Its good to note a point of what you read.