Delete from

In this code...


procedure TfrmPrincipal.Button1Click(Sender: TObject);
var
  manager: TObjectManager;
  Grupos: TList<TGrupos>;
  Grupo: TGrupos;
begin
  manager := TObjectManager.Create(connSQLite);
  try
    Grupos := manager.Find<TGrupos>().List;
    for Grupo in Grupos do
      manager.remove(Grupo);
  finally
    manager.Free;
  end;
end;

the line ->  manager.remove(Grupo); returns for me Access Violation... 

Something i'm doing wrong?

How is TGroups class declared and implemented? What is the call stack at the point of Access Violation?

procedure TfrmPrincipal.Button1Click(Sender: TObject);
var
  manager: TObjectManager;
  Grupos: TList<TGrupos>;
  Grupo: TGrupos;
begin
  manager := TObjectManager.Create(connSQLite);
  try
    Grupos := manager.Find<TGrupos>().List;
    for Grupo in Grupos do
      showmessage(Grupo.Grupo);
    // manager.remove(Grupo);
  finally
    manager.Free;
  end;
end;

In this line -> manager.remove(Grupo); all commands work(save, saveorupdate, etc), except the remove...

In this code all groups are displayed correctly with showmessage.

Exception: First chance exception at $00AF044E. Exception class $C0000005 with message 'access violation at 0x00af044e: read of address 0x00000004'.

Environment: 
-Windows 7
-Delphi 10.1 Berlin and Delphi 10.2 Tokyo

How is TGroups class declared and implemented? What is the call stack at the point of Access Violation?


I can only guess that you have a recursive mapping (TGroups maps to TGroups) with a cascade set, so when you Remove a group, you also remove related groups. Thus it might be you are removing a TGroups that is already destroyed. With recursive mapping there isn't much you can do, you must manually take of that and be sure you are not accessing a group that has been already destroyed.

Hello, i found what was the problem. Analyzing the class i found the property TColumnProp.Lazy and so it became easier to understand the error. But, how should REMOVE be done in this case?


CLASS
[Column('IMAGEM', [TColumnProp.Lazy])]
FIMAGEM: TBlob;

I don't understand how TColumnProp.Lazy is related to the mentioned error? Can you please explain better?

You should have no issue in removing an object with lazy properties. 

ok, i'll send the code


Class
  [Entity, AutoMapping]
  [Id('FCD_GRUPO', TIdGenerator.None)]
  TGrupos = class
  private
    [Column('CD_GRUPO', [TColumnProp.Required])]
    FCD_GRUPO: Integer;

    [Column('GRUPO', [], 50)]
    FGRUPO: Nullable<string>;

    [Column('IMAGEM', [TColumnProp.Lazy])]
    FIMAGEM: TBlob;

    [Column('SUB_ASSOCIADO', [], 50)]
    FSUB_ASSOCIADO: Nullable<string>;

    [Column('GRUPO_DELIVERY', [])]
    FGRUPO_DELIVERY: Nullable<Integer>;
    // FGRUPO_DELIVERY: Nullable<Boolean>;

    [Column('GRUPO_MESA', [])]
    FGRUPO_MESA: Nullable<Integer>;
    // FGRUPO_MESA: Nullable<Boolean>;
  public
    property CD_GRUPO: Integer read FCD_GRUPO write FCD_GRUPO;
    property GRUPO: Nullable<string> read FGRUPO write FGRUPO;
    property IMAGEM: TBlob read FIMAGEM write FIMAGEM;
    property SUB_ASSOCIADO: Nullable<string> read FSUB_ASSOCIADO
      write FSUB_ASSOCIADO;
    property GRUPO_DELIVERY: Nullable<Integer> read FGRUPO_DELIVERY
      write FGRUPO_DELIVERY;
    property GRUPO_MESA: Nullable<Integer> read FGRUPO_MESA write FGRUPO_MESA;

IMPLEMENTATION

ON CREATE
TMappingExplorer.Default.GetTable(TComplemento).Name := 'GRUPOS'; 
//Only to learn how to set table with AUTOMAPPING

procedure TfrmPrincipal.btnRemoveClick(Sender: TObject);
var
  Manager: TObjectManager;
  Grupos: TList<TGrupos>;
  Grupo: TGrupos;
begin
  Manager := TObjectManager.Create(conn);
  try
    Grupos := Manager.Find<TGrupos>().List;
    for Grupo in Grupos do
    begin
      Manager.remove(Grupo); //EXCEPTION IN THIS LINE
    end;
  finally
    Manager.Free;
  end;
end;


PS: When we remove the blob field from the class or remove the TColumnProp.Lazy property from it, the error has not ocurred any more.

PS2: The Class was exported with DataModeler

I still don't see any problem. Are you able to create a small project that reproduces the problem with a SQLite database? If you can send to me I can debug and check what's wrong.

We were able to simulate the error with the Echo example, inserting only a new property in the TCustomer Class of type TBlob with TColumnProp.Lazy.

CLASS
type
  [Entity, Automapping]
  TCustomer = class
  private
    FId: TGuid;
    FName: string;
    [Column('IMAGEM', [TColumnProp.Lazy])]
    FImage:TBlob;
  public
    property Id: TGuid read FId write FId;
    property Name: string read FName write FName;
    property Image: TBlob read FImage write FImage;
  end;


When trying to delete by AureliusDataSet, we recived the same error.

ERRO: "First chance exception at $006AE95D. Exception class $C0000005 with message 'access violation at 0x006ae95d: read of address 0x00000004'. Process EchoBasicDemo.exe (10656)"

If you want, we can send the modified project to your email, so that you can analyze
Link of broken project

https://www.xpointsolucoes.com.br/basic.rar


Ok, you didn't mention you were using TMS Echo. We were able to reproduce and fix the problem, it's caused by the TMS Echo logger. If you need a patch before we release a new version with this fix, please send us an e-mail directly asking for the patch.