Důležité:
POZOR! Od verze 2.0.2019.0900 se zavádí funkcionalita Kmenové karty výrobních čísel (VČ):

  • Aktualizační skript z verzí nižších než 2.0.2019.0900 zajišťuje generování kmenových karet výrobních čísel do nové tabulky TabVyrCK dle nejdříve založeného stavu VČ v tabulce TabVyrCS.
  • Na databázích, kde se ve velkém rozsahu zadávají VČ (tj. s počty stavů VČ řádově ve stovkách tisíc), může aktualizace trvat déle. Počítejte s tím při plánování updatu z verzí nižších než 2.0.2019.0900.
  • Podrobnosti k funkcionalitě naleznete v Poradně.

Helios Orange Core

Z Asseco Solutions
Přejít na: navigace, hledání
groups: lcs ; lcseditor ; partner (ro) ; translator (ro) ; customer (ro) ; anonymous (ro) ;


Obsah

ÚVOD

Tento dokument popisuje vytváření pluginů pro ekonomický systém Helios Orange s použitím tzv. „jádra pluginu“. Dané jádro je sada unit pro programování ve vývojovém prostředí Delphi XE7. Nelze ho použít pro programování pluginu např. v programovacím jazyce Visual Basic.

Pomocí jádra lze definovat vlastní tabulky, definované přehledy, definované vazby, externí akce, externí atributy (uživatelské i editovatelné), externí triggery i uložené procedury. Dále jádro podporuje automatickou kontrolu konzistence všech výše uvedených objektů s generováním změnových skriptů. Také podporuje verzování pluginu s možností programátorem definovaných změnových skriptů při přechodu na vyšší verzi pluginu.

SEZNAM UNIT JÁDRA

Jednotlivé unity jádra je možno rozdělit na 2 skupiny – systémové unity (editor, akce, instalace…) a unity definiční (definice tabulek, přehledů, externích atributů…). Systémové unity jsou společné pro všechny pluginy, unity definiční jsou závislé na konkrétním pluginu.

Systémové unity se dále dělí na „lokální“ a „společné“. Jestliže na vývoji pluginu pracuje více vývojářů a unity jsou umístěny někde ve společném úložišti (např. na síti), je třeba mít unity označené jako lokální v adresáři projektu pluginu na lokálním počítači a nemít ve společném adresáři na síti. Je to proto, aby překladač přeložil změny ve vložených souborech typu include (soubory vložené pomocí direktivy $I). Obecně platí, že překladač přeloží vložený soubor z adresáře, kde se nachází unita, ve které je vložen!!! Tudíž by se mohlo stát, že překlad nebude reflektovat změny provedené v include souboru na lokálním počítači, ale bude brát soubor ze sítě.

Systémové unity

Lokální unity

plgType.pas

Unita, která v sobě soustředí jednotlivé include pro definici verze, tabulek, soudečků, přehledů, hlášek a ostatních typů a konstant:

  • plgVerze.INC..............verze pluginu
  • plgTypeTabulka.INC..........definice typu TplgTabulka
  • plgTypeSoudky.INC..........definice typu TplgSoudek
  • plgTypeBrowse.INC..........definice typu TplgBrowse
  • plgTypeTxtJadro.INC..........definice "typu" TplgTxt – hlášky jádra
  • plgTypeTxtEx.INC..........definice "typu" TplgTxt – ostatní hlášky
  • plgTypeJadro.INC..........základní typy a konstanty jádra
  • plgTypeZbytek.INC..........všechny ostatní typy a konstanty


plgHlasky.pas

Unita v sobě zapouzdřuje include pro definici hlášek:

  • plgHlaskyJadro.INC..........definice hlášek jádra
  • plgHlaskyEx.INC..........definice ostatních hlášek

Společné unity

plgAbout.pas, plgAbout.dfm

Zobrazení základních informací o daném pluginu (název, verze, umístění, minimální podporované verze systému Helios Orange a SQL Serveru apod.). Také zobrazuje technický popis.


plgAkce.pas

Obecný předek pro akce nad přehledy. Nazývá se též akční modul.


plgAlter.pas, plgAlter.dfm

Okno zobrazující změny, které budou provedeny v databázi.


plgAutoImp.pas, plgAutoImp.dfm

Zde se provádí test a případný automatický import definovaných formulářů, filtrů a opisů.


