martedì 13 novembre 2012

AX 2009 - Number Sequence, premessa e sviluppo modulo custom

Le sequenza numerica è uno strumento molto utilizzato in quanto permette la creazione automatica di valori alfanumerici, sequenziali ed unici per specifici campi, ogni volta che quest'ultimi vengono inizializzati.

È possibile specificare la continuità o meno nelle sequenze generate. È anche possibile specificare il formato del numero definendone il formato (vedi "loadModule").

Se vogliamo dare vita ad una NumberSequence completamente custom, la prima cosa da creare e definire è l'Extended Data Type per tale sequenza, definendo il tipo (stringa), lunghezza e label. Consiglio anche la creazione di un nuovo enumerato di tipo "NumberSeqModule" (es. ExampleEnum) .

La classe di riferimento per le sequenze numeriche è la NumberSequenceReference, ed essa è estesa dalle varie sottoclassi che rappresentano i vari moduli (NumberSequenceReference_Customer, NumberSequenceReference_Ledger ecc. ecc.).

Come secondo passo, per la creazione di un modulo custom, è quindi necessario definire una classe (NumberSequenceReference_Custom) che estenda quella di riferimento e contenga i metodi in override "loadModule" e "numberSeqModule".

  Class NumberSeqReference_Custom extends NumberSeqReference   
  {   
  }   

Nel primo si specificano le caratteristiche della sequenza, il secondo deve restituire l'enumerato NumberSeqModule creato in precedenza.

  protected void loadModule()   
  {   
   NumberSequenceReference numRef;   
   ;    
   numRef.DataTypeId       = typeId2ExtendedTypeId(typeid(EDTCreato));   
   numRef.ReferenceHelp     = "Etichetta di help";   
   numRef.WizardContinuous    = true;  
   numRef.WizardManual      = NoYes::No;   
   numRef.WizardAllowChangeDown = NoYes::No;   
   numRef.WizardAllowChangeUp  = NoYes::No;  
   numRef.wizardHighest     = 99999999;   
   numRef.SortField       = 1;   
   this.create(numRef);   
  }   

 public static NumberSeqModule numberSeqModule()  
 {  
   return NumberSeqModule::ExampleEnum;  
 }  

