Files
polstrin-sap/documentation/sap-business-one-service-layer.md
JiriUhlir fea25d7429 first
2026-07-15 09:03:28 +02:00

71 lines
4.1 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# SAP Business One Service Layer Connector (POLSTRIN)
Connector komunikuje výhradně přes SAP Business One Service Layer `/b1s/v1` instalace POLSTRIN
(`https://ws.polstrin.cz:50000`). Specifika instalace jsou v [polstrin-specifika.md](polstrin-specifika.md).
Hlavní vlastnosti:
- login/logout přes Service Layer
- správa `B1SESSION` a `ROUTEID`, jedna sdílená session mezi requesty
- automatický re-login po expiraci session
- SAP credentials výhradně z environment variables (AppFactory secrets), ne z requestů
- volitelná ochrana `/api` rout hlavičkou `X-Api-Key` (secret `API_KEY`)
- OData parametry `$select`, `$filter`, `$top`, `$skip`, `$orderby`
- stránkování přes `odata.nextLink` a `@odata.nextLink`
- generický přístup k libovolnému entity setu přes `/api/entities/...` (POLSTRIN UDO tabulky `U_*`)
- retry pro dočasné chyby
- zod validace konfigurace a hlavních response tvarů
Bezpečnostní pravidla:
- konfigurace se čte výhradně z environment variables (`SAP_B1_*`, `API_KEY`)
- SAP credentials se nikdy nepřijímají v requestech, nelogují a nevrací v response
- hesla, cookies a session tokeny se nelogují
- testy nepoužívají reálný SAP přístup
- pro self-signed certifikáty je dostupné `rejectUnauthorized`, ale produkčně se doporučuje důvěryhodný certifikát
## Detaily komunikace se Service Layer
- **Login** `POST /b1s/v1/Login` s `{ CompanyDB, UserName, Password, Language? }`.
`Language` se posílá jako celé číslo (Service Layer očekává `Edm.Int32`); nenumerická
hodnota se vynechá. Z odpovědi se čtou cookies `B1SESSION` a `ROUTEID` (s fallbackem na
`SessionId` v body) a `SessionTimeout` (minuty) pro výpočet expirace.
- **Autentizované requesty** posílají `Cookie: B1SESSION=…; ROUTEID=…`. Při `401`
connector jednou provede re-login a request zopakuje; re-login nesnižuje retry budget,
takže funguje i při `SAP_B1_RETRY_COUNT=0`.
- **Logout** `POST /b1s/v1/Logout` se posílá **s aktivní session cookie**, jinak by
Service Layer nevěděl, kterou session ukončit, a nechal by ji běžet až do timeoutu.
- **Verze a system info** login response obsahuje `Version` (např. `1000230` = SAP B1
10.0 PL 23) a `SessionTimeout`; connector si je ukládá (`client.loginInfo`, přežije
logout) a HTTP endpoint `POST /api/session/login` je vrací v odpovědi.
`GET /api/system/info` navíc vrátí přehled instalace: service document (`GET /b1s/v1/`
→ dostupné entity sety), `UserFieldsMD` (UDF), `UserTablesMD` (UDT), `UserObjectsMD`
(UDO) a `CompanyService_GetAdminInfo`. Sekce, na kterou SAP uživatel nemá práva, se
vrátí jako `{ "error": "…" }`, aby jedno chybějící oprávnění neshodilo celý přehled
(chyba je v odpovědi vidět, nejde o tiché selhání).
- **Stránkování** následuje `odata.nextLink` i `@odata.nextLink`. U absolutních
nextLinků se zachová i query string (`$skip` apod.), takže `listAll` nezacyklí.
## Reverse proxy a Swagger
Aplikace běží za AppFactory proxy na `/apps/<app-id>` (Caddy `handle_path` prefix před
předáním do containeru odstraní, takže container vidí routy bez prefixu a z requestu
veřejnou cestu nelze odvodit). Stejný přístup jako sousední služba `google-service`:
- `/docs` se servíruje **přímo jako HTML** (`GET /docs`), bez `swagger-ui-express` a bez
statického middleware proto **nevzniká žádný redirect `/docs` → `/docs/`**, který by za
proxy zahodil prefix `/apps/<app-id>` (to byla příčina bílé stránky).
- Swagger UI assety se načítají z CDN (`unpkg.com/swagger-ui-dist@5`).
- Spec URL je `ROOT_PATH + /openapi.json`, takže odkazuje na veřejné
`/apps/<app-id>/openapi.json`.
- `servers[0].url` se nastaví z `ROOT_PATH` (jinak `/`), takže Swagger `Try it out` volá
`…/apps/<app-id>/api/<resource>`.
| Kontrola | Lokálně (bez ROOT_PATH) | S `ROOT_PATH=/apps/sap-bo` |
|---|---|---|
| `GET /health` | 200 | 200 |
| `GET /docs` (Swagger UI) | 200, žádný redirect | 200, žádný redirect |
| `GET /openapi.json` | 200 | 200 |
| spec URL v `/docs` | `/openapi.json` | `/apps/sap-bo/openapi.json` |
| `servers[0].url` v OpenAPI | `/` | `/apps/sap-bo` |