plgDmGlob.pas, plgDmGlob.dfm

Globální objekt DataModuleGlobPLG, který obsahuje seznam ikonek Heliosu v rozměrech 16x16, 20x20 a 32x32 a jejich indexy. Využívá unitu sqIcons pro načtení ikonek z Helios.EXE. Indexy ikonek pro nastavení vlastnosti ImageIndex jsou v proměnné Idx.

Příklad Ikonka pro tisk má index DataModuleGlobPLG.Idx.iiPrint


plgEdit.pas, plgEdit.dfm

Obecný předek DB editoru.


plgFrame.pas, plgFrame.dfm

Obecný předek pro „frejmy“. Automaticky spolupracuje s editorem. Lze použít pouze na formuláři poděděném z plgEdit.


plgFDotah.pas, plgFDotah.dfm

Frejm pro automatické dotažení a kontrolu jednoho klíčového atributu – např. číslo zakázky, číslo nákladového okruhu apod. Děděno z plgFrame.


plgFDotah2.pas, plgFDotah2.dfm

Frejm pro automatické dotažení a kontrolu jednoho klíčového atributu a jednoho upřesňujícího atributu. Např. číslo a název skladu. Děděno z plgFDotah.


plgFDotah3.pas, plgFDotah3.dfm

Frejm pro automatické dotažení a kontrolu jednoho klíčového atributu a dvou upřesňujících atributů. Např. číslo zaměstnance společně s jeho příjmením a jménem. Děděno z plgFDotah2.


plgFDotah4.pas, plgFDotah4.dfm

Frejm pro automatické dotažení a kontrolu jednoho klíčového atributu a tří upřesňujících atributů. Děděno z plgFDotah3.


plgFCisOrg.pas, plgFCisOrg.dfm

Speciální frejm pro dotažení organizace vázané přes číslo organizace. Děděno z plgFDotah.


plgFCisOrgID.pas, plgFCisOrgID.dfm

Speciální frejm pro dotažení organizace vázané přes ID. Děděno z plgFCisOrg.


plgFGrid.pas, plgFGrid.dfm

Speciální frejm pro zobrazení přehledu na editoru. Děděno z plgFrame.


plgForm.pas, plgForm.dfm

Obecný předek pro nedatabázová okna, tedy okna, která nejsou děděna z plgEdit.


plgHlaskyJadro.inc, plgTypeTxtJadro.inc

Definice hlášek používaných v jádře a jejich identifikátorů.


plgInfoAkce.pas, plgInfoAkce.dfm

Formulář se zobrazením informace o akci, která trvá delší dobu.


plgInstalace.pas, plgInstalace.dfm

Unita odpovědná za kontrolu konzistence datových struktur pluginu a případné změny v databázi.


plgKonfigBase.pas

Předek pro definici systémových proměnných pluginu (GUID, systémový název, veřejný název apod.).


plgLadit.pas

Kontroly správného zadání definic (tabulek, přehledů, atributů apod.), duplicitních GUID atd. Kontroly lze vypnout pomocí IFDEF BezLadit (doporučeno pouze pro distribuční verzi pluginu!!).


plgMail.pas

Objekty pro poslání elektronické pošty pomocí programu HeMail, popř. přes CDO rozhraní.


plgMain.pas

Podpůrné procedury a funkce pro práci s definicemi datových struktur (tabulky, přehledy), pro překlad hlášek, pro inicializaci pluginu apod.


plgObjekt.pas Objekt TPluginObject – základní vstupní bod pluginu. Zde se provádí kontroly verze, inicializace pluginu a volání správné externí akce.


plgProgressBar.pas, plgProgressBar.dfm

Formulář pro zobrazení průběhu s možností přerušení.


plgQuery.pas

Zapouzdřuje memory dataset z unity dxmdaset pro editor.


dxmdaset.pas, cxVer.inc

Developer Express Visual Component Library - ExpressMemData - Developer Express Inc.


plgSpravce.pas

Seznam aktivních volání pluginu – jedná se o seznam rozhraní IHelios. Lze využít pro dohledání vlastníka a jeho editoru či datového modulu.


plgTypeJadro.inc

Základní datové typy a konstanty použité v jádře.


plgUta.pas

Znovupoužitelné definice atributů, jakési vzory.

