Artificial Intelligence Blogs Posts
cancel
Showing results for 
Search instead for 
Did you mean: 
DEEPA_DORAIRAJ
Product and Topic Expert
Product and Topic Expert
1,516

SAP COMMUNITY  |  SERIES: PART 2 OF 6  |  SAP AI CORE  |  GENERATIVE AI HUB

SAP Generative AI Hub: Using the Python SDK for SAP Data Tasks

Updated March 2026: Corrected environment section — Jupyter notebooks run in SAP Business Application Studio (BAS)

Five practical SAP use cases with working Python code — across SAP AI Launchpad notebooks, local scripts, and BTP applications — using the generative-ai-hub-sdk for clean, production-ready authentication.

By Deepa Dorairaj   |  SAP AI Solution Architect  |  Part 2 of 6  |  Published 2026

TL;DR: Once your Generative AI Hub is configured (see Part 1), the generative-ai-hub-sdk Python package handles OAuth token management automatically — removing the biggest friction point from direct API integration. This article covers SDK installation and configuration across three environments (AI Launchpad notebooks, local Python scripts, BTP applications), followed by five working code examples for real SAP data tasks: exception log summarization, HANA query analysis, ABAP/SQL code generation, master data classification, and structured data extraction from SAP documents.

Series Context

This is Part 2 of a 6-part series on SAP Generative AI Hub. Part 1 covered the complete setup path from BTP entitlements to your first API call. If you haven't configured your AI Core instance and resource group yet, start there before continuing.

This part focuses on practical Python integration — the code patterns you'll use for real SAP workloads, across the three environments where SAP practitioners most commonly run Python against the Hub.

 

Environment

Best For

Key Consideration

AI Launchpad Notebooks

Interactive development, rapid prototyping

Credentials pre-configured — fastest to start

Local Python Script

Automation, scheduled jobs, local development

Requires .env file with service key credentials

BTP Application

Production workloads, CAP integration, APIs

Credentials via BTP environment variables or secrets

SDK INSTALLATION & CONFIGURATION 

Installing and Configuring the generative-ai-hub-sdk

Why the SDK Over Direct API Calls

Part 1 showed the raw OAuth 2.0 flow using direct API calls — which is useful to understand what's happening under the hood. For any real workload, the generative-ai-hub-sdk is the better path. It handles token acquisition, token refresh, retry logic, and deployment ID resolution automatically. Your application code focuses on the task, not the authentication plumbing.

Installation

# Install the SAP Generative AI Hub SDK
pip install sap-ai-sdk-gen
 
# Optional but recommended — for HANA connection examples later
pip install hdbcli pandas python-dotenv

Configuration: AI Launchpad Notebooks

    Environment: SAP Business Application Studio (BAS) — Jupyter Notebooks 

Setting Up a BAS Dev Space for Jupyter

SAP Business Application Studio is the browser-based IDE available on BTP that supports Jupyter notebooks via the built-in Jupyter and Python extensions. This is the SAP-native interactive notebook environment for Python development — not SAP AI Launchpad, which does not provide a notebook interface.

BAS is available to all BTP customers and trial users. No additional entitlement beyond BAS subscription is required to run Jupyter notebooks.

Dev Space Setup — Step by Step

Step 1 — Create a Dev Space:

  • Open SAP Business Application Studio from your BTP subaccount
  • Click Create Dev Space
  • Name it (e.g. GenAIHub_Dev) and select SAP HANA Native Application as the type
  • Under Additional SAP Extensions, select Python Tools
  • Click Create Dev Space and wait for status to show Running
  • Click the dev space name to open it

Step 2 — Install pip and required packages:

Open a terminal in BAS (F1 → Open Terminal) and run:

# Install pip if not already available
curl https://bootstrap.pypa.io/get-pip.py > get-pip.py && python3 get-pip.py
echo "export PATH=/home/user/.local/bin:$PATH" >> ~/.bashrc && source ~/.bashrc
 
# Create a virtual environment for your project
python3 -m venv ~/.venv/genai
source ~/.venv/genai/bin/activate
 
# Install the SAP Generative AI Hub SDK and Jupyter kernel
pip install sap-ai-sdk-gen ipykernel hdbcli pandas python-dotenv
python -m ipykernel install --user --name genai --display-name 'GenAI Hub'

Step 3 — Create the AI Core credentials file:

Create .aicore-config.json in your home directory with your AI Core service key values:

