REST API Export von Artikeldaten

Hallo zusammen,

ich benötige Hilfe bei der Einrichtung meiner REST API Verbindung.

:white_check_mark: Folgendes habe ich bereits:

:cross_mark: Was mir fehlt:

  • PLENTY_CLIENT_ID
  • PLENTY_CLIENT_SECRET

Ich finde in den Benutzereinstellungen keine Möglichkeit, diese Daten zu generieren. Wo genau muss ich in Plenty diese Client ID und Secret erstellen, um den OAuth2 Token Abruf erfolgreich durchzuführen?

Danke vorab für eine kurze Schritt-für-Schritt Info oder einen Screenshot aus dem Backend.

Mit Api Nutzer und Passwort kannst du dir über die Login Route einen auth token erstellen:

Danke für deine Antwort.

Ich dachte, für die REST API braucht man zusätzlich Client ID und Secret aus den OAuth2 Clients.

In meinem Backend finde ich aber keinen Menüpunkt für OAuth2 Clients.

Weißt du, ob es ohne geht oder muss das vom Support freigeschaltet werden?

Meines Wissens war das geplant, wurde aber nie fertig gestellt. Zumindest hab ich davon nix mit bekommen :thinking:

Unsere API-Anwendungen gehen alle über User + Passwort, und damit auf der /login-Route den Token holen, und alle 24h aktualisieren.

Hey,

Unsere PlentyONE REST-API Anwendungen verfahren auch alle mit dem User + Password für den initialen Login, und danach eben mit dem Token.
Client-ID / Secrets haben wir nie verwendet.

Sven von der webimpact® GmbH
www.webimpact.io
webimpact GmbH Logo Banner PlentyONE Enterprise Partner
:envelope: office@webimpact.io
:telephone_receiver: +49 (0) 2974 77 999 99

Hey Sven,
danke für deine Rückmeldung.

Heißt das, ihr nutzt tatsächlich nur User + Passwort ohne Client ID / Secret, um ein Token zu generieren?

In der Plenty Doku steht ja, dass für den Password Grant immer Client ID und Secret nötig sind.

Könntest du mir sagen, wie genau euer Request aussieht (z. B. Beispiel-POST-Body), damit ich prüfen kann, ob ich etwas falsch aufbaue?

Danke dir!

Hey @Bermaro,

ganz genau.

Anbei ein Request Beispiel:

Darauf erhalte ich diese Response:

Sven von der webimpact® GmbH
www.webimpact.io
webimpact GmbH Logo Banner PlentyONE Enterprise Partner
:envelope: office@webimpact.io
:telephone_receiver: +49 (0) 2974 77 999 99

Ich habe dazu in Postman ein Pre-request Skript, womit ich bei jedem Request ein Token generiere und mich damit anmelde.

pm.sendRequest({
    url: "https://www.DEINEURL.de/rest/login",
    method: 'POST',
    header: {
        'content-type': 'application/json'
    },
    body: {
        mode: 'raw',
        raw: JSON.stringify({"username":"XXXXXXXXXX","password":"XXXXXXXXXXXXX"})
    }
}, (err, res) => pm.collectionVariables.set("BEARER", res.json().accessToken));

Dazu setze ich eine Env-Variable „BEARER“, welches dann das Auth Token enthält

In dem Titel deines Posts geht es um die Artikeldaten. Deine Beschreibung umfasst jedoch die LogIn Problematik. Daher gehe ich nun mal auf die Artikel ein:

Es gibt mehrere Routen um an seine Artikel zu kommen. PlentyONE empfiehlt die sog. PIM Routen, welche aktuell auch verwende. Jedoch nicht die einfache Route sondern die sogenannte Scroll Route, da diese mehr als 10.000 Varianten abrufen kann.

Zum Abrufen aller Artikel mit der TagID 25 kannst du beispielsweise diese GET Methode aufrufen:

/rest/pim/variations/scroll?tagIds=in:25

Alternative (veraltete Route) wäre, die items Route. In diesem Beispiel wird die ItemID 3359 aufgerufen mitsamt den Eigenschaften auf DE und FR

