Skip to content
Merged
1 change: 1 addition & 0 deletions container-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ services:
orbit_version_info: "singularity ${SINGULARITY_VERSION} ${SINGULARITY_DEPLOYMENT_STATUS} https://github.com/underground-software/singularity"
environment:
TZ: ${SINGULARITY_TIMEZONE}
HOSTNAME: ${SINGULARITY_HOSTNAME}
volumes:
- type: volume
source: orbit-db
Expand Down
2 changes: 1 addition & 1 deletion nginx_snippets/server_https/00-orbit-paths.conf
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ location @login {
return 303 /login?target=$uri;
}

location ~* ^((.*\.md)|/log(in|out)|/activity|/dashboard|/register|/cgit.*)$ {
location ~* ^((.*\.md)|/log(in|out)|/activity|/dashboard|/register|/Containerfile|/cgit.*)$ {
include uwsgi_params;
proxy_intercept_errors on;
proxy_pass http://orbit:9098;
Expand Down
101 changes: 95 additions & 6 deletions orbit/radius.py
Original file line number Diff line number Diff line change
Expand Up @@ -636,6 +636,17 @@ def form_respond():
<h3>Password: {password}</h3><br>''')


def extract_basic_auth(rocket):
if (auth_str := rocket.env.get('HTTP_AUTHORIZATION')) is None:
return
if not auth_str.startswith('Basic '):
return
cred_str = base64.b64decode(auth_str.removeprefix('Basic '))
username, password = cred_str.decode().split(':', maxsplit=1)

return username, password


def determine_cache_entry(cred_str):
import hashlib
import time
Expand All @@ -647,15 +658,12 @@ def determine_cache_entry(cred_str):

def http_basic_auth(rocket):
import authcache
if (auth_str := rocket.env.get('HTTP_AUTHORIZATION')) is None:
if not (creds := extract_basic_auth(rocket)):
return
if not auth_str.startswith('Basic '):
return
cred_str = base64.b64decode(auth_str.removeprefix('Basic '))
cache_entry = determine_cache_entry(cred_str)
username, password = creds
cache_entry = determine_cache_entry(':'.join(creds))
if authcache.entry_exists(cache_entry):
return True
username, password = cred_str.decode().split(':', maxsplit=1)
if not check_credentials(username, password):
return
authcache.add_entry(cache_entry)
Expand Down Expand Up @@ -713,6 +721,85 @@ def cgit_internal_server_error(msg):
return cgit_internal_server_error(type(ex))


def handle_containerfile(rocket):
nano_default_editor = 'nano-default-editor' \
if not rocket.queries_query('vim') else ''

hostname = os.getenv("HOSTNAME")
if creds := extract_basic_auth(rocket):
username, password = creds
if not creds or not check_credentials(username, password):
rocket.headers.append(('WWW-Authenticate', 'Basic realm="podman"'))
return rocket.raw_respond(HTTPStatus.UNAUTHORIZED)
return rocket.raw_respond(HTTPStatus.OK, f'''
FROM fedora:41

RUN <<DNF
dnf -y update
dnf install -y --setopt=install_weak_deps=False \
git \
tar \
make \
gcc \
qemu-system-riscv \
binutils-riscv64-linux-gnu \
gcc-riscv64-linux-gnu \
bc \
flex \
bison \
openssl-devel \
elfutils-libelf-devel \
ncurses-devel \
dwarves \
git-email \
vim \
nano \
{nano_default_editor} \
mutt \
cpio \
wget \
strace
dnf clean all
DNF

RUN useradd {username} -U
USER {username}:{username}
WORKDIR /home/{username}/

RUN cat <<'MUTTRC' > ~/.muttrc
set realname="Your Name Here"
set my_username="{username}"
set my_password="{password}"
set course_domain="{hostname}"
set spoolfile=
set record=
set folder=
set sort=threads
set from="$my_username@$course_domain"
set header_cache=~/.cache/mutt
set smtp_url="smtps://$my_username:$my_password@$course_domain:465"
push "<change-folder>pops://$my_username:$my_password@$course_domain:995"\n
macro index l "|git am -s"\n
MUTTRC

RUN cat <<'GITCONFIG' > ~/.gitconfig
[user]
name = Your Name Here
email = {username}@{hostname}
[sendemail]
smtpUser = {username}
smtpPass = {password}
smtpserver = {hostname}
smtpserverport = 465
smtpencryption = ssl
GITCONFIG

VOLUME /home

ENTRYPOINT ["/usr/bin/bash", "-l", "-i"]
'''.strip().encode())


def handle_error(rocket):
error_num_str = rocket.queries_query('num')
try:
Expand Down Expand Up @@ -762,6 +849,8 @@ def application(env, SR):
return handle_logout(rocket)
case '/mail_auth':
return handle_mail_auth(rocket)
case '/Containerfile':
return handle_containerfile(rocket)
case '/activity':
return handle_activity(rocket)
case '/error':
Expand Down