Inoltre,bisogna modificare i metodi construct() e moduleList() nella classe NumberSeqReference stessa per aggiungere i riferimenti alla nuova classe-modulo creata.


  static public container moduleList()    
  {    
   container moduleList;    
   ;    
   moduleList += NumberSeqReference_Bank::numberSeqModule();    
   moduleList += NumberSeqReference_BOM::numberSeqModule();    
   moduleList += NumberSeqReference_Customer::numberSeqModule();    
   moduleList += NumberSeqReference_Document::numberSeqModule();    
   moduleList += NumberSeqReference_ForeignTrade::numberSeqModule();    
   moduleList += NumberSeqReference_General::numberSeqModule();    
   moduleList += NumberSeqReference_Inventory::numberSeqModule();    
   moduleList += NumberSeqReference_Ledger::numberSeqModule();    
   moduleList += NumberSeqReference_Location::numberSeqModule();    
   moduleList += NumberSeqReference_MasterPlanning::numberSeqModule();    
   moduleList += NumberSeqReference_Production::numberSeqModule();    
   moduleList += NumberSeqReference_Project::numberSeqModule();    
   moduleList += NumberSeqReference_PurchaseOrder::numberSeqModule();    
   moduleList += NumberSeqReference_Route::numberSeqModule();    
   moduleList += NumberSeqReference_SalesOrder::numberSeqModule();    
   moduleList += NumberSeqReference_Tax::numberSeqModule();    
   moduleList += NumberSeqReference_Vendor::numberSeqModule();    
   moduleList += NumberSeqReference_Internet::numberSeqModule();    
   moduleList += NumberSeqReference_Asset::numberSeqModule();   
   //Riferimento alla nostra classe-modulo    
   moduleList += NumberSeqReference_Custom::numberSeqModule();  
   return moduleList;   
  }   

 public static numberSeqReference construct(NumberSeqModule _module)   
  {   
   switch (_module)   
   {   
    case (NumberSeqReference_Ledger::numberSeqModule())   : return new NumberSeqReference_Ledger(_module);   
    case (NumberSeqReference_Tax::numberSeqModule())   : return new NumberSeqReference_Tax(_module);   
    case (NumberSeqReference_Bank::numberSeqModule())   : return new NumberSeqReference_Bank(_module);   
    case (NumberSeqReference_SalesOrder::numberSeqModule())  : return new NumberSeqReference_SalesOrder(_module);   
    case (NumberSeqReference_ForeignTrade::numberSeqModule()) : return new NumberSeqReference_ForeignTrade(_module);   
    case (NumberSeqReference_Customer::numberSeqModule())  : return new NumberSeqReference_Customer(_module);   
    case (NumberSeqReference_PurchaseOrder::numberSeqModule()) : return new NumberSeqReference_PurchaseOrder(_module);   
    case (NumberSeqReference_Vendor::numberSeqModule())   : return new NumberSeqReference_Vendor(_module);   
    case (NumberSeqReference_Inventory::numberSeqModule())  : return new NumberSeqReference_Inventory(_module);   
    case (NumberSeqReference_BOM::numberSeqModule())   : return new NumberSeqReference_BOM(_module);   
    case (NumberSeqReference_Route::numberSeqModule())   : return new NumberSeqReference_Route(_module);   
    case (NumberSeqReference_Production::numberSeqModule())  : return new NumberSeqReference_Production(_module);   
    case (NumberSeqReference_MasterPlanning::numberSeqModule()) : return new NumberSeqReference_MasterPlanning(_module);   
    case (NumberSeqReference_Project::numberSeqModule())  : return new NumberSeqReference_Project(_module);   
    case (NumberSeqReference_Location::numberSeqModule())  : return new NumberSeqReference_Location(_module);   
    case (NumberSeqReference_Document::numberSeqModule())  : return new NumberSeqReference_Document(_module);   
    case (NumberSeqReference_General::numberSeqModule())  : return new NumberSeqReference_General(_module);   
    case (NumberSeqReference_Internet::numberSeqModule())  : return new NumberSeqReference_Internet(_module);   
    case (NumberSeqReference_Asset::numberSeqModule())   : return new NumberSeqReference_Asset(_module);   
    // Riferimento alla nostra classe-modulo  
    case (NumberSeqReference_Custom::numberSeqModule())     : return new NumberSeqReference_Custom(_module);   
  }   
   throw error(strFmt("@SYS53742"));   
  }  

Ora è necessario parametrizzare la NumberSequence e richiamarla quando occorre.

Innanzi tutto occorre creare una tabella parametrica e relativo form.
E' necessario poi definire all'interno della tabella i metodi numberSeqModule() e numberSeqReference():

 client server static NumberSeqModule numberSeqModule()  
 {  
   return NumberSeqReference_Custom::numberSeqModule();  
 }  

 client server static NumberSeqReference numberSeqReference()  
 {  
   return NumberSeqReference::construct(NumberSeqReference_Custom::numberSeqModule());  
 }  

Nel form, altresì, vanno inseriti come datasource sia la nuova tabella parametrica che la tabella NumberSequenceReference.
Ed inoltre:
- i metodi numberSeqPreInit(), numberSeqPostInit();
- il metodo executeQuery nel datasource NumberSequenceReference.

Dopo di che nel nostro form custom, potremo inserire i nostri riferimenti alla sequence creata, dopo aver definito codice, nome, minimo, massimo, formato ecc. nella tabella NumberSequenceTable (quest'ultima procedura si puo eseguire anche tramite wizard in Basic -> Setup -> NumberSequences -> Number Sequences).

Infine occorrerà solamente "staccare" di volta in volta la sequence. Manualmente si può fare così:

 ...    
   ExtendedTypeId id = TypeID2ExtendedTypeId(TypeId(EDTCreato));  
   NumberSeq num = NumberSeq::newGetNum(NumberSequenceReference::find(id));  
   str  sequence;  
   ;  
   num.used(); // segnalo la sequence come "in uso"
   sequence = num.num();  
 ...  

Nessun commento:

Posta un commento