vosetu.

Wie Systeme miteinander sprechen: Die Anatomie der Unternehmensintegration

Die meisten Unternehmensprojekte bestehen darin, bestehende Systeme zum Sprechen zu bringen.

Mit einem Experten sprechen
Individuelle Softwareentwicklung·26. Juli 2026·9 Min. Lesezeit#entegrasyon#api#mimari#kurumsal

Why is integration harder than it looks?

Making two systems talk is technically an exchange of data; in practice it is reconciling two different world views. On one side a customer record has five fields, on the other twenty-five; one sends dates with a time zone, the other bare; in one a cancelled record is deleted, in the other its status changes. The real work of integration is not moving data but writing the rules that translate those differences.

The second difficulty is ownership: which system owns which data? If both sides can update the same customer record, sooner or later two different truths appear, and without a rule deciding which wins, the data quietly corrupts. The first step of integration design is not writing code but naming a single owner for each piece of data.

The third is that the other side is not under your control. An external system goes into maintenance, changes version, adds a field, changes its response format, or simply slows down. A flow you tested and passed in your own code stops working the day the other side changes. That is why integration code must be written more defensively than the rest.

Adapter architecture: growing without touching the core

The architectural answer to integration is the adapter: everything that talks to an external system lives in a module separate from the application core. The core speaks only its own language; the adapter does the translation. Without that separation, the external system's field names, error codes and quirks leak everywhere, and dropping that system becomes impossible.

The way we wrote it as a rule: adding a new external system means a new adapter and one registration line; the core is untouched. That discipline gives two things. First, an integration written for one client puts no other client's product at risk. Second, when that system is dropped one day, the place to delete is obvious — a single folder.

Three things must stay inside the adapter: field mapping, error translation and credentials. Field mapping converts the outside model into yours; error translation turns the other side's error codes into states you understand; credentials live in environment variables, not in code. When those three spill out, being an adapter loses its meaning.

Identity: the same user across different systems

In an organisation with several systems the most visible integration need is identity: the same person does not want to walk around with a separate password in each. A central identity service solves that — the user signs in once and the other applications recognise it. Its second benefit matters more: when someone leaves, you cut their access from one place.

We apply this approach across our own product family: the applications have no local sign-in, identity comes from a central service. The price is that the service becomes critical — when it is down, no application can be entered. So keeping the identity service alive is a higher-priority operational concern than any individual application.

The most commonly skipped topic in identity integration is authorisation. Identity answers 'who is this person'; authorisation answers 'what can this person do here'. Moving the second to the centre is not always right — each application has its own world of roles. A practical balance: identity at the centre, authorisation in the application.

Consistency: solving 'I sent it but it never arrived'

The hardest problem in sending data between two systems is that writing to your own database and sending to the other side are not a single unit. You write the record, try to send it, and the other side does not answer at that moment — the record exists with you and not with them. Or the reverse: it is sent while your own write fails. Both produce silent inconsistency.

The known solution is to write the outgoing message into your own database in the same transaction: the record and the 'to be sent' note are created together, a separate process picks the note up, delivers it and marks it once successful. No message is lost; at worst it is delayed. In our product where money moves, we use exactly this pattern.

The second rule is to be resilient to retries. A network error can send the same message twice; if the other side treats it as two operations, you get duplicates. The solution is to attach a unique id to every message and ensure the other side does not process the same id twice. In integrations, 'at least once' delivery is normal; your job is turning it into 'exactly one effect'.

The cheapest integration: files and exports

Not every integration has to be a live connection. If moving data once a day between two systems is enough, export and import in a standard file format is the cheapest, most durable and most understandable solution. It takes hours to set up, is easy to diagnose when broken, and does not depend on the other side's infrastructure.

This should not be dismissed: the need for live integration is often not real but a default preference. When you ask whether there is a concrete business requirement behind 'make it instant', the answer is frequently 'seeing it in the morning would be enough'. In such cases choosing the simple solution both speeds the project up and lightens operations.

That is why we keep import and export as a basic capability in our own products. It matters for data ownership and it satisfies most integration needs without a live connection. And if the other side offers no modern interface — a common situation in the enterprise world — it is the only practical route anyway.

Error handling: when the other side does not answer

The quality of integration code shows not on the happy path but at the moment of failure. What happens when the other side slows down: does the request wait forever, or give up in a reasonable time and retry? An integration without a timeout locks up your own system when the other side stalls — and from outside it looks like 'our system is down'.

