Developer ToolsFree generatorPDF, Excel, Word exportBaan IV / Infor LNAll Infor LN and Baan tools

Infor LN AFS (stpapi) Session Automation Script Generator

The Application Function Server (AFS) runs a standard Baan or LN 4GL session without its form, so a program can insert, update and delete records with all of the session's own checks. This generator writes the stpapi calls in the order Infor documents, with error recovery and session cleanup.

Fill in

A 4GL session code, e.g. tcmcs0145m000 (Areas, table tcmcs045).

Generated code
Download:

Header

|******************************************************************************
|* AFS functions driving session tcmcs0145m000
|* Values are passed as strings: use str$() for numbers, etol() for enums
|******************************************************************************
#pragma used dll ottstpapihand

Insert

function extern long afs.area.insert(ref string o.mess())
{
	long	retval
	string	recover.msg(500)

	stpapi.put.field("tcmcs0145m000", "tcmcs045.creg", "EU1")
	stpapi.put.field("tcmcs0145m000", "tcmcs045.dsca", "Europe region 1")

	retval = stpapi.insert("tcmcs0145m000", true, o.mess)
	if not retval then
		| ends the update mode of the session after an error
		retval = stpapi.recover("tcmcs0145m000", recover.msg)
	endif

	stpapi.end.session("tcmcs0145m000")
	return(isspace(o.mess))
}

Update

function extern long afs.area.update(ref string o.mess())
{
	long	retval
	string	recover.msg(500)

	stpapi.put.field("tcmcs0145m000", "tcmcs045.creg", "EU1")
	retval = stpapi.find("tcmcs0145m000", o.mess)
	if retval <> 1 then
		| 0 = not found or error, 2 = a different record was found
		stpapi.end.session("tcmcs0145m000")
		return(false)
	endif

	stpapi.put.field("tcmcs0145m000", "tcmcs045.dsca", "Europe region 1")
	retval = stpapi.update("tcmcs0145m000", true, o.mess)
	if not retval then
		retval = stpapi.recover("tcmcs0145m000", recover.msg)
	endif

	stpapi.end.session("tcmcs0145m000")
	return(isspace(o.mess))
}

Delete

function extern long afs.area.delete(ref string o.mess())
{
	long	retval
	string	recover.msg(500)

	stpapi.put.field("tcmcs0145m000", "tcmcs045.creg", "EU1")
	retval = stpapi.find("tcmcs0145m000", o.mess)
	if retval <> 1 then
		stpapi.end.session("tcmcs0145m000")
		return(false)
	endif

	| do.save must be true for delete
	retval = stpapi.delete("tcmcs0145m000", true, o.mess)
	if not retval then
		retval = stpapi.recover("tcmcs0145m000", recover.msg)
	endif

	stpapi.end.session("tcmcs0145m000")
	return(isspace(o.mess))
}

Signatures follow the Infor Integration 6.2 Developer's Guide for Application Function Server: stpapi.put.field(session, field, value), stpapi.find(session, err) returning 0, 1 or 2, stpapi.insert / stpapi.update / stpapi.delete(session, do.save, err) returning 1 on success, stpapi.recover(session, err) and stpapi.end.session(session). Compile with #pragma used dll ottstpapihand or link ottstpapihand. Multi-occurrence and main sessions with a separate detail session (such as sales orders) need stpapi.synchronize.dialog and stpapi.change.view calls; check the guide and the session's own AFS DLL before driving them.

Move an AFS program to BODs or REST

Send us an existing AFS program and your LN version, and we will outline the BOD or REST replacement and the risks.

Optional. The tool and every export work without this. No spam.

Was this tool useful?

How to use it

Enter the session code, the key field and value, and one data field and value, both as table.field names exactly as the session form uses them. The output has one function each for insert, update and delete. Add more stpapi.put.field lines for extra fields, in the order a user would enter them, because AFS runs the session's field logic and a field can depend on one entered earlier. Put the code in a library or 3GL script in your own VRC and call the function from your integration program. Every function returns true when the action succeeded and hands back the error text in o.mess when it did not.

How AFS works

The first stpapi call for a session starts it and creates the field buffer; before.program and the main table and form before sections run at that point. stpapi.put.field only fills the buffer. stpapi.insert then runs the add choice, the field loop with each field's checks and the session's DAL check.property hooks, and with do.save set to true also the update.db choice. If anything fails, the function returns 0 with the message, and stpapi.recover must be called to leave update mode before any other call. stpapi.end.session ends the session and runs its end.program choice. For update and delete, stpapi.find with the key fields makes the record current first.

  • AFS library naming: parent session with f after the module, e.g. tcmcsf0145m000
  • stpapi.find returns 0 (not found or error), 1 (found) or 2 (a different record found)
  • stpapi.delete only supports do.save = true

Worked example

With the defaults the generator drives Areas (tcmcs0145m000), a simple single-occurrence session on table tcmcs045 with the area code creg and description dsca. The insert function puts EU1 and the description, inserts with do.save true and ends the session. The update function puts the key, finds the record, checks for return value 1, changes the description and updates. If you run the insert twice, the second call returns false with the session's duplicate key message in o.mess, which is exactly what a user would see.

Version notes and alternatives

AFS follows UI logic, so a session redesign in a new feature pack can break an AFS program even though the table did not change. Sessions with question boxes need answers set in advance through the AFS functions for questions, and sessions with a main and detail form need dialog synchronization. Infor community answers report that calling standard sessions through AFS is not available in multi-tenant LN Cloud. For new integrations, BODs through ION or the LN REST APIs are the paths Infor develops further; keep AFS for existing on-prem programs and quick internal automation.

Frequently Asked Questions

How do I start an LN session from a program?

With AFS you do not start it explicitly: the first stpapi call that names the session, usually stpapi.put.field, starts it in the background and creates the field buffer. End it with stpapi.end.session when you are done, otherwise the session instance stays active for later calls.

Why does stpapi.insert fail when the same data works in the session?

Usually the field order or a missing field. AFS runs the field checks in the session's order, so a field validated against an earlier one fails if that one is not put first. Questions the session asks also need preset answers. Read the message in the error string and compare with a manual entry.

Do I have to call stpapi.recover after an error?

Yes. After an insert, update or delete fails, call stpapi.recover before any other stpapi call on that session. Otherwise the session stays in update mode, and the later end.session call can still write the record you meant to reject.

Where can I see which AFS steps a session needs?

Look for an existing AFS DLL for the session (the session name with f after the module) and read its functions, such as the ones Infor generates with ttstpcreatdll. The Infor Developer's Guide for Application Function Server lists every stpapi function.

If you want routine LN updates driven from a plain-English request with a human approving each change, we can build that on your own servers on top of AFS or BODs.

ArchRay builder
Design the on-prem AI stack for Infor LN and Baan: model, GPUs, RAG pipeline, guardrails
See memory, speed and cost as you swap parts, then export the diagram. Free, in your browser.
Open the builder

Keep exploring

Free tools

ERP fixes and how-tos

Guides

AI on your ERP

Integrations

Comparisons

Software