Definiční unity

plgBrowse.pas, plgTypeBrowse.inc

Seznam definic přehledů a jejich identifikátorů.


plgExtAkce.pas

Definice externích akcí pro standardní přehledy Helios Orange.


plgExtAttr.pas

Definice externích atributů.


plgExtTrigger.pas

Definice externích triggerů = triggery pro existující tabulky Helios Orange.


plgHlaskyEx.inc, plgTypeTxtEx.inc

Definice hlášek používaných v pluginu a jejich identifikátorů.


plgKonfig.pas

Obsahuje nastavení důležitých konstant závislých na daném pluginu. Zde je třeba definovat GUID pluginu a jeho systémové názvy. Blíže viz Nastavení základních konstant pluginu. Dále je zde možnost vlastní inicializace pluginu – např. přednastavení globálních proměnných daného pluginu, kontrola vyžadovaných hodnot apod.


plgSoudky.pas, plgTypeSoudky.inc

Definice soudečků používaných pluginem.


plgTable.pas, plgTypeTabulka.inc

Seznam tabulek a jejich identifikátorů.


plgTypeZbytek.inc

Tvůrce pluginu zde může umístit globální konstanty a proměnné daného pluginu.


plgUProc.pas

Definice uložených procedur.


plgUtaDef.inc, plgTypeUta.inc

Možnost definice vlastních vzorů pro atributy.


plgVazby.pas

Definice vazeb mezi přehledy pluginu nebo tabulkami Helios Orange.


plgVerze.inc

Aktuální verze pluginu.


plgZmeny.pas

Definice změnových skriptů. Zde se definují skripty pro změny v databázi, které nelze provést automatickou detekcí změn v plgInstalace (např. změna názvu atributu, předvyplnění nového atributu podle různých kritérií apod.).

ZAČÍNÁME NOVÝ PLUGIN

Základní nastavení

Pro vytvoření základní kompilovatelné kostry pluginu stačí 3 kroky:

  • Vytvořit nový projekt
  • Vyplnit plgKonfig.pas
  • Nastavit verzi plgVerze.inc

Nastavení projektu v Delphi

Projektový soubor vypadá zhruba takto (cesta na soubory samozřejmě záleží na konkrétním umístění):

library Plugin<MojeJmeno>;
 
uses
plgObjekt,
plgEdit in 'Lib\plgEdit.pas' {frmPlgEditor},
plgForm in 'Lib\plgForm.pas' {frmPlgPredek},
plgFrame in 'Lib\plgFrame.pas' {FramePLG: TFrame},
plgFGrid in 'Lib\plgFGrid.pas' {FramePLGGrid: TFrame},
plgFDotah in 'Lib\plgFDotah.pas' {FramePLGDotah: TFrame},
plgFDotah2 in 'Lib\plgFDotah2.pas' {FramePLGDotah2: TFrame},
plgFDotah3 in 'Lib\plgFDotah3.pas' {FramePLGDotah3: TFrame},
plgFDotah4 in 'Lib\plgFDotah4.pas' {FramePLGDotah4: TFrame},
plgFCisOrg in 'Lib\plgFCisOrg.pas' {FramePLGCisOrg: TFrame},
plgFCisOrgID in 'lib\plgFCisOrgID.pas' {FramePLGCisOrgID: TFrame};
 
{$R *.RES}
 
begin
end.

Komentář k uses

Unity plgEdit a plgForm jsou nutné, jestliže chcete vytvářet editory děděním. Pokud by nebyly v uses uvedeny (a to i s cestou a komentářem!), tak by nešlo vytvořit potomka přes Delphi – File – New. Unity obsahující frejmy je třeba uvést v případě, že je chcete používat na DB editorech (potomci editoru z plgEdit).


Nastavení projektu

Jestliže chcete debugovat plugin, je třeba zaškrtnout ve vlastnostech projektu na záložce Linker v sekci EXE and DLL options check box Include remote debug symbols. Dále je vhodné v sekci Memory sizes nastavit Image base na $70000000.

Nastavení systémových konstant pluginu

Nastavení systémových konstant pluginu se děje v unitě plgKonfig.pas. Co a jak je nutné nastavit je popsáno v komentářích v dané unitě.

