andgineer / TRegExpr

Regular expressions (regex), pascal.
https://regex.sorokin.engineer/en/latest/
MIT License
174 stars 62 forks source link

LastError not always cleared #310

Closed User4martin closed 1 year ago

User4martin commented 1 year ago

The first call to Exec fails and sets LastError. The 2nd call however succeeds. Yet LastError is still set.

On the other hand, if one has an error compiling a RegEx (r.Expression := ...; r.Compile) then LastError is cleared (in case a prior compile or exec had set an error. Actually Clearing happens in CompileRegExpr, it might want to be done earlier (e.g. when the new Expression is assigned)

var
  RegEx: TRegExpr;

begin
  RegEx := TRegExpr.Create('a');
  RegEx.InputString := 'foobar';
  try
    writeln(1);
    writeln(RegEx.Exec(-9));
  except
  end;
  try
    writeln(2);
    writeln(RegEx.Exec(2));
  except
  end;
  writeln(RegEx.LastError);

output:

1
2
TRUE
1006
Alexey-T commented 1 year ago

Must be easy to fix. Todo.

Alexey-T commented 1 year ago

@User4martin See what I did in https://github.com/alexey-t/TRegExpr/tree/clear-lasterror , ok?

User4martin commented 1 year ago

Not sure. It relies on the exception skipping that code, if an error was newly set? But Exception throwing is in a virtual method, so it can be substituted by non-exception.

My proposal, in ExecPrim

  if programm = nil then
  begin
    Compile;   /// will clear the error, if run
    if programm = nil then
      Exit;
  end
  else 
    fLastError := reeOk;

If we did not try to compile, we have a valid program => so any error can be cleared, and a new match be attempted?


Actually, if it was an error compiling, it will try to compile for each attempted exec... But that is a different issue.

Alexey-T commented 1 year ago

yes, your proposal is smarter. Pls do the PR. Increase 163 to 164.

User4martin commented 1 year ago

will do - but may be a couple of days

User4martin commented 1 year ago

I opted to clear it ahead of that line. (nicely stashing it into the "internal clearing").

If the program gets compiled, the error will be cleared twice, but that causes no harm.