Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Начинающим";
Текущий архив: 2008.03.09;
Скачать: [xml.tar.bz2];

Вниз

Проблема с написанием Service а   Найти похожие ветки 

 
patrick1968 ©   (2008-02-11 17:24) [0]

Появилась такая задача, решить которую надумал при помощи сервиса (до этого с этим не сталкивался), тема простая в случае появления определенного файла в определенном месте его необходимо перекинуть в др. место (наверное всё просто да только не работает) вот код:

unit Unload1;

interface

uses
 Windows, Messages, SysUtils, Classes, Graphics, Controls, SvcMgr, Dialogs, ActiveX, IniFiles,
 DB, ADODB;

type
 TUnload = class(TService)
   OraConnection: TADOConnection;
   procedure ServiceExecute(Sender: TService);
   procedure ServiceStart(Sender: TService; var Started: Boolean);
 private
   { Private declarations }
 public
   QDesk : integer;
   TempPath, arrPath, ConnectStringIn, ConnectStringOut : string;
   arrDesk : array of string;
   function GetServiceController: TServiceController; override;
   { Public declarations }
 end;

var
 Unload: TUnload;

implementation

{$R *.DFM}

procedure ServiceController(CtrlCode: DWord); stdcall;
begin
 Unload.Controller(CtrlCode);
end;

function TUnload.GetServiceController: TServiceController;
begin
 Result := ServiceController;
end;

procedure TUnload.ServiceExecute(Sender: TService);
begin
 CoInitialize(nil);
 while not terminated do begin
              FileCreate(arrDesk[0] + "cash001s.db");
    if FileExists(arrDesk[0] + "cash001.db")
       then begin
              FileCreate(arrDesk[0] + "cash001s.db");
              MoveFile(PChar(arrDesk[0] + "cash001.db"),PChar(TempPath + "cash001.db"));
       end;
    serviceThread.ProcessRequests(false);
    CoUnInitialize;
 end;
end;

procedure TUnload.ServiceStart(Sender: TService; var Started: Boolean);
var UnloadIni : TIniFile;
    ind, idx : integer;
