Author Instructions โ
How to write, preview, and publish tutorials on the SAP Developers tutorial platform.
This document describes the current authoring workflow and flags planned improvements in ยง11 below. If you have edit access to a repo under the sap-tutorials GitHub organization, you are the audience.
1. The big picture โ
You write Markdown Platform fetches & rebuilds Readers see HTML
โโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโ
sap-tutorials/<repo>/ โโโถ tutorials-ims CI โโโถ developers.sap.com
*.md + images (fetch โ Hugo โ publish) /tutorials/<slug>You never touch the rendering pipeline, the Hugo site, or the database. You write Markdown in a tutorial repo, open a pull request, and after it is merged the platform takes over.
2. Where tutorials live โ
Tutorials are stored in repos under the sap-tutorials GitHub organization. Each repo holds one tutorial set (typically grouped by product or topic). A single Markdown file in that repo represents one tutorial and becomes one URL on the platform.
Naming convention:
| File | Becomes |
|---|---|
sap-tutorials/abap-core-development/tutorials/abap-cloud-ui-from-interface.md | /tutorials/abap-cloud-ui-from-interface |
sap-tutorials/abap-core-development/tutorials/abap-cloud-ui-from-interface/001-find-interface.png | image referenced from the tutorial |
The filename (without .md) becomes the slug โ the public URL segment. Slugs must be unique across the entire sap-tutorials org.
Quiz / validation files โ
If your tutorial has a quiz, validation rules live in a parallel <repo>-Contribution repo (private) under the same org as a rules.vr file with the same slug. The platform fetches it automatically when the build runs.
3. Anatomy of a tutorial โ
โ Live examples โ see the Tutorial Platform Features for Authors mission for working tutorials that demonstrate every piece of syntax described below: the CODECHECK demo, free-text grading, AUTOAUTHOR, and the feature cookbook (OS variants, branches, mermaid, codetabs, glossary, lightbox).
A tutorial Markdown file has three required parts: frontmatter, an introduction, and steps.
3.1 Frontmatter โ
YAML block at the very top of the file, fenced with ---:
---
parser: v2
auto_validation: true
primary_tag: programming-tool>abap-development
tags: [tutorial>beginner, programming-tool>abap-development, software-product>sap-business-technology-platform]
time: 15
author_name: Jane Doe
author_profile: https://github.com/janedoe
---| Field | Required | Notes |
|---|---|---|
parser | Yes | Always v2 for new tutorials. V1 ([ACCORDION-BEGIN] markers) is legacy. |
primary_tag | Yes | One tag from the platform taxonomy โ drives categorization. |
tags | Yes | Array. First tag should be tutorial>beginner, tutorial>intermediate, or tutorial>advanced. |
time | Yes | Estimated minutes to complete. Integer. |
auto_validation | No | Set true if the tutorial has quiz rules in the -Contribution repo. |
author_name, author_profile | Recommended | Shown on the tutorial page. |
video | No | Optional intro video shown as a styled player at the top of the steps. See ยง3.3 Adding a video. |
A canonical taxonomy of allowed primary_tag and tags values is maintained in the platform's Tags entity. To add a new tag or category, see Center Admin ยง "Import a new tag".
3.2 Title and introduction โ
Immediately after the frontmatter:
# Generate your own custom UI Service based on a Business Object Interface
<!-- description -->Business Object Interfaces are provided by SAP in order to release business objects...
## You will learn
- How to generate a custom UI Service based on a C1-released Business Object Interface
- How to identify the authorization objects required to consume it
## Prerequisites
- SAP BTP, ABAP Environment
- A package located in the software component ZLOCAL
---# Title(single H1) โ the tutorial title.<!-- description -->...โ a comment marker followed by the short description shown in catalog pages and search results.## You will learnand## Prerequisitesโ H2 sections, conventional and recommended.- The standalone
---after Prerequisites separates the introduction from the steps.
TIP
Only include a single contiguous set of bullet points in the Prerequisites section, and don't include any normal paragraphs. Otherwise the rendered version may be unpredictable and not what you intend.
3.2.1 Adding a video โ
Many tutorials include a companion video. There are two supported ways to add one; the frontmatter approach is preferred for a single intro video.
Preferred โ video: frontmatter. Add a video object to the frontmatter. The platform renders it as a styled, responsive 16:9 player at the top of the Steps section:
---
parser: v2
primary_tag: products>sap-hana-cloud
tags: [tutorial>beginner, products>sap-hana]
time: 20
author_name: Jane Doe
author_profile: https://github.com/janedoe
video:
url: https://www.youtube.com/watch?v=6WY70LyLS1c
title: Create a User Interface with CAP
---| Field | Required | Notes |
|---|---|---|
video.url | Yes | A YouTube watch/short/embed URL (or a bare 11-char YouTube ID), a Vimeo URL, or an openSAP microlearning / SAP video URL. |
video.title | No | Accessible title for the player. Defaults to Video tutorial. |
Supported hosts: YouTube (youtube.com, youtu.be), Vimeo (vimeo.com, player.vimeo.com), microlearning.opensap.com, and the SAP video service. An unrecognized host is ignored (no broken frame) โ the build logs a warning naming the slug.
Also supported โ raw HTML in the body. You can still embed a player inline anywhere in the tutorial (including a ## Video Version section before the first step) using a raw <iframe>:
## Video Version
<iframe width="560" height="315" src="https://www.youtube.com/embed/6WY70LyLS1c" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen></iframe>The iframe host must be on the platform allowlist (same hosts as above) or it is stripped for security. <video> elements are also supported. See the platform reference iframe allowlist.
TIP
Don't do both for the same video. If you set video: frontmatter, remove any ## Video Version iframe so the player isn't rendered twice.
3.3 Steps (V2 parser) โ
Each step is a ### H3 heading followed by content:
### Find the released Business Object Interface
1. In the Project Explorer, select **Released Objects** โ `USE_IN_CLOUD_DEVELOPMENT`.
2. Right-click on the interface `I_BankTP` and select **Generate ABAP Repository Objects**.

### Configure the generated artifacts
Continue with the next step...Rules of thumb:
- One H3 per step. Avoid H4/H5 inside a step โ they don't render as nested navigation.
- Step titles become the table of contents on the right of the rendered page.
- Step content is plain Markdown: lists, code fences, images, links, bold/italic.
- Inline HTML is escaped for safety. Stick to Markdown.
3.4 Images โ
Place images alongside the Markdown file in a folder named after the slug:
abap-cloud-ui-from-interface.md
abap-cloud-ui-from-interface/
001-find-interface.png
002-start-generator.pngReference them with relative paths:
The platform automatically resolves these to raw.githubusercontent.com URLs at build time. Do not hardcode https://github.com/... URLs.
3.5 Option blocks โ
When a step has variants, wrap each variant in an OPTION block. There are two flavors โ generic (per-step tabs) and OS-conditional (driven by a global picker at the top of the tutorial).
3.5.1 Generic option blocks (Java vs Node, JSON vs XML, Cloud vs On-premise) โ
[OPTION BEGIN [JSON]]
...content for the JSON path...
[OPTION END]
[OPTION BEGIN [XML]]
...content for the XML path...
[OPTION END]The platform renders these as a tab strip inside the step. Each step's tabs are independent.
3.5.2 OS-conditional content (Windows vs macOS vs Linux vs BAS) โ NEW โ
When the variants are about the operating system, the platform automatically detects this and wires every OS block on the page to a single global picker at the top of the tutorial. The reader picks their OS once; their choice persists across tutorials.
Use any of these labels โ they're all recognized:
| Canonical OS | Recognized labels |
|---|---|
| Windows | Windows, Win, Win32, Win64 |
| macOS | macOS, MacOS, Mac OS, Mac, OS X, Darwin |
| Linux | Linux, Ubuntu, Debian, Fedora, Unix |
| BAS | BAS, Business Application Studio, SAP BAS |
Combined labels are fine โ Mac and Linux matches both, Mac & Linux likewise.
[OPTION BEGIN [Windows]]
Open PowerShell and run `cd $HOME\projects`
[OPTION END]
[OPTION BEGIN [Mac and Linux]]
Open a terminal and run `cd ~/projects`
[OPTION END]The reader sees only the variant matching their OS. Their choice persists across tutorials.
Defaults & detection. First-time visitors get auto-detected (Windows / macOS / Linux from the browser; BAS detected when the tutorial is opened from inside Business Application Studio). After they pick an OS, that choice is remembered.
Missing variants. When a step doesn't cover the reader's chosen OS, the platform shows the closest match and a small banner: "No Linux instructions for this step โ showing macOS." Use this when one OS path is genuinely identical to another.
Existing OS-tabbed tutorials get the picker for free. No author migration required โ the heuristic detects OS-flavored OPTION blocks automatically.
Author override. If the auto-detection mis-classifies your tabs (e.g. you have a tab named Linux that's actually about a Linux container product, not the OS), add to your frontmatter:
osOverrides:
step-3-deploy-the-app: regular # force this step's group to NOT be OS-conditional
step-5-install-cli: os # force this step's group to BE OS-conditionalThe key is the slugified step heading.
3.5.3 AI-assisted OS variants (VS Code) โ NEW โ
The Tutorials VS Code extension can generate the missing OS variants for you. Write your step for one OS, then ask the extension to "generate OS variants" โ it returns translated Windows / macOS / Linux / BAS blocks you can review and accept inline. See the [VS Code extension docs](TODO: link added when plugin ships) for the workflow.
3.6 Code blocks โ
Use fenced code blocks with a language tag. Supported languages include abap, js, ts, java, cds, sql, bash, yaml, json, xml, html, css. CDS code uses dedicated highlighting (see npm run build:highlight).
\`\`\`cds
entity Books : managed {
key ID : Integer;
title : localized String(111);
}
\`\`\`4. The author workflow today โ
1. Fork or branch in sap-tutorials/<repo>
2. Add or edit a .md file under tutorials/
3. Commit any new images in the slug-named folder
4. Open a PR against main
5. PR review + merge (current review is informal โ see ยง11)
6. Push to main โ repo dispatch event โ tutorials-ims CI
7. CI re-fetches your tutorial, rebuilds Hugo, publishes to HANA
8. Live at developers.sap.com/tutorials/<your-slug> within a few minutesThe notification step (6) is wired by adding a small workflow file to your tutorial repo โ see tutorial-repo-dispatch.yml. Org admins typically handle this once per repo.
5. Local preview โ
To see your tutorial render exactly the way it will on production:
git clone https://github.com/sap-tutorials/tutorials-ims.git
cd tutorials-ims
npm install
npm run fetch-tutorials # Pulls every tutorial from the org (cached after first run)
npm run dev # Hugo dev server at http://localhost:1313Open http://localhost:1313/tutorials/<your-slug> to see your page.
To force a re-fetch of just-merged content, delete .tutorial-cache/<your-slug>.sha and re-run npm run fetch-tutorials. To force a full re-fetch, delete the entire .tutorial-cache/ directory.
A GITHUB_TOKEN environment variable with repo:read scope is recommended; without it you may hit GitHub rate limits.
5.1 Previewing on the QA channel โ
The QA channel is a deployed author-preview environment separate from production. It renders content sourced exclusively from *-Contribution repos at /tutorials-qa/*, gated by the Tutorial.Author BTP scope.
Key points:
- What it shows โ only content from your
<repo>-Contributionrepo (the private companion that holds quiz rules and draft tutorial content). It is not a copy of the production channel. - Access requirement โ you must hold the
Tutorial.Authorrole collection in the BTP subaccount. Ask a Center Admin (center-admin.md) to assign it. - Setup โ the one-time infrastructure setup (CI secrets, dispatch-token distribution, HDI binding, role-collection creation) is documented in ../developers/operations/qa-channel-bootstrap.md. You do not need to repeat this; it is done once per environment.
- Local dev server โ your local
npm run devdoes not use any QA flag. The QA flag (hugo.qa.toml) only applies to the deployed QA build. Running locally is always sufficient for layout and step rendering checks. - Triggering a QA rebuild โ push a change to the
*-Contributionrepo. The same repo-dispatch mechanism used for production fires a QA-specific CI workflow that fetches from-Contributionrepos only, builds with the QA Hugo config, and publishes to the QA HANA instance. - URL pattern โ
https://<approuter>/tutorials-qa/<your-slug>(requiresTutorial.Authorscope; access is denied to unauthenticated users).
6. Pre-submit checklist โ
Run through this before opening your PR:
- [ ] Frontmatter is valid YAML (no tab characters, no missing quotes around tags with
:). - [ ]
parser: v2is set. - [ ]
primary_tag,tags,time, and the H1 title are present. - [ ] Tutorial has a
<!-- description -->line right after the H1. - [ ] Every step is an
### H3. No H1/H2 inside the step body. - [ ] All images referenced in the Markdown exist in the slug-named folder.
- [ ] Image paths are relative, not absolute GitHub URLs.
- [ ] Code fences have a language tag.
- [ ] Inline HTML is avoided (or limited to allowed tags only).
- [ ] If you used
OPTIONblocks, eachBEGINhas a matchingEND. - [ ] Tutorial renders cleanly in
npm run devwith no warnings.
7. What happens after merge โ
| Step | Where | Duration |
|---|---|---|
| GitHub Action sends repo dispatch | Your tutorial repo | seconds |
tutorials-ims CI checks out, fetches all tutorials (cached) | GitHub Actions runner | ~3 s cached / ~2 min cold |
| Hugo rebuilds the static site | Runner | 5โ10 s |
| Delta publish: only changed slugs upload to HANA | CAP backend | 2โ4 s |
| LRU cache invalidates; next request serves new content | Production | immediate |
Total: typically under a minute for incremental edits, a few minutes for a full rebuild. See build.md for details.
If the build fails, the dispatch run will be red in the tutorials-ims GitHub Actions tab. Common causes:
- Bad YAML in frontmatter
- Missing image referenced from Markdown
- Unbalanced
OPTIONblocks or HTML tags - Slug collision with an existing tutorial
8. Updating and rolling back โ
Quick edits โ
Push a change to main of the source repo. The pipeline picks it up automatically โ no manual step.
Rollback โ
Production content is versioned. If a published change is broken, ask a Center Admin to roll back โ see center-admin.md ยง Content rollback. Rollback reverts the manifest pointer; you still need to follow up with a corrective PR.
9. (Reserved) โ
This section number is reserved for future use. See ยง11 for known gaps.
10. Where to ask for help โ
| Question type | Where |
|---|---|
| "Is my Markdown structured correctly?" | Open a draft PR; a repo group owner can review a draft PR and flag issues |
| "Why didn't my change appear on production?" | Check the tutorials-ims GitHub Actions runs; look for the failed dispatch |
| "How do I add a new tag / category?" | See Center Admin ยง "Import a new tag" โ taxonomy is centrally managed |
| "I need a preview before merging" | Run locally per ยง5, or request QA channel access (ยง5.1) โ see ../developers/operations/qa-channel-bootstrap.md (Tutorial.Author scope required) |
| Anything else | Platform team channel (internal) |
11. Known gaps and near-term improvements โ
These items are listed here so authors know what to expect โ and what not to expect โ from the current workflow.
| Gap | Current state |
|---|---|
| Editorial review gate | Informal PR review in source repo; no formal Author QA lane |
| Approval / sign-off workflow | None โ merge equals publish; no reviewer roles |
| PR preview deploys | None โ preview requires local clone (ยง5) or QA channel (ยง5.1) |
| VS Code authoring extension | None โ live preview, frontmatter validation, link checking are planned |
| Reporting / analytics for authors | Available to platform admins only; author/management views not yet published |
| Tag taxonomy reference | Not yet author-facing; copy tags from a similar existing tutorial for now |
| Tag bulk import | Manual via Center Admin; CSV / API import planned |
| Per-tutorial rollback | Whole content-set rollback only; per-slug rollback not yet available |
| Precommit validation | Build errors land in .tutorial-cache/errors.json; author-facing npm run validate-tutorials partially in place but not published |
If any of these items become a blocker for your work, open an issue on the project's GitHub repository.
Reference: related docs โ
- build.md โ the full technical pipeline (fetch โ parse โ Hugo โ HANA)
- hugo-migration.md โ why Hugo, layout conventions
- tutorial-repo-dispatch.yml โ the GitHub Action your repo needs in order to trigger rebuilds
- repo-group-owners.md โ for repo owners reviewing your PRs
- center-admin.md โ for taxonomy, tag onboarding, and rollback
- ../developers/operations/qa-channel-bootstrap.md โ author-preview channel