Sign in Join
Wiki copytemporary

Executing External Programs/sk: what changed

Revision 2 to 3. Removed lines have a minus sign; added lines have a plus sign.

OldNewLine
1-## Contents
2-
3- * 1 Úvod
4- * 2 SysUtils.ExecuteProcess
5- * 3 TProcess
6- * 3.1 Jednoduchý príklad
7- * 3.2 Vylepšený príklad
8- * 3.3 Čítanie veľkého výstupu
9- * 3.4 Použitie vstupu a výstupu z TProcess
10- * 3.5 Pokyny pre použitie TProcess
11- * 3.6 Príklad komunikácie s procesom aspell
12-
131## Úvod
142
15-Je mnoho spôsobov ako spustiť externé programy. Zameriame sa na jeden z nich.
3+Je mnoho spôsobov ako spustiť externé programy. Zameriame sa na jeden z nich.
164
175## SysUtils.ExecuteProcess
186
19-najjednoduchší spôsob, ak nepotrebujete rúry (_pipes_) alebo žiadne formu ovládania je jednoducho použiť
20-```
21-SysUtils.ExecuteProcess('/full/path/to/binary',['arg1','arg2']);
7+najjednoduchší spôsob, ak nepotrebujete rúry (*pipes*) alebo žiadne formu ovládania je jednoducho použiť
8+
9+``` pascal
10+ SysUtils.ExecuteProcess('/full/path/to/binary',['arg1','arg2']);
2211```
2312
2413## TProcess
2514
26-Môžete použiť TProcess na spustenie externých programov. Výhody tohoto spôsobu sú:
15+Môžete použiť TProcess na spustenie externých programov. Výhody tohoto spôsobu sú:
2716
28- * Nezávislý na platforme
29- * Schopnosť čítať zo stdin a stdout.
17+- Nezávislý na platforme
18+- Schopnosť čítať zo stdin a stdout.
3019
31- **Poznámka** : TProcess nie je terminal/shell! Nemôžete priamo spustiť alebo presmerovať výstup pomocou operátorov ako "|", ">", "<", "&" atď. Možno získať rovnaký výsledok s TProcess pomocou Pascal, príklady nasledujú...
20+
21+**Poznámka**: TProcess nie je terminal/shell! Nemôžete priamo spustiť alebo presmerovať výstup pomocou operátorov ako "\|", "\>", "\<", "&" atď. Možno získať rovnaký výsledok s TProcess pomocou Pascal, príklady nasledujú...
3222
3323### Jednoduchý príklad
34-```
35-// Toto je ukážkový program ktorý vám ukáže ako
36- // spustiť externý program.
37- program launchprogram;
38-
39- // Tu si "použijeme" unity ktoré budeme potrebovať
40- uses
41- Classes, SysUtils, Process;
42-
43- // Toto je definícia premennej APRocess
44- // typu "TProcess"
45- var
46- AProcess: TProcess;
47-
48- // Začiatok programu
49- begin
50- // Vytvoríme objekt TProcess
51- // pridelíme ho do premennej AProcess
52- AProcess := TProcess.Create(nil);
53-
54- // Povieme novému procesu aký príkaz má vykonať
55- // Použime FPC prekladač
56- AProcess.CommandLine := 'ppc386 -h';
57-
58- // Definujeme nastavenie pre spustenie.
59- // Toto nastavenie zaručí že náš program
60- // nebude pokračovať až kým sa proces neskončí
61- AProcess.Options := AProcess.Options + [poWaitOnExit];
62-
63- // Teraz keď už proces vie čo má robiť
64- // ho môžeme spustiť.
65- AProcess.Execute;
66-
67- // Toto sa dosiahne až po skončení procesu.
68- AProcess.Free;
69- end.
24+
25+``` pascal
26+ // Toto je ukážkový program ktorý vám ukáže ako
27+ // spustiť externý program.
28+ program launchprogram;
29+
30+ // Tu si "použijeme" unity ktoré budeme potrebovať
31+ uses
32+ Classes, SysUtils, Process;
33+
34+ // Toto je definícia premennej APRocess
35+ // typu "TProcess"
36+ var
37+ AProcess: TProcess;
38+
39+ // Začiatok programu
40+ begin
41+ // Vytvoríme objekt TProcess
42+ // pridelíme ho do premennej AProcess
43+ AProcess := TProcess.Create(nil);
44+
45+ // Povieme novému procesu aký príkaz má vykonať
46+ // Použime FPC prekladač
47+ AProcess.CommandLine := 'ppc386 -h';
48+
49+ // Definujeme nastavenie pre spustenie.
50+ // Toto nastavenie zaručí že náš program
51+ // nebude pokračovať až kým sa proces neskončí
52+ AProcess.Options := AProcess.Options + [poWaitOnExit];
53+
54+ // Teraz keď už proces vie čo má robiť
55+ // ho môžeme spustiť.
56+ AProcess.Execute;
57+
58+ // Toto sa dosiahne až po skončení procesu.
59+ AProcess.Free;
60+ end.
7061```
7162
72-To je všetko! Práve ste sa naučili ako spustit externý program použitím TProcess.
63+To je všetko! Práve ste sa naučili ako spustit externý program použitím TProcess.
7364
74-To je všetko pekné, ale ako získam výstup spusteného programu? Tak sa na to pozrime, trochu rozšírime náš priklad.
65+To je všetko pekné, ale ako získam výstup spusteného programu? Tak sa na to pozrime, trochu rozšírime náš priklad.
7566
7667### Vylepšený príklad
77-```
78-// Toto je ukážkový program ktorý vám ukáže ako
79- // spustiť externý program.
80- program launchprogram;
81-
82- // Tu si "použijeme" unity ktoré budeme potrebovať
83- uses
84- Classes, SysUtils, Process;
85-
86- // Toto je definícia premennej APRocess
87- // typu "TProcess"
88- // Teraz pridáme aj TStringList aby sme
89- // mohli uložiť výstup procesu.
90- var
91- AProcess: TProcess;
92- AStringList: TStringList;
93-
94- // Začiatok programu
95- begin
96- // Vytvoríme objekt TProcess
97- // pridelíme ho do premennej AProcess
98- AProcess := TProcess.Create(nil);
99-
100- // Vytvoríme TStringList a pridelíme ho
101- AStringList := TStringList.Create;
102-
103- // Povieme novému procesu aký príkaz má vykonať
104- // Použime FPC prekladač
105- AProcess.CommandLine := 'ppc386 -h';
106-
107- // Definujeme nastavenie pre spustenie.
108- // Toto nastavenie zaručí že náš program
109- // nebude pokračovať až kým sa proces neskončí
110- // Zároveň ho nastavíme tak, aby sme mohli
111- // čítať výstup.
112- AProcess.Options := AProcess.Options + [poWaitOnExit, poUsePipes];
113-
114- // Teraz keď už proces vie čo má robiť
115- // ho môžeme spustiť.
116- AProcess.Execute;
117-
118- // Toto sa dosiahne až po skončení procesu.
119-
120- // Teraz načítame výstup programu
121- // do TStringListu.
122- AStringList.LoadFromStream(AProcess.Output);
123-
124- // Uložíme výstup do súboru
125- AStringList.SaveToFile('output.txt');
126-
127- // Teraz keď je už výstup uložený
128- // môžeme uvolniť objekty.
129- AStringList.Free;
130- AProcess.Free;
131- end.
68+
69+``` pascal
70+ // Toto je ukážkový program ktorý vám ukáže ako
71+ // spustiť externý program.
72+ program launchprogram;
73+
74+ // Tu si "použijeme" unity ktoré budeme potrebovať
75+ uses
76+ Classes, SysUtils, Process;
77+
78+ // Toto je definícia premennej APRocess
79+ // typu "TProcess"
80+ // Teraz pridáme aj TStringList aby sme
81+ // mohli uložiť výstup procesu.
82+ var
83+ AProcess: TProcess;
84+ AStringList: TStringList;
85+
86+ // Začiatok programu
87+ begin
88+ // Vytvoríme objekt TProcess
89+ // pridelíme ho do premennej AProcess
90+ AProcess := TProcess.Create(nil);
91+
92+ // Vytvoríme TStringList a pridelíme ho
93+ AStringList := TStringList.Create;
94+
95+ // Povieme novému procesu aký príkaz má vykonať
96+ // Použime FPC prekladač
97+ AProcess.CommandLine := 'ppc386 -h';
98+
99+ // Definujeme nastavenie pre spustenie.
100+ // Toto nastavenie zaručí že náš program
101+ // nebude pokračovať až kým sa proces neskončí
102+ // Zároveň ho nastavíme tak, aby sme mohli
103+ // čítať výstup.
104+ AProcess.Options := AProcess.Options + [poWaitOnExit, poUsePipes];
105+
106+ // Teraz keď už proces vie čo má robiť
107+ // ho môžeme spustiť.
108+ AProcess.Execute;
109+
110+ // Toto sa dosiahne až po skončení procesu.
111+
112+ // Teraz načítame výstup programu
113+ // do TStringListu.
114+ AStringList.LoadFromStream(AProcess.Output);
115+
116+ // Uložíme výstup do súboru
117+ AStringList.SaveToFile('output.txt');
118+
119+ // Teraz keď je už výstup uložený
120+ // môžeme uvolniť objekty.
121+ AStringList.Free;
122+ AProcess.Free;
123+ end.
132124```
133125
134126### Čítanie veľkého výstupu
135127
136-V predchádzajúcom príklade sme čakali na ukončenie programu a potom sme čítali čo mal program zapísané do výstupu. Ale predstavte si, že program zapisuje na výstup veľké množstvo dát, rúra sa plní a volaný program čaká na jej vyprázdnenie (prečítanie). Ale volajúci program z rúry nečíta, pretože čaká na ukončenie volaného programu. Nastalo uviaznutie.
128+V predchádzajúcom príklade sme čakali na ukončenie programu a potom sme čítali čo mal program zapísané do výstupu. Ale predstavte si, že program zapisuje na výstup veľké množstvo dát, rúra sa plní a volaný program čaká na jej vyprázdnenie (prečítanie). Ale volajúci program z rúry nečíta, pretože čaká na ukončenie volaného programu. Nastalo uviaznutie.
137129
138-Takže nasledujúci príklad nepoužíva poWaitOnExit, ale číta z výstupu, zatiaľ čo program stále beží. Výstup je uchovávaný v pamäťovom streame, ktorý môže byť neskôr použitý na prečítanie výstupu do TStringList.
139-```
140-program procoutlarge;
141- {
142- Copyright (c) 2004 by Marc Weustink
143-
144- Tento príklad je vytvorený v nádeji, že bude užitočný,
145- ale BEZ AKEJKOĽVEK ZÁRUKY; dokonca bez implicitnej záruky
146- MERCHANTABILITY alebo FITNESS FOR A PARTICULAR PURPOSE.
147- }
148-
149- uses
150- Classes, Process, SysUtils;
151-
152- const
153- READ_BYTES = 2048;
154-
155- var
156- S: TStringList;
157- M: TMemoryStream;
158- P: TProcess;
159- n: LongInt;
160- BytesRead: LongInt;
161-
162- begin
163- // Nemôžeme tu použiť poWaitOnExit, lebo nepoznáme
164- // veľkosť výstupu. V Linuxe je veľkosť
165- // výstupnej rúry 2 kB. Ak je výstupných dátviac,
166- // musíme dáta prečítať. To však nie je možné, keďže
167- // sme čakajúci. Takže by tu nastalo uviaznutie.
168- //
169- // Na buferovanie výstupu použijeme dočasný Memorystream
170-
171- M := TMemoryStream.Create;
172- BytesRead := 0;
130+Takže nasledujúci príklad nepoužíva poWaitOnExit, ale číta z výstupu, zatiaľ čo program stále beží. Výstup je uchovávaný v pamäťovom streame, ktorý môže byť neskôr použitý na prečítanie výstupu do TStringList.
131+
132+``` pascal
133+ program procoutlarge;
134+ {
135+ Copyright (c) 2004 by Marc Weustink
136+
137+ Tento príklad je vytvorený v nádeji, že bude užitočný,
138+ ale BEZ AKEJKOĽVEK ZÁRUKY; dokonca bez implicitnej záruky
139+ MERCHANTABILITY alebo FITNESS FOR A PARTICULAR PURPOSE.
140+ }
141+
142+ uses
143+ Classes, Process, SysUtils;
144+
145+ const
146+ READ_BYTES = 2048;
147+
148+ var
149+ S: TStringList;
150+ M: TMemoryStream;
151+ P: TProcess;
152+ n: LongInt;
153+ BytesRead: LongInt;
154+
155+ begin
156+ // Nemôžeme tu použiť poWaitOnExit, lebo nepoznáme
157+ // veľkosť výstupu. V Linuxe je veľkosť
158+ // výstupnej rúry 2 kB. Ak je výstupných dátviac,
159+ // musíme dáta prečítať. To však nie je možné, keďže
160+ // sme čakajúci. Takže by tu nastalo uviaznutie.
161+ //
162+ // Na buferovanie výstupu použijeme dočasný Memorystream
163+
164+ M := TMemoryStream.Create;
165+ BytesRead := 0;
166+
167+ P := TProcess.Create(nil);
168+ P.CommandLine := 'ppc386 -va bogus.pp';
169+ P.Options := [poUsePipes];
170+ WriteLn('-- executing --');
171+ P.Execute;
172+ while P.Running do
173+ begin
174+ // overenie, že máme dosť priestoru
175+ M.SetSize(BytesRead + READ_BYTES);
173176
174- P := TProcess.Create(nil);
175- P.CommandLine := 'ppc386 -va bogus.pp';
176- P.Options := [poUsePipes];
177- WriteLn('-- executing --');
178- P.Execute;
179- while P.Running do
180- begin
181- // overenie, že máme dosť priestoru
182- M.SetSize(BytesRead + READ_BYTES);
183-
184- // skús ho prečítať
185- n := P.Output.Read((M.Memory + BytesRead)^, READ_BYTES);
186- if n > 0
187- then begin
188- Inc(BytesRead, n);
189- Write('.')
190- end
191- else begin
192- // žiadne dáta, počkať 100 ms
193- Sleep(100);
194- end;
195- end;
196- // čítať poslednú časť
197- repeat
198- // overenie, že máme dosť priestoru
199- M.SetSize(BytesRead + READ_BYTES);
200- // skús ho prečítať
201- n := P.Output.Read((M.Memory + BytesRead)^, READ_BYTES);
202- if n > 0
203- then begin
204- Inc(BytesRead, n);
205- Write('.');
206- end;
207- until n <= 0;
208- if BytesRead > 0 then WriteLn;
209- M.SetSize(BytesRead);
210- WriteLn('-- executed --');
211-
212- S := TStringList.Create;
213- S.LoadFromStream(M);
214- WriteLn('-- linecount = ', S.Count, ' --');
215- for n := 0 to S.Count - 1 do
216- begin
217- WriteLn('| ', S[n]);
218- end;
219- WriteLn('-- end --');
220- S.Free;
221- P.Free;
222- M.Free;
223- end.
177+ // skús ho prečítať
178+ n := P.Output.Read((M.Memory + BytesRead)^, READ_BYTES);
179+ if n > 0
180+ then begin
181+ Inc(BytesRead, n);
182+ Write('.')
183+ end
184+ else begin
185+ // žiadne dáta, počkať 100 ms
186+ Sleep(100);
187+ end;
188+ end;
189+ // čítať poslednú časť
190+ repeat
191+ // overenie, že máme dosť priestoru
192+ M.SetSize(BytesRead + READ_BYTES);
193+ // skús ho prečítať
194+ n := P.Output.Read((M.Memory + BytesRead)^, READ_BYTES);
195+ if n > 0
196+ then begin
197+ Inc(BytesRead, n);
198+ Write('.');
199+ end;
200+ until n <= 0;
201+ if BytesRead > 0 then WriteLn;
202+ M.SetSize(BytesRead);
203+ WriteLn('-- executed --');
204+
205+ S := TStringList.Create;
206+ S.LoadFromStream(M);
207+ WriteLn('-- linecount = ', S.Count, ' --');
208+ for n := 0 to S.Count - 1 do
209+ begin
210+ WriteLn('| ', S[n]);
211+ end;
212+ WriteLn('-- end --');
213+ S.Free;
214+ P.Free;
215+ M.Free;
216+ end.
224217```
225218
226219### Použitie vstupu a výstupu z TProcess
227220
228-Viz príklad processdemo na [Lazarus-CCR SVN](<https://lazarus-ccr.svn.sourceforge.net/svnroot/lazarus-ccr/examples/process>).
221+Viz príklad processdemo na [Lazarus-CCR SVN](https://lazarus-ccr.svn.sourceforge.net/svnroot/lazarus-ccr/examples/process).
229222
230223### Pokyny pre použitie TProcess
231224
232-Ak vytvárate cez platformný program, môžete zmeniť príkazový riadok v závislosti na OS, pomocou direktív "{$IFDEF}s" a "{$ENDIF}s".
225+Ak vytvárate cez platformný program, môžete zmeniť príkazový riadok v závislosti na OS, pomocou direktív "{\$IFDEF}s" a "{\$ENDIF}s".
233226
234-Príklad:
235-```
236-{...}
237- AProcess:TProcess.Create(nil)
238- {$IFDEF WIN32}
239- AProcess.CommandLine := 'calc.exe'; //Windows Calc
240- {$ENDIF}
241- {$IFDEF LINUX}
242- AProcess.CommandLine := 'kcalc'; //KDE Calc
243- {$ENDIF}
244- AProcess.Execute; //in alternative, you can use AProcess.Active:=True
245- {...}
227+Príklad:
228+
229+``` pascal
230+ {...}
231+ AProcess:TProcess.Create(nil)
232+ {$IFDEF WIN32}
233+ AProcess.CommandLine := 'calc.exe'; //Windows Calc
234+ {$ENDIF}
235+ {$IFDEF LINUX}
236+ AProcess.CommandLine := 'kcalc'; //KDE Calc
237+ {$ENDIF}
238+ AProcess.Execute; //in alternative, you can use AProcess.Active:=True
239+ {...}
246240```
247241
248242### Príklad komunikácie s procesom aspell
249243
250-V zdrojovom kóde [pasdoc](<http://pasdoc.sourceforge.net/>) môžete nájsť dve unity, ktoré vykonávajú kontrolu pravopisu komunikáciou s bežiacim procesom aspell cez rúry:
244+V zdrojovom kóde [pasdoc](http://pasdoc.sourceforge.net/) môžete nájsť dve unity, ktoré vykonávajú kontrolu pravopisu komunikáciou s bežiacim procesom aspell cez rúry:
251245
252- * [PasDoc_ProcessLineTalk.pas unit](<http://pasdoc.svn.sourceforge.net/viewvc/*checkout*/pasdoc/trunk/source/component/PasDoc_ProcessLineTalk.pas>) implementuje triedu TProcessLineTalk, potomka TProcess, ktorú možno jednoducho použiť na komunikáciu s ktorýmkoľvek procesom na báze riadok-po-riadku.
253- * [PasDoc_Aspell.pas unit](<http://pasdoc.svn.sourceforge.net/viewvc/*checkout*/pasdoc/trunk/source/component/PasDoc_Aspell.pas>) implementuje triedu TAspellProcess, ktorá vykonáva kontrolu pravopisu pomocou základnej inštancie TProcessLineTalk pre spustenie aspell a komunikáciu so spusteným procesom aspell.
246+- [PasDoc_ProcessLineTalk.pas unit](http://pasdoc.svn.sourceforge.net/viewvc/*checkout*/pasdoc/trunk/source/component/PasDoc_ProcessLineTalk.pas) implementuje triedu TProcessLineTalk, potomka TProcess, ktorú možno jednoducho použiť na komunikáciu s ktorýmkoľvek procesom na báze riadok-po-riadku.
247+- [PasDoc_Aspell.pas unit](http://pasdoc.svn.sourceforge.net/viewvc/*checkout*/pasdoc/trunk/source/component/PasDoc_Aspell.pas) implementuje triedu TAspellProcess, ktorá vykonáva kontrolu pravopisu pomocou základnej inštancie TProcessLineTalk pre spustenie aspell a komunikáciu so spusteným procesom aspell.
254248
255249Obe jednotky sú vcelku nezávislé od zvyšku zdrojového kódu pasdoc, takže môžu poslúžiť ako príklady skutočného použitia TProcess na spustenie a komunikáciu s inými programmi cez rúry.
256250
257251---
258-*From the Free Pascal wiki, page "Executing External Programs/sk", as the Internet Archive kept it on 2022-12-09. Copyright stays with the author who wrote it, according to the old wiki's [[Licensing]] page. If you have concerns about this material, [message the admin](/wiki-contact).*
252+*From the Free Pascal wiki, page "Executing External Programs/sk", as it stood on 2020-02-14 after a change by Trev, out of the wiki's dump of 2024-05-26. Copyright stays with the author who wrote it, according to the old wiki's [[Licensing]] page. If you have concerns about this material, [message the admin](/wiki-contact).*

Back to history