POZOR!! Jazykové mutace pro názvy soudečků, přehledů a atributů se uplatní pouze při instalaci pluginu. Jinými slovy – pokud je třeba, aby přehledy byly v angličtině, je nutné nejprve přepnout jazyk Helios Orange do angličtiny a poté spustit instalaci pluginu. V případě vyžadované změny jazyka je třeba toto provést znovu. Pokud ke stejnému Helios Orange přistupuje více uživatelů s různě nastaveným jazykem, musí se dohodnout na jazyku pluginu. Jediné co respektuje nastavení jazyka nezávisle na jazyku instalace jsou popisky v editorech a chybová hlášení.

Po nastavení konstant lze projekt kompilovat a plugin instalovat.

Verzování pluginu

V pluginu se vyskytuje několik proměnných obsahujících verzi.

  1. Verze pluginu.......... definuje se v plgVerze.inc
  2. Minimální verze Heliosu vyžadovaná pluginem..........definuje se v plgKonfig.pas
  3. Verze jádra.......... je uložena v plgTypeJadro.inc
  4. Minimální verze Heliosu vyžadovaná jádrem..........je uložena v plgTypeJadro.inc
Upozornění Vývojář pluginu může měnit pouze první dvě verze, tedy verze týkající se pluginu!!!

Verze se zadává v hexa tvaru a má tento formát: $<major:2><minor:2><rok:4><měsíc:2><den:2>.

Např. $010020060809.

  • Nijak se nekontroluje, zda-li se opravdu jedná o platné datum, takže je klidně možné zadat i 99999999, rozhodně se to ale nedoporučuje kvůli přehlednosti.
  • Major verze nesmí být nula, musí být alespoň 1! Doporučujeme nechat 0100 a měnit pouze část obsahující „datum“ (umožní to lépe určit, kdy byla vytvořena distribuce daného pluginu).
  • Při změně verze je třeba dbát na to, aby následující byla číselně výše než předchozí!

Názvové a programovací konvence

Kvůli čitelnosti, přehlednosti a zabránění kolizí mezi pluginy různých programátorů, popř. výrobců, jsou navržena následující pravidla. Níže používané označení <identifikátor> je co nejjednoznačnější označení daného pluginu – tento identifikátor se zadává v konfiguraci pluginu do proměnné FPluginIdentifikator. Jádro pak hlídá, zda-li jsou názvy určitých objektů vytvořeny s použitím tohoto identifikátoru. Podrobnosti viz níže. Jedná se o tyto objekty:

  • Tabulky.......... Tab<identifikátor><název>
  • Definované přehledy.......... hvw_<identifikátor><název>, popř. hvw_<GUID_bez_pomlček>
  • Uložené procedury.......... <prefix>_<identifikátor>_<název>
  • Externí atributy.......... _<identifikátor>_<název>

Názvy unit

Názvy unit by měly být vytvářeny následovně: <prefix><identifikátor><název>.<přípona>.

Pro určité typy unit jsou určeny tyto předdefinované prefixy:

  • pdt... unity obsahující definice tabulek ([p]lugin [d]efinice [t]abulky)
  • ped... unity obsahující databázové editory – děděné z plgEdit ([p]lugin [ed]itor)
  • pdm... unity obsahující externí akce ([p]lugin [d]atový [m]odul – vychází z pojmosloví Helios Orange)
  • pfr... unity obsahující nedatabázové editory – děděné z plgForm ([p]lugin [f]o[r]mulář)
  • plg... tento prefix je vyhrazen pro unity jádra, NEPOUŽÍVAT!!

Ostatní unity mohou mít jakýkoliv jiný prefix (např. pom, dlg, xxx apod.).


Každá unita daného pluginu by také měla obsahovat hlavičku se systémovým názvem pluginu (a to včetně definičních unit – u nich hlavně, jelikož mají stejný název u všech pluginů!!).

Příklad Příklad hlavičky:
{ *************************************************************************** }
{ }
{ PluginXXX Moje firma }
{ }
{ *************************************************************************** }

Názvy tabulek a definovaných přehledů

Názvy tabulek a přehledů by měly být vytvářeny takto: <prefix><identifikátor><název>.

<Název> by měl být stejný pro sobě odpovídající tabulku a přehled.

Povinné prefixy

  • Tab... pro tabulky
  • hvw_... pro definované přehledy
Příklad TabMujIdentProdejna a hvw_MujIdentProdejna.