/rest/items?lang=de,fr&with=variations.properties&id=in:3359

In allen Artikelrouten hast du eine Pagination, mit welcher du dich durchhangeln musst, wenn mehr Artikel zurückkommen, als pro „Seite“ angezeigt werden können. Jede „Seite“ ist ein separater Call.

Wenn du weitere Fragen hierzu hast, hau raus. Welche Felder und Routen es gibt, steht auch ausführlich in der Doku:

Hallo zusammen,

ich arbeite an einem Tool zur automatischen Optimierung von Artikeltexten und habe ein Problem beim Zurückschreiben der Daten über die REST API.

Mein Setup:

  • PlentyMarkets System: p22871.my.plentysystems.com
  • Ich lade Artikel mit Tag ID 110 erfolgreich über die API
  • Artikel werden korrekt gefunden und angezeigt
  • Problem: Beim Zurückschreiben bekomme ich immer HTTP 503 Fehler

Was funktioniert: :white_check_mark: Login und Token abrufen :white_check_mark: Artikel laden mit: GET /rest/items/variations :white_check_mark: Artikeldaten werden korrekt angezeigt

Was nicht funktioniert: :cross_mark: Artikel-Updates mit: PATCH /rest/items/variations/{id}

Fehlermeldung:

HTTP 503 - Service Unavailable
"upstream connect error or disconnect/reset before headers. reset reason: connection termination"

Mein Update-Request:

json

{
  "itemTexts": [
    {
      "lang": "de", 
      "name": "Neuer Produktname"
    }
  ]
}

Was ich bereits versucht habe:

  • Lange Pausen zwischen den Requests (5-15 Sekunden)
  • Mehrere Versuche pro Update
  • Verschiedene Timeouts getestet
  • Bei ALLEN Updates kommt der 503 Fehler

Meine Fragen:

  1. Ist die API-Route /rest/items/variations/{id} korrekt für itemTexts-Updates?
  2. Muss ich eventuell einen anderen Endpunkt verwenden?
  3. Brauche ich spezielle Berechtigungen für Text-Updates?
  4. Gibt es aktuell bekannte Probleme mit der API?
  5. Sollte ich die Daten anders strukturieren?

Zusatzinfo: Das Tool soll Produktnamen, Beschreibungen und Meta-Daten automatisch optimieren. Das Laden der Daten klappt perfekt, nur beim Zurückschreiben hakt es.

Ich bin noch relativ neu bei der PlentyMarkets API-Entwicklung und wäre für jeden Hinweis sehr dankbar!

Vielen Dank im Voraus!

Hey @Bermaro

Eine Möglichkeit:


PUT /rest/items/{id}/variations/{variationId}/descriptions/{lang}

Sven von der webimpact® GmbH
www.webimpact.io
webimpact GmbH Logo Banner PlentyONE Enterprise Partner
:envelope: office@webimpact.io
:telephone_receiver: +49 (0) 2974 77 999 99

Verwende PUT anstelle von PATCH.
Die Route ist richtig, was fehlt ist die Sprache:

/rest/items/2/variations/1000/descriptions/de

Der Body darf keine JSON Liste enthalten. Probiers hiermit

{
  "itemId":2,
  "lang": "de",
  "name": "Test",
  "technicalData": "Hallo Welt",
  "description": "Hallo Welt"
}

Nachdem ich mit eurer Hilfe das Content-Update Problem gelöst habe (danke @sleunig und @Tim für die PUT-Route!), stoße ich jetzt auf ein neues Problem mit dem Tag-Management.

Funktioniert jetzt perfekt: :white_check_mark:

  • Content-Updates mit PUT /rest/items/{itemId}/variations/{variationId}/descriptions/de
  • Login/Token wie von @sleunig gezeigt (ohne Client-ID/Secret)
  • Artikel laden mit Tag-Filterung

Neues Problem: :cross_mark: Ich versuche Tags über die REST API zu setzen/entfernen. Die API-Calls scheinen erfolgreich zu sein (HTTP 200), aber die Tags erscheinen nicht in PlentyMarkets.

Verwendete API-Endpunkte

