Ошибка "SQLITE BUSY" при работе с Sqliite БД

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение artem78 » 05.02.2022 17:49:32

Исходники проекта во вложении. Ошибка происходит здесь:
procedure TTasksFrame.StartTrackingToolButtonClick(Sender: TObject);
begin
with DataModule1.PeriodsDataset do
begin
// ToDo: Check if no unfinished periods
Append;
FieldByName('task_id').AsInteger
:= DataModule1.TasksDataset.FieldByName('id').AsInteger;
FieldByName('begin').AsDateTime := Now;
Post;
ApplyUpdates; <-----
end;
end;


Жду помощи специалистов.
У вас нет необходимых прав для просмотра вложений в этом сообщении.
artem78
новенький
 
Сообщения: 50
Зарегистрирован: 09.08.2015 18:52:24

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение Снег Север » 05.02.2022 19:26:50

При попытке установить в лазарь эту дурацкую приблуду - sql3la, он меня обвалился. Пользуйтесь нормальными компонентами - SqlDB, ZeosDB. Скорее всего у вас установлен AutoCommit, вот оно и валится на ApplyUpdates.
Аватара пользователя
Снег Север
долгожитель
 
Сообщения: 3050
Зарегистрирован: 27.11.2007 16:14:47

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение iskander » 05.02.2022 19:42:32

artem78 писал(а):Жду помощи специалистов.

О, я уже думал, что объявив приказом по полку отсутствие в SQLite3 типа DATETIME, вы решили, что ловить здесь больше нечего.
Вижу у вас появились новые идеи - использовать Sqldb вместе с Sqlite3Dataset, один конь в упряжке хорошо, а два ещё лучше.
Рискну, однако, предположить, что в этом и есть проблема, не хотят они на добровольной основе делиться доступом к базе.
iskander
энтузиаст
 
Сообщения: 608
Зарегистрирован: 08.01.2012 18:43:34

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение artem78 » 06.02.2022 15:04:34

iskander писал(а):Рискну, однако, предположить, что в этом и есть проблема, не хотят они на добровольной основе делиться доступом к базе.

Я об этом не подумал.
artem78
новенький
 
Сообщения: 50
Зарегистрирован: 09.08.2015 18:52:24

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение iskander » 06.02.2022 15:35:59

Для того чтобы в этом убедиться, требуется как минимум скомпилировать ваш пример, но вы же не захотели облегчить жизнь рядового помогальщика, там кроме Sqlite3Dataset болтается ещё некий UniqueInstance, который мне совсем ни разу не упёрся.
Глядя в код модуля tasks, могу предложить вот такой вариант
Код: Выделить всё
unit tasks;

{$mode objfpc}{$H+}

interface

uses
  Classes, SysUtils, FileUtil, Forms, Controls, ComCtrls, DBGrids, taskedit, datamodule, Dialogs;

type

  { TTasksFrame }

  TTasksFrame = class(TFrame)
    TasksDBGrid: TDBGrid;
    ToolBar1: TToolBar;
    AddToolButton: TToolButton;
    RemoveToolButton: TToolButton;
    EditToolButton: TToolButton;
    SeparatorToolButton: TToolButton;
    StartTrackingToolButton: TToolButton;
    StopTrackingToolButton: TToolButton;
    ShowTimeToolButton: TToolButton;
    procedure AddToolButtonClick(Sender: TObject);
    procedure EditToolButtonClick(Sender: TObject);
    procedure RemoveToolButtonClick(Sender: TObject);
    procedure ShowTimeToolButtonClick(Sender: TObject);
    procedure StartTrackingToolButtonClick(Sender: TObject);
    procedure StopTrackingToolButtonClick(Sender: TObject);
  private
    { private declarations }
  public
    { public declarations }
  end;

implementation

uses
  Variants;

{$R *.lfm}

{ TTasksFrame }

procedure TTasksFrame.AddToolButtonClick(Sender: TObject);
begin
  DataModule1.TasksDataset.Append;
  if TaskEditForm.ShowModal = mrOK then
  begin
    DataModule1.SQLTransaction1.EndTransaction;
    DataModule1.TasksDataset.FieldByName('created').AsDateTime := Now;
    DataModule1.TasksDataset.Post;
    DataModule1.TasksDataset.ApplyUpdates;
    DataModule1.StatsSQLQuery.Open;
  end
  else
    DataModule1.TasksDataset.Cancel;
end;

procedure TTasksFrame.EditToolButtonClick(Sender: TObject);
begin
  if DataModule1.TasksDataset.IsEmpty then
    Exit;

  DataModule1.TasksDataset.Edit;
  if TaskEditForm.ShowModal = mrOK then
  begin
    DataModule1.SQLTransaction1.EndTransaction;
    DataModule1.TasksDataset.FieldByName('modified').AsDateTime := Now;
    DataModule1.TasksDataset.Post;
    DataModule1.TasksDataset.ApplyUpdates;
    DataModule1.StatsSQLQuery.Open;
  end
  else
    DataModule1.TasksDataset.Cancel;
end;

procedure TTasksFrame.RemoveToolButtonClick(Sender: TObject);
var
  Msg: String;
