-
Content Count
2990 -
Joined
-
Last visited
-
Days Won
134
Everything posted by Remy Lebeau
-
indy Delphi and INDY: how to send a "DELETE" (the "Delete" button is in HTML page using ASP) to delete a "message" in the forum
Remy Lebeau replied to programmerdelphi2k's topic in Network, Cloud and Web
Since you are asking how to implement this with Indy, you should have posted this in the Indy group: https://en.delphipraxis.net/forum/35-indy/ You don't really have a choice in that matter. This is an all-or-nothing kind of deal. You are basically simulating a web browser, so you are going to receive whatever a web browser would receive to render data onscreen for the user to interact with. What you decide to do with that data is up to you. But if this is not the kind of data you want, then you should check if the website in question offers a separate REST API to access the data in another format that is more machine-oriented rather than user-oriented. You are not sending any data to the server, so you shouldn't be assigning values to those properties at all. And? What is your actual question about them? You are going to have to look at the underlying HTTP requests that a normal web browser submits for those actions, and then replicate them in your code accordingly. Because that is what you are asking for from the server. You are requesting data from a URL of an HTML webpage, so HTML is what you get back. Unless the server explicitly supports that operation for the URL in question (ie, via a URL query parameter or the 'Accept' header, etc), then you won't be able to get what you want. Either find another URL that gives you the data you want in the format you want, or else you will just have to deal with the HTML you are given. Only if the server supports giving out JSON. But, there is no way for anyone here to tell you how to do that, since you haven't even explained which website you are trying to access in the first place. If all you have is HTML, then you are just going to have to parse it to extract what you want from it. You probably don't need step 2 at all. Chances are, you can likely just look at the HTML of the edit webpage to determine the URL that it submits to, and then you can make your code Post() to that same URL with the appropriate headers and data as needed. Again, just look at the HTML for the appropriate webpage, and then have your code post your data to the same URL. Same as above. Determine the URL that the delete webpage submits to, and then make your code post an appropriate request to that same URL. OK, so what is the problem? Most modern web browsers have a built-in debugger that can show the raw HTTP traffic. TIdHTTP is just a wrapper for the HTTP protocol, so see what kind of HTTP requests a web browser sends for the actions you are interested in, and then replicate those requests in your TIdHTTP code. Not that hard, really. -
TIdFTP has a PassiveUseControlHost property for that exact purpose. It is False by default. TIdFTP has a UseExtensionDataPort property to enable use of EPSV if the server supports it. This is also False by default.
-
Sending Email via GMail Using OAuth 2.0 via Indy
Remy Lebeau replied to Ugochukwu Mmaduekwe's topic in Indy
Failed how, exactly? Since you are posting this in an Indy forum, I'll give you an Indy answer - You can either turn on 2-Factor Authentication in your Google account and then create an App-Specific password for Indy to use, thus not requiring OAuth2 and no code changes or upgrades needed to use TIdSMTP/TIdPOP3/TIdIMAP4. Or, if you must use OAuth2, then install the latest Indy OAuth2 branch code (https://github.com/IndySockets/Indy/tree/sasl-oauth) into your Delphi 2010 (which Indy still supports), replacing any Indy version you may already have installed (https://github.com/IndySockets/Indy/wiki/Updating-Indy), and then you can use TIdHTTP to retrieve an access token from Google, and use TIdSASLXOAuth2 to use that token with TIdSMTP/TIdPOP3/TIdIMAP4. -
Seems to be a duplicate of
-
Converting C++ API Post Request into Delphi Code
Remy Lebeau replied to robhercarlos's topic in General Help
You already received comments on there, which you have not fully responded to. So why are you posting it here, too? -
Compare two TIntegerDynArray
Remy Lebeau replied to shineworld's topic in RTL and Delphi Object Pascal
If there is any possibility that FGCodeLinePoints could be passed in to SetGCodeLinePoints() (eg: GCodeEditor1.GCodeLinePoints := GCodeEditor1.GCodeLinePoints;), then I would also add a pointer equality check as well, since dynamic arrays are implemented as ref-counted pinters, eg: procedure TGCodeEditor.SetGCodeLinePoints(Value: TIntegerDynArray); function IsEqualIntegerDynArray(const A, B: TIntegerDynArray): Boolean; var L: Integer; begin if Pointer(A) = Pointer(B) then Exit(True); // <-- HERE L := Length(A); if L <> Length(B) then Exit(False); Result := CompareMem(PInteger(A)^, PInteger(B)^, Sizeof(Integer) * L); end; begin if not IsEqualIntegerDynArray(FGCodeLinePoints, Value) then begin FGCodeLinePoints := Value; Invalidate; end; end; -
Via object hierarchies in memory, like any other. FMX's TForm establishes object hierarchies via its Parent, ParentForm, and Children properties. Just as VCL's TForm establishes object hierarchies via its Parent and Controls properties.
-
I was looking at this one instead (which is what Indy implements): Authenticate an IMAP, POP or SMTP connection using OAuth
-
I'm no expert in OAuth, but are you sure that is the correct scope to use for requesting accessing to IMAP? Also, it looks like you are bypassing the OAuth "/authorize" url, which returns an authorization token that you can submit to the "/token" url. Why? Is that even a valid flow?
-
Delphi XE - error connect DROPBOX via Indy TidHTTP (htttps)
Remy Lebeau replied to polasss's topic in Network, Cloud and Web
You chopped off some of the error message. It is complaining that the "protocol version" is not accepted. Even though you are setting the version to TLS 1.2, chances are that Indy or OpenSSL is falling back to TLS 1.0 or 1.1 instead, which will fail if the server actually requires TLS 1.2. Also, something else to consider - even if TLS 1.2 were being used correctly, most TLS 1.2 servers nowadays require clients to use the SNI extension to send the requested hostname in the TLS handshake (so appropriate certificates can be used), but Indy 10.5.9 did not support SNI. So upgrading to an up-to-date Indy version will gain you that feature. 10.5.9 is VERY old. Even if you don't update Delphi/Indy,, you should at least make sure you are using an updated OpenSSL. The last version of OpenSSL that Indy 10.6.2 officially supports is 1.0.2u (1.0.2.21). Support for OpenSSL 1.1+/3.0 is a WIP (https://github.com/IndySockets/Indy/pull/299), if you want to try it. -
Indy - upgrade to new version - error E2202 Required package 'paclientcore' not found
Remy Lebeau replied to polasss's topic in Indy
Nothing in Indy depends on that package. Double-check that your DPK and DPROJ files didn't pick up something unexpected by accident. -
Delphi XE - error connect DROPBOX via Indy TidHTTP (htttps)
Remy Lebeau replied to polasss's topic in Network, Cloud and Web
Nothing in Indy depends on that package. Double-check that your DPK and DPROJ files didn't pick up something unexpected by accident. -
Offhand, the code you have shown looks OK (except for the potential memory leaks), but I can't really answer your question, because you didn't show how you are obtaining the token in the first place, or what settings you have used for it.
-
Yes. This works for me: procedure TForm1.Button11Click(Sender: TObject); var MyXMLDocument : IXMLDocument; DocElement, FounderNode : IXMLNode; begin MyXMLDocument := NewXMLDocument(); MyXMLDocument.Active := True; DocElement := MyXMLDocument.CreateElement('ab', 'MyString'); MyXMLDocument.DocumentElement := DocElement; // alternatively: // DocElement := MyXMLDocument.AddChild('ab', 'MyString'); DocElement.DeclareNamespace('xsi', 'https://www.guru99.com/XMLSchema-instance'); DocElement.DeclareNamespace('xsd', 'https://www.guru99.com/XMLSchema'); // if this call is present then the 'xmlns=MyString' attribute will be at the end of the element, // but if this is omitted then the attribute will be at the front of the element instead, due to // the earlier CreateElement/AddChild call... DocElement.DeclareNamespace('', 'MyString'); FounderNode := DocElement.AddChild('founder'); FounderNode.Text := 'Krishna'; MyXMLDocument.SaveToFile('TestOne01.XML'); end; It is important that the 'ab' element actually have the 'MyString' namespace assigned to it, so that any child nodes can inherit it. When an `xmlns` attribute appears on a child node, it means the namespace was not inherited correctly.
-
The only HWND available in FMX comes from the TForm itself. Child controls do not have their own HWNDs. You can get the Form's HWND by using either WindowHandleToPlatform() or FormToHWND() in the FMX.Platform.Win unit. Otherwise, if you want a child control that has an HWND, you will have to create it yourself using the Win32 API CreateWindow/Ex() API directly.
-
That will only work for TForm handles (and alternatively, you can use FormToHWND() instead). In FMX, only a TForm has an actual Win32 HWND assigned, its child control do not have their own HWNDs, like they do in VCL. FMX child control are custom-drawn directly onto the TForm's window.
-
That line should be this instead: MyXMLDocument.DocumentElement.DeclareNamespace('', 'MyString'); Which is equivalent to this: MyXMLDocument.DocumentElement.SetAttributeNS('xmlns', 'http://www.w3.org/2000/xmlns/', 'MyString'); The DeclareNamespace() documentation does not mention that the Prefix parameter can be a blank string, but it is actually supported. This will treat the attribute as an actual namespace declaration in the DOM, even though it doesn't have a prefix assigned. It should also assign the 'MyString' namespace to the DocumentElement since that element doesn't have a prefix assigned, either. You are creating the element, but you are not assigning any text to it, which is why the element appears as </founder>. You need to add this after calling AddChild(): FounderNode.Text := 'Krishna'; Also, you may or may not need to specify the desired namespace when calling AddChild(), as well (this part I always forget about when exactly a namespace should be specified and when it can be inherited from the parent element - once you start dealing with namespaces in XML, you will find that you need to specify namespaces in add/insert and search operations more often than not): FounderNode := MyXMLDocument.DocumentElement.AddChild('founder', 'MyString');
-
Subscribe to a web stream and listen to incoming streams
Remy Lebeau replied to p-samuel's topic in Network, Cloud and Web
If that is the case, if each event is its own HTTP chunk, then you can use the TIdHTTP.OnChunkReceived event to handle the stream events. At the moment, you still have to provide a TStream in order for the OnChunkReceived event to fire (I may change that in the future), but you can use TIdEventStream with no event hanlders assigned so that the chunks written to the stream are ignored. -
TidHTTP under FMX for android does not work
Remy Lebeau replied to JohnLM's topic in Network, Cloud and Web
That is a VERY old version of Indy. Indy has been in 10.6.2.x since 2015. You should seriously consider upgrading to the latest version from Indy's GitHub repo. -
Seems you already asked this on StackOverflow, and a few answers were posted there: https://stackoverflow.com/questions/74422756/
-
Seems to be. I can't access anything on alpha.mike-r.com, so it must be down. I'm sure you can find another QOTD server online somewhere. There are a few mentioned on the bottom on https://wiki.freepascal.org/QOTD, for instance. Just look around.
-
Indy HttpClient send JSON to https://login.microsoftonline.com/
Remy Lebeau replied to marcin's topic in Indy
Why are you trying to send JSON? That is not what Microsoft's documentation tells you to send: https://learn.microsoft.com/en-us/azure/active-directory/develop/v2-oauth2-auth-code-flow#redeem-a-code-for-an-access-token The body is NOT to be JSON at all. It needs to be a '&'-delimited list of 'name=value' pairs instead. The TIdHTTP.Post() method handles the 'application/x-www-form-urlencoded' format for you, but only if you give it a TStrings (like TStringList), not a TStream, eg: requestBody := TStringList.Create; requestBody.Add('grant_type=client_credentials'); requestBody.Add('client_id=xxx'); requestBody.Add('client_secret=_xxx_'); requestBody.Add('scope=https://graph.microsoft.com/.default'); url := 'https://login.microsoftonline.com/' + TenantID + '/oauth2/v2.0/token'; FLastResult := IdHTTP.Post(url, requestBody); -
[Question/Feature] SSL/TLS fallback using magic bytes
Remy Lebeau replied to FearDC's topic in ICS - Internet Component Suite
I have implemented this kind of logic before, but only in plain socket code (though I suppose it can be applied to socket libraries like ICS or Indy, too). It requires the TLS server to peek not recv the first few bytes of a new connection, and only if those bytes belong to the header of a TLS handshake then enable TLS on that connection (allowing the previously-peeked bytes to now be read by whatever TLS library you use), otherwise don't enable TLS on the connection and just read the connection raw. -
Subscribe to a web stream and listen to incoming streams
Remy Lebeau replied to p-samuel's topic in Network, Cloud and Web
The screenshot you provided appears to be an actual websocket event. 'text/event-stream' is just a stream of linebreak-delimited events. TIdHTTP is not currently designed to handle that kind of stream. Using TIdEventStream is going to give you arbitrary blocks of data as they are read off the socket, which you are assuming are complete events, but that is not guaranteed (or even likely) to happen. To be safe, you would have to buffer the stream data, break it up on linebreaks as they become available, and decode only complete events as UTF-8. The code you have presented has the potential to decode incomplete events. In this type of situation, it would be useful if TIdHTTP had a flag available to tell it not to read the response body at all and just exit, letting the caller then read the body from the IOHandler directly as needed. Similar to the existing hoNoReadMultipartMIME and hoNoReadChunked flags, but for other kinds of responses. Such a flag does not exist at this time. -
Subscribe to a web stream and listen to incoming streams
Remy Lebeau replied to p-samuel's topic in Network, Cloud and Web
That is only part of the response, and not even the relevant part, eihter. That snippet shows that you are requesting an unencrypted HTTP url and being redirected to an encrypted HTTPS url, but it is not showing the contents of the subsequent HTTPS request or its response, which contains the actual event data.