begin
 CoInitialize(nil);

 UnloadIni := TIniFile.Create("prUnload.ini");
 if not FileExists("prUnload.ini")
    then begin
          UnloadIni.WriteInteger( "MAIN", "QDESK", 1);
          UnloadIni.WriteString( "MAIN", "TEMPPATH", "C:\");
          UnloadIni.WriteString( "MAIN", "ARRPATH", "");
          UnloadIni.WriteString( "MAIN", "CONNECTSTRING_IN", "");
          UnloadIni.WriteString( "MAIN", "CONNECTSTRING_OUT", "");
          QDesk := UnloadIni.ReadInteger( "MAIN", "QDESK", 1);
          TempPath := UnloadIni.ReadString( "MAIN", "TEMPPATH", "");
          ArrPath := UnloadIni.ReadString( "MAIN", "ARRPATH", "");
          ConnectStringIn := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_IN", "");
          ConnectStringOut := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_OUT", "");
         end
       else begin
             QDesk := UnloadIni.ReadInteger( "MAIN", "QDESK", 1);
             TempPath := UnloadIni.ReadString( "MAIN", "TEMPPATH", "");
             ArrPath := UnloadIni.ReadString( "MAIN", "ARRPATH", "");
             ConnectStringIn := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_IN", "");
             ConnectStringOut := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_OUT", "");
            end;
 UnloadIni.Free;

 try
  OraConnection.ConnectionString := ConnectStringIn;
  OraConnection.Connected := true;
 except
 end;

 SetLength( arrDesk, QDesk);
 ind := 0;
 idx := 1;
 arrDesk[ind] := "";
 while (idx <= Length(arrPath)) do begin
    if arrPath[idx] <> ","
      then arrDesk[ind] := arrDesk[ind] + arrPath[idx]
      else begin
            inc(ind);
            arrDesk[ind] := "";
           end;
    inc(idx);
 end;

 CoUnInitialize;

end;


в стартовой процедуре определил переменные, которые нужны при Execute"е, только там она их не видит почему-то, помогите разобраться, заранее благодарен.


 
Сергей М. ©   (2008-02-11 17:31) [1]


> в стартовой процедуре определил переменные, которые нужны
> при Execute"е


Это какие же ?

И зачем в обработчике OnExecute вызовы CoInitialize/CoUnInitialize ?


 
Palladin ©   (2008-02-11 17:45) [2]


> patrick1968 ©   (11.02.08 17:24)

ну как бы задача понятна... проблема только непонятна... кто на ком стоял...


 
patrick1968 ©   (2008-02-11 17:47) [3]

массив arrDesk, который определяется в старте и объявлен в разделе public, а CoInitialize/CoUnInitialize на будущее т.к. далее буду использовать ADO вычитал на каком-то форуме об этой необходимости.(вообще написание сервисов для меня - новинка, поэтому может есть ссылка на толковую статью, чтобы не задавать слишком простых вопросов)


 
Palladin ©   (2008-02-11 17:49) [4]


> массив arrDesk, который определяется в старте и объявлен
> в разделе public

ну и чего с того то? проблемма где? я вот в упор понять не могу


> в стартовой процедуре определил переменные, которые нужны
> при Execute"е, только там она их не видит


что это вообще значит...


>  CoInitialize/CoUnInitialize на будущее т.к. далее буду
> использовать ADO вычитал на каком-то форуме об этой необходимости

их необходимость более чем под вопросом


 
patrick1968 ©   (2008-02-11 17:57) [5]

проблема в том, что прога не работает (MoveFile) не перетаскивается файл


 
Palladin ©   (2008-02-11 18:00) [6]


> проблема в том, что прога не работает

замечательная проблема


>  (MoveFile) не перетаскивается файл

ты это визуально определил, аль GetLastError поймал?


 
patrick1968 ©   (2008-02-11 18:03) [7]

ВИзуально, а что разве так не должно быть?


 
Palladin ©   (2008-02-11 18:03) [8]

мда... ознакомился подробней с твоим кодом...
бред...


 
Palladin ©   (2008-02-11 18:06) [9]

идем читаем
http://www.delphimaster.ru/articles/panov/index.html

потом долго думаем...
кстати пока думаем, форматируем исходный код и пытаемся объяснить мне почему CoInitialize вызвано перед циклом While, а CoUninitialize вызывается на каждой итерации... честно честно, мне очень интересно...


 
ketmar ©   (2008-02-11 19:16) [10]

что это ([0]) было? %-)

---
Understanding is not required. Only obedience.


 
Slym ©   (2008-02-12 04:41) [11]

в ServiceStart запускай дополнительный поток, в котором делай все что угодно: CoInitialize, создавай конекшены, мувь файло... ServiceExecute не для этого


 
Slym ©   (2008-02-12 04:42) [12]

в ServiceStart запускай дополнительный поток, в котором делай все что угодно: CoInitialize, создавай конекшены, мувь файло... ServiceExecute не для этого


 
Сергей М. ©   (2008-02-12 08:27) [13]


> patrick1968 ©   (11.02.08 17:47) [3]
>
> массив arrDesk, который определяется в старте


При старте он не определяется.

Определяется он как раз в public, создается (с нулевой длиной) при создании объекта UnLoad, а при старте просто изменяется его длина.


> прога не работает (MoveFile) не перетаскивается файл
>


А причем здесь тогда

> она их не видит


?

Видимость переменной - понятие, относящееся ко времени компиляции, а не ко времени выполнения.


 
ANB   (2008-02-12 09:46) [14]


> FileCreate(arrDesk[0] + "cash001s.db");

Скажи, пожалуйста, что делает у тебя этот оператор ?