begin
  if DataModule1.TasksDataset.IsEmpty then
    Exit;

  Msg := Format('Are you sure to delete task "%s"?', [DataModule1.TasksDataset.FieldByName('name').AsString]);
  if MessageDlg(Msg, mtConfirmation, [mbYes, mbNo], 0) = mrYes then
  begin
    DataModule1.SQLTransaction1.EndTransaction;
    DataModule1.TasksDataset.Delete;
    DataModule1.TasksDataset.ApplyUpdates;
    DataModule1.StatsSQLQuery.Open;
  end;
end;

procedure TTasksFrame.ShowTimeToolButtonClick(Sender: TObject);
var
  TotalTime: TTime;
  Period: TTime;
begin
  TotalTime:=EncodeTime(0,0,0,0);

  with DataModule1.SQLQuery1 do
  begin
    Close();
    SQL.Text := 'select begin, end from periods where task_id = ' + IntToStr(DataModule1.TasksDataset.FieldByName('id').AsInteger) + ';';
    Open();

    while not EOF do
    begin
      if FieldByName('end').IsNull then
        Period := Now - FieldByName('begin').AsDateTime
      else
        Period := FieldByName('end').AsDateTime - FieldByName('begin').AsDateTime;

      TotalTime:=TotalTime+Period;
      Next;
    end;
  end;

  ShowMessage(TimeToStr(TotalTime));
end;

procedure TTasksFrame.StartTrackingToolButtonClick(Sender: TObject);
begin
  DataModule1.SQLTransaction1.EndTransaction;
  with DataModule1.PeriodsDataset do
  begin
    // ToDo: Check if no unfinished periods
    Append;
    FieldByName('task_id').AsInteger
      := DataModule1.TasksDataset.FieldByName('id').AsInteger;
    FieldByName('begin').AsDateTime := Now;
    Post;
    ApplyUpdates;
  end;
  DataModule1.StatsSQLQuery.Open;
end;

procedure TTasksFrame.StopTrackingToolButtonClick(Sender: TObject);
begin
  with DataModule1.SQLQuery1 do
  begin
    Close;
    SQL.Text := 'update periods set end=:end WHERE `end` IS NULL';
    // ToDo: Check if only one result
    ParamByName('end').AsDateTime:=now - 2415018.5;
    ExecSQL;
    SQLTransaction.CommitRetaining;
    //Close;
  end;
  DataModule1.PeriodsDataset.Close;
  DataModule1.PeriodsDataset.Open;
end;

end.

Надеюсь это поможет.
iskander
энтузиаст
 
Сообщения: 608
Зарегистрирован: 08.01.2012 18:43:34

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение artem78 » 07.02.2022 19:33:13

iskander писал(а):некий UniqueInstance

Он присутствует в сетевом менеджере пакетов.
artem78
новенький
 
Сообщения: 50
Зарегистрирован: 09.08.2015 18:52:24

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение iskander » 07.02.2022 21:17:06

Вау, да вы никак решили озаботиться моим просвещением? Весьма похвально, да, что бы я без вас делал...

То есть вы считаете, что каждый, ни в чём не повинный помогальщик просто обязан установить на свой компьютер кучу совершенно ему не нужного хлама только потому, что вы не озаботились очистить от него свой пример?
Последний раз редактировалось iskander 07.02.2022 23:26:36, всего редактировалось 1 раз.
iskander
энтузиаст
 
Сообщения: 608
Зарегистрирован: 08.01.2012 18:43:34

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение artem78 » 07.02.2022 21:26:55

На отдельном примере продемонстрировать проблему было затруднительно, поэтому дал всё что есть (к счастью, кода там совсем немного).
artem78
новенький
 
Сообщения: 50
Зарегистрирован: 09.08.2015 18:52:24

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение iskander » 07.02.2022 21:31:25

Ну а код-то из поста выше опробовали?
iskander
энтузиаст
 
Сообщения: 608
Зарегистрирован: 08.01.2012 18:43:34

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение artem78 » 07.02.2022 23:08:02

iskander писал(а):Ну а код-то из поста выше опробовали?

Да. Похоже, работает как надо. Спасибо.

Добавлено спустя 22 часа 39 минут 49 секунд:
Снег Север писал(а):Пользуйтесь нормальными компонентами - SqlDB, ZeosDB

Какие между ними различия? Какой из них порекомендуете выбрать?
artem78
новенький
 
Сообщения: 50
Зарегистрирован: 09.08.2015 18:52:24

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение Снег Север » 08.02.2022 23:16:04

artem78 писал(а):Какие между ними различия? Какой из них порекомендуете выбрать?

ZeosDB более универсальные, но для 99% случаев вполне годятся SqlDB.
Аватара пользователя
Снег Север
долгожитель
 
Сообщения: 3050
Зарегистрирован: 27.11.2007 16:14:47

Re: Ошибка "SQLITE BUSY" при работе с Sqliite БД

Сообщение iskander » 09.02.2022 08:25:00

Он об этом уже спрашивал.
iskander
энтузиаст
 
Сообщения: 608
Зарегистрирован: 08.01.2012 18:43:34


Вернуться в Lazarus

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 2

Рейтинг@Mail.ru