Files
google-service/documentation/google-api-communication.md
T
JiriUhlir 8f7f8404c3 upt
2026-06-15 16:00:12 +02:00

272 lines
9.9 KiB
Markdown

# Google API communication
Sluzba poskytuje obecnou komunikacni vrstvu pro Google API. Neobsahuje secrets ve zdrojovem kodu a pro verejne routovani pouziva `ROOT_PATH`, aby Swagger/OpenAPI fungoval za AppFactory prefixem `/apps/<app-id>`.
## Discovery
- `GET /google/discovery/apis` vraci seznam Google API dostupnych pres Google Discovery service.
- `GET /google/discovery/apis/{api}/{version}/rest` vraci REST discovery dokument konkretniho API, napr. `drive/v3`.
Discovery endpointy slouzi k dohledani dostupnych resource, metod, schema a OAuth scope pro konkretni Google API.
## OAuth
- `POST /google/oauth/token` podporuje `authorization_code` a `refresh_token` grant.
- `GET /google/oauth/scopes` vraci doporucene scopes pro podporovane sluzby.
- `GET /google/oauth/authorize-url` vygeneruje Google consent URL.
- `POST /google/oauth/service-account-token` podporuje service account JWT bearer flow.
- `POST /google/oauth/revoke` revokuje token.
- `GET /google/oauth/tokeninfo` vraci informace o access tokenu nebo ID tokenu.
OAuth client a service account hodnoty je vhodne predavat pres environment variables:
- `GOOGLE_CLIENT_ID`
- `GOOGLE_CLIENT_SECRET`
- `GOOGLE_SERVICE_ACCOUNT_EMAIL`
- `GOOGLE_PRIVATE_KEY`
- `GOOGLE_SCOPES`
### Env promenne a request alternativy
Swagger obsahuje `GET /google/configuration`, ktery vypise podporovane env promenne, jejich pouziti a alternativy v requestu. Endpoint nevraci hodnoty secrets.
- `GOOGLE_CLIENT_ID`: `clientId`, `X-Google-Client-Id`
- `GOOGLE_CLIENT_SECRET`: `clientSecret`, `X-Google-Client-Secret`
- `GOOGLE_REDIRECT_URI`: `redirectUri`, `X-Google-Redirect-Uri`
- `GOOGLE_SERVICE_ACCOUNT_EMAIL`: `serviceAccountEmail`, `X-Google-Service-Account-Email`
- `GOOGLE_PRIVATE_KEY`: `privateKey`, `X-Google-Private-Key`
- `GOOGLE_SCOPES`: `scope`, `scopes`, `X-Google-Scopes`
- `GOOGLE_SERVICE_ACCOUNT_JSON`: `serviceAccountJson`, `serviceAccountJsonEnv`, `X-Google-Service-Account-Json`, `X-Google-Service-Account-Json-Env`
- `GOOGLE_ACCESS_TOKEN`: `Authorization: Bearer <token>`, `accessToken`, `accessTokenEnv`, `X-Google-Access-Token`, `X-Google-Access-Token-Env`
- `GOOGLE_API_KEY`: `apiKey`, `apiKeyEnv`, `X-Google-Api-Key`, `X-Google-Api-Key-Env`
### Service account JSON
Google service account JSON neobsahuje `access_token`. Obsahuje hlavne `client_email`, `private_key` a `token_uri`. Sluzba z techto poli sama vytvori JWT assertion, zavola Google OAuth token endpoint a ziska docasny `access_token`.
Produktove endpointy proto lze volat primo s:
- `serviceAccountJson` v body
- `X-Google-Service-Account-Json` header
- `serviceAccountJsonEnv` nebo `X-Google-Service-Account-Json-Env`, napr. `GOOGLE_SERVICE_ACCOUNT_JSON`
Je nutne dodat scopes:
- `serviceAccountScopes` v body
- `X-Google-Service-Account-Scopes` header
- nebo `GOOGLE_SCOPES`
Priklad pro zapis do Sheets:
```json
{
"spreadsheetUrl": "https://docs.google.com/spreadsheets/d/1abcDEFghiJKLmnopQRstuVWXyz/edit#gid=0",
"sheetName": "Objednavky",
"mode": "append",
"values": [
["2026-06-15", "ACME", 1234]
],
"serviceAccountScopes": [
"https://www.googleapis.com/auth/spreadsheets"
],
"serviceAccountJson": {
"type": "service_account",
"project_id": "project-id",
"private_key_id": "key-id",
"private_key": "-----BEGIN PRIVATE KEY-----\n...\n-----END PRIVATE KEY-----\n",
"client_email": "service-account@project-id.iam.gserviceaccount.com",
"client_id": "123456789",
"token_uri": "https://oauth2.googleapis.com/token"
}
}
```
### OAuth krok za krokem
1. Zavolej `GET /google/oauth/scopes`.
2. Vyber scopes, napr. Sheets + Drive metadata:
```text
https://www.googleapis.com/auth/spreadsheets https://www.googleapis.com/auth/drive.metadata.readonly
```
3. Zavolej:
```text
GET /google/oauth/authorize-url?redirectUri=https://example.test/oauth/callback&scopes=https://www.googleapis.com/auth/spreadsheets https://www.googleapis.com/auth/drive.metadata.readonly
```
4. Otevri `authorizationUrl` z odpovedi.
5. Po souhlasu Google presmeruje na `redirectUri` s query parametrem `code`.
6. Code vymen:
```json
{
"grantType": "authorization_code",
"code": "code-from-google-redirect",
"redirectUri": "https://example.test/oauth/callback"
}
```
7. `access_token` posilej do produktovych endpointu jako:
```text
Authorization: Bearer <access_token>
```
Pro dlouhodobe pouziti si uloz `refresh_token` mimo zdrojovy kod a obnovuj token pres:
```json
{
"grantType": "refresh_token",
"refreshToken": "stored-refresh-token"
}
```
## Obecne REST volani
`POST /google/request` je genericka proxy pro Google REST API. Request obsahuje HTTP metodu, cilovou Google URL nebo kombinaci `baseUrl` a `path`, volitelne query parametry, body a autorizaci.
Priklad volani Google Drive:
```json
{
"method": "GET",
"baseUrl": "https://www.googleapis.com",
"path": "/drive/v3/files",
"query": {
"pageSize": 10
},
"accessTokenEnv": "GOOGLE_ACCESS_TOKEN"
}
```
Z bezpecnostnich duvodu jsou povolene jen HTTPS URL na Google domenach. Requesty na jine hosty sluzba odmita.
## Konkretni produktove endpointy
Krome obecne proxy jsou dostupne konkretni wrappery nad nejbeznejsimi Google API:
### Calendar
- `GET /google/calendar/calendars`
- `POST /google/calendar/calendars`
- `GET /google/calendar/calendars/{calendarId}`
- `PATCH /google/calendar/calendars/{calendarId}`
- `DELETE /google/calendar/calendars/{calendarId}`
- `GET /google/calendar/calendars/{calendarId}/events`
- `POST /google/calendar/calendars/{calendarId}/events`
- `GET /google/calendar/calendars/{calendarId}/events/{eventId}`
- `PATCH /google/calendar/calendars/{calendarId}/events/{eventId}`
- `DELETE /google/calendar/calendars/{calendarId}/events/{eventId}`
- `POST /google/calendar/calendars/{calendarId}/events/{eventId}/move`
### Sheets
- `GET /google/sheets/spreadsheets` - seznam Google Sheets souboru; `spreadsheetId` je `files[].id`
- `POST /google/sheets/spreadsheets`
- `GET /google/sheets/spreadsheets/{spreadsheetId}`
- `GET /google/sheets/spreadsheets/{spreadsheetId}/sheets` - seznam tabu/listu; numericke `sheetId` je `sheets[].properties.sheetId`, A1 range pouziva `sheets[].properties.title`
- `POST /google/sheets/write-by-url` - zapis hodnot podle plne URL spreadsheetu a nazvu listu
- `POST /google/sheets/spreadsheets/{spreadsheetId}/batch-update`
- `GET /google/sheets/spreadsheets/{spreadsheetId}/values?range=Sheet1!A1:B10`
- `PUT /google/sheets/spreadsheets/{spreadsheetId}/values?range=Sheet1!A1`
- `POST /google/sheets/spreadsheets/{spreadsheetId}/values/append?range=Sheet1!A1`
- `POST /google/sheets/spreadsheets/{spreadsheetId}/values/batch-update`
- `POST /google/sheets/spreadsheets/{spreadsheetId}/values/batch-clear`
#### Zapis podle URL a nazvu listu
Endpoint `POST /google/sheets/write-by-url` je urceny pro bezny zapis bez rucni prace se `spreadsheetId` a A1 range.
```json
{
"spreadsheetUrl": "https://docs.google.com/spreadsheets/d/1abcDEFghiJKLmnopQRstuVWXyz/edit#gid=0",
"sheetName": "Objednavky",
"startCell": "A1",
"mode": "append",
"valueInputOption": "USER_ENTERED",
"values": [
["Datum", "Zakaznik", "Castka"],
["2026-06-15", "ACME", 1234]
]
}
```
Chovani:
- `mode=append` vola Google Sheets append a prida radky pod existujici tabulku.
- `mode=update` vola Google Sheets update a prepise bunky od `startCell`.
- `sheetName` muze obsahovat mezery i apostrofy; sluzba ho sama escapuje do A1 range.
- `spreadsheetUrl` muze byt bezna URL ve tvaru `https://docs.google.com/spreadsheets/d/{spreadsheetId}/edit#gid=0`.
### Drive
- `GET /google/drive/files`
- `POST /google/drive/files`
- `GET /google/drive/files/{fileId}`
- `PATCH /google/drive/files/{fileId}`
- `DELETE /google/drive/files/{fileId}`
- `GET /google/drive/files/{fileId}/export?mimeType=application/pdf`
- `GET /google/drive/files/{fileId}/permissions`
- `POST /google/drive/files/{fileId}/permissions`
- `DELETE /google/drive/files/{fileId}/permissions/{permissionId}`
### Gmail
- `GET /google/gmail/profile`
- `GET /google/gmail/messages`
- `GET /google/gmail/messages/{messageId}`
- `POST /google/gmail/messages/send`
- `GET /google/gmail/labels`
- `POST /google/gmail/labels`
### Docs, Slides a Forms
- `POST /google/docs/documents`
- `GET /google/docs/documents/{documentId}`
- `POST /google/docs/documents/{documentId}/batch-update`
- `POST /google/slides/presentations`
- `GET /google/slides/presentations/{presentationId}`
- `POST /google/slides/presentations/{presentationId}/batch-update`
- `POST /google/forms/forms`
- `GET /google/forms/forms/{formId}`
- `POST /google/forms/forms/{formId}/batch-update`
- `GET /google/forms/forms/{formId}/responses`
### People a Tasks
- `GET /google/people/connections`
- `GET /google/people/{resourceName}`
- `POST /google/people/contacts`
- `PATCH /google/people/{resourceName}`
- `DELETE /google/people/{resourceName}`
- `GET /google/tasks/lists`
- `POST /google/tasks/lists`
- `GET /google/tasks/lists/{tasklistId}/tasks`
- `POST /google/tasks/lists/{tasklistId}/tasks`
- `PATCH /google/tasks/lists/{tasklistId}/tasks/{taskId}`
- `DELETE /google/tasks/lists/{tasklistId}/tasks/{taskId}`
## Kde vzit ID
- `calendarId`: `GET /google/calendar/calendars`, hlavni kalendar lze typicky volat jako `primary`.
- `eventId`: `GET /google/calendar/calendars/{calendarId}/events`.
- `spreadsheetId`: `GET /google/sheets/spreadsheets`, pole `files[].id`.
- `sheetId`: `GET /google/sheets/spreadsheets/{spreadsheetId}/sheets`, pole `sheets[].properties.sheetId`.
- `fileId`: `GET /google/drive/files`, pole `files[].id`.
- `messageId`: `GET /google/gmail/messages`, pole `messages[].id`.
- `documentId`: ID Google Docs souboru z Drive.
- `presentationId`: ID Google Slides souboru z Drive.
- `formId`: ID Google Forms souboru z Drive nebo odpoved z `POST /google/forms/forms`.
## AppFactory overeni
Po deploy over:
- `GET /apps/google-service/health`
- `GET /apps/google-service/docs`
- `GET /apps/google-service/openapi.json`
OpenAPI dokument musi obsahovat `servers[0].url` s hodnotou `ROOT_PATH`, napr. `/apps/google-service`, aby Swagger UI volalo endpointy pres verejnou proxy cestu.