{
  "AICORE_AUTH_URL": "https://<subdomain>.authentication.<region>.hana.ondemand.com",
  "AICORE_CLIENT_ID": "<clientid from service key>",
  "AICORE_CLIENT_SECRET": "<clientsecret from service key>",
  "AICORE_BASE_URL": "<AI_API_URL from service key>",
  "AICORE_RESOURCE_GROUP": "default"
}

Step 4 — Create and run a notebook:

  • In BAS Explorer, right-click and select New File → name it test_genai.ipynb
  • Open the file — BAS will open it in the Jupyter editor
  • Click Select Kernel → Python Environments → select GenAI Hub (your venv)
  • If prompted to install ipykernel, confirm — it installs automatically

Step 5 — Verify the SDK connection in the first notebook cell:

# Verify SDK picks up credentials from .aicore-config.json
from gen_ai_hub.proxy.native.openai import OpenAI
 
client = OpenAI()
print('SDK connected successfully')

Do not commit .aicore-config.json to any Git repository. If you clone a repository into BAS and push back to Git, add .aicore-config.json to your .gitignore before the first commit. BAS has Git integration enabled by default — credential exposure via accidental commit is a real risk.

Once your dev space is running and the venv is activated, the SDK reads .aicore-config.json automatically. All five use case examples in this article run without any additional configuration changes from the BAS notebook environment.

Persisting the Virtual Environment Across BAS Sessions

BAS dev spaces suspend after inactivity. The virtual environment persists between sessions, but you must re-activate it each time you open a new terminal:

# Re-activate venv at the start of each BAS session

source ~/.venv/genai/bin/activate

Tip: Add the activation command to your BAS dev space's shell profile (~/.bashrc) so it runs automatically when a new terminal opens: echo 'source ~/.venv/genai/bin/activate' >> ~/.bashrc

Configuration: Local Python Script

    Environment: Local Python Script 

For local development, create a configuration file that points the SDK to your AI Core service key credentials. Store this as .aicore-config.json in your home directory or reference it via an environment variable.

environment variable.
# ~/.aicore-config.json — from your AI Core service key
{
  "AICORE_AUTH_URL": "https://<your-subdomain>.authentication.<region>.hana.ondemand.com",
  "AICORE_CLIENT_ID": "<clientid from service key>",
  "AICORE_CLIENT_SECRET": "<clientsecret from service key>",
  "AICORE_BASE_URL": "<AI_API_URL from service key>",
  "AICORE_RESOURCE_GROUP": "default"
}

Never commit .aicore-config.json to version control. Add it to your .gitignore immediately. For team environments, use environment variables (AICORE_AUTH_URL, AICORE_CLIENT_ID, etc.) instead of the config file — the SDK reads both patterns automatically.

Configuration: BTP Application

    Environment: BTP Application 

In BTP applications, bind the AI Core service instance to your application. The SDK reads credentials from the VCAP_SERVICES environment variable that BTP injects automatically at runtime — no manual credential management required.

# BTP injects VCAP_SERVICES automatically when AI Core is bound
# The SDK reads it without any additional configuration
from gen_ai_hub.proxy.core.proxy_clients import get_proxy_client
 
# SDK auto-resolves from VCAP_SERVICES in BTP runtime
proxy_client = get_proxy_client('gen-ai-hub')

Once credentials are configured for your target environment, all five use case examples below work identically across all three environments. The SDK abstracts the credential source — your application code does not change.

FIVE SAP USE CASES WITH WORKING CODE 

SAP Data Tasks: Working Code Examples

The following examples cover five practical SAP use cases. Each uses the same SDK pattern — choose your preferred model by changing one parameter. All examples use Claude 3.5 Sonnet as the default; swap the model_name value for GPT-4o, Gemini, or Mistral as needed based on the model comparison in this week's LinkedIn post.

 

Use Case

What the Model Does

Exception log summarization

Parse and summarize SAP SM21 / application error logs into structured root cause analysis

HANA query result analysis

Interpret query output and surface anomalies, trends, or data quality issues

ABAP / SQL / HANA code generation

Generate or explain code from natural language descriptions

Master data classification

Tag and categorize SAP master data records against defined classification schemes

Structured data extraction

Pull structured fields from SAP documents, change logs, or transport descriptions

Use Case 1: Summarizing SAP Exception Logs

SAP exception logs — SM21 system logs, application error dumps, job logs — are high-volume and time-consuming to triage manually. This pattern feeds raw log text to the model and returns a structured root cause summary with recommended actions.

# Use Case 1: SAP Exception Log Summarization
from gen_ai_hub.proxy.langchain.openai import ChatOpenAI
from langchain.schema import HumanMessage, SystemMessage
 