Názvy uložených procedur

Názvy uložených procedur by měly být vytvářeny takto: <prefix>_<identifikátor>_<název>.

Jako <prefix> je vhodné použít např. pp ([p]lugin [p]rocedure), není to ale podmínkou. Rozhodně ale není dobré používat prefix ep ([e]xternal [p]rocedure) a hp ([H]elios [p]rocedure), pokud to není opravdu nutné (např. ep_ExtEd_... pro práva uživatelských externích atributů)!!.

Zapojení pluginu do Helios Orange

Hotový plugin se do Helios Orange zapojí přes přehled Speciální pluginy (Možnosti – Konfigurace / správa systému – Systémové konstanty – nad databází pravá myš – Externí akce – v přehledu externích akcí pravá myš – Speciální pluginy). V daném přehledu se zvolí F2 – Přidat plugin, najde se odpovídající DLL a tlačítko Otevřít. Plugin se zařadí do přehledu a automaticky se spustí jeho instalace. Po instalaci dojde k ukončení Helios Orange. Reinstalace, popř. instalace nové verze pluginu se spouští ve stejném přehledu akcí Instalace. Je možno také zobrazit informace o pluginu pomocí akce O pluginu….

PROGRAMOVÁNÍ PLUGINU

Definice tabulek

Každá tabulka by měla mít svou definici v samostatné unitě se stejným názvem jako tabulka (pouze s jiným prefixem). Např. tabulka TabMojePrvni by měla být v unitě pdtMojePrvni.

Definice tabulky se skládá z definice atributů, omezení, triggerů a dalších informací.

Tabulka

Pravidla pro vytváření názvu tabulky jsou popsány výše.

Atributy

Omezení

Triggery

Definice přehledů

Nedávat do create datového modulu žádné selecty apod., datový modul se vytváří při instalaci.

Definice vazeb

Definice externích akcí

Definice externích atributů

Definice externích triggerů

Definice externích triggerů se provádí v unitě plgExtTrigger. Struktura definice (TplgExterniTrigger) je v unitě plgTypeJadro.inc.

Upozornění POZOR! První položka v seznamu (tedy GDefiniceExtTrigger[0]) musí zůstat nevyplněna!!!


Zde se definují externí triggery pro standardní tabulky Helios Orange. Každá tabulka Helios Orange může mít triggery definované systémem Helios Orange a pak 1 tzv. externí trigger. Jeho název musí splňovat jednoduché pravidlo: et_<JmenoTabulky>. Každý jiný trigger bude systémem Helios Orange při spuštění smazán. POZOR - není jednoznačně určeno pořadí provádění těchto triggerů! Je třeba také dát pozor na rekurzivní volání – pokud budou u tabulky 2 triggery a v obou se bude provádět UPDATE dané tabulky, budou se triggery volat stále dokola!


Při instalaci se definice kontroluje proti databázi. Pokud trigger v DB neexistuje nebo došlo ke změně definice, je automaticky vygenerován změnový skript. Jestliže byla z unity odstraněna definice externího triggeru, která již v DB existuje, instalace toto nezjistí a trigger z DB nesmaže! Ke smazání je třeba využít mechanizmu změnových skriptů.

Příklad Příklad definice externího triggeru:
,(JmenoTabulky  : 'TabCisOrg';
TriggerSkript :
'CREATE TRIGGER et_TabCisOrg ON TabCisOrg FOR INSERT,UPDATE,DELETE'#13+
'AS'#13+
 
'IF @@ROWCOUNT = 0 RETURN'#13+
'SET NOCOUNT ON'#13+
....
)

Definice uložených procedur

Definice uložených procedur se provádí v unitě plgUProc. Struktura definice (TplgUlozenaProcedura) je v unitě plgTypeJadro.inc.

Upozornění POZOR! První položka v seznamu (tedy SeznamUlozenychProcedur[0]) musí zůstat nevyplněna!!!


Vlastní definice každé procedury musí začínat CREATE PROCEDURE dbo.<nazev_podle_pravidel>.

Při instalaci se definice kontroluje proti databázi. Pokud procedura v DB neexistuje nebo došlo ke změně definice, je automaticky vygenerován změnový skript.

