ek9_add_method
Inserts the method (signature, a require-guarded stub body and the return) at the construct's canonical member position; answers status, edits[] and summary, a same-signature method as conflicts[] (signature-collision). Records reject named methods.
When to use it
'Add a method to CustomerOrder' is one call with symbol:'CustomerOrder', name, parameters:['code as Integer'], returnType and statements:['rtn: ...'] (the body) - no file, no line, nothing left to fill.
When not to use it
- The member is an OPERATOR (==, <=>, ?, $, …) - use
ek9_add_operator; a CONSTRUCTOR (the type's own name) - useek9_add_constructor. - You want ALL trait methods added at once — use
ek9_implement_methods(batch). - You want a FIELD, not a method — use
ek9_add_field. - The target construct does not exist yet — create it with
ek9_new_constructfirst.
Details
Inserts exactly ONE method per call; a same-signature second call yields status:conflicts (kind 'signature-collision' — rename, change the parameter shape, or add override:true if overriding an inherited method). status:error when the target genus rejects methods (record/program/text/enumeration …) or isAbstract targets a non-abstract class/component. No override-inheritance analysis is performed — a bad override surfaces only on the apply-path verify compile as would-fail.
Arguments
| Argument | Type | Required | What it is |
|---|---|---|---|
emptyBody | boolean | When true, generate ONLY the signature (declaration + parameters + return-with-default) with no placeholder body - no 'require param?' preconditions, no '//AI' lead, for a body you then supply with ek9_insert_statements. NOTE: EK9 flags unused parameters, so a shell WITH parameters will would-fail on apply until a body uses them; only the no-parameter-with-return shape compiles standalone. | |
file | string | The EK9 source file - OPTIONAL when symbol is a construct name; required to anchor on a member or a use site. | |
isAbstract | boolean | Add 'as abstract'. Only valid on traits and classes already marked 'as abstract'. | |
name | string | yes | The new method's name (camelCase). |
override | boolean | Add 'override' prefix when overriding a parent or trait method. | |
parameters | array of any | Parameter list, each ONE item as DATA - {name:'code', type:'Integer'} - never a {name} and a {type} as two items, and never with '->' or '<-' in it; the tool writes the arrows and the layout. ('code as Integer' is also accepted.) A malformed item is rejected before anything is rendered. Empty / omitted means a no-arg method. | |
pure | boolean | Add 'as pure' modifier. Default false. | |
returnType | string | Return TYPE only, e.g. 'String', 'List of Integer' - never '<- rtn as String', never a name: the tool writes the '<- rtn as <Type>?' declaration, and the body assigns 'rtn: <expr>'. Omitted means no return. | |
statements | array of string | The body, one statement or one block per entry (assign 'rtn: <value>' on every path when there is a return): the method is complete in this call - no stub, no second ek9_insert_statements call. Parsed alone first; a problem names the entry and its fix. | |
symbol | string | yes | The class, trait, component or service the method is added to - a bare name ('Order') finds its file workspace-wide; 'mod::Order' when the name is declared in two modules. |
visibility | string: public | private | protected | The method's access. Default public. |
It also takes the arguments every tool takes.
Recorded calls
Real calls, recorded against small projects and checked on every build - a changed answer fails it. 3 of the 9 recorded are shown.
One of two trait members is progress
Request
{
"name" : "area",
"override" : true,
"pure" : true,
"returnType" : "Float",
"statements" : [ "rtn: side * side" ],
"symbol" : "Square"
}
Response
{
"conflicts" : [ ],
"edits" : [ {
"after" : "\n override area() as pure\n <- rtn as Float?\n rtn: side * side",
"endLine" : 23,
"file" : "task.ek9",
"startLine" : 23,
"type" : "insert"
} ],
"meta" : {
"serverMs" : "<timing>"
},
"resolvedPath" : "<workspace-root>/task.ek9",
"risk" : {
"crossesModuleBoundary" : false,
"estimatedSeverity" : "trivial",
"fileCount" : 1,
"lineCount" : 1,
"touchesPublicApi" : false,
"touchesTests" : false
},
"status" : "applied",
"summary" : "Added method 'area' to Square",
"workspaceHash" : "<workspace-hash>",
...
Cut short here: 3 more lines. The whole recorded call.
Return type with question mark
Request
{
"name" : "sayCount",
"parameters" : [ {
"name" : "count",
"type" : "Integer"
} ],
"pure" : true,
"returnType" : "String?",
"statements" : [ "rtn: count == 0 <- \"empty\" : count == 1 <- \"one item\" : $count + \" items\"" ],
"symbol" : "Basket",
"verbosity" : "summary"
}
Response
{
"conflicts" : [ ],
"corrected" : [ "returnType 'String?' read as 'String' - the return is declared '<- rtn as String?' already" ],
"edits" : [ {
"endLine" : 18,
"file" : "task.ek9",
"startLine" : 18,
"type" : "insert"
} ],
"meta" : {
"serverMs" : "<timing>"
},
"resolvedPath" : "<workspace-root>/task.ek9",
"risk" : {
"crossesModuleBoundary" : false,
"estimatedSeverity" : "trivial",
"fileCount" : 1,
"lineCount" : 1,
"touchesPublicApi" : false,
"touchesTests" : false
},
"status" : "applied",
"summary" : "Added method 'sayCount' to Basket",
"workspaceHash" : "<workspace-hash>",
...
Cut short here: 3 more lines. The whole recorded call.
Add no arg pure method apply
Request
{
"constructName" : "Greeter",
"file" : "Greeter.ek9",
"name" : "farewell",
"pure" : true
}
Response
{
"conflicts" : [ ],
"edits" : [ {
"after" : "\n farewell() as pure\n ready <- true\n require ready?\n //AI: Implement farewell",
"endLine" : 10,
"file" : "Greeter.ek9",
"startLine" : 10,
"type" : "insert"
} ],
"meta" : {
"serverMs" : "<timing>"
},
"resolvedPath" : "<workspace-root>/Greeter.ek9",
"risk" : {
"crossesModuleBoundary" : false,
"estimatedSeverity" : "trivial",
"fileCount" : 1,
"lineCount" : 1,
"touchesPublicApi" : false,
"touchesTests" : false
},
"status" : "applied",
"summary" : "Added method 'farewell' to Greeter",
"workspaceHash" : "<workspace-hash>",
...
Cut short here: 3 more lines. The whole recorded call.
See also
- Show me in the IDE: Chapter 16: a class, built
- Show me in the IDE: Chapter 17: an abstract type and its subtypes, built
- Show me in the IDE: Chapter 18: traits and delegation, built
- Show me in the IDE: Chapter 19: a component, built
- Show me in the IDE: Chapter 23: the game, built and played
- Fixes E05260