llm = ChatOpenAI(proxy_model_name='claude-3.5-sonnet')
 
log_text = '''
  [SM21 Log Extract]
  E  RABAX  INCLUDE: ZREPORT_DELTA_LOAD Line 847
  E  Runtime Error: COMPUTE_INT_PLUS_OVERFLOW
  E  Date: 2026-03-10  Time: 04:32:17
  E  Work process terminated abnormally
'''
 
messages = [
  SystemMessage(content='''You are an SAP Basis and ABAP expert.
  Analyze SAP exception logs and return:
  1. Root cause (one sentence)
  2. Affected component
  3. Severity: Critical / High / Medium / Low
  4. Recommended action
  Be concise and technical.'''),
  HumanMessage(content=f'Analyze this SAP log:\n{log_text}')
]
 
response = llm(messages)
print(response.content)

Output example — Root cause: Integer overflow in delta load procedure at ZREPORT_DELTA_LOAD line 847 due to 32-bit counter exceeding maximum value. Component: ABAP Runtime. Severity: Critical. Action: Cast counter variable to BIGINT and redeploy procedure.

Use Case 2: Analyzing HANA Query Results

This pattern connects to HANA Cloud, executes a query, and passes the result set to the model for interpretation — surfacing anomalies, trends, or data quality issues that would otherwise require manual review.

# Use Case 2: HANA Query Result Analysis
import hdbcli.dbapi as hdb
import pandas as pd
from gen_ai_hub.proxy.langchain.openai import ChatOpenAI
from langchain.schema import HumanMessage, SystemMessage
 
# Connect to HANA Cloud
conn = hdb.connect(
    address='<your-hana-host>.hanacloud.ondemand.com',
    port=443,
    user='<user>',
    password='<password>',
    encrypt=True
)
 
# Run your query and load into DataFrame
query = '''
  SELECT PLANT, MATERIAL, SUM(QUANTITY) AS TOTAL_QTY,
         COUNT(*) AS RECORD_COUNT
  FROM STOCK_OVERVIEW
  GROUP BY PLANT, MATERIAL
  ORDER BY TOTAL_QTY DESC
  LIMIT 50
'''
df = pd.read_sql(query, conn)
 
# Pass result to model for analysis
llm = ChatOpenAI(proxy_model_name='claude-3.5-sonnet')
 
messages = [
  SystemMessage(content='You are an SAP data analyst. Identify anomalies, trends, and data quality issues in SAP query results. Be specific and reference actual values from the data.'),
  HumanMessage(content=f'Analyze this SAP stock query result:\n{df.to_string()}')
]
 
response = llm(messages)
print(response.content)

Do not pass full production datasets to the model. Apply LIMIT clauses and aggregate before sending. For sensitive SAP data, review your BTP data residency settings and confirm model data handling aligns with your organization's data governance policy before deploying to production.

Use Case 3: Generating ABAP / SQL / HANA Code from Natural Language

This pattern accepts a plain-language description of a requirement and returns production-ready ABAP, SQL, or HANA SQL code. Useful for accelerating development, explaining existing code, or onboarding team members to unfamiliar syntax.

# Use Case 3: SAP Code Generation from Natural Language
from gen_ai_hub.proxy.langchain.openai import ChatOpenAI
from langchain.schema import HumanMessage, SystemMessage
 
llm = ChatOpenAI(proxy_model_name='gpt-4o')
# GPT-4o recommended for ABAP — see model comparison article
 
requirement = '''
  Write a HANA SQL procedure that:
  - Reads from a virtual table SOURCE_SCHEMA.ORDERS
  - Filters records where CHANGE_DATE > last_run_date parameter
  - Inserts new records into TARGET_SCHEMA.ORDERS_DELTA
  - Updates a control table DELTA_CONTROL with the new last_run_date
  - Handles errors with a rollback
'''
 
messages = [
  SystemMessage(content='''You are a senior SAP HANA SQL developer.
  Generate clean, production-ready HANA SQL code.
  Include comments explaining key sections.
  Flag any HANA-specific considerations or limitations.'''),
  HumanMessage(content=f'Generate HANA SQL for this requirement:\n{requirement}')
]
 
response = llm(messages)
print(response.content)

 

Use Case 4: Classifying SAP Master Data

Master data classification — tagging materials, vendors, cost centers, or GL accounts against defined schemes — is high-volume and rule-heavy. This pattern uses the model to apply a classification schema to a batch of records and return structured JSON output ready for loading back into SAP.

