Split construct method by models. Part2.
Last time we tried to resolve the problem with separate construct method by model in one layer using new future in ax delegate and event handler.At this article we will try to resolve the same problem using another approach.
It was first time introduced in Unit testing (source Classes\SysTestCase\testMethods + Classes\SysTest\invoke - try to find methods in object by specific mask), and now in AX 2012 we can find very similar method using name conversational in financial dimension (\Classes\DimensionEnabledType\getSystemDefinedDimensionsServer - try to find Views by name consist of specific mask). Lets try to use it.
From previous topic we have next conditions
- TestBaseClass - in model A01
- TestBaseClass01_Model01 in model A01
- TestBaseClass02_Model02 in model A02
in TestBaseClass (model A01) we create new static method constructFromCode()
public static TestBaseClass constructFromCode(SalesTable _salesTable) { #define.codeConstructor('codeConstructor') TestBaseClass ret; SysDictClass sysDictClass = new SysDictClass(classNum(TestBaseClass)) ; DictMethod method = null; Set methods; SetEnumerator se; Set orderedSet = new Set(Types::String); ExecutePermission executePermission; ; // source Classes\SysTestCase\testMethods methods = sysDictClass.methods(false, true, false); se = methods.getEnumerator(); while (se.moveNext()) { method = se.current(); if (method && method.accessSpecifier() == AccessSpecifier::public && method.returnType() != Types::void && method.parameterCnt() == 1) { if (strStartsWith(method.name(), #codeConstructor)) { orderedSet.add(method.name()); } } // if methods } // while // part 2 - split init call // source \Classes\SysTest\invoke executePermission = new ExecutePermission(); executePermission.assert(); se = orderedSet.getEnumerator(); while (se.moveNext()) { // part 2.1 call methods ret = sysDictClass.callStatic(se.current(), _salesTable); if (ret) break; } CodeAccessPermission::revertAssert(); // init default value if (!ret) { ret = new TestBaseClass(); } ret.parmSalesTable(_salesTable); return ret; }next we need to create 2 additional methods in TestBaseClass
codeConstructorClass01_M01 in A01 model
public static TestBaseClass codeConstructorClass01_M01(SalesTable _salesTable) { TestBaseClass01_Model01 testBaseClass01_Model01 = TestBaseClass01_Model01::construct(); if (testBaseClass01_Model01.findDetermination(_salesTable)) return testBaseClass01_Model01; return null; }and codeConstructorClass02_M02 in A02 model
public static TestBaseClass codeConstructorClass02_M03(SalesTable _salesTable) { TestBaseClass02_Model02 testBaseClass02_Model02 = TestBaseClass02_Model02::construct(); if (testBaseClass02_Model02.findDetermination(_salesTable)) return testBaseClass02_Model02; return null; }let's create and run a job to check our implementation
static void TestBaseClass2(Args _args) { SalesTable salesTable; // cursor TestBaseClass baseClass;
setPrefix("SalesInfo2"); while select salesTable { baseClass = TestBaseClass::constructFromCode(salesTable); baseClass.showInfo(); } info("done"); }and results are
Results
Summary.
We can use various solutions to make construct method independent from models and layers.
Комментариев нет:
Отправить комментарий