Concepte

Sarcini asincrone

Cum să urmărești operațiile de lungă durată prin Job API

Unele operații durează: publicarea unui anunț necesită traducerea descrierii, procesarea geolocației și optimizarea fotografiilor. În loc să te facă să aștepți, API-ul lansează aceste sarcini în fundal și returnează un jobId pentru urmărire.

Când se returnează jobId

OperațieCe se întâmplă în fundal
Publicare anunțTraducere descriere, procesare locație, analiză fotografii
Încărcare fișiere mediaOptimizare, generare previzualizări

Cum funcționează

1. Cererea returnează jobId

La publicarea unui anunț, statusul se schimbă în pending_active și se returnează jobId:

{
  "id": 42,
  "externalId": "APT-001",
  "status": "pending_active",
  "publicUrl": "https://rentix.md/announcement/42",
  "updated": true,
  "jobId": 789
}

2. Verifică statusul sarcinii

Folosește GET /job/status pentru a urmări progresul:

async function waitForJob(jobId) {
  while (true) {
    const response = await fetch(
      `https://crm.rentix.md/api/v1/job/status?id=${jobId}`,
      { headers: { 'Authorization': 'ApiKey YOUR_API_KEY' } }
    );

    const job = await response.json();

    if (job.status === 'completed') {
      console.log('Sarcină finalizată:', job.resultData);
      return job;
    }

    if (job.status === 'failed') {
      throw new Error(job.publicErrorMessage);
    }

    // Așteaptă o secundă înainte de următoarea verificare
    await new Promise(r => setTimeout(r, 1000));
  }
}

const job = await waitForJob(789);

3. Statusurile sarcinilor

StatusDescriereCe să faci
pendingÎn coadăAșteaptă
processingÎn execuțieAșteaptă
completedSuccesVerifică resultData
failedEroareVerifică publicErrorMessage
failed_retryableEroare temporarăPoți repeta operația

Exemple de răspunsuri

Sarcină în coadă

{
  "id": 789,
  "type": "announcement_finalize",
  "status": "pending",
  "queuePosition": 3,
  "createdAt": "2026-02-08T12:00:00.000Z"
}

queuePosition: 3 — înaintea sarcinii tale sunt încă 3 în coadă.

Sarcină în execuție

{
  "id": 789,
  "type": "announcement_finalize",
  "status": "processing",
  "queuePosition": null,
  "createdAt": "2026-02-08T12:00:00.000Z"
}

Sarcină finalizată

{
  "id": 789,
  "type": "announcement_finalize",
  "status": "completed",
  "resultData": {
    "announcementId": 42,
    "completedOperations": ["translate_description", "process_location", "analyze_images"],
    "finalStatus": "active"
  },
  "createdAt": "2026-02-08T12:00:00.000Z",
  "completedAt": "2026-02-08T12:00:15.000Z"
}

După finalizarea cu succes, statusul anunțului devine active.

Sarcină cu eroare

{
  "id": 789,
  "type": "announcement_finalize",
  "status": "failed",
  "publicErrorMessage": "Nu s-au putut procesa imaginile",
  "isRetryable": true,
  "createdAt": "2026-02-08T12:00:00.000Z",
  "completedAt": "2026-02-08T12:00:10.000Z"
}

Cu isRetryable: true poți repeta operația — trimite aceeași cerere de publicare.

Câmpurile răspunsului

CâmpTipDescriere
idnumberID-ul sarcinii
typestringTipul operației
statusstringStatusul curent
resultDataobjectRezultat (la completed)
publicErrorMessagestringMesaj de eroare
isRetryablebooleanDacă se poate repeta
queuePositionnumberPoziția în coadă
createdAtstringOra creării
completedAtstringOra finalizării

Recomandări

Frecvența interogărilor

Nu interoga statusul mai des de o dată pe secundă — creează încărcare suplimentară și nu accelerează execuția.

Logare

Salvează jobId în loguri. Asta va ajuta la diagnosticarea problemelor — suportul va putea găsi sarcina după ID.

Gestionarea erorilor

Verifică isRetryable. Dacă true — problemă temporară, poți repeta. Dacă false — trebuie să corectezi datele.

Scenariu tipic de publicare

1. PUT /listings { externalId: "APT-001", announcementStatus: "active" }
   → status: "pending_active", jobId: 789

2. GET /job/status?id=789
   → status: "pending", queuePosition: 3

3. GET /job/status?id=789 (după 5 sec)
   → status: "processing"

4. GET /job/status?id=789 (după 10 sec)
   → status: "completed", resultData.finalStatus: "active"

5. Anunțul este publicat pe rentix.md
Copyright © 2026