Odoo-Migration: Erfahrungen aus vier Altsystemen

Vier Altsysteme, 15 Jahre Daten, ein Zielsystem. Was dabei überraschend einfach war, was hart erarbeitet werden musste – und wo KI wirklich hilft.

Diagramm eines Computersystems

06.08.2026 | Intern

In den letzten Monaten haben wir bei RTP vier sehr unterschiedliche Systeme nach Odoo 19 migriert. Nicht als Testlauf, sondern mit unseren echten Produktivdaten aus 20 Jahren Firmengeschichte. Geschrieben haben wir die Migrationswerkzeuge mit Claude Code, iterativ und pragmatisch.

Dieser Artikel beschreibt, was dabei funktioniert hat, welche Muster sich in allen Migrationen wiederholten – und an welchen Stellen es trotz KI-Unterstützung echtes Verständnis brauchte.

Das Wichtigste zuerst: ein verbundener Datenbestand

Alle Migrationen liefen in dieselbe Odoo-Instanz – und genau das war der Punkt. Die gemeinsamen Achsen sind Unternehmen, Mitarbeitende und Projekte. Eine Wissensseite aus Notion verlinkt heute auf ein Projekt, das ursprünglich aus ActiveCollab stammt, und dieses Projekt hängt an derselben Firma wie die Rechnungen aus Bexio.

Statt sauber migrierter, aber isolierter Datensilos steht am Ende ein zusammenhängender Bestand. Das war von Anfang an das eigentliche Ziel – und es ist der Punkt, der den ganzen Aufwand rechtfertigt. Alles Weitere in diesem Artikel beschreibt, wie wir dorthin gekommen sind.

Die Ausgangslage: vier Systeme, vier Welten

Bexio enthielt unsere komplette Buchhaltung: Kontakte, Artikel, Angebote und Aufträge, Kunden- und Lieferantenrechnungen, Zahlungen und die zugehörigen PDF-Belege. Über 600 Kontakte und rund 4'400 Rechnungen. Buchhaltungsdaten verzeihen keine Ungenauigkeit – hier zählt jeder Rappen.

ActiveCollab war unsere Projektwelt: mehr als 400 Projekte, über 30'000 Tasks und Subtasks, rund 90'000 Kommentare, dazu Zeiterfassung, Meilensteine, Mitarbeitende und Kundenzuordnungen. Zudem wanderten über 25'000 Anhänge mit einem Volumen von rund 15 GB nach Odoo. Alles quervernetzt, alles voneinander abhängig.

Notion beherbergte unser Wissen: rund 1'000 Seiten mit tiefen Hierarchien, Datenbanken, internen Verlinkungen und Anhängen. Unstrukturiert im besten Sinne – und entsprechend schwer maschinell zu fassen.

Dazu kam unsere Zeiterfassung: sämtliche Einträge seit Anfang Jahr, auf die Minute genau. Genau erfasste Arbeitszeit, die wir nicht verlieren wollten – weil genau diese Historie die Grundlage für jede spätere Auswertung ist.

Der rote Faden: Muster, die überall funktionieren

So unterschiedlich die vier Quellsysteme waren – einige Prinzipien haben sich in jeder der Migrationen bewährt.

Jeder Datensatz bekommt eine stabile Kennung. Das ist das wichtigste Fundament. Jeder migrierte Datensatz erhält in Odoo eine eindeutige, aus der Quelle abgeleitete ID. Damit wird ein erneuter Durchlauf zum Update statt zum Duplikat. Genau das ermöglicht iteratives Arbeiten: migrieren, prüfen, Fehler finden, korrigieren, erneut laufen lassen – ohne dass der Datenbestand jedes Mal explodiert. Ohne dieses Prinzip wäre eine Migration dieser Grössenordnung ein einziger nervenaufreibender Big Bang.

Saubere Trennung der Schichten. Quellsystem-Anbindung, reine Datenumwandlung, Odoo-Anbindung und Ablaufsteuerung blieben strikt getrennt. Das klingt nach Lehrbuch, zahlt sich aber sofort aus: Jedes Teil lässt sich einzeln testen und verstehen, und wenn etwas schiefgeht, ist schnell klar, wo.

Auf Bestehendes matchen statt blind neu anlegen. Firmen, Personen und Projekte existieren oft mehrfach über die Systeme hinweg. Wir haben zuerst über E-Mail, dann über den Namen und schliesslich über unscharfen Abgleich mit Schwellenwert gesucht – dabei bewusst konservativ. Eine stille Fehlverknüpfung ist deutlich unangenehmer als ein Duplikat, das man sieht und korrigieren kann.

Die Reihenfolge entscheidet. Produkte müssen vor Verkaufsbelegen existieren, Rechnungen vor Zahlungen, Eltern-Tasks vor Subtasks, Datenbank-Container vor ihren Einträgen, Anhänge vor der Seite, die sie referenziert. Wer diese Abhängigkeiten nicht vorher durchdenkt, läuft in eine Kaskade von Folgefehlern.

Zwei Durchgänge bei quervernetzten Inhalten. Bei ActiveCollab und Notion konnten interne Verlinkungen erst im zweiten Durchgang aufgelöst werden, weil die Ziel-Datensätze beim ersten Durchlauf schlicht noch nicht existierten. Bei Bexio war das nicht nötig – Buchhaltungsdaten sind erfreulich linear.

Nicht jede Quelle braucht eine Schnittstelle. Die Zeiterfassung haben wir bewusst nicht über eine API angebunden, sondern per CSV überführt. Die Daten waren sauber strukturiert, der Umfang klar begrenzt, und sie mussten genau einmal wandern. Eine API-Anbindung hätte hier mehr Aufwand als Nutzen gebracht. Es lohnt sich, diese Frage bei jeder Quelle neu zu stellen, statt reflexartig zur technisch anspruchsvollsten Lösung zu greifen.

