Mysql
 sql >> Datenbank >  >> RDS >> Mysql

MySQL Producer Consumer mit mehreren ausgewählten Threads

Ich habe eine praktische Lösung für Sie, die ich in einem Projekt an meinem Arbeitsplatz gesehen habe. Anstatt nur 0 und 1 für unvollständig und abgeschlossen zu verwenden, erweitern Sie Ihr Set um weitere Fälle.

Nennen wir diese Spalte Status . Hier sind die verschiedenen Werte dieser Spalte und die entsprechenden Zustände des Jobs.

  1. Wenn der Status 0 ist, wurde der Job von keinem Worker-Thread übernommen.
  2. Wenn der Status 1 ist, wurde der Job von einem Worker-Thread übernommen und wird verarbeitet.
  3. Wenn der Status 2 ist, ist der Job fehlgeschlagen. (Sie sollten die Möglichkeit eines Verarbeitungsfehlers berücksichtigen.)
  4. Wenn der Status 3 ist, wurde der Auftrag abgeschlossen.

Ihre Threads sollten eine Logik enthalten, die nur Jobs aufnimmt, deren Status 0 ist, und den Status auf 1 ändert. Dadurch können andere Threads die Jobs, die gerade verarbeitet werden, nicht aufnehmen. Wenn der Job abgeschlossen ist, wird der Status auf 3 gesetzt und wenn der Job fehlschlägt, wird der Status auf 2 gesetzt. Dann kann der Thread weitergehen und nach einem anderen Job suchen, der noch abgeschlossen werden muss.

Sie könnten die Threads auch bitten, Jobs mit Status 2 aufzunehmen, aber Sie müssen eine Logik definieren, um eine endliche Anzahl von Wiederholungen anzugeben.

BEARBEITEN:

Nach einer lange Diskussion , sind wir gemeinsam auf die Lösung gestoßen. Meine obige Antwort ist in einem allgemeineren Zustand gut, wenn der „Job“ ein Prozess ist, der einige Zeit in Anspruch nimmt. Aber das war beim Problem des OP nicht der Fall.

Die Lösung, die schließlich funktionierte, war also diese:

BEGIN 
SELECT * FROM Jobs WHERE JobID = (SELECT * FROM Jobs WHERE completed = 0 LIMIT 1) LOCK IN SHARE MODE;
UPDATE Jobs SET completed = 1 WHERE JobID = (PREVIOUS ID); 
COMMIT;