Jestliže byla z unity odstraněna definice uložené procedury, která již v DB existuje, instalace toto nezjistí a uloženou proceduru z DB nesmaže! Ke smazání je třeba využít mechanizmu změnových skriptů.

Příklad Příklad začátku uložené procedury:
,(Text:
'CREATE PROCEDURE dbo.pp_PluginXXX_VytvorNovouPolozku'#13+
'@Param1 INT,'#13+
'@Param2 INT'#13+
'AS'#13+
 
'SET NOCOUNT ON'#13+

)

Definice změnových skriptů

Definice změnových skriptů se provádí v unitě plgZmeny. Struktura definice (TplgZmenovySkript) je v unitě plgTypeJadro.inc.

Upozornění POZOR! První položka v seznamu (tedy GZmenoveSkripty[0]) musí zůstat nevyplněna!!!

Každý změnový skript je jednoznačně označen číslem verze, které se porovnává s číslem verze v databázi a podle toho se rozhoduje, zda-li bude spuštěn či nikoliv - pokud je číslo verze změnového skriptu větší než verze v DB, bude spuštěn a verze v DB bude nastavena na verzi skriptu. Změnové skripty se kontrolují a spouští na začátku instalace ještě před kontrolou tabulek, atributů, procedur, vazeb, přehledů a dalších věcí.


Změnové skripty lze využít pro ty změny v DB, které není možné detekovat automatickým instalátorem. Jedná se např. o smazání nepotřebných uložených procedur, externích triggerů, externí atributů apod. Dále je možné použít je pro smazání různých constraints, které by jinak způsobily, že neprojdou automaticky generované změny - smazání defaultů, checků, počítaných atributů apod.


Každý skript by měl být napsán tak, aby šel spustit vícekrát. Měl by obsahovat kontroly na existenci či neexistenci DB objektů, se kterými bude pracovat a používat EXEC (pokud např. ve skriptu vytvářím tabulku, kterou vzápětí plním hodnotami, pak by bez použití EXEC SQL Server vrátil chybové hlášení o neexistujících atributech - skript se překládá jako celek a tabulka v danou chvíli neexistuje).


Příklad Příklady testů

(2. parametr systémové funkce OBJECT_ID() - je to sysobjects.xtype):


existuje tabulka TabXXX ?

IF OBJECT_ID('TabXXX','U')IS NOT NULL ...

existuje sloupec ABC v tabulce TabXXX ?

IF COLUMNPROPERTY(OBJECT_ID('TabXXX','U'),'ABC','AllowsNull')IS NOT NULL ...

existuje default DF__TabXXX__ABC na sloupci ABC v tabulce TabXXX ?

IF OBJECT_ID('DF__TabXXX__ABC','D')IS NOT NULL ...


Změnové skripty jsou při spouštění obaleny BEGIN TRANS .. COMMIT. Z těchto důvodů by se nemělo používat RETURN, jelikož by zůstala neuzavřená transakce a došlo by k chybě. Jestliže je RETURN nutné použít (vše se ale dá napsat tak, aby to nutné nebylo!), tak je třeba použít např. tuto kontrukci:

IF @@TRANCOUNT>0 ROLLBACK  /* nebo COMMIT dle situace */
RETURN

Pokud je kód spouštěn přes EXEC() nebo sp_executesql, tak tam naopak ROLLBACK (COMMIT) být NESMÍ, protože RETURN ukončuje jen daný EXEC(). Úplně nejlepší je RETURNu se ve změnových skriptech zcela vyhnout.


Postup při vytváření nového změnové skriptu:

  1. V unitě plgVerze.INC zvětšit číslo verze.
  2. Nové číslo verze plgVerze.INC zadat do definice změnového skriptu do proměnné PlatiOd.
  3. Napsat vlastní skript.
Příklad Příklad:
(PlatiOd :	$010020051102;
Skript : 'IF COLUMNPROPERTY(OBJECT_ID(''TabMojeXXX'',''U''),''AttrXX'',''AllowsNull'')IS NOT NULL'#13+
'EXEC(''UPDATE TabMojeXXX SET AttrXX = 10 WHERE AttrXX IS NULL'')'
)

Jazykové mutace

Osobní nástroje
Jmenné prostory
Varianty
Akce
Navigace
dokumentace orange
dokumentace easy
společné návody a tipy
interní dokumentace
Nástroje
další nástroje
Tisk/export