Rate-Limiting ernst nehmen. Jede API tickt anders. Die eine liefert Limits im Header mit, die nächste erlaubt eine feste Anzahl Anfragen pro Sekunde, die dritte verlangt exponentielles Zurückfahren nach Fehlern. Wer das erst reaktiv löst, verliert unnötig Zeit.

Wo es wirklich knifflig wurde

Jedes System hatte seine eigenen Stolperfallen. Hier die wichtigsten, ohne allzu tief einzusteigen.

Bexio – wo Präzision zählt. Bexio rundet die Mehrwertsteuer zeilenweise, Odoo global. Über tausende Belege ergibt das systematische Differenzen im Rappenbereich, die man kennen und gezielt behandeln muss. Deutlich unangenehmer ist die Währungsrundung: Sobald in Odoo Buchungen existieren, lässt sie sich nicht mehr ändern. Wer die Einstellung vorher nicht sauber setzt, hat ein Problem, das sich nicht mehr elegant lösen lässt. Und Steuern lassen sich nicht über den Prozentsatz zuordnen – 8,1 % auf Material, auf Investitionen oder im Reverse-Charge-Verfahren sind buchhalterisch drei verschiedene Dinge.

ActiveCollab – wo alles zusammenhängt. Hier lag die Schwierigkeit in der Vernetzung. Ein in der Oberfläche gelöschter Datensatz, dessen Kennung im Zielsystem überlebt hat, muss sauber neu angelegt werden statt einen Fehler zu werfen. Zuordnungen ohne klaren Ursprung brauchen deterministisch erzeugte Kennungen, damit ein erneuter Durchlauf nicht jedes Mal neue Duplikate produziert. Und Odoo selbst hat Eigenheiten, die man kennen muss: Beim Anlegen hängt es automatisch den aktuellen Benutzer an Datensätze an, und Datumsfelder von Anhängen überschreibt es konsequent auf den Importzeitpunkt.

Notion – wo Struktur fehlt. Die grössten Probleme lagen hier in der Struktur der Inhalte selbst. Tief verschachtelte und sich gegenseitig referenzierende Seiten liefen in Endlosschleifen, solange der Import nicht über alle Ebenen hinweg festhielt, was er bereits besucht hatte. Noch heimtückischer war die Unterscheidung zwischen einer verlinkten Datenbankansicht und der eigentlichen Datenbank: Beide sehen auf den ersten Blick gleich aus, aber wer die Referenz für das Original hält, importiert sämtliche Einträge ein zweites Mal. Das Unterscheidungsmerkmal steckt an einer Stelle, an der man es nicht zuerst sucht.

Dazu kam eine stille Falle: Odoos HTML-Bereinigung entfernt unbekannte Attribute kommentarlos, weshalb unsere Marker für interne Links spurlos verschwanden – ohne Fehlermeldung. Die Lösung war, sie als HTML-Kommentar zu transportieren, der die Bereinigung überlebt. Und ein Problem, das sich technisch gar nicht lösen lässt: Für ehemalige Workspace-Mitglieder liefert Notion nur noch eine anonyme Kennung – ohne Name, ohne E-Mail. Diese Zuordnung mussten wir von Hand nachpflegen.

Übergreifend gilt eine Erfahrung, die vermutlich jede Migration teilt: Die Dokumentation sagt X, die Schnittstelle tut Y. Jedes der vier Systeme hatte Abweichungen, die man sich hart erarbeiten musste.

Was die KI beigetragen hat – und was nicht

Die Zusammenarbeit mit Claude Code lief nicht als grosser Wurf, sondern in kleinen Schleifen. Ein Symptom melden – etwa dass auf einer migrierten Seite ein Element fehlt. Die Ursache am echten Datensatz diagnostizieren. Korrigieren. Gegen die Stage-Umgebung verifizieren. Weiter zum nächsten Punkt.

Entscheidend war, dass die Prüfung an echten Daten stattfand statt an Annahmen. Wegwerf-Testdatensätze und gezielte Einzelfälle brachten mehr Klarheit als jede theoretische Überlegung.

Was nicht delegierbar war: die Design-Entscheidungen. Ob ein bestimmter Verweis überhaupt aufgelöst werden soll oder besser ignoriert wird. Ob eine Sortierung fachlich überhaupt Sinn ergibt. Wie konservativ das Matching sein muss. Diese Fragen betreffen das Geschäft, nicht den Code – und sie blieben bei uns.

Herausgekommen ist kein Wegwerf-Skript, sondern getesteter, dokumentierter und wiederholbarer Code.

Was wir mitnehmen

Eine Migration ist heute kein reines Werkzeugproblem mehr. Der mechanische Teil – Code schreiben, Schnittstellen anbinden, Daten umformen – ist mit guter KI-Unterstützung deutlich günstiger geworden, als er es noch vor zwei Jahren war.

Was teuer bleibt, ist das Verständnis: Wie ist das Datenmodell aufgebaut? Welche Eigenheiten hat die Schnittstelle? In welcher Reihenfolge muss was passieren? Und welche Fälle sind so speziell, dass sie eine bewusste Entscheidung brauchen?

Wer beides verbindet – die Geschwindigkeit der KI und das Verständnis für Fach und System – migriert schneller, sauberer und vor allem wiederholbar. Und landet am Ende nicht in neuen Silos, sondern in einem Datenbestand, der tatsächlich zusammenhängt.