Tags setzen:

javascript

POST /rest/items/variations/variation_tags
{
  "variationId": 19913,
  "tagId": 111
}

Tags entfernen:

javascript

DELETE /rest/items/variations/variation_tags/{variationId}/{tagId}

Code-Beispiel (Node.js/Axios)

javascript

// Tag setzen
async function setItemTag(token, variationId, tagId) {
  try {
    const response = await axios.post(
      `${PLENTY_BASE_URL}items/variations/variation_tags`,
      {
        variationId: parseInt(variationId),
        tagId: tagId
      },
      { 
        headers: { 
          'Authorization': `Bearer ${token}`,
          'Content-Type': 'application/json'
        }
      }
    );
    
    console.log(`✅ Tag ${tagId} gesetzt für Variation ${variationId} (Status: ${response.status})`);
    return true;
    
  } catch (error) {
    console.error(`❌ Tag-Fehler:`, error.response?.data || error.message);
    return false;
  }
}

// Tag entfernen
async function removeItemTag(token, variationId, tagId) {
  try {
    const response = await axios.delete(
      `${PLENTY_BASE_URL}items/variations/variation_tags/${variationId}/${tagId}`,
      { 
        headers: { 
          'Authorization': `Bearer ${token}`
        }
      }
    );
    
    console.log(`✅ Tag ${tagId} entfernt von Variation ${variationId} (Status: ${response.status})`);
    return true;
    
  } catch (error) {
    console.error(`❌ Tag-Entfernung-Fehler:`, error.response?.data || error.message);
    return false;
  }
}

Hintergrund: Content-Updates funktionieren bereits

Basierend auf den Tipps aus diesem Forum (danke @sleunig und @Tim!) verwende ich erfolgreich:

Login (ohne Client-ID/Secret):

javascript

POST /rest/login
{
  "username": "MEIN_USER",
  "password": "MEIN_PASSWORD"
}

Content-Updates (funktioniert perfekt):

javascript

PUT /rest/items/{itemId}/variations/{variationId}/descriptions/de
{
  "itemId": 1147302325,
  "lang": "de",
  "name": "Neuer Produktname",
  "description": "Neue Beschreibung",
  "technicalData": "Neue technische Daten"
}

Das funktioniert alles einwandfrei! :white_check_mark:

Das Tag-Problem

Jetzt möchte ich zusätzlich Tags automatisch setzen/entfernen, um den Workflow zu steuern:

  • Tag 110: „AI Export“ → Artikel bereit für Optimierung
  • Tag 111: „AI Importiert“ → Artikel wurde optimiert
  • Tag 113: „AI Fehler“ → Bei Problemen

Was ich bereits versucht habe

Was ich bereits versucht habe

:white_check_mark: Funktionierende API-Calls (dank eurer Hilfe):

  • POST /rest/login → Token-Generierung (ohne Client-ID/Secret)
  • GET /rest/items/variations?with=tags → Tags werden korrekt angezeigt
  • PUT /rest/items/{itemId}/variations/{variationId}/descriptions/de → Content-Update funktioniert

:cross_mark: Nicht funktionierende API-Calls:

  • POST /rest/items/variations/variation_tags → HTTP 200, aber Tag nicht sichtbar
  • DELETE /rest/items/variations/variation_tags/{variationId}/{tagId} → HTTP 200, aber Tag nicht entfernt

Bereits geprüft:

  • :white_check_mark: Berechtigungen: REST API Vollzugriff aktiviert (Content-Updates funktionieren ja)
  • :white_check_mark: Token: Gleicher Token funktioniert für andere API-Calls
  • :white_check_mark: Tag-IDs: Tag 110, 111, 113 existieren im System (sehe sie beim GET)
  • :white_check_mark: Variation-IDs: Verwende korrekte variationId (gleiche wie beim Content-Update)
  • :white_check_mark: Content-Type: application/json gesetzt
  • :white_check_mark: Datentypen: variationId als Integer, tagId als Integer

Log-Ausgaben

🏷️ Setze Tag "AI Importiert" (ID: 111) für Variation 19913...
✅ Tag "AI Importiert" erfolgreich gesetzt für Variation 19913 (Status: 200)

