Skip to content
back to the presentation
Talk summary2019

The Web Through a Backend Engineer’s Eyes: What Comes Next

A twenty-minute talk at the GetIT Meetup: Alexander Polomodov, who runs development in Tinkoff's customer acquisition unit, walks through five layers of the backend — code organisation, data storage, system design, infrastructure and automation — shows where each of them is heading, and in the Q&A explains why one of their applications still lives on bare metal.

GetIT Meetup9 min read

This summary is shorter than the full talk; examples and assessments reflect the author’s experience and views.

The main thread of the material
01

Acquisition: from spaghetti to onion

Alexander opens with an introduction: he graduated from one of the best technical universities in Russia, worked as a developer and a team lead in several companies, and joined the customer acquisition unit two and a half years ago. His teams own the unauthenticated zone of the site — the front page and everything visible before you enter a product's account — and their own content management system for creating news, vacancies and other pages for the web and partly for the mobile apps. The other half of the work is automating the buying of advertising: the budget for attracting new users is large, and Alexander lists the five most popular channels, among them contextual and social network advertising. There are many users, so hypotheses are tested before rollout: A/B, split and multivariate tests, and when the result is ambiguous, personalisation of pages for particular segments. He has twenty minutes, so every section ends with a slide of books.

The first layer of the evolution is code. Long ago people wrote spaghetti: the structure is invisible, and it is unclear how to make a change without something firing somewhere else — Alexander admits this is how he started. Then came layered architecture, with a presentation layer, a business logic layer and a storage layer, a big leap forward that still prescribed no rules for who depends on whom and how the layers talk to each other. The gap was closed by dependency injection and, with it, onion and hexagonal architectures: the outer layers, meaning interfaces and services, depend on the domain, while the domain does not change with the interface the system uses to talk to the world. He closes the section with books and articles on organising code properly.

02

From normal forms to microservices

Data storage travelled a similar road. At first state lived in the file system, and the developer described not only which data he needed but how to find it on disk, in which directory and how to append to a file — slow, painful and not reusable. Then came Codd with relational theory and the SQL standard, which suited record-keeping systems: entities, relationships, normal forms, and data fetched declaratively, with the planner doing the searching. In the 2010s came scenarios where a relational database does not scale horizontally enough or answers too slowly, and NoSQL was born: the term, Alexander recalls, started as a hunt for an unused hashtag for a meetup and by now is not worth spelling out. Such solutions traded the guarantees of relational databases — SQL, ACID, sometimes transactions — for BASE, with basic availability and eventual consistency. Keeping consistency at application level proved inconvenient, and NewSQL appeared: horizontal scaling, operation across regions, transactions and the familiar syntax. Here he recalls the CAP theorem, cites the Google Spanner white paper with its cross-region transactions and five nines of availability, and names Designing Data-Intensive Applications as the best book of the section.

System design began with the monolith that held all the logic: any change called for a full regression, dependencies were opaque, and a monolith with spaghetti code inside is, as Alexander puts it, a delicacy for connoisseurs. Service-oriented architecture promised to assemble an application out of ready services, but turned into a set of heavy interface systems sticking out into the internet with their own descriptions: integrating with them was hard, and the idea never flew despite the effort. Microservices, he notes, differ from SOA conceptually only by the prefix: nobody really knows what size a service must be to count as micro, yet saying you build microservice architecture is now popular. Next come serverless and functions as a service: events and handlers, excellent for some tasks, except that the orchestration logic has to be baked into the client. The books here are Sam Newman and a small volume on the mistakes of cutting a domain too finely; the manifestos are the twelve-factor app and a joke about a one-factor one.

03

Bare metal, Kubernetes and the Q&A

Where all of this runs is a ladder of its own. Alexander remembers physical machines the administrators named after Italian women: recalling what was deployed where felt like going through your girlfriends. Bare metal fails at isolation and resource utilisation, and a box per application is too expensive, so x86 virtualisation arrived, proposed by people whose research project turned into a good business, followed by virtualised disks and networks. Idle capacity is best sold on: AWS put its spare hardware to work outside the peak sale seasons and holds most of the market, competing with Microsoft Azure and GCP. Containers cut the cost of the guest OS and sit well on microservices, but you cannot juggle them by hand: the de facto orchestrator became Kubernetes, of which Alexander is a certified administrator. The top of the ladder is platform as a service: you throw in code and pay for the resources. Automation has to keep up: from laying out artifacts by hand, through Capistrano and Fabric some five years ago, to CI/CD systems such as Bamboo and TeamCity, and then to Netflix-style chaos engineering, where problems are injected into applications to see how cascading failures are prevented.

As for what lies ahead: the monolith of two and a half years ago has broken up into roughly 45 microservices — rolling them out is convenient, but a cross-cutting change such as one format for inter-service communication instead of JSON means updating all forty-five. Databases are better taken as a service where security allows, because most teams have no good DBA, and part of the load — converting a page's images into a convenient format, say — is covered by FaaS with no queue to build. The first question from the room, on how layered architecture differs from onion, he defers to the break as too long. The second: do these patterns suit every business domain? His counter-example: the application that buys advertising at real-time auctions must fit a 100-millisecond response budget, so it is not cut into services, and on a shared physical host it hit a ceiling because of noisy neighbours — non-functional requirements decide. The third, on GCP and clearing it with security, leads to a hybrid: the web and content management live in the cloud, while data and the services around it stay in the Moscow data centres, reached over a dedicated channel; Google's data centre in Finland gives 17 milliseconds.

Takeaways

What to take away

  1. 01Layers gave structure but no rules for dependencies: those came with dependency injection and onion architecture, where the domain does not depend on the interfaces facing the world.
  2. 02NoSQL traded the guarantees of relational databases for horizontal scaling, and NewSQL brought back transactions and SQL: Google Spanner sustains five nines of availability that way.
  3. 03SOA and microservices diverge only by the prefix; forty-five services make rollouts cheap and any cross-cutting change expensive.
  4. 04Non-functional requirements beat fashion: an application with a 100-millisecond response budget belongs on a monolith on bare metal, not on a shared host with noisy neighbours.

Sources