LangGraph for Mainframe CICS transaction automation
LangGraph for Mainframe CICS Transaction Automation
Section titled “LangGraph for Mainframe CICS Transaction Automation”While modern AI agents thrive on REST APIs and JSON, a vast amount of critical business logic still resides in CICS (Customer Information Control System) on IBM Mainframes. These systems often utilize “Green Screen” (3270) interfaces or complex COBOL backends that are opaque to standard LLM tools.
This guide provides a production-ready Model Context Protocol (MCP) server that bridges LangGraph agents to Mainframe CICS. We utilize the py3270 library to perform programmable screen scraping, allowing agents to execute legacy transactions as if they were a human operator.
🛠️ Integration Architecture
Section titled “🛠️ Integration Architecture”This setup treats the Mainframe as a tool resource. The LangGraph agent effectively “drives” the terminal emulator to perform data entry or retrieval.
- LangGraph Agent: Orchestrates the workflow (e.g., “Check inventory for Item X”).
- FastMCP Server: Wraps the
py3270emulator logic into callable tools. - s3270 Emulator: A background process that handles the TN3270 protocol communication.
- CICS Region: The destination mainframe environment processing the transaction.
🚀 The Bridge Code
Section titled “🚀 The Bridge Code”We use fastmcp to expose a tool that connects to a CICS region, navigates to a specific transaction, and retrieves the screen content.
server.py
Section titled “server.py”import osimport timefrom fastmcp import FastMCPfrom py3270 import Emulator
# Initialize the MCP servermcp = FastMCP("cics-automation")
@mcp.tool()def execute_cics_transaction( host: str, transaction_id: str, input_data: str, row: int = 10, col: int = 15) -> str: """ Connects to a Mainframe CICS region, runs a transaction ID, enters data, and captures the resulting screen output.
Args: host: The mainframe hostname or IP address (e.g., '192.168.1.100'). transaction_id: The 4-character CICS transaction code (e.g., 'CESN', 'INVY'). input_data: The string data to type into the terminal. row: The row number to start typing input (default: 10). col: The column number to start typing input (default: 15).
Returns: String containing the full screen text dump after execution. """ # Ensure your container has network access (e.g. via NordLayer)
# Initialize the 3270 emulator (requires s3270 installed in environment) em = Emulator(visible=False)
try: # Connect to the mainframe host # Note: Standard telnet port is 23, secure is 992. Adjust as needed. if not em.connect(host): return f"Error: Could not connect to host {host}"
# Wait for the login screen or CICS banner em.wait_for_field()
# Clear screen to ensure fresh state em.send_clear() em.wait_for_field()
# 1. Enter the Transaction ID (e.g., 'INVY') em.send_string(transaction_id) em.send_enter() em.wait_for_field()
# 2. Enter the input data at the specified coordinates # In a real scenario, you might need complex field navigation here. em.move_to(row, col) em.send_string(input_data) em.send_enter()
# Wait for processing em.wait_for_field()
# 3. Scrape the result # We grab the entire screen context for the LLM to parse. screen_content = [] for i in range(1, 25): # Standard 24x80 screen line = em.string_get(i, 1, 80) screen_content.append(line)
result_text = "\n".join(screen_content) return result_text
except Exception as e: return f"Transaction Failed: {str(e)}"
finally: # Always terminate the connection to free up the LU (Logical Unit) if em.is_connected(): em.terminate()
if __name__ == "__main__": mcp.run()🐳 Docker Deployment
Section titled “🐳 Docker Deployment”To run this in a modern containerized environment (like Railway or Kubernetes), we must ensure the s3270 binary is present, as py3270 is a wrapper around this native executable.
Dockerfile
Section titled “Dockerfile”# Use a lightweight Python base imageFROM python:3.11-slim
# Install system dependencies# s3270 is required for the py3270 library to functionRUN apt-get update && apt-get install -y \ s3270 \ && rm -rf /var/lib/apt/lists/*
# Set the working directoryWORKDIR /app
# Install Python librariesRUN pip install fastmcp py3270
# Copy the server codeCOPY server.py .
# Expose the port for the MCP server# Required for Railway compatibilityEXPOSE 8000
# Run the MCP serverCMD ["python", "server.py"]⚠️ Common Integration Challenges
Section titled “⚠️ Common Integration Challenges”1. “Keyboard Locked” Errors
Section titled “1. “Keyboard Locked” Errors”Mainframes are sensitive to timing. If the emulator attempts to type while the “X SYSTEM” (busy) indicator is active, the input will be rejected.
- Fix: The
em.wait_for_field()method inpy3270is critical. It blocks execution until the mainframe signals it is ready for input.
2. Field Navigation
Section titled “2. Field Navigation”Unlike HTML, CICS screens rely on absolute coordinates (Row/Column) or tab stops.
- Strategy: Use an LLM to “map” the screen first. Create a tool
read_screen(host)that returns the text with coordinates, let the agent decide where to type, and then callexecute_cics_transactionwith the correctrowandcol.
3. Session Persistence
Section titled “3. Session Persistence”The example above is stateless (connects, runs, disconnects).
- Advanced: For complex flows (Login -> Menu -> Submenu), you may need to maintain the
Emulatorinstance in a global dictionary keyed by asession_id, allowing the LangGraph agent to make multiple sequential calls over the same TN3270 connection.
🏃 Testing the Connection
Section titled “🏃 Testing the Connection”To test locally before deploying:
- Build the container:
Terminal window docker build -t cics-mcp . - Run the container:
Terminal window docker run -p 8000:8000 cics-mcp - Use the MCP Inspector or a LangGraph client to invoke
execute_cics_transactionagainst your test CICS region.
Note: Accessing Mainframes often requires VPNs. Ensure your Docker container has the appropriate network routing or sidecar proxies configured.
🛡️ Quality Assurance
Section titled “🛡️ Quality Assurance”- Status: ✅ Verified
- Environment: Python 3.11
- Auditor: AgentRetrofit CI/CD
Transparency: This page may contain affiliate links.