На будующее :
1) Выкини сервис и напиши сначала обычное приложение, в котором нужные тебе действия выполняй под кнопкой.
2) Учти граблю : файл может быть обнаружен экзистом, но при этом еще писаться, посему ты должен убедится, что файл уже весь записали, и только потом его перемещать.


 
patrick1968 ©   (2008-02-12 11:22) [15]

Сервис выкидывал, делал всё под кнопкой - работает как надо, а все эти операторы вставлял для проверки, оригинальный код Execute следующий

procedure TUnload.ServiceExecute(Sender: TService);
begin
CoInitialize(nil);
while not terminated do begin
   if FileExists(arrDesk[0] + "cash001.db")
      then begin
             MoveFile(PChar(arrDesk[0] + "cash001.db"),PChar(TempPath + "cash001.db"));
      end;
   serviceThread.ProcessRequests(false);
end;
   CoUnInitialize;
end;

причем если удаляю экзист, и просто на том месте создаю файл с путем arrDesk[0], только создает она его не там где надо а в system32, получается так что в данной ситуации можно использовать только потоки?


 
Dennis I. Komarov ©   (2008-02-12 11:45) [16]

> [15] patrick1968 ©   (12.02.08 11:22)

Остовной поток сервиса - для его управления. Все действия в дополнительные нити.

> причем если удаляю экзист, и просто на том месте создаю
> файл с путем arrDesk[0], только создает она его не там где
> надо а в system32, получается так что в данной ситуации
> можно использовать только потоки?


ЗЫ У тебя проблемы с CurrentDir


 
ANB   (2008-02-12 12:21) [17]


> работает как надо

Начни писать длинннный файл. А пока он пишется - нажми кнопку. Удивись.


 
patrick1968 ©   (2008-02-12 13:04) [18]

Попытался через дополнительный поток

вот код

unit Unload1;

interface

uses
 Windows, Messages, SysUtils, Classes, Graphics, Controls, SvcMgr, Dialogs, ActiveX, IniFiles,
 DB, ADODB;

type

 TMainThread = class(TThread)
 private
 public
   QDesk : integer;
   TempPath, arrPath, ConnectStringIn, ConnectStringOut : string;
   arrDesk : array of string;
   OraConnection: TADOConnection;
   constructor Create;
 protected
    procedure DoWork;
    procedure Execute; override;
 end;

 TUnload = class(TService)
   OraConnection: TADOConnection;
   procedure ServiceExecute(Sender: TService);
 private
   { Private declarations }
 public
   function GetServiceController: TServiceController; override;
   { Public declarations }
 end;

var
 MainThread : TMainThread;
 Unload: TUnload;

implementation

{$R *.DFM}

procedure ServiceController(CtrlCode: DWord); stdcall;
begin
 Unload.Controller(CtrlCode);
end;

function TUnload.GetServiceController: TServiceController;
begin
 Result := ServiceController;
end;

constructor TMainThread.Create;
var UnloadIni : TIniFile;
    ind, idx : integer;
