Say local RPG development and most teams mean VS Code with Code for IBM i, or RDi where the seats are already paid for. Your source lives in git on your own machine. You edit it there, press Deploy, and the members go up to the IFS so the partition can run CRTSQLRPGI on them.
Only the editing is local. The compile is a job on the IBM i, the program runs on the IBM i, and the compile errors come back in a spool file, so every developer needs a profile, a library list, and a partition that is up. Change one bucket boundary in an aging program and you are queued behind whatever else the machine is doing that afternoon.
Compiling RPG Without the IBM i
The same source compiles on the developer's own machine, unchanged, DDS included. Triton RPG reads the display file, the subfile, and the embedded SQL as they sit in your library and compiles it to a class you run on the JVM, with the 5250 front end wired into it, so your team goes on maintaining the RPG they already maintain.
An aging inquiry, compiled and run:
rpgc ARINQUIRY.rpgle -o out --dds-path .
java -cp out:triton-rpg.jar:jline.jar:h2.jar ARINQUIRY
AR Aging Inquiry
As of: 08/10/2026 Open items: 11
InvNo Customer Name Due Date Balance Days Aging
1001 Acme Corporation 2025-11-15 2500.00 268 Over 90
1002 Baker Industries 2025-12-20 3200.00 233 Over 90
1003 Acme Corporation 2026-02-01 1300.00 190 Over 90
1004 Central Services 2026-02-15 3100.00 176 Over 90
1005 Baker Industries 2026-03-15 750.00 148 Over 90
1006 Central Services 2026-04-01 2250.00 131 Over 90
1007 Delta Electronics 2026-04-15 1500.00 117 Over 90
1008 Central Services 2026-04-25 890.00 107 Over 90
1009 Delta Electronics 2026-05-15 3000.00 87 61-90
1010 Eagle Supplies 2026-05-30 975.00 72 61-90
1011 Eagle Supplies 2026-06-15 5500.00 56 31-60
Aging Summary
Current: 0.00 1-30: 0.00 31-60: 5500.00
61-90: 3975.00 Over 90: 15490.00 Total: 24965.00
F3=Exit F5=Refresh
That is the aging inquiry your users know, running on a laptop with no IBM i behind it: the subfile scrolls, F5 reloads, and F3 exits, all from the display file already in your library:
ARINQUIRY.rpgle
DCL-F ARINQUIRY WORKSTN SFILE(SFLREC:wRRN);
That compile takes a third of a second. Move a bucket boundary, run those two commands again, and the new totals are on the screen.
The compiler reads the source file you name and the DDS directory you point it at, so the size of the library the program came out of never enters into it.
Pointing It at Db2 for i
Those rows came out of an in-memory database on the same machine, loaded from a file of INSERT statements, with no change to the RPG. QSYS2.GENERATE_SQL writes the CREATE TABLE statements for your own files straight off the partition, and a SELECT gets you as many rows as a developer needs to work with. The JDBC URL decides which database answers, so the same compiled program reads your Db2 for i once you give it four environment variables:
export JDBC_URL="jdbc:as400://myhost/WHITEHORN1"
export JDBC_DRIVER="com.ibm.as400.access.AS400JDBCDriver"
export JDBC_USER="MYUSER"
export JDBC_PASSWORD="MYPASS"
On a developer's machine those four point at a test database and are set by hand. Anywhere shared, they come from the same credential store your other applications use rather than from a file in the repository.
Your team gets two places to run one program: an in-memory copy while the code is changing, with data they can reload at will, and your Db2 for i when they want real volumes. The same arrangement is how a JUnit suite tests RPG on a build server with no partition in the pipeline.
The Error Comes Back Where You Typed It
Misspell a variable and the compile says so, with the line and the column:
[ERROR] ARINQUIRY.rpgle:168:19 — TRN2135: Undefined variable 'wDuDate'
The same diagnostics run in the editor as you type, through a language server that installs beside the compiler, so an undeclared field is underlined before you save. A copy member you have open is read from the editor rather than from disk, which means adding a field to it clears the errors in every program that includes it before anything is written.
Start With One Program
Nothing has to move for you to try this. Put one program in a directory with its display file and compile it. Copy members and anything it CALLs come along the same way, a directory at a time. Neither the source nor the green screen changes, and the copy on the partition keeps running for the people who use it every day.
The object you ship still comes off the partition, compiled by IBM's compiler, the way your auditors expect; every compile before that one happens on the developer's machine. A new hire can read your code and run it against a throwaway copy of the data on their first day, with no profile and no library list. Pick the program you are already dreading a change to, and start there.
Want RPG development off the partition?
Start a Conversation