feat(akquise): mehrere Berater je Eintrag, je Berater eine Opportunity

Ein gefundenes Projekt passt oft zu mehr als einem Berater, und fuer
jeden geht eine eigene Bewerbung heraus. Das Feld "Berater" liess bisher
nur einen Namen zu.

Gespeichert wird eine kommagetrennte Liste in crm_acquisitions.consultant
(auf VARCHAR(500) erweitert, Migration in db.js) und keine eigene
Zuordnungstabelle: die Namen sind reiner Text, die Auswahlliste in
crm_acquisition_options ist eine Pflegehilfe und kein Fremdschluessel.
Suche, Sortierung und Anzeige der Liste arbeiten damit weiter auf einem
Feld. Die Funktionen zum Zerlegen stehen in acquisitionRules.js, das
Gegenstueck fuer das Frontend in src/types.ts, geprueft von
server/test/acquisition.test.mjs.

Zerlegt wird an vier Stellen:

- Uebernahme: je Berater eine Opportunity, alle in einer Transaktion.
  Ihre Titel tragen den Namen in Klammern, weil die Opportunity kein
  eigenes Feld fuer den Berater hat und in Pipeline und Liste sonst
  identische Zeilen stehen; bei einem einzigen Berater bleibt der Titel
  unveraendert. In den Notizen steht neben dem eigenen Berater auch, mit
  wem er sich das Projekt teilt. Der Eintrag merkt sich die erste
  Opportunity - sie entscheidet nur darueber, ob er wieder im Eingang
  auftaucht.
- Verlauf (crm_acquisition_history): ein Berater je Zeile. Ein Eintrag
  mit drei Beratern sind drei Bewerbungen, "Nico, Lisa" waere sonst ein
  eigener Schluessel neben "Nico" und "Lisa".
- Dashboard: dieselbe Zaehlung. Die Summe der Balken liegt damit ueber
  der Gesamtzahl "Bewerbungen", die weiter die Eintraege zaehlt.
- Auswahlliste pflegen: Umbenennen ersetzt den Namen innerhalb der
  Liste, Loeschen zaehlt auch, wer nur einer von mehreren ist. Ein
  Gleichheitsvergleich uebersah beides.

In der Oberflaeche haengt das Auswahlfeld jeweils einen Namen an, die
Gewaehlten stehen als Plaketten darunter und lassen sich einzeln
entfernen; ein bereits gewaehlter Berater verschwindet aus der Liste.
Bewusst kein <select multiple>: Strg-Klick ist mit der Maus unauffindbar
und mit einer Beruehrung gar nicht bedienbar.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
Sascha Wolf
2026-09-09 10:35:43 +02:00
co-authored by Claude Opus 5
parent a866cd9a52
commit 62dce64739
18 changed files with 684 additions and 91 deletions
+24 -3
View File
@@ -112,7 +112,10 @@ zeigt das Diagramm das **Ende** des Zeitraums und lässt sich nach links scrolle
die aktuellen Tage stehen rechts.
Rechts daneben steht **Bewerbungen je Berater** für denselben Zeitraum. Einträge
ohne hinterlegten Berater erscheinen als *Ohne Berater*.
ohne hinterlegten Berater erscheinen als *Ohne Berater*. Ein Eintrag mit mehreren
Beratern zählt bei **jedem** von ihnen: für jeden ist ein Profil herausgegangen.
Die Summe der Balken liegt damit über der Gesamtzahl *Bewerbungen* oben, die die
Einträge zählt - beides ist so gewollt.
### Anstehende Interviews und „Beim Kunden"
@@ -147,13 +150,26 @@ weg.
| **Anbieter** | Freitext: Vermittler oder Portal, z. B. Hays. Vorschläge aus den bisherigen Einträgen |
| **Kanal** | Auswahl: auf welchem Weg es kam |
| **Projekttitel** | das einzige Pflichtfeld |
| **Berater** | Auswahl: für wen das Projekt passt |
| **Berater** | Auswahl: für wen das Projekt passt - **mehrere möglich** |
| **Link** | Adresse der Ausschreibung. Ist einer hinterlegt, wird der Titel in der Liste anklickbar und öffnet ihn in einem neuen Tab |
*Von*, *Kanal* und *Berater* sind **Auswahllisten**. Ihre Inhalte stehen unter
*Einstellungen → Akquise* und lassen sich dort von jedem Benutzer pflegen. Ist
eine Liste noch leer, steht unter dem Feld ein Verweis dorthin.
**Berater** nimmt **mehrere Namen** auf - ein Projekt passt oft zu mehr als
einem. Jede Auswahl hängt einen Namen an und erscheint darunter als Plakette;
das Kreuz daran nimmt ihn wieder weg. Ein bereits gewählter Berater steht nicht
mehr im Auswahlfeld, es zeigt also immer nur, wer noch zu haben ist.
> **Was mehrere Berater bedeuten:** Beim Übernehmen entsteht **je Berater eine
> Opportunity** - jeder durchläuft seinen eigenen Vorgang, einer kann gewonnen
> werden und ein anderer verloren. Ihre Titel bekommen den Namen in Klammern
> angehängt, damit sie sich in Pipeline und Liste auseinanderhalten lassen; bei
> einem einzigen Berater bleibt der Titel unverändert. Im Dashboard zählt der
> Eintrag bei **jedem** der Berater - drei Berater sind drei versendete Profile,
> also drei Bewerbungen.
**Von** ist mit dem **angemeldeten Benutzer** vorbelegt - in der Regel trägt
jeder seine eigenen Funde ein. Trägt Markus etwas für Artur ein, wählt er Artur
aus der Liste. Der eigene Name steht dabei immer zur Auswahl, auch wenn ihn
@@ -183,7 +199,7 @@ wird geleert - für das nächste Projekt aus derselben Quelle.
| **Von** | wer den Fund hereingebracht hat |
| **Anbieter**, **Kanal** | woher es kam |
| **Projekttitel** | mit Link anklickbar (neuer Tab); darunter klein Endkunde, Tagessatz bzw. Festpreis und Personentage |
| **Berater** | für wen |
| **Berater** | für wen; bei mehreren stehen sie als einzelne Plaketten |
| **Opportunity** | ein Klick macht daraus eine Opportunity in der Phase *Erstgespräch Berater* |
| Pfeil / Stift / Papierkorb | zurück in die Akquise (nur im Archiv), bearbeiten (füllt das Formular oben) und löschen (legt den Eintrag in den **Papierkorb**) |
@@ -268,6 +284,11 @@ im Archiv.
Der Knopf **Opportunity** legt sie sofort an: Phase *Erstgespräch Berater*, 10 % Wahrscheinlichkeit,
zuständig ist der angemeldete Benutzer. Mit übernommen werden Titel, Endkunde,
Beschreibung, Tagessatz, Laufzeit, Projektpreis, Zeitraum und nächster Schritt.
Sind **mehrere Berater** hinterlegt, entsteht **je Berater eine Opportunity**
mit denselben Projektdaten; ihr Titel trägt den Namen in Klammern. In den Notizen
steht neben dem eigenen Berater auch, mit wem er sich das Projekt teilt
(*Auch beworben*).
Anbieter, Von, Kanal, Berater und Link haben in der Opportunity kein Feld - sie
landen als Herkunftsvermerk in den internen Notizen, damit nachvollziehbar
bleibt, woher das Projekt kam.