📜 ⬆️ ⬇️

VIP service pattern

In the previous article we looked at a small pattern to simplify the code of users of services, in this article we will consider a special type of service. This pattern is used in architectures with layers, if the architecture in question has no layers, then the pattern may not have the desired effect or be harmful at all.

Architectural layers
Unfortunately on Habré there are no articles describing what layers are, but outside there is a habrauseur primepix article

The pattern is not tied to programming languages.

Update: Added an example from real practice.
')
Picture to attract attention:




Imagine a situation, we have a large project, which has already been formed and has passed the stage of rapid redesign. The project has layers, everything is implemented technically correctly (yes, it happens) and the architecture allows you to implement a subset of the current functionality. Development goes according to plans without excesses and crunches.

But at some point, an idea or demand arises in one of the bright heads of designers / investors / creative directors or artists (underline the necessary). This idea does not fit into the current architecture. This may not necessarily be an idea as a new functionality, it may be, for example, support for the custom functionality / mode of one of the middleware vendors which gives some advantage, for example technical.

What do designers / architects do in this situation? The most correct decision is the rejection of new functionality by all available methods, because the most good code is code that is not written. This code is easily maintained and contains the minimum number of bugs. Impact methods can be different, from pressure by authority to the use of various tricks, for example, to allow you to beat yourself in Quake .

The second solution, if the situation permits, in the working order is a revision of the architecture and, if necessary, redesign.

If there is no time for evaluation and redesign, and the solution is required “yesterday”, then we have to take “technical debt”. The hardest case - the functionality must be thrown through several layers.

Forwarding functionality:


The negative consequences of such decisions are known. The upper layers become dependent on the details of the lower layers, services appear as intermediaries that are needed only to forward functionality, etc.

This pattern serves to solve the problem of littering the architecture with oversights and their negative impact on the architecture as a whole. The essence of the pattern is to encapsulate all the debts in a single service, or a chain of services. This service will be a facade to all technical debts of the system.

Forbid Encapsulation:


It is important to understand that this pattern is not part of the architecture and is needed only to encapsulate temporary solutions, allowing you to gain time for evaluation and redesign without destroying the current architecture.

Real life example
IMO game project. Codebase about 3000 C # files. The client is written in C #, OGRE (C ++) was used for rendering.

Fragment of client architecture


The bottommost “Render” layer is the implementation of the render, along with implementations of various effects (animation scenes, particles) and scene objects with animation support (skeletal, morph). Everything related to the display in one form or another was implemented in this layer.

The “Render facade” layer was the interface (facade) to the renderer and contained all the wrappers of the native code for use in C #.

The “Scene graph” layer was a place to simulate objects and their interaction.

The “Logic” layer simulated objects and displayed logic on simulation objects.

In this fragment, other systems that were in these layers are omitted, for example, there is no UI (which was also C # wrappers for C ++).

The objects in the scene layer of the graph were the simplest objects that contained the position and orientation. Supported hierarchy as well as managing abstract animation through identifiers (roughly speaking, start and stop by id).

After the next burst of creativity, designers needed to change the colors of materials depending on the logic in runtime. The motivation was the following - “There is no time to explain, make us a change in the color of materials!”, However, in the game dev, this is a common practice (emoticon).

To add such functionality, it was necessary to disfigure object interfaces by adding such a specific thing as material and to forward through all layers. Moreover, not all objects in principle had material, for example, light sources and cameras or composite animation objects, for example, asteroid belts, etc.

Forward functionality (shown in red)


There was not enough time for thinking and especially for experiments, so it was decided to temporarily arrange this functionality as an independent service. In this case, even the object interface was not affected, a certain implementation of the extension methods only in a global context.

VIP service implementation


At the same time, at every stage and in every chain of service, all kinds of paranoid checks were done so that the service data did not break the operation of the system or become a source of failures.

Over time, various methods for very tricky widgets and other problem solutions appeared and disappeared in this service.

And the functionality of the materials was removed from the service after the implementation of a full-fledged animation graph with support for all aspects of visualization. And the designer pointed out the change of materials as part of the animation.



Pros:


Minuses:


Thank you all for your understanding!

Source: https://habr.com/ru/post/205516/


All Articles