🗑️ Entferne Tag "AI Export" (ID: 110) von Variation 19913...
✅ Tag "AI Export" erfolgreich entfernt von Variation 19913 (Status: 200)

Aber: In PlentyMarkets Backend sehe ich keine Änderungen an den Tags!

Fragen an die Community

Da ihr mir beim Content-Update so gut geholfen habt, hoffe ich auf weitere Unterstützung! :blush:

  1. Sind die Tag-API-Endpunkte korrekt? Nutzt ihr andere Routen für Variation-Tags?
  2. Workflow-Frage: Verwendet ihr Tags für automatische Workflows? Wenn ja, wie setzt/entfernt ihr sie?
  3. Alternative Ansätze: Gibt es andere Wege als REST API für Tag-Management?
  4. Cache-Problem: @sleunig @Tim - habt ihr ähnliche „HTTP 200 aber nichts passiert“ Probleme gehabt?
  5. PIM vs. Items: Sollte ich eventuell die PIM-Routen für Tags verwenden statt der items-Routen?

System-Info

  • PlentyMarkets: Version 7.x
  • API-Version: Latest REST API
  • Entwicklung: Node.js mit Axios
  • Authentifizierung: OAuth Token (funktioniert für andere APIs)

Erwartetes Verhalten

Nach erfolgreichem API-Call sollte der Tag in PlentyMarkets Backend sichtbar sein:

  • Artikel → Variation → Tab „Einstellungen“ → Bereich „Tags“

Tatsächliches Verhalten

  • API gibt HTTP 200 zurück
  • Keine Fehlermeldung
  • Aber Tag ist nicht sichtbar/gesetzt

Hat jemand von euch Tag-Management über die REST API erfolgreich implementiert?

Euer Input beim Content-Update war Gold wert - hoffe auf ähnlich gute Tipps für Tags! :folded_hands:

Update: Tests mit alternativen Routen

Inspiriert von @Tim’s PIM-Route Tipp habe ich auch versucht:

Variante 1: Item-basierte Route

javascript

POST /rest/items/{itemId}/variations/{variationId}/variation_tags
{
  "tagId": 111
}

Variante 2: Batch-Update

javascript

PUT /rest/items/variations/variation_tags
[
  {
    "variationId": 19913,
    "tagId": 111
  }
]

Alles mit gleichem Ergebnis: HTTP 200, aber keine sichtbaren Änderungen.

Gibt es einen „Tag-Cache“ der geleert werden muss? Oder verwende ich die falschen API-Endpunkte?

Die Api gibt leider gerne Code 200 zurück, obwohl gar nichts passiert ist.

Schau dir mal die /rest/v2/tags/relationships Routen an.

Vermutlich so in der Art zum Anlegen

POST /rest/v2/tags/relationships
{
  "tagId": 111,
  "type": "variation",
  "value": 19913
}

Über die neuen Pim Routen müsste es auch gehen: PUT /rest/pim/variations/tags, hab ich aber noch nie genutzt und die Doku fehlt. Müsste man rumraten.

Mit PUT /rest/items/variations sollte es auch gehen, über diese Route kann man eigentlich alles an einer Variante ändern. Würde bei einem neuem Projekt aber eher auf die PIM-Routen gehen, da es gut möglich ist, dass die alten Routen irgendwann eingestellt werden.

Setzen eines Tags an einer Variante

POST rest/tags/relationships

Und diesen Body

{
  "tagId": 22,
  "tagType": "variation",
  "relationshipValue": 1000
}

relationshipValue = ID der Variante

Das ist der 200er Response:

{
    "tagId": 22,
    "tagType": "variation",
    "relationshipValue": 1000,
    "updatedAt": "2025-07-17T11:26:07+02:00",
    "createdAt": "2025-07-17T11:26:07+02:00"
}

Löschen eines Tags an einer Variante

DELETE rest/tags/relationships

Und diesen Body

{
  "tagId": 22,
  "tagType": "variation",
  "relationshipValue": 1000
}

Response: 200 ohne Body