The second mechanism is bounding retries. Retrying a failed message forever means thousands of accumulated requests firing at once when the other side recovers. Retrying at increasing intervals and, after a certain number of failures, stopping and notifying a human protects both sides.

The third is visibility: failed messages accumulating somewhere, and that somewhere being watched. If records in a 'could not send' state sit quietly in a column, nobody looks. A queue visible in the panel, noticeable when its count grows, is the most practical indicator of an integration's health.

Small details, big failures: dates, numbers, encoding

Most integrations break not on large architectural problems but on small differences of format. Dates are the classic: one side sends with a time zone, the other receives it bare, and records shift by three hours. The rule is simple: dates must always travel between systems with time-zone information, and storage must use a single zone. Localising at display time is cheap; untangling confusion in storage is expensive.

The second is number format. Decimal separators, thousand separators and rounding rules can differ between systems, and in monetary calculations that difference becomes inconsistency. Carrying monetary values as integer minor units rather than floating-point decimals erases most of this class of bug up front. Where rounding happens must also be written down — if both systems round separately, the totals will not agree.

The third is character encoding, and in Turkish content it shows immediately: if letters like 'ß', 'ğ' and 'İ' arrive broken, the problem is not in the data but in the transfer format's encoding. Always include a sample record with Turkish characters, long text and spaces in your integration tests; that single row catches a pile of complaints before production.

How do you test an integration when the other side is absent?

The most frustrating part of building an integration is that the other side's test environment is often missing or broken. The only route then is writing a fake service that imitates it: a small layer returning the expected responses and able to simulate failures too. This makes development independent of the other side's calendar.

The fake service's most valuable use is not the happy path but the unhappy one. In a real environment it is hard to produce the scenario 'what if the other side does not answer for five seconds'; in a fake service it is one line. Timeouts, partial responses, unexpected error codes and the same message arriving twice — no integration should go to production without testing those four.

There is also the record-and-replay method: capturing real responses from the live environment and replaying them in tests. This captures the other side's real behaviour and prevents your fake service from being too optimistic. If the captured responses contain personal data, remember to mask it; test data falls under data protection too.

Responsibility: who fixes it when the integration breaks?

The most argument-prone part of integration projects is who is responsible when something fails. When something between two systems stops working, both vendors tend to point at the other and the client is left in the middle. The only way to prevent that is naming an 'integration owner' at the start: who looks first and who makes the diagnosis must be written down.

What makes diagnosis possible is logging. Recording every outgoing and incoming message with a timestamp and an id ends the 'we sent it' versus 'we did not receive it' argument in minutes. How long those logs are kept must also be agreed up front — if they contain personal data, keeping them indefinitely is not an option.

The third item is notification: how far in advance will the other side tell you about a change? In enterprise integrations the most common cause of an outage is a version change made on the other side without warning. A simple 'change notification' clause in the contract is cheaper than one night of downtime.

Opening your own system: designing the endpoint

The other direction of integration is your own system opening a door outward. The first rule here is that a door you open is protected on the day it opens: authentication, rate limiting and abuse protection are not tasks for later. Our public endpoints carry that protection from the start — because protection added later also leaves data to clean up.

The second rule is contract stability. An endpoint you expose is no longer only your program but your users' as well; removing a field or changing its meaning breaks their systems. When change is needed, you keep the old one alive for a while, serve the new version at a separate address and allow time for migration.

The third is honesty: saying what is not there. Our products today have no outbound event notifications (webhooks); we tell a client who wants integration that up front and explain what is possible with the existing routes — endpoints and exports. Presenting something on the roadmap as if it existed is the most expensive misunderstanding in integration projects.

Conclusion

Integration is the invisible but most time-consuming part of enterprise projects, and its success rests on a few principles: keeping every external system in its own adapter, naming a single owner for each piece of data, writing messages into a queue so none is lost, making errors visible, and protecting every door you open from day one.

And do not dismiss the cheapest solution: if the need is a daily transfer, exchanging files is often more durable than a live connection. If you have systems that need to talk, let us start by discussing who owns which data — half of integration projects are solved by that question alone.

Machen wir heute den ersten Schritt

Beschreiben Sie Ihren Bedarf in einer Nachricht; wir melden uns innerhalb von 24 Stunden.

Wie Systeme miteinander sprechen: Die Anatomie der Unternehmensintegration · Vosetu