FORMAT: 1A HOST: http://pos.prelive.qnips.com/api/pos/v3 # Qnips Web API v3 Addendum Dieses Dokument dient als Diskussionsgrundlage für eine Erweiterung der [Qnips Web API v3](http://docs.qnipsapi1draft.apiary.io/). Die hier beschriebenen Erweiterungen (wie neue Resourcen, Properties, usw.) müssen noch nicht implementiert worden sein, weswegen Requests gegen unsere API fehlschlagen oder eine unerwartete Response ausliefern können. # Warenkorb-Handling ## Positionen vom Warenkorb Den Positionen vom Warenkorb wurden zwei neue Properties hinzugefügt. ### Mengen und Einheiten Mit der **Unit** Property kann die Einheit definiert werden, die via *Amount* referenziert wird. Aktuell unterstützen wir die folgenden Einheiten. | Wert | Einheit | | --- | --- | | 0 | Stückzahl | | 1 | Kilogramm | Im gleichen Schritt unterstützt **Amount** nun Fließkommazahlen, sodass z.B. eine Gramm-genaue Eingabe erfolgen kann. ### Positionsgenaue IDs Jeder Position kann mittels **PositionId** eine (möglichst eindeutige) ID zugeordnet werden. Sollte der Warenkorb im Folgenden einen Coupon auslösen, wird die auslösende Position in der Response über die *RewardTriggeringPositionId* notiert werden. ## Setzen/Ändern von Warenkorb-Information beim Grant In dem Body des **POST basket-grant** requests können nun bestimmte Informationen vom Warenkorb erneut übergeben werden. Im genauen sind das **BillNumber** und **Timestamp**. ## Zahlungsarten für digitalen Bon In der **POST basket** sowie der **POST basket-grant** Resource besteht zukünftig die Möglichkeit, die für diese Transaktion genutzten Zahlungsarten an Qnips zu übermittelt, damit der Nutzer diese in seinem digitalen Kassenbon in der App einsehen kann. Der Body des jeweiligen Requests wird dafür um ein neues Feld `PaymentMethods` erweitert: { … "PaymentMethods": [ { "Name": "Bar", "Amount": 13.64 } ] … } Sollte dieses Feld gesetzt und der digitale Bon in der App aktiviert sein, werden diese Informationen dem Nutzer der App angezeigt. ## Freitext und QR-Code für Kassenbon Der Response der **POST basket-grant** Resource werden zwei neue Felder `ReceiptText` (**string, optional**) sowie `QrCodeContent` (**string, optional**) hinzugefügt. ### ReceiptText Sollte dieses Feld gesetzt und nicht leer sein, enthält es einen Backend-generierten Freitext der beim Druck des Kassenbons respektiert werden soll. Steuerzeichen für NewLine und bold? ### QrCodeContent Sollte dieses Feld gesetzt und nicht leer sein, enthält es eine URL die als QR-Code auf dem Kassenbon gedruckt werden soll. In der aktuellen Version wird dieses Feld dann gesetzt sein, wenn bei dem Grant des Baskets kein `ConsumerIdentToken` mit diesem Basket verknüpft ist. Da die QR-Codes auf den Kassenbons für die Nutzer gedacht sind, die nicht direkt an der Kasse mit einer Karte oder Smartphone ihren Token übermittelt haben, brauchen wir eine Möglichkeit auch Warenkörbe ohne Token an das Qnips Backend übermittelt zu bekommen. Hierfür könnte man eine Konfigurationseinstellung vorsehen, die – sofern gesetzt – bei Abschluss einer Transaktion ohne Qnips-Token an der Kasse einen **POST basket** mit dem aktuellen Warenkorb und direkt folgend einen **POST basket-grant** aufruft. Dadurch wird das neue Feld `QrCodeContent` im Response gesetzt sein, wodurch der QR-Code auf den Kassenbon gedruckt werden kann. # Infos zu Tokens abrufen Es wird eine neue Methode [GET tokens/info/{tokenId}](#reference/tokens/token-identifizieren) angelegt, die verschiedene Informationen zu dem angefragten Token zurück gibt. ## Guthabenverwendung Dem Nutzer einer Guthabenkarte soll eine Möglichkeit geboten werden, mit der er die Verwendung des Guthabens einstellen kann. Wenn er z.B. seine Guthabenkarte lediglich für das Sammeln von Treuepunkten verwenden will, soll er nicht immer wieder mit der Guthabenfunktion angesprochen werden. Hierfür haben wir ein neues Feld `BalanceType` definiert, das genau diese Informationen tragen kann. Die Kasse soll dieses Feld bei der Abrechnung eines Warenkorbes respektieren. ## PIN-Erfassung Es wird eine Möglichkeit geschaffen, mit der definiert werden kann, ob aus Sicherheitsgründen eine PIN-Eingabe durch den Nutzer bei der nächsten Zahlung mit der Guthabenkarte (BalanceWithdraw) notwendig ist. Je nach Wunsch des Kunden kann dies z.B. bei der erstmaligen Nutzung der Guthabenkarte oder bei jeder Nutzung geschehen. ## Info-URL Die neue Property `InfoUrl` kann eine (optionale) URL enthalten, die von der Kasse aufgerufen werden soll. Hinter dieser URL können weitere Informationen liegen, die auf dem Kassendisplay angezeigt werden sollen. **Zur Diskussion:** Größe der Embedded Webview? ## Tag-System auf Tokens Jeder Token kann mit beliebig vielen Tags markiert werden. Über diese Tags kann z.B. eine bestimmte Preisebene ausgewählt werden. ### Beispiel { "Name": "Mitarbeiter", "Groups": [ "priceLevel" ] } Sollte dieser Tag in der Response enthalten sein, wurde diesem Token ein Tag mit dem Namen `Mitarbeiter` zugewiesen. Da dieser Tag selbst der Gruppe `priceLevel` angehört, definiert dieser Tag, dass ab jetzt – wenn möglich – die Preisebene mit dem Namen **Mitarbeiter** verwendet werden soll. # Zahlungsvorgänge mit Guthaben Die bestehenden Resourcen zum Aufladen (`addBalance`) und Abheben (`withdrawBalance`) von Guthaben werden um weitere, optionale Query-Parameter erweitert um eine nachträgliche Zuordnung der Zahlungsvorgänge und Warenkörbe zu erleichtern. **Noch offen:** Stornos, Refund, Entladen einer Karte ## Aufladen von Guthaben | Query | Beschreibung | | --- | --- | | `merchantReference` | Interne Referenz/Vorgangsnummer in der Kasse | | `type` | Entweder **payin** oder **refund** | | `payinType` | Bei *type = payin* kann hier die Zahlungsart definiert werden | | `referenceBasketId` | Wenn die Aufladung während eines Einkaufs erfolgt kann hier die zugehörige BasketId übermittelt werden | | `description` | Feld für weitere Freitext-Ergänzungen zur Protokollierung | ### Verfügbare Zahlungsarten | Wert | Zahlungsart | | --- | --- | | 0 | nicht erfasst | | 1 | Bar | | 2 | ec-Karte / Girocard | | 3 | Mastercard | | 4 | Visa Card | | 5 | American Express | | 6 | andere Kreditkarte | | 7 | Rechnung | | 8 | Bankeinzug | | 9 | Geldkarte | | 10 | Girogo | | 11 | Paypass MasterCard | | 12 | Vpass Visa | **Hinweis:** Diese Liste von Zahlungsarten ist nicht final und kann bei Bedarf erweitert werden. ## Abheben von Guthaben | Query | Beschreibung | | --- | --- | | `merchantReference` | Interne Referenz/Vorgangsnummer in der Kasse | | `type` | Entweder **basket** oder **payout** (reserved) | | `referenceBasketId` | Wenn das Abheben während eines Einkaufs erfolgt kann hier die zugehörige BasketId übermittelt werden | | `description` | Feld für weitere Freitext-Ergänzungen zur Protokollierung | | `pin` | PIN der Karte, falls für das Abheben eine PIN-Eingabe notwendig ist (vgl. **RequiresPin**) | # Group tokens ## Token identifizieren [/tokens/info/{tokenId}] ### GET tokens/info/{tokenId} [GET] Hiermit können verschiedene Informationen zu einem Token abgefragt werden. *Bitte bilden Sie zur* **{tokenId}** *eine Checksumme (siehe Security-Token aus dem Original Dokument) und geben Sie diese im `SecurityToken`-Header an.* | Feld | Beschreibung | | --- | --- | | `IdentString` | **string** - Dieser String enthält einen eindeutigen Bezeichner für den Token und kann in einer verkürzten Form auf der Kasse angezeigt werden. (Verkürzt bedeutet hier, dass nur die letzten 3 oder 4 Zeichen erkennbar sind: `1234567890` wird zu `******7890`) | `TokenType` | **string** - Entweder **consumerIdentifier** oder **giftCard** Zu einem basket kann nur einziger consumerIdentifier eingereicht werden. Der Parameter giftCard entfällt. Zusätzliche GiftCards des Kunden können über balanceWithdraw als Zahlungsmittel genutzt werden.| | `Balance` | **decimal** - Das momentan auf diesem Token hinterlegte Guthaben | | `MaxBalance` | **decimal** - Der Maximalbetrag an Guthaben, den dieser Token tragen darf | | `RemainingBalanceToAdd` | **decimal** - Der Maximalbetrag an Guthaben, der im aktuellen Kalendermonat noch auf diesem Token hinterlegt werden kann. | | `IsWithdrawBalanceAllowed` | **boolean** - Gibt an, ob Bezahlungen aus dem Guthaben heraus für diesen Token erlaubt ist | | `IsAddBalanceAllowed` | **boolean** - Gibt an, ob Guthaben-Aufladungen für diesen Token erlaubt ist | | `RelatedGiftCards` | **Array von verknüpften Geschenkkarten** - Nur bei **consumerIdentifier** möglich. Jedes Element aus dem Array enthält eine **GiftCardId** und die aktuelle **Balance** | | `RequiresPin` | **boolean** - Für die nächste Nutzung der Guthabenkarte ist eine PIN-Erfassung erforderlich. Dieser Wert kann sich nach jeder Nutzung abändern, weswegen dieser Wert nicht gecached werden sollte. | | `InfoUrl` | **string, optional** - Eine URL, die die Kasse aufruft, um auf dem Kassendisplay weitere Infos anzuzeigen | | `ConsumerIdentityInfo` | **Objekt wie weiter unten spezifiziert** - Handelt es sich bei dem Token um einen Token mit `TokenType` = **consumerIdentifier**, so wird hier ein Objekt mit weiteren Informationen, wie Tags oder Infos zu seinen Treuepunkteständen ausgegeben. | ### ConsumerIdentityInfo-Objekt | Feld | Beschreibung | | --- | --- | | `Tags` | **Array von zuordneten Tags** - Dieses System kann zum Beispiel für Preisebenen, Status, etc. verwendet werden. Jedes Element aus dem Array enthält **Name** und eine Liste von **Groups**, in denen der jeweilige Tag enthalten ist. | | `LoyaltySchemeProgressInfos` | **Array von LoyaltySchemeProgressInfo-Objekten** - Info über eventuell berets gesammelte Treuepunkte des Konsumenten. | ### LoyaltySchemeProgressInfo-Objekt | Feld | Beschreibung | | --- | --- | | `LoyaltySchemeId` | **integer** - Dies ist die Qnips-interne ID des Treuepunte-Programms. | | `LoyaltySchemeName` | **string** - Dies ist der Name des Treuepunte-Programms, wie er auch in den Apps gezeigt wird. | | `MaxPoints` | **integer** - Gibt an, wieviele Punkte in diesem Programm gesammelt werden müssen, damit ein Rabatt ausgegeben wird. | | `CurrentPoints` | **integer** - Gibt an, wieviele Punkte der Konsument in diesem Treuepunkte-Programm bereits gesammelt hat. | + Parameters + tokenId (string, `cardId123`) ... Geben Sie hier den von einem Trägermedium ausgelesenen Token an. Als Alternative kann der ausgelesene Token als HTTP Header *Token* übertragen werden. + Request + Header DevKey: {Ihr Key} TrackingUnitId: {trackingUnitId} Token: {tokenId} SecurityToken: {Checksumme über {tokenId}} + Response 200 (application/json) + Body { "IdentString": "1234567890", "TokenType": "consumerIdentifier", // oder "giftCard" "Balance": 10.58, "MaxBalance": 100.00, "RemainingBalanceToAdd": 5.08, "IsWithdrawBalanceAllowed": true, "IsAddBalanceAllowed":true, "RelatedGiftCards": [ { "GiftCardId": "giftCard123", "Balance": 20.04 } ], "RequiresPin": true, "InfoUrl": "http://...", "ConsumerIdentityInfo":{ "Tags": [ { "Name": "Mitarbeiter", "Groups": [ "priceLevel" ] } ], "LoyaltySchemeProgressInfos": [ { "LoyaltySchemeId": 123, "LoyaltySchemeName": "Jedes 10. Heißgetränk umsonst", "MaxPoints": 10, "CurrentPoints": 3 } ] } } + Response 500 // HTTP-InternalServerError: Ein unbekannten Problem bei der Verarbeitung aufgetreten { "ErrorMessage": "some explanation" "StackTrace": "text" } + Response 403 // HTTP-Forbidden: trackingUnitId ist noch nicht vom Merchant aktiviert + Response 401 // HTTP-Unauthorized: DevKey, trackingUnitId oder SecurityToken nicht angegeben/falsch + Response 400 { "ErrorId": 123, "ErrorText": "Details zum Fehler" }