What happened to OC? - CLOSED Carnage?!
Sign in to follow this  
Followers 0
Kavawuvi

SAPP HTTP Client

11 posts in this topic

Tiddy-bits:

The response returns null if it contains any character between 0x80 and 0xFF?

Fixed! I also fixed a couple other things, though they were mainly just typos (mainly, checking if it was null was broken, and the above example was broken. all was fixed).

 

Lastly, I added http_response_length which will read the number of bytes received from the stream, returning 0 if it's null or otherwise empty.

giraffe likes this

Share this post


Link to post
Share on other sites

I don't have a server so don't use any of this but just wanted to say congrats on all the advances you've made with SAPP.

WaeV, Sceny and Kavawuvi like this

Umh7x1l.gif

Share this post


Link to post
Share on other sites

Forgot to note, you CAN actually use downloaded data with SAPP's read_XXXX functions if you convert it to a numerical pointer. Example:

local response = http_client.http_get("https://dl.dropboxusercontent.com/u/30298900/ui.map", true)
local length = http_client.http_response_length(response)
cprint("Downloaded " .. (math.ceil(length / 1000 / 1000 * 100) / 100) .. " megabytes.")
if length < 0x800 then
    cprint("Failed to retrieve the map.")
    http_client.http_destroy_response(response)
    return
end

local map_pointer = tonumber(ffi.cast("uint32_t",http_client.http_read_response(response)))

local head = read_dword(map_pointer + 0) == 0x68656164
local foot = read_dword(map_pointer + 0x7FC) == 0x666F6F74

if head == false or foot == false then
    cprint("Map is invalid.")
    http_client.http_destroy_response(response)
    return
end

cprint("Map Name: " .. read_string(map_pointer + 0x20))
cprint("Map Build Version: " .. read_string(map_pointer + 0x40))

local file_size_in_header = read_dword(map_pointer + 0x8)
cprint("File size in header: " .. file_size_in_header .. " bytes...")

if(file_size_in_header == length) then
    cprint("File size in header is correct.")
else
    cprint("File size in header is wrong. It is off by " .. math.abs(file_size_in_header - length) .. " bytes.")
end

local meta_data = read_dword(map_pointer + 0x10)
if meta_data > length then
    cprint("Tag data is located outside of the map file for some reason. Backing off...")
    http_client.http_destroy_response(response)
    return
end
local scnr_tag_id = read_word(map_pointer + meta_data + 0x4)

local scnr_tag_entry = read_dword(map_pointer + meta_data) - 0x40440000 + scnr_tag_id * 0x20 + meta_data
if scnr_tag_entry < 0 or scnr_tag_entry > length then
    cprint("Scnr tag is located outside of the map file for some reason. Backing off...")
    http_client.http_destroy_response(response)
    return
end

local scnr_tag_name_pointer = read_dword(map_pointer + scnr_tag_entry + 0x10) - 0x40440000 + meta_data
if scnr_tag_name_pointer < 0 or scnr_tag_name_pointer > length then
    cprint("Scnr tag path is located outside of the map file for some reason. Backing off...")
    http_client.http_destroy_response(response)
    return
end

cprint("Principal scenario tag: " .. read_string(map_pointer + scnr_tag_name_pointer))

http_client.http_destroy_response(response)

In the console, this shows up as:

Downloaded 2.65 megabytes.
Map Name: ui
Map Build Version: 01.00.00.0563
File size in header: 2649984 bytes...
File size in header is correct.
Principal scenario tag: levels\ui\ui

This is probably a little more than what most people will do, but it works. As usual, using a pointer after it's been destroyed will crash this server. However, you do need to destroy pointers if you want to prevent memory leaks.

Share this post


Link to post
Share on other sites

I've updated this asset to include a second argument to http_get. If it is true, then the request will be done asynchronously, which will prevent the request from blocking the main thread, allowing game logic to continue as the request is being made. This is useful for requests that need to made during the game while other players are present. Setting it to false will use the same functionality as before, which is simpler but will halt game logic until the request is finished as usual.

 

You can then check if the request is completed using the functions listed in the OP periodically using timers. Note that SAPP timers only accept string arguments (the request cannot be converted to a string), so you will need to store the request using a global variable.

 

I've also included the source code.

NeX, WaeV and Chalwk like this

Share this post


Link to post
Share on other sites

Is it possible to do a post request and set headers, with the sapp http client here?  I'm pretty ignorant of how this was made, but I think being able to do an http post request and set headers and data for the request would open up possibilities to use the client with any generic oauth api.  I've seen a couple of discord bots released that use an external framework for the sending/requesting data from the discord api, but I believe the http client would be able to do those requests if post was possible.  If the function is already there I would appreciate a code snippet of how to do a POST request, otherwise I'm going out on a limb and requesting for it to be implemented.  A host like elite game servers would probably take some coaxing to allow extra executables to run on their services, but the problem could be solved here if someone wanted to make oauth api requests.  Elite game servers has let me upload the sapp http client with no issues probably because it's all only .dll files.  The current version of the sapp http client is working perfectly for what I'm using it for and all the data I send to my webserver is in a query string like ?var1=value1&var2=value2, so I don't necessarily need to do post, but it would probably be useful down the line to make scripts that use an http api more compatible across different hosts.  If this doesn't make sense then that's ok too because I don't understand some components of it so I may be wrong.

Chalwk likes this

Share this post


Link to post
Share on other sites
20 minutes ago, Kavawuvi said:

Gosh, I don't have easy access to the original source code for it as it's sitting on my old MacBook Air which hardly works anymore. Unfortunately this was before I was super staunch against closed source things in the Halo community, so it never crossed my mind that I'd want to extend this functionality or even maintain this old project from years ago.

 

That being said, I've had a lot of good luck with cURL (libcurl) on Chimera doing POST requests, so it should be possible to take libcurl and use it with SAPP if the FFI stuff hasn't changed. I'll give it a look later this week, as right now I'm working on some Vulkan stuff on Linux, and switching over to my Windows 10 PC to work on this stuff can be a little inconvenient with this setup.

Thanks!  Curl would be even better, I'm trying to begin to understand how things can be included with ffi in lua, but I've never really done much with compiled languages before, my experience stems from scripting languages.  I'm enjoying my time with sapp and chimera scripting and learning more all the time.

Chalwk and Enclusion like this

Share this post


Link to post
Share on other sites
Sign in to follow this  
Followers 0
  • Recently Browsing   0 members

    No registered users viewing this page.