begin
 inherited Create(True);    

 UnloadIni := TIniFile.Create("prUnload.ini");
 if not FileExists("prUnload.ini")
    then begin
          UnloadIni.WriteInteger( "MAIN", "QDESK", 1);
          UnloadIni.WriteString( "MAIN", "TEMPPATH", "C:\");
          UnloadIni.WriteString( "MAIN", "ARRPATH", "");
          UnloadIni.WriteString( "MAIN", "CONNECTSTRING_IN", "");
          UnloadIni.WriteString( "MAIN", "CONNECTSTRING_OUT", "");
          QDesk := UnloadIni.ReadInteger( "MAIN", "QDESK", 1);
          TempPath := UnloadIni.ReadString( "MAIN", "TEMPPATH", "");
          ArrPath := UnloadIni.ReadString( "MAIN", "ARRPATH", "");
          ConnectStringIn := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_IN", "");
          ConnectStringOut := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_OUT", "");
         end
       else begin
             QDesk := UnloadIni.ReadInteger( "MAIN", "QDESK", 1);
             TempPath := UnloadIni.ReadString( "MAIN", "TEMPPATH", "");
             ArrPath := UnloadIni.ReadString( "MAIN", "ARRPATH", "");
             ConnectStringIn := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_IN", "");
             ConnectStringOut := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_OUT", "");
            end;
 UnloadIni.Free;

 try
  OraConnection.ConnectionString := ConnectStringIn;
  OraConnection.Connected := true;
 except
 end;

 SetLength( arrDesk, QDesk);
 ind := 0;
 idx := 1;
 arrDesk[ind] := "";
 while (idx <= Length(arrPath)) do begin
    if arrPath[idx] <> ","
      then arrDesk[ind] := arrDesk[ind] + arrPath[idx]
      else begin
            inc(ind);
            arrDesk[ind] := "";
           end;
    inc(idx);
 end;

 Self.Priority := tpHighest;
 Resume;                      
end;

procedure TMainThread.DoWork;
begin
  if FileExists(arrDesk[0] + "cash001.db")
     then begin
           FileCreate(arrDesk[0] + "cash001s.db");
          end;
end;

procedure TMainThread.Execute;
begin
    while not Terminated do
    begin
        Synchronize(DoWork);
        Sleep(1000);
    end;
end;

procedure TUnload.ServiceExecute(Sender: TService);
begin
MainThread := TMainThread.Create;
end;

end.

в итоге при старте службы пишет что служба была запущена а затем остановлена т.к. нечего делать. Может есть какой пример по написанию службы при помощи создания доп потоков?


 
Palladin ©   (2008-02-12 13:06) [19]

да забудь ты про SeviceExucte!
поток стартуй на ServiceStart
поток останавливай на ServiceStop


 
Dennis I. Komarov ©   (2008-02-12 13:20) [20]

> procedure TUnload.ServiceExecute(Sender: TService);
> begin
> MainThread := TMainThread.Create;
> end;
>
> end.
>
> в итоге при старте службы пишет что служба была запущена
> а затем остановлена т.к. нечего делать. Может есть какой
> пример по написанию службы при помощи создания доп потоков?

После того, как служба создала поток, ее действие закончилось - она и остановилася

написать службу при помощи создания доп. потоков - низя :)

Сперва разберись с ними по отдельности, а потом склеишь.


 
patrick1968 ©   (2008-02-12 13:28) [21]

