|
@@ -10,13 +10,21 @@ which has a tutorial available :ref:`here <doc_http_request_class>`.
|
|
Here's an example of using the :ref:`HTTPClient <class_HTTPClient>`
|
|
Here's an example of using the :ref:`HTTPClient <class_HTTPClient>`
|
|
class. It's just a script, so it can be run by executing:
|
|
class. It's just a script, so it can be run by executing:
|
|
|
|
|
|
-.. code-block:: console
|
|
|
|
|
|
+.. tabs::
|
|
|
|
+
|
|
|
|
+ .. code-tab:: console GDScript
|
|
|
|
|
|
c:\godot> godot -s http_test.gd
|
|
c:\godot> godot -s http_test.gd
|
|
|
|
|
|
|
|
+ .. code-tab:: console C#
|
|
|
|
+
|
|
|
|
+ c:\godot> godot -s HTTPTest.cs
|
|
|
|
+
|
|
It will connect and fetch a website.
|
|
It will connect and fetch a website.
|
|
|
|
|
|
-::
|
|
|
|
|
|
+.. tabs::
|
|
|
|
+
|
|
|
|
+ .. code-tab:: gdscript GDScript
|
|
|
|
|
|
extends SceneTree
|
|
extends SceneTree
|
|
|
|
|
|
@@ -28,7 +36,7 @@ It will connect and fetch a website.
|
|
var http = HTTPClient.new() # Create the Client.
|
|
var http = HTTPClient.new() # Create the Client.
|
|
|
|
|
|
err = http.connect_to_host("www.php.net", 80) # Connect to host/port.
|
|
err = http.connect_to_host("www.php.net", 80) # Connect to host/port.
|
|
- assert(err == OK) # Make sure connection was OK.
|
|
|
|
|
|
+ assert(err == OK) # Make sure connection is OK.
|
|
|
|
|
|
# Wait until resolved and connected.
|
|
# Wait until resolved and connected.
|
|
while http.get_status() == HTTPClient.STATUS_CONNECTING or http.get_status() == HTTPClient.STATUS_RESOLVING:
|
|
while http.get_status() == HTTPClient.STATUS_CONNECTING or http.get_status() == HTTPClient.STATUS_RESOLVING:
|
|
@@ -39,7 +47,7 @@ It will connect and fetch a website.
|
|
else:
|
|
else:
|
|
yield(Engine.get_main_loop(), "idle_frame")
|
|
yield(Engine.get_main_loop(), "idle_frame")
|
|
|
|
|
|
- assert(http.get_status() == HTTPClient.STATUS_CONNECTED) # Could not connect
|
|
|
|
|
|
+ assert(http.get_status() == HTTPClient.STATUS_CONNECTED) # Check if the connection was made successfully.
|
|
|
|
|
|
# Some headers
|
|
# Some headers
|
|
var headers = [
|
|
var headers = [
|
|
@@ -54,12 +62,12 @@ It will connect and fetch a website.
|
|
# Keep polling for as long as the request is being processed.
|
|
# Keep polling for as long as the request is being processed.
|
|
http.poll()
|
|
http.poll()
|
|
print("Requesting...")
|
|
print("Requesting...")
|
|
- if not OS.has_feature("web"):
|
|
|
|
- OS.delay_msec(500)
|
|
|
|
- else:
|
|
|
|
|
|
+ if OS.has_feature("web"):
|
|
# Synchronous HTTP requests are not supported on the web,
|
|
# Synchronous HTTP requests are not supported on the web,
|
|
# so wait for the next main loop iteration.
|
|
# so wait for the next main loop iteration.
|
|
yield(Engine.get_main_loop(), "idle_frame")
|
|
yield(Engine.get_main_loop(), "idle_frame")
|
|
|
|
+ else:
|
|
|
|
+ OS.delay_msec(500)
|
|
|
|
|
|
assert(http.get_status() == HTTPClient.STATUS_BODY or http.get_status() == HTTPClient.STATUS_CONNECTED) # Make sure request finished well.
|
|
assert(http.get_status() == HTTPClient.STATUS_BODY or http.get_status() == HTTPClient.STATUS_CONNECTED) # Make sure request finished well.
|
|
|
|
|
|
@@ -106,3 +114,106 @@ It will connect and fetch a website.
|
|
print("Text: ", text)
|
|
print("Text: ", text)
|
|
|
|
|
|
quit()
|
|
quit()
|
|
|
|
+
|
|
|
|
+ .. code-tab:: csharp
|
|
|
|
+
|
|
|
|
+ class HTTPTest : SceneTree
|
|
|
|
+ {
|
|
|
|
+ // HTTPClient demo.
|
|
|
|
+ // This simple class can make HTTP requests; it will not block, but it needs to be polled.
|
|
|
|
+ public override async void _Initialize()
|
|
|
|
+ {
|
|
|
|
+ Error err;
|
|
|
|
+ HTTPClient http = new HTTPClient(); // Create the client.
|
|
|
|
+
|
|
|
|
+ err = http.ConnectToHost("www.php.net", 80); // Connect to host/port.
|
|
|
|
+ Debug.Assert(err == Error.Ok); // Make sure the connection is OK.
|
|
|
|
+
|
|
|
|
+ // Wait until resolved and connected.
|
|
|
|
+ while (http.GetStatus() == HTTPClient.Status.Connecting || http.GetStatus() == HTTPClient.Status.Resolving)
|
|
|
|
+ {
|
|
|
|
+ http.Poll();
|
|
|
|
+ GD.Print("Connecting...");
|
|
|
|
+ OS.DelayMsec(500);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ Debug.Assert(http.GetStatus() == HTTPClient.Status.Connected); // Check if the connection was made successfully.
|
|
|
|
+
|
|
|
|
+ // Some headers.
|
|
|
|
+ string[] headers = { "User-Agent: Pirulo/1.0 (Godot)", "Accept: */*" };
|
|
|
|
+
|
|
|
|
+ err = http.Request(HTTPClient.Method.Get, "/ChangeLog-5.php", headers); // Request a page from the site.
|
|
|
|
+ Debug.Assert(err == Error.Ok); // Make sure all is OK.
|
|
|
|
+
|
|
|
|
+ // Keep polling for as long as the request is being processed.
|
|
|
|
+ while (http.GetStatus() == HTTPClient.Status.Requesting)
|
|
|
|
+ {
|
|
|
|
+ http.Poll();
|
|
|
|
+ GD.Print("Requesting...");
|
|
|
|
+ if (OS.HasFeature("web"))
|
|
|
|
+ {
|
|
|
|
+ // Synchronous HTTP requests are not supported on the web,
|
|
|
|
+ // so wait for the next main loop iteration.
|
|
|
|
+ await ToSignal(Engine.GetMainLoop(), "idle_frame");
|
|
|
|
+ }
|
|
|
|
+ else
|
|
|
|
+ {
|
|
|
|
+ OS.DelayMsec(500);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ Debug.Assert(http.GetStatus() == HTTPClient.Status.Body || http.GetStatus() == HTTPClient.Status.Connected); // Make sure the request finished well.
|
|
|
|
+
|
|
|
|
+ GD.Print("Response? ", http.HasResponse()); // The site might not have a response.
|
|
|
|
+
|
|
|
|
+ // If there is a response...
|
|
|
|
+ if (http.HasResponse())
|
|
|
|
+ {
|
|
|
|
+ headers = http.GetResponseHeaders(); // Get response headers.
|
|
|
|
+ GD.Print("Code: ", http.GetResponseCode()); // Show response code.
|
|
|
|
+ GD.Print("Headers:");
|
|
|
|
+ foreach (string header in headers)
|
|
|
|
+ {
|
|
|
|
+ // Show headers.
|
|
|
|
+ GD.Print(header);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if (http.IsResponseChunked())
|
|
|
|
+ {
|
|
|
|
+ // Does it use chunks?
|
|
|
|
+ GD.Print("Response is Chunked!");
|
|
|
|
+ }
|
|
|
|
+ else
|
|
|
|
+ {
|
|
|
|
+ // Or just Content-Length.
|
|
|
|
+ GD.Print("Response Length: ", http.GetResponseBodyLength());
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // This method works for both anyways.
|
|
|
|
+ List<byte> rb = new List<byte>(); // List that will hold the data.
|
|
|
|
+
|
|
|
|
+ // While there is data left to be read...
|
|
|
|
+ while (http.GetStatus() == HTTPClient.Status.Body)
|
|
|
|
+ {
|
|
|
|
+ http.Poll();
|
|
|
|
+ byte[] chunk = http.ReadResponseBodyChunk(); // Read a chunk.
|
|
|
|
+ if (chunk.Length == 0)
|
|
|
|
+ {
|
|
|
|
+ // If nothing was read, wait for the buffer to fill.
|
|
|
|
+ OS.DelayMsec(500);
|
|
|
|
+ }
|
|
|
|
+ else
|
|
|
|
+ {
|
|
|
|
+ // Append the chunk to the read buffer.
|
|
|
|
+ rb.AddRange(chunk);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // Done!
|
|
|
|
+ GD.Print("Bytes Downloaded: ", rb.Count);
|
|
|
|
+ string text = Encoding.ASCII.GetString(rb.ToArray());
|
|
|
|
+ GD.Print(text);
|
|
|
|
+ }
|
|
|
|
+ Quit();
|
|
|
|
+ }
|
|
|
|
+ }
|