Repository navigation
release: v1.40.2 (DEV→main promotion) - #2853
Merged
Merged
Conversation
The #2552 global identity-pin `before('*')` hook (srv/server.js) was registered on EVERY ApplicationService, including the internal CronService. On a scheduled tick the hook calls `pinResolvedUser(req.user, cds.tx(req))`, and `cds.tx(req)` dereferences `ctx.context._set` on the cron event's context — which is not a real EventContext — throwing `ctx.context._set is not a function` on EVERY tick. The throw is caught fail-open (WARN), so jobs still run, but: - it spams the PROD log on every scheduled tick, and - after an instance restart (e.g. a blue-green swap) resets the canary clocks, the noise coincides with the scheduler-stall canary (#2782) firing a false ALERT. The pin is a pure no-op on a cron tick anyway — a scheduled tick's user is always system/anonymous. Skip CronService by its fully-qualified name (com.sap.developers.ims.CronService) in the hook-registration loop. Regression first observed on PROD after the 1.40.1 blue-green swap; the hook + the throwing `cds.tx(req)` form both shipped in 1.40.0 (a3412e0 / 60c6a5b). Test: extend test/hybrid/cron-service-schedule.test.js to assert the identity-pin before(*) handler is NOT registered on CronService. Runs in the post-deploy hybrid CI job (needs a HANA bind profile; not runnable in a fresh worktree without `npm run bind:setup`). Follow-up (separate issue): the same #2552 hook also throws `Cannot set property userId of #<XsuaaToken> which has only a getter` on every authenticated request in PROD — a distinct bug in pinResolvedUser's write to the read-only XsuaaToken getter, not addressed here. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
…ser (#2552) Second #2552 regression, surfaced in PROD logs during the 1.40.1 scheduler diagnosis: on EVERY authenticated request, the identity-pin hook threw `Cannot set property userId of #<XsuaaToken> which has only a getter`. Root cause: pinResolvedUser pinned the resolved sapId by assigning `user.authInfo.token.userId = row.sapId`. In PROD the real @sap/xssec XsuaaToken exposes `userId` as a GETTER-ONLY property, so the bare assignment throws. Caught fail-open (WARN), but it fired on every authed request and the pin silently never cached anything on the XSUAA path. Fix: cache the resolved sapId on `user.attr.sapId` (always a plain writable object) as the source of truth, and only mirror onto `authInfo.token.userId` when that slot is actually writable (checked via getOwnPropertyDescriptor, wrapped defensively). The idempotency short-circuit now reads `user.attr.sapId` first, falling back to the token for older pins. The dev/basic-auth path (writable token) still mirrors userId as before. Test: 4 new cases in test/unit/resolve-db-user-resolve.test.js exercising a getter-only token (reproducing the XsuaaToken), asserting no throw, sapId cached on attr, idempotent re-call, and the writable-token mirror path. All 34 tests in the file pass (`vitest run`). Paired with the CronService guard in this PR — both are #2552 before('*') identity-pin regressions from 1.40.0. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
…tity-pin fix(identity): two #2552 before(*) pin regressions — CronService stall + XsuaaToken getter
The Joule/Sapphire App Space hero gradients are dark in both light and dark mode, but the base .hero only inherited --sapShell_TextColor, which resolves to a dark value under the Horizon light theme. That left the banner text near-illegible on the purple gradient (/app-space/?theme=joule in light mode, reported by DJ Adams). Pin the themed hero (and its loading skeleton) to white regardless of the active Horizon palette. Verified via vite dev harness: hero text is rgb(255,255,255) with the fix and rgb(34,53,72) without, in light+joule; dark mode unchanged.
…ero-contrast fix(#2839): white hero text for themed App Space banners
convertOptionBlocks spliced OPTION shortcodes flush-left, which closed the surrounding numbered list. Figures inside an os-panel — or trailing an OPTION group in the same substep — then rendered as a top-level <figure> sibling of the list, losing their indentation under the substep (the 'centered vs left-aligned image' QA report). PR #2822 only adjusted figure text-align (CSS), which cannot re-nest a DOM sibling, so the figures stayed un-indented. Approach A: indent the shortcode WRAPPER lines to the substep so the block stays inside the <li> (list never closes), while the panel BODY stays at column 0 so os-panel.html's markdownify pass parses code fences/images as markdown (preserves the #2703 behaviour). The old flush-left tail-dedent is removed — with the list open, trailing content keeps its substep indent. Verified through real Hugo renders (incl. the live Tutorials-Contribution hana-clients-install source): figures nest as li > ol > figure; #2703 code fences unaffected. New render-level regression test added.
Disable the three hidden scavenger-hunt clues (homepage, /ai/, /api-docs/) by commenting out their render entry points in baseof.html and the api-docs shortcode call. The feature's data/layouts/CSS are kept dormant so it can be re-enabled next Devtoberfest by uncommenting. No backend/CDS/seed changes; pure Hugo frontend.
…-clues fix(#2841): remove the 3 hidden Devtoberfest scavenger hunt clues
…escape-2820 fix(options): keep OPTION-block figures nested in the list item (#2820)
Basic setup to connect the existing tutorials-aicore instance to the tutorials-hana container for DB-native VECTOR_EMBEDDING (issue #2810), ahead of any rewrite. - db/src/_grants.hdbgrants: grant CREATE PSE to the container user via the existing tutorials-kg-grantor UPS. Capability probe confirmed the _RT user already holds CREATE REMOTE SOURCE; CREATE PSE was the only missing privilege for the sapgenaihub remote source. - docs/developers/operations/hana-aicore-embeddings.md: setup runbook (built-in NLP tier A, AI Core remote-source tier B, PSE+remote source SQL with DEV worked values, PROD checklist, auto-embedding appendix). PSE paste step described in prose (no literal PEM markers) to avoid a gitleaks private-key false positive. - docs/superpowers/specs: design doc with verified DEV facts. - CLAUDE.md: link the runbook in the deep-dive list. Tier A (built-in SAP_GXY.20250407) verified on DEV: 768-dim vector. Tier B deploy-gated on the CREATE PSE grant landing via db-deployer.
…edding-setup docs(#2810): HANA-native AI Core embedding setup + grant CREATE PSE
…grants The first attempt added CREATE PSE to _grants.hdbgrants under the tutorials-kg-grantor SQL grantor. That failed on DEV deploy (20261019-105602): the deployer emitted GRANT "CREATE PSE" TO ...#OO, which HANA rejects as 'invalid role name' — a system privilege cannot be granted that way, and the grantor lacks CREATE PSE WITH ADMIN OPTION. Correct HDI-native mechanism (per the @sap/hdi-deploy README): a role at the exact path src/defaults/default_access_role.hdbrole named default_access_role is auto-granted by the container object owner to the service instance's global access role on deploy — so a system privilege listed in it is granted by #OO with no external grantor. - db/src/defaults/default_access_role.hdbrole: new; system_privileges [CREATE PSE]. Path + name are the trigger for the deployer special case. - db/src/_grants.hdbgrants: reverted to SPARQL-only (remove CREATE PSE). - runbook: B1 rewritten to the default_access_role mechanism + the failed hdbgrants attempt recorded. No .hdinamespace needed (db/src defines no real namespace prefix); db/src/.hdiconfig already maps .hdbrole.
…-role fix(#2810): grant CREATE PSE via default_access_role.hdbrole
Second DEV deploy (20261019-115443) failed: com.sap.hana.di.role: "CREATE PSE": invalid system privilege CREATE PSE is the SQL STATEMENT, not a system-privilege name. The privilege that authorizes CREATE PSE is TRUST ADMIN; ALTER PSE ... SET OWN CERTIFICATE needs CERTIFICATE ADMIN. The default_access_role mechanism itself was correct (the artifact deployed and reached the grant) — only the privilege names were wrong. - default_access_role.hdbrole: system_privileges now [TRUST ADMIN, CERTIFICATE ADMIN]. - runbook: B1 corrected; both failed attempts recorded; verify query and tier table updated.
fix(#2810): PSE privileges are TRUST ADMIN + CERTIFICATE ADMIN, not CREATE PSE
…iner grant Remove db/src/defaults/default_access_role.hdbrole entirely. The PSE and remote source are one-time, database-level admin objects — shared across containers/apps — not HDI container artifacts. Baking TRUST ADMIN into default_access_role would over-privilege every app binding user permanently for a one-time setup, and the container #OO can't delegate PKI system privileges anyway (confirmed: #OO not allowed to grant CERTIFICATE ADMIN, DEV 20261019-125352). This also unblocks DEV deploys, which were failing every db-deployer run on the TRUST ADMIN grant since #2846/#2847. Correct split (runbook rewritten): - B1: a HANA admin creates PSE + remote source once (needs TRUST ADMIN + CREATE REMOTE SOURCE). CERTIFICATE ADMIN is managed-PSE-only, not needed. - B2: container gets only GRANT EXECUTE ON REMOTE SOURCE TUTORIALS_AICORE. - B3: VECTOR_EMBEDDING proof, unchanged. - All three failed container-grant attempts recorded in a details block. default_access_role.hdbrole remains the right mechanism for privileges the container user should own long-term — just not for this.
…ntainer fix(#2810): PSE setup is instance-level admin, not a container grant
The container EXECUTE grant on the AI Core remote source belongs on the broker-created <schema>::external_privileges_role (SAP HDI's documented path for external-object access), NOT a specific _RT user and NOT default_access_role.hdbrole: - each CF binding mints a new _RT user, so a per-user grant breaks on rebind (and fails outright if the binding is gone: 'invalid user name'); - the role is auto-assigned to every binding user and persists for the life of the container; - default_access_role.hdbrole would REVOKE the container's default run-time-schema permissions as a side effect, and #OO can't grant EXECUTE on a remote source it doesn't own. Verified on DEV + PROD (2026-10-19): a container _RT user inheriting only ::external_privileges_role returned a 1536-dim text-embedding-3-small vector via TUTORIALS_AICORE. PROD section marked DONE.
…eges-role docs(#2810): B2 grant via external_privileges_role; DEV+PROD live
The HANA AI Core embeddings runbook was added to docs/developers/operations/ without a matching sidebar entry, so check-docs-sidebar.cjs failed every 'Deploy Docs to GitHub Pages' build. Add the alphabetical Operations entry.
…a-aicore fix(#2810): register hana-aicore-embeddings in docs sidebar
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Release 1.40.2 — DEV → main promotion
Patch release promoting the fixes and docs merged to
DEVsince 1.40.1 tomainfor a PROD deploy.Version bumps
tutorials-ims).deploy/mta.yamltutorials-mcp)mta-mcp.yamlChanges in this window (10 PRs since 1.40.1)
No user-facing features — all fixes, reliability hardening, and author/ops docs. Patch bump per convention.
What's New digest
hugo/data/whats_new.jsonrefreshed with the 10 PRs since 1.40.1 (849 entries total).Deploy status
Main
tutorials-imsalready deployed + smoke-verified on DEV via deploy-watcher (mtar 1.40.1-equivalent, 342 smoke tests passed, from the sameorigin/DEVHEAD0ad36d50). This PR promotes tomainfor the PROD deploy.🤖 Generated with Claude Code