Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
IdFTP.Quit deprecated?
#1
When I build my project in Lazarus 1.8.4 (FPC 3.0.4) I always get warnings from IdFTP.Quit calls being deprecated.


Code:
Compile Project, Target: bin/AGILicMgr: Success, Warnings: 2
AGILicMgr.dpr(262,20) Warning: Symbol "Quit" is deprecated
AGILicMgr.dpr(269,15) Warning: Symbol "Quit" is deprecated

This is the first warning location:

Code:
    if IdFTPtfr.Connected then
    begin
      IdFTPtfr.Quit; // <== Warning here
    end;

But I have looked at the on-line documentation where there is no sign of any deprecation...

What gives? Is the IndyLaz package installed via OnLinePackageManager somehow broken?

The further effect of this problem is that there are no tool-tips for the IdFTP component, when I press period after the IdFTP variable Lazarus just displays this in the message box:



Code:
Codetools, Errors: 1
IdGlobal.pas(1889,105) Error: expected ;, but deprecated found

And no popup in the editor suggests any valid command.
Reply
#2
(10-25-2018, 11:03 AM)BosseB Wrote: When I build my project in Lazarus 1.8.4 (FPC 3.0.4) I always get warnings from IdFTP.Quit calls being deprecated.

That means your code is outdated and needs to be updated.

In Indy 9 and earlier, the QUIT command is sent to the FTP server only if the TIdFTP.Quit() method is called.  If you call Disconnect() without calling Quit() first, no QUIT command is sent.  TIdFTP.Quit() sends the QUIT command and then calls Disconnect():

Code:
procedure TIdFTP.Quit;
begin
 if Connected then begin
   WriteLn('QUIT');      {Do not translate}
 end;
 Disconnect;
end;

In Indy 10, the QUIT command is now handled by DisconnectNotifyPeer() instead, which Disconnect() calls when its optional ANotifyPeer parameter is True. TIdFTP.Quit() simply calls Disconnect(True), which is why Quit() is deprecated:

Code:
procedure TIdTCPConnection.Disconnect(ANotifyPeer: Boolean);
var
 ...
begin
 try
   ...
   if ANotifyPeer then begin
     ...
     try
       if Connected then begin
         DisconnectNotifyPeer;
       end;
     except
       // TODO: maybe allow only EIdConnClosedGracefully and EIdSocketError?
     end;
   end;
 ...
end;

procedure TIdTCPConnection.Disconnect;
begin
 // The default should be to tell the other side we are disconnecting
 Disconnect(True);
end;

Code:
procedure TIdFTP.DisconnectNotifyPeer;
begin
 inherited DisconnectNotifyPeer;
 IOHandler.WriteLn('QUIT');      {do not localize}
 IOHandler.CheckForDataOnSource(100);
 if not IOHandler.InputBufferIsEmpty then begin
   GetInternalResponse;
 end;
end;

procedure TIdFTP.Quit;
begin
 Disconnect;
end;

(10-25-2018, 11:03 AM)BosseB Wrote: This is the first warning location:

Code:
    if IdFTPtfr.Connected then
    begin
      IdFTPtfr.Quit; // <== Warning here
    end;

When using Indy 10, simply replace Quit() with Disconnect():

Code:
if IdFTPtfr.Connected then
begin
 IdFTPtfr.Disconnect;
end;

FYI, you can call Disconnect() without checking with Connected() first.

(10-25-2018, 11:03 AM)BosseB Wrote: But I have looked at the on-line documentation where there is no sign of any deprecation...

The documentation is out of date, it hasn't been updated in years.

(10-25-2018, 11:03 AM)BosseB Wrote: What gives? Is the IndyLaz package installed via OnLinePackageManager somehow broken?

No.  Your code is simply old, it was written for Indy 9 and not updated for Indy 10.

(10-25-2018, 11:03 AM)BosseB Wrote: The further effect of this problem is that there are no tool-tips for the IdFTP component, when I press period after the IdFTP variable Lazarus just displays this in the message box:

Code:
Codetools, Errors: 1
IdGlobal.pas(1889,105) Error: expected ;, but deprecated found

