Download the PHP package valu/valuso without Composer
On this page you can find all versions of the php package valu/valuso. It is possible to download/install these versions without Composer. Possible dependencies are resolved automatically.
Package valuso
Short Description Zend Framework 2 module for service oriented application architecture
License BSD-3-Clause
Homepage http://www.mediacabinet.fi/
Informations about the package valuso
ValuSo
ValuSo is a Zend Framework 2 module for service oriented application architecture.
Installation
Use Composer and install package
valu/valuso
:
Type dev-master
, when asked which version to install. Now it is ready to be used as a library. To use it as a ZF2 module, add valuso
to your modules in config/application.config.php
.
Service Layer
Defines an application's boundary with a layer of services that establishes a set of available operations and coordinates the application's response in each operation. - Randy Stafford, EAA
In ValuSo the service layer is implemented using service broker
, which passes operations to correct service implementations and collects their responses. When an operation is invoked, the service broker calls the registered closure
or __invoke
method of service class. If invoke is not available, the service class is wrapped with a special proxy class
, that implements the invoke method by mapping the operation name to method name.
The consumer of a service doesn't know who actually implements the service and where (locally or in an external system).
The concept and implementation of the service layer is similar to router/controller interaction in MVC pattern. However, they operate on different levels. Controller is an endpoint that receives the user’s (or client’s) raw request (e.g. from HTTP). Controller then needs to decide who is actually responsible of processing the request. With service layer available, the controller calls appropriate services and returns response that may actually be an aggregation of multiple responses from different services.
NoMVC or MVSC
With ValuSo, the developer may choose to ignore the common MVC pattern or extend it with the service layer. ValuSo comes with three pre-configured routes for HTTP REST
, HTTP RPC
and console
interfaces. These routes point to ServiceController
, which provides two actions:
- httpAction for HTTP REST/RPC requests and
- consoleAction for console requests.
These actions are able to transform client’s requests into service calls and service responses into correct HTTP/CLI response format (which is JSON in both cases).
ValuSo is designed to work with applications, where the back end needs to be completely separated from the front end. For this reason the concept of View in MVC pattern is often obscure.
Features
Convenient and IDE-safe way to use services
Typically service is accessed calling service() method of the ServiceBroker class. This method initializes a new Worker object. To skip this initialization, it is possible to call ServiceBroker's execute() or dispatch() directly.
Invoke services via HTTP
ValuSo provides end points (controllers) for HTTP REST and RPC interfaces. The difference between these two interfaces is minor and you should stick to using either one. Both interfaces return responses in JSON format.
Using REST interface to lock user account:
Response:
Using RPC interface to find a group:
Response:
Execute batch-operations
Batch operations are important, for performance reasons, especially when the services are invoked via external interface.
Response
Easy to use existing classes as services
ServiceBroker expects that the class registered as a service provides __invoke() method. In most cases the classes don't implement this method, which indicates the ServiceBroker (or ServicePluginManager to be exact) that these services should be wrapped with a special proxy class. With this feature, it is possible to use almost any existing class as a service.
Context-aware services
Often the services need to know, in which context they are executed. Mostly, because some services shouldn't be exposed to external interfaces. Following example demonstrates this by calling update operation in unsupported context.
Aspect-oriented programming with annotated services
There are lots of cross-cutting concerns with services. Most services need to trigger events, provide logging and access control mechanism. The best way to achieve these features, without messing the actual business code, is to annotate the operations.
Multiple respondents for one service
Often there is only one class or closure per service, but the architecture is not limited to that. You can actually register any number of classes/closures for the same service name.
Extend any existing service with your implementation
Usually, if service implementation doesn't support certain operation, it throws UnsupportedOperationException. CommandManager doesn't stop execution here, but finds the next registered class/closure for the service and gives it a chance to execute the operation. This feature can be used to extend existing services.
Listening to services
It is often important to listen to service operations. ServiceBroker provides an instance of EventManager and automatically triggers events before and after operation has been invoked. EventManagerAware service classes can also trigger events of their own.
Calling services from within service
It is common to use another service from within service class. To make this easy, ValuSo provides ServiceBrokerAware interface. This interface is used to inject ServiceBroker instance. There's also a built-in trait, ServiceBrokerTrait, that implements the interface for you.
Using proxy() method to call internal method
When service proxy classes are used, the proxy class implements missing __invoke method, maps operation name to internal method name and calls that method. Proxy class actually overrides the default method. Typical proxy method implementation looks something like this:
As you can see, on the first line it calls the real method implementation and the following code lines define event parameters and finally trigger a 'post' event.
You cannot call these proxy methods normally from within the real class. It is however, made possible via special proxy() method. The reason for this is, that without using the proxy() method it is not possible to call another method and still trigger its events etc.
If proxy instance is not available, the proxy() method returns reference to $this
. This pattern ensures that the service can be tested and used also without the proxy instance.
Getting started
There's usually one class per service. The service class is initialized using ZF2's ServiceManager, which means that you need to configure either service class name or factory class name.
Consider following example from ValuUser module. The module registers a single service, named simply User. Only class name is configured for the service.
Often the service cannot be initialized without injecting some dependencies or configuring the service. In these scenarios, a service factory should be used to initialize the service (consult Zend Framework's documentation for using ServiceManager).
It is also possible to register an instance of invokable class or closure. For performance reasons this is usually not recommended. Services should be initialized only when needed.
Configuration options
ValuSo configurations are read from valu_so configuration namespace.
All versions of valuso with dependencies
doctrine/common Version >=2.1
zendframework/zendframework Version >=2.0
slm/queue Version 0.3.*
slm/queue-beanstalkd Version >=0.2