# Use Case 4: SAP Master Data Classification
import json
from gen_ai_hub.proxy.langchain.openai import ChatOpenAI
from langchain.schema import HumanMessage, SystemMessage
 
llm = ChatOpenAI(proxy_model_name='claude-3.5-sonnet')
 
materials = [
  {'MATNR': '000000000010001234', 'MAKTX': 'Hydraulic Pump Assembly 250bar'},
  {'MATNR': '000000000010005678', 'MAKTX': 'Office Chair Ergonomic Mesh Black'},
  {'MATNR': '000000000010009012', 'MAKTX': 'SAP S4HANA License Annual Renewal'},
]
 
classification_schema = ['Mechanical Components', 'Office Supplies',
                         'Software & Licenses', 'Raw Materials', 'Services']
 
messages = [
  SystemMessage(content=f'''Classify SAP material master records.
  Return ONLY valid JSON array. No explanation.
  Schema: {classification_schema}
  Format: [{{'MATNR': '...', 'CATEGORY': '...', 'CONFIDENCE': 'High/Medium/Low'}}]'''),
  HumanMessage(content=f'Classify these materials:\n{json.dumps(materials)}')
]
 
response = llm(messages)
classified = json.loads(response.content)
print(json.dumps(classified, indent=2))

Prompt the model to return only JSON with no preamble or explanation when you need structured output for downstream processing. Claude is particularly consistent at following this instruction on classification tasks.

Use Case 5: Extracting Structured Data from SAP Documents

SAP landscapes accumulate semi-structured text in transport request descriptions, change log comments, functional spec attachments, and ticket notes. This pattern extracts structured fields from unstructured SAP document text — turning narrative descriptions into queryable data.

# Use Case 5: Structured Data Extraction from SAP Documents
import json
from gen_ai_hub.proxy.langchain.openai import ChatOpenAI
from langchain.schema import HumanMessage, SystemMessage
 
llm = ChatOpenAI(proxy_model_name='claude-3.5-sonnet')
 
transport_description = '''
  TR: DEVK912345 - FI Delta Load Fix
  Developer: firstname.lastname@company.com
  Changed ZFI_DELTA_LOAD procedure to fix integer overflow on
  BKPF document counter. Root cause was 32-bit INT hitting max
  value after 2.1B records. Cast to BIGINT. Tested on DEV and QA.
  Affected tables: BKPF, BSEG. No customizing changes.
  Approved by: firstname1.lastname1@company.com on 2026-03-08
'''
 
messages = [
  SystemMessage(content='''Extract structured data from SAP transport descriptions.
  Return ONLY valid JSON. No explanation.
  Fields: transport_id, title, developer, approver, approval_date,
  affected_tables (list), root_cause, change_type, tested_systems (list)'''),
  HumanMessage(content=f'Extract fields from:\n{transport_description}')
]
 
response = llm(messages)
extracted = json.loads(response.content)
print(json.dumps(extracted, indent=2))

Choosing the Right Model per Use Case

Based on practical testing across these five patterns — and detailed in this week's LinkedIn model comparison post — here are the recommended model defaults:

 

Use Case

What the Model Does

Exception log summarization

Claude 3.5 Sonnet — consistent on long, noisy log text

HANA query result analysis

Claude 3.5 Sonnet — structured output quality, handles wide DataFrames

ABAP / SQL / HANA code generation

GPT-4o — broader SAP code knowledge, stronger on ABAP specifics

Master data classification

Claude 3.5 Sonnet — reliable JSON-only output, consistent confidence scoring

Structured data extraction

Claude 3.5 Sonnet — long-form document coherence, clean JSON output

Swap model_name='gpt-4o' or model_name='mistral-large' in any example to compare outputs. The SDK pattern is identical across all models.

What's Next in This Series

  • Part 3: Building Your First Prompt Pipeline — chaining prompts, managing context, structured outputs for multi-step SAP workflows
  • Part 4: Connecting to HANA Cloud Vector Store — embedding generation, REAL_VECTOR storage, RAG on your SAP data
  • Part 5: Integrating AI Core into a BTP CAP Application — production-grade AI in your SAP extension layer
  • Part 6: Extending SAP Joule with Foundation Models — custom Joule skills backed by Generative AI Hub

If you work through any of these examples and run into environment-specific issues — particularly around BTP binding or AI Launchpad notebook credential resolution — drop a comment below. The configuration edge cases are where community knowledge adds the most value.

7 Comments