Skip to content

Commit

Permalink
python backend wip
Browse files Browse the repository at this point in the history
  • Loading branch information
a-sync committed May 1, 2024
1 parent d016b74 commit 0d06911
Show file tree
Hide file tree
Showing 5 changed files with 94 additions and 155 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@

backend/__pycache__/
3 changes: 1 addition & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@ Only alphanumeric characters + `_` and the optional `*` prefix/suffix is allowed
NodeJS or PHP runtime is required to relay backend calls to the steam API. _(CORS disabled 😔)_
Spin up an instance on `http://localhost/` with one of these commands:
* nodejs: `node server.js`
* python: `python server.py`
* php: `php -S 0.0.0.0:80`
* docker (php): `docker-compose up`

Expand All @@ -99,9 +100,7 @@ _The app can be served from under any subdomain or path._
* https://github.com/TehGreatFred/armaModIDFormatter

## TODO
* python backend
* prompt for the preset name before saving if it's not set
* resolve unmet workshop dependencies on demand
* preset file to URL converter
* add a section for the most recently updated mods ordered by date DESC
* show mod size and last update on hover in modlist
176 changes: 72 additions & 104 deletions backend/index.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,117 +2,85 @@
import json
import http.client
import urllib.parse
from http.server import BaseHTTPRequestHandler, HTTPServer

CACHE_MAX_AGE = int(os.getenv('CACHE_MAX_AGE', '0'))
STEAM_WEB_API_KEY = os.getenv('STEAM_WEB_API_KEY', '')

class RequestHandler(BaseHTTPRequestHandler):
def do_POST(self):
content_length = int(self.headers['Content-Length'])
post_data = self.rfile.read(content_length)
data = json.loads(post_data)

id_list = [str(id) for id in data['payload'] if str(id).isdigit()]
if not id_list:
self.send_error(400, 'Invalid payload')
return

if data['api'] == 'app':
response = []
for id in id_list:
conn = http.client.HTTPSConnection("store.steampowered.com")
conn.request("GET", "/api/appdetails?appids=" + id)
res = conn.getresponse()
data = json.loads(res.read())
if data[id]['success']:
response.append(data[id]['data'])
self.send_response(200)
self.send_header('Content-type', 'application/json')
self.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
self.end_headers()
self.wfile.write(json.dumps({"response": response}).encode())
else:
if data['api'] == 'file' and STEAM_WEB_API_KEY:
api = 'IPublishedFileService/GetDetails'
params = {
'key': STEAM_WEB_API_KEY,
'appid': 107410,
'publishedfileids': id_list,
'includetags': True,
'includeadditionalpreviews': False,
'includechildren': False,
'includekvtags': False,
'includevotes': False,
'short_description': False,
'includeforsaledata': False,
'includemetadata': False,
'return_playtime_stats': False,
'strip_description_bbcode': False
}
conn = http.client.HTTPSConnection("api.steampowered.com")
conn.request("GET", "/" + api + "/v1/?" + urllib.parse.urlencode(params))
res = conn.getresponse()
self.send_response(200)
self.send_header('Content-type', 'application/json')
self.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
self.end_headers()
self.wfile.write(res.read())
elif data['api'] == 'file':
api = 'ISteamRemoteStorage/GetPublishedFileDetails'
params = {'itemcount': len(id_list), 'publishedfileids': id_list}
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
conn = http.client.HTTPSConnection("api.steampowered.com")
conn.request("POST", "/" + api + "/v1/?", urllib.parse.urlencode(params), headers)
res = conn.getresponse()
self.send_response(200)
self.send_header('Content-type', 'application/json')
self.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
self.end_headers()
self.wfile.write(res.read())
elif data['api'] == 'collection':
api = 'ISteamRemoteStorage/GetCollectionDetails'
params = {'collectioncount': len(id_list), 'publishedfileids': id_list}
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
conn = http.client.HTTPSConnection("api.steampowered.com")
conn.request("POST", "/" + api + "/v1/?", urllib.parse.urlencode(params), headers)
res = conn.getresponse()
self.send_response(200)
self.send_header('Content-type', 'application/json')
self.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
self.end_headers()
self.wfile.write(res.read())
else:
self.send_error(400, 'Invalid api')

def run(server_class=HTTPServer, handler_class=RequestHandler):
server_address = ('', 8000)
httpd = server_class(server_address, handler_class)
httpd.serve_forever()

if __name__ == "__main__":
run()

################################################
#todo upd modular:

import os
import json
import http.client
import urllib.parse

CACHE_MAX_AGE = int(os.getenv('CACHE_MAX_AGE', '0'))
STEAM_WEB_API_KEY = os.getenv('STEAM_WEB_API_KEY', '')

def handle_post(request, response):
content_length = int(request.headers['Content-Length'])
post_data = request.rfile.read(content_length)
def handle_post(rh):
content_length = int(rh.headers['Content-Length'])
post_data = rh.rfile.read(content_length)
data = json.loads(post_data)

id_list = [str(id) for id in data['payload'] if str(id).isdigit()]
if not id_list:
response.send_error(400, 'Invalid payload')
rh.send_error(400, 'Invalid payload')
return

# Your previous script goes here
# ...
if data['api'] == 'app':
resdata = []
for id in id_list:
conn = http.client.HTTPSConnection("store.steampowered.com")
conn.request("GET", "/api/appdetails?appids=" + id)
res = conn.getresponse()
data = json.loads(res.read())
if data[id]['success']:
resdata.append(data[id]['data'])
rh.send_response(200)
rh.send_header('Content-type', 'application/json')
rh.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
rh.end_headers()
rh.wfile.write(json.dumps({"response": resdata}).encode())
elif data['api'] == 'file' and STEAM_WEB_API_KEY:
api = 'IPublishedFileService/GetDetails'
params = {
'key': STEAM_WEB_API_KEY,
'appid': 107410,
'publishedfileids': id_list,
'includetags': True,
'includeadditionalpreviews': False,
'includechildren': False,
'includekvtags': False,
'includevotes': False,
'short_description': False,
'includeforsaledata': False,
'includemetadata': False,
'return_playtime_stats': False,
'strip_description_bbcode': False
}
conn = http.client.HTTPSConnection("api.steampowered.com")
conn.request("GET", "/" + api + "/v1/?" + urllib.parse.urlencode(params))
res = conn.getresponse()
rh.send_response(200)
rh.send_header('Content-type', 'application/json')
rh.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
rh.end_headers()
rh.wfile.write(res.read())
elif data['api'] == 'file':
api = 'ISteamRemoteStorage/GetPublishedFileDetails'
params = {'itemcount': len(id_list), 'publishedfileids': id_list}
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
conn = http.client.HTTPSConnection("api.steampowered.com")
conn.request("POST", "/" + api + "/v1/?", urllib.parse.urlencode(params), headers)
res = conn.getresponse()
rh.send_response(200)
rh.send_header('Content-type', 'application/json')
rh.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
rh.end_headers()
rh.wfile.write(res.read())
elif data['api'] == 'collection':
print(f"id_list: {id_list}")
api = 'ISteamRemoteStorage/GetCollectionDetails'
params = {'collectioncount': len(id_list), 'publishedfileids': id_list}
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
conn = http.client.HTTPSConnection("api.steampowered.com")
conn.request("POST", "/" + api + "/v1/?", urllib.parse.urlencode(params), headers)
res = conn.getresponse()
print(f"Response status: {res.status}")
print(f"Sending POST request to: {urllib.parse.urlencode(params)}")
rh.send_response(200)
rh.send_header('Content-type', 'application/json')
rh.send_header('Cache-Control', 'max-age=' + str(CACHE_MAX_AGE))
rh.end_headers()
rh.wfile.write(res.read())
else:
rh.send_error(400, 'Invalid api')
15 changes: 10 additions & 5 deletions main.js
Original file line number Diff line number Diff line change
Expand Up @@ -76,9 +76,17 @@ async function init() {

render(presetIds);
id('dl-button').addEventListener('click', downloadPreset);
id('loading').className = 'dnone';
id('main').className = '';
} else {
if (confirm('Redirect to the README?')) window.location.replace('https://github.com/a-sync/arma3pregen#readme');
else id('loading').textContent = 'No valid IDs found in the URL.';
id('dl-button').className = 'dnone';
id('loading').replaceChildren();
id('loading').textContent = 'No valid IDs found in the URL.';
id('loading').appendChild(e('br'));
const a = e('a', 'README');
a.href = 'https://github.com/a-sync/arma3pregen#readme';
id('loading').appendChild(a);
id('main').className = '';
}
} catch (err) {
console.error(err);
Expand Down Expand Up @@ -263,9 +271,6 @@ function render(ids) {
}

renderDownloadButton();

id('loading').className = 'dnone';
id('main').className = '';
}

function renderSingleItem(i, mod, collection, optionals) {
Expand Down
53 changes: 9 additions & 44 deletions server.py
Original file line number Diff line number Diff line change
@@ -1,33 +1,21 @@
import os
import json
import http.server
import urllib.parse
from http.server import BaseHTTPRequestHandler, HTTPServer
from backend.index import handle_post

CACHE_MAX_AGE = int(os.getenv('CACHE_MAX_AGE', '0'))
STEAM_WEB_API_KEY = os.getenv('STEAM_WEB_API_KEY', '')
PORT = int(os.getenv('PORT', '80'))

class RequestHandler(BaseHTTPRequestHandler):
def do_POST(self):
if self.path == '/backend':
content_length = int(self.headers['Content-Length'])
post_data = self.rfile.read(content_length)
data = json.loads(post_data)

id_list = [str(id) for id in data['payload'] if str(id).isdigit()]
if not id_list:
self.send_error(400, 'Invalid payload')
return

# Your previous script goes here
# ...

if self.path == '/backend/':
handle_post(self)
else:
self.send_error(404, 'Not Found')

def do_GET(self):
if self.path in ['/index.html', '/main.css', '/main.js', '/']:
if self.path == '/':
base_path = self.path.split('?')[0].split('#')[0]

if base_path in ['/index.html', '/main.css', '/main.js', '/']:
if base_path == '/':
file_path = '/index.html'
else:
file_path = self.path
Expand All @@ -52,32 +40,9 @@ def do_GET(self):
self.send_error(404, 'Not Found')

def run(server_class=HTTPServer, handler_class=RequestHandler):
server_address = ('', 8000)
server_address = ('', PORT)
httpd = server_class(server_address, handler_class)
httpd.serve_forever()

if __name__ == "__main__":
run()


#########################################
#todo: upd modular

import os
import json
import http.server
import urllib.parse
from http.server import BaseHTTPRequestHandler, HTTPServer
from backend.index import handle_post # Import the function

class RequestHandler(BaseHTTPRequestHandler):
def do_POST(self):
if self.path == '/backend':
handle_post(self, self) # Call the function
else:
self.send_error(404, 'Not Found')

# Rest of your code...

if __name__ == "__main__":
run()

0 comments on commit 0d06911

Please sign in to comment.