Oh no, not THAT old issue again  Angry  Sad <sigh>

The offending line in IdGlobal.pas is this:

Code:
 // For linux the user needs to set this variable to be accurate where used (mail, etc)
 GOffsetFromUTC: TDateTime = 0{$IFDEF HAS_DEPRECATED}{$IFDEF USE_SEMICOLON_BEFORE_DEPRECATED};{$ENDIF} deprecated{$ENDIF};

(there is a similar declaration in IdWship6.pas on line 432 for a global boolean variable named GIdIPv6FuncsAvailable).

USE_SEMICOLON_BEFORE_DEPRECATED is defined only for FPC 2.4.4 - 2.6.1.  I've gone back and forth on this issue several times in the FreePascal/Lazarus forum about whether the semicolon is necessary or not (see this topic, and also the end of this message).  Delphi and FreePascal 2.6.2+ do not need the semicolon:

Code:
 GOffsetFromUTC: TDateTime = 0 deprecated;

But older versions of FreePascal do:

Code:
 GOffsetFromUTC: TDateTime = 0; deprecated;

Hence why USE_SEMICOLON_BEFORE_DEPRECATED exists.

You are using FreePascal 3.0.4, so the semicolon should not be needed.

Since the popup error is related to code completion, which is an IDE feature, not a compiler feature, this makes me think that you found a Lazarus IDE bug that doesn't handle the newer code syntax that omits the semicolon, even though the compiler accepts the syntax.

Reply
#3
Should I post it as an error in the lazarus group? (I use GMane and a newsreader for interactions with the lazarus and fpc mail lists)
Since Lazarus brings up the IdGlobals unit at the line you showed, is there some modification I can do to it so this goes away?
The line I get to is not something I really understand:
Code:
GOffsetFromUTC: TDateTime = 0{$IFDEF HAS_DEPRECATED}{$IFDEF USE_SEMICOLON_BEFORE_DEPRECATED};{$ENDIF} deprecated{$ENDIF};
Reply
#4
(10-25-2018, 09:22 PM)BosseB Wrote: Should I post it as an error in the lazarus group?

Yes.  This is not an Indy issue.  The code itself is known to work fine, in both Delphi and FreePascal.  The issue is with Lazarus itself.

(10-25-2018, 09:22 PM)BosseB Wrote: Since Lazarus brings up the IdGlobals unit at the line you showed, is there some modification I can do to it so this goes away?

Well, since we know FreePascal 3.x supports deprecated, you can remove that IFDEF:

Code:
GOffsetFromUTC: TDateTime = 0{$IFDEF USE_SEMICOLON_BEFORE_DEPRECATED};{$ENDIF} deprecated;

And we know FreePascal 3.x does not require the semicolon before deprecated, so you can remove that IFDEF, too:

Code:
GOffsetFromUTC: TDateTime = 0 deprecated;

Now, if Lazarus still exhibits the problem, try adding the semicolon back in:

Code:
GOffsetFromUTC: TDateTime = 0; deprecated;

Either way, you will have something clean and definitive to report to the Lazarus people.

(10-25-2018, 09:22 PM)BosseB Wrote: The line I get to is not something I really understand:

What don't you understand exactly?  There is a global variable GOffsetFromUTC that is marked as deprecated in compilers that support that, but there is an ambiguity in FreePascal only about the syntax needed to deprecate such a variable declaration.

Reply
#5
What I did not see was that the conditionals handled the presence of the semicolon itself....

I just tested the same project in Windows (32 bit) and it does not do the same.
If I enter IdFTPtfr on a line and wait until it is highlighted and then hit period the tooltips show up with the IdFTP methods (including Quit).
So there is definitely a problem with the UNIX version of IndyLaz...
By changing to this line without deprecated and the ifdefs everything starts working OK:
(Could not get any variation with deprecated in the line to work.)
Code:
GOffsetFromUTC: TDateTime = 0;

Tooltips appear as they should and the compile works too.

I have sent a message to the Lazarus list now (via GMane) concerning this issue.
Reply


Forum Jump:


Users browsing this thread: 1 Guest(s)