Так сделал, служба стартует нормально только переменные которые фигурируют в конструкторе (например arrDesk[0] которая на том этапе равна "D:\CASSA\") в процедуре DoWork равна "" наверное есть какая-то хитрость?


 
Сергей М. ©   (2008-02-12 13:31) [22]


> переменные которые фигурируют в конструкторе


> в процедуре DoWork


Какой такой "конструктор" ? Какая DoWork ?!
Ни того ни другого в приведенном коде и в помине нет


 
Palladin ©   (2008-02-12 13:31) [23]


> procedure TMainThread.Execute;
> begin
>     while not Terminated do
>     begin
>         Synchronize(DoWork);
>         Sleep(1000);
>     end;
> end;

ты опять бредишь?
и по ссылке мы не ходили по моей
и гдето про synchronize узнали
и решили что это круто
и заюзали


 
Palladin ©   (2008-02-12 13:33) [24]


> Self.Priority := tpHighest;

а за это вообще пожизненный эцих с гвоздями


 
Slym ©   (2008-02-12 13:35) [25]

   while not Terminated do
   begin
       Synchronize(DoWork);
       Sleep(1000);
   end;

Откуда эти мертвяки лезут? А выкрутасы с ini на елку вместо гирлянд весить...
сделай модуть (unit) со своим потоком... отладь его в обычном приложении... а уж потом его к сервису приленкуешь


 
Slym ©   (2008-02-12 13:37) [26]

и OraConnection у тебя для понта или реально гдето используется?


 
patrick1968 ©   (2008-02-12 13:47) [27]

Да все эти выкрутасы с этих ссылок и взял, из примеров


 
Slym ©   (2008-02-12 13:56) [28]

var
 UnloadIni : TIniFile;
begin
 UnloadIni := TIniFile.Create("prUnload.ini");
 try
   if not FileExists(UnloadIni.FileName) then
   begin
     UnloadIni.WriteInteger( "MAIN", "QDESK", 1);
     UnloadIni.WriteString( "MAIN", "TEMPPATH", "C:\");
     UnloadIni.WriteString( "MAIN", "ARRPATH", "");
     UnloadIni.WriteString( "MAIN", "CONNECTSTRING_IN", "");
     UnloadIni.WriteString( "MAIN", "CONNECTSTRING_OUT", "");
   end;
   QDesk := UnloadIni.ReadInteger( "MAIN", "QDESK", 1);
   TempPath := UnloadIni.ReadString( "MAIN", "TEMPPATH", "");
   ArrPath := UnloadIni.ReadString( "MAIN", "ARRPATH", "");
   ConnectStringIn := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_IN", "");
   ConnectStringOut := UnloadIni.ReadString( "MAIN", "CONNECTSTRING_OUT", "");
 finally
   UnloadIni.Free;
 end;


 
ketmar ©   (2008-02-12 14:02) [29]

>[23] Palladin © (2008-02-12 13:31:00)
как это «где-то»? очен даже известно, где. некий неприкасаемый это популяризировал, чтоб ему ни дна, ни покрышки.

---
Understanding is not required. Only obedience.


 
Palladin ©   (2008-02-12 14:10) [30]


> [27] patrick1968 ©   (12.02.08 13:47)

та все эти выкрутасы ты тупо скопировал и необоснованно использовал, непонимая чего к чему, а по ссылкам они очень даже обосновано использованы...


 
Dennis I. Komarov ©   (2008-02-12 15:09) [31]

> [29] ketmar ©   (12.02.08 14:02)

Злой ты какой-то сегодня :)


> [27] patrick1968 ©   (12.02.08 13:47)

Переходим к убитым енотам: 50


 
ketmar ©   (2008-02-12 15:11) [32]

>[31] Dennis I. Komarov © (2008-02-12 15:09:00)
>Злой ты какой-то сегодня :)

не спал ещё. %-)

---
Understanding is not required. Only obedience.


 
Palladin ©   (2008-02-12 15:27) [33]


> [32] ketmar ©   (12.02.08 15:11)

w3k ждал? :)


 
Leonid Troyanovsky ©   (2008-02-12 15:28) [34]


> Slym ©   (12.02.08 13:35) [25]

> Откуда эти мертвяки лезут?

Из вредных советов.
http://podgoretsky.com/DM/BadTips.html#bt-04

--
Regards, LVT.


 
ketmar ©   (2008-02-12 15:33) [35]

>[33] Palladin © (2008-02-12 15:27:00)
вообще-то жрачки. %-)

---
Understanding is not required. Only obedience.


 
Сергей М. ©   (2008-02-12 15:35) [36]


> в случае появления определенного файла в определенном месте
> его необходимо перекинуть в др. место


Логика, ведущая в тупик.



Страницы: 1 вся ветка

Форум: "Начинающим";
Текущий архив: 2008.03.09;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.56 MB
Время: 0.033 c
2-1202980099
bataniQ
2008-02-14 12:08
2008.03.09
Frame в Главной форме...


15-1201861717
barakuda
2008-02-01 13:28
2008.03.09
меню с большими иконками 32*32...


2-1202553943
fics
2008-02-09 13:45
2008.03.09
Компонент "ЛИНИЯ"


2-1202923180
Kirill
2008-02-13 20:19
2008.03.09
Cursor


11-1185096701
Dy1
2007-07-22 13:31
2008.03.09
Посоветуйте плз компонент для печати





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский