mirror of
https://github.com/laurivosandi/certidude
synced 2025-10-30 08:59:13 +00:00
Integrate LEDE image builder
This commit is contained in:
@@ -82,7 +82,7 @@ class SessionResource(object):
|
||||
attributes = {}
|
||||
for key in listxattr(path):
|
||||
if key.startswith(b"user.machine."):
|
||||
attributes[key[13:]] = getxattr(path, key).decode("ascii")
|
||||
attributes[key[13:].decode("ascii")] = getxattr(path, key).decode("ascii")
|
||||
|
||||
# Extract lease information from filesystem
|
||||
try:
|
||||
@@ -131,6 +131,9 @@ class SessionResource(object):
|
||||
),
|
||||
request_submission_allowed = config.REQUEST_SUBMISSION_ALLOWED,
|
||||
authority = dict(
|
||||
builder = dict(
|
||||
profiles = config.IMAGE_BUILDER_PROFILES
|
||||
),
|
||||
tagging = [dict(name=t[0], type=t[1], title=t[2]) for t in config.TAG_TYPES],
|
||||
lease = dict(
|
||||
offline = 600, # Seconds from last seen activity to consider lease offline, OpenVPN reneg-sec option
|
||||
@@ -208,6 +211,7 @@ def certidude_app(log_handlers=[]):
|
||||
from .attrib import AttributeResource
|
||||
from .bootstrap import BootstrapResource
|
||||
from .token import TokenResource
|
||||
from .builder import ImageBuilderResource
|
||||
|
||||
app = falcon.API(middleware=NormalizeMiddleware())
|
||||
app.req_options.auto_parse_form_urlencoded = True
|
||||
@@ -240,6 +244,9 @@ def certidude_app(log_handlers=[]):
|
||||
# Bootstrap resource
|
||||
app.add_route("/api/bootstrap/", BootstrapResource())
|
||||
|
||||
# LEDE image builder resource
|
||||
app.add_route("/api/build/{profile}/{suggested_filename}", ImageBuilderResource())
|
||||
|
||||
# Add CRL handler if we have any whitelisted subnets
|
||||
if config.CRL_SUBNETS:
|
||||
from .revoked import RevocationListResource
|
||||
|
||||
52
certidude/api/builder.py
Normal file
52
certidude/api/builder.py
Normal file
@@ -0,0 +1,52 @@
|
||||
|
||||
import click
|
||||
import falcon
|
||||
import logging
|
||||
import os
|
||||
import subprocess
|
||||
from certidude import config, const
|
||||
from certidude.auth import login_required, authorize_admin
|
||||
from jinja2 import Template
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
class ImageBuilderResource(object):
|
||||
@login_required
|
||||
@authorize_admin
|
||||
def on_get(self, req, resp, profile, suggested_filename):
|
||||
model = config.cp2.get(profile, "model")
|
||||
build_script_path = config.cp2.get(profile, "command")
|
||||
overlay_path = config.cp2.get(profile, "overlay")
|
||||
site_script_path = config.cp2.get(profile, "script")
|
||||
suffix = config.cp2.get(profile, "filename")
|
||||
|
||||
build = "/var/lib/certidude/builder/" + profile
|
||||
if not os.path.exists(build + "/overlay/etc/uci-defaults"):
|
||||
os.makedirs(build + "/overlay/etc/uci-defaults")
|
||||
os.system("rsync -av " + overlay_path + "/ " + build + "/overlay/")
|
||||
|
||||
if site_script_path:
|
||||
template = Template(open(site_script_path).read())
|
||||
with open(build + "/overlay/etc/uci-defaults/99-site-config", "w") as fh:
|
||||
fh.write(template.render(authority_name=const.FQDN))
|
||||
|
||||
proc = subprocess.Popen(("/bin/bash", build_script_path),
|
||||
stdout=open(build + "/build.log", "w"), stderr=subprocess.STDOUT,
|
||||
close_fds=True, shell=False,
|
||||
cwd=build,
|
||||
env={"PROFILE":model, "PATH":"/usr/sbin:/usr/bin:/sbin:/bin"},
|
||||
startupinfo=None, creationflags=0)
|
||||
proc.communicate()
|
||||
|
||||
for dname in os.listdir(build):
|
||||
if dname.startswith("lede-imagebuilder-"):
|
||||
for root, dirs, files in os.walk(os.path.join(build, dname, "bin", "targets")):
|
||||
for filename in files:
|
||||
if filename.endswith(suffix):
|
||||
path = os.path.join(root, filename)
|
||||
click.echo("Serving: %s" % path)
|
||||
resp.body = open(path, "rb").read()
|
||||
resp.set_header("Content-Disposition", ("attachment; filename=%s" % suggested_filename))
|
||||
return
|
||||
raise falcon.HTTPNotFound()
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import falcon
|
||||
import logging
|
||||
import os
|
||||
from certidude import const, config, authority
|
||||
from certidude.decorators import serialize
|
||||
from jinja2 import Environment, FileSystemLoader
|
||||
@@ -26,9 +27,10 @@ class ScriptResource():
|
||||
except AttributeError: # No tags
|
||||
pass
|
||||
|
||||
script = named_tags.get("script", config.SCRIPT_DEFAULT)
|
||||
script = named_tags.get("script", "default.sh")
|
||||
assert script in os.listdir(config.SCRIPT_DIR)
|
||||
resp.set_header("Content-Type", "text/x-shellscript")
|
||||
resp.body = env.get_template(script).render(
|
||||
resp.body = env.get_template(os.path.join(script)).render(
|
||||
authority_name=const.FQDN,
|
||||
common_name=cn,
|
||||
other_tags=other_tags,
|
||||
|
||||
Reference in New Issue
Block a user