Skip to content

Commit

Permalink
chore: sync assets for OCI images (#9497)
Browse files Browse the repository at this point in the history
* chore: sync assets for OCI images

Signed-off-by: iromli <[email protected]>

* chore(docker-jans-casa): cleanup code

---------

Signed-off-by: iromli <[email protected]>
Co-authored-by: Mohammad Abudayyeh <[email protected]>
  • Loading branch information
iromli and moabu authored Sep 16, 2024
1 parent af9d2bc commit 4b07e84
Show file tree
Hide file tree
Showing 9 changed files with 157 additions and 35 deletions.
4 changes: 2 additions & 2 deletions docker-jans-auth-server/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ RUN /opt/jython/bin/pip uninstall -y pip setuptools
# ===========

ENV CN_VERSION=1.1.5-SNAPSHOT
ENV CN_BUILD_DATE='2024-09-06 13:09'
ENV CN_BUILD_DATE='2024-09-14 11:49'

ENV CN_SOURCE_URL=https://jenkins.jans.io/maven/io/jans/jans-auth-server/${CN_VERSION}/jans-auth-server-${CN_VERSION}.war

Expand Down Expand Up @@ -103,7 +103,7 @@ RUN mkdir -p ${JETTY_BASE}/jans-auth/agama/fl \
/app/static/rdbm \
/app/schema

ENV JANS_SOURCE_VERSION=b645f0bdb706b933bf5c93fc261a6f00ce5a1882
ENV JANS_SOURCE_VERSION=0f3838b05931401dbfcccd493ad8457435a56ed6
ARG JANS_SETUP_DIR=jans-linux-setup/jans_setup

# note that as we're pulling from a monorepo (with multiple project in it)
Expand Down
2 changes: 1 addition & 1 deletion docker-jans-auth-server/scripts/lock.py
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ def ctx(self) -> dict[str, _t.Any]:
"jans_opa_host": "localhost",
"jans_opa_port": 8181,
"base_endpoint": "jans-auth",
"tokenEndpoint": f"https://{hostname}/jans-auth/restv1/token",
"jans_auth_token_endpoint": f"https://{hostname}/jans-auth/restv1/token",
}

# client
Expand Down
18 changes: 18 additions & 0 deletions docker-jans-auth-server/scripts/upgrade.py
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,24 @@ def _transform_lock_dynamic_config(conf, manager):
conf["baseEndpoint"] = f"https://{hostname}/jans-auth/v1"
should_update = True

# new audit endpoint groups
for audit_endpoint in ["telemetry/bulk", "health/bulk", "log/bulk"]:
if audit_endpoint in conf["endpointGroups"]["audit"]:
continue
conf["endpointGroups"]["audit"].append(audit_endpoint)
should_update = True

# new endpoint details
for k, v in {
"jans-config-api/lock/audit/telemetry/bulk": ["https://jans.io/oauth/lock/telemetry.readonly", "https://jans.io/oauth/lock/telemetry.write"],
"jans-config-api/lock/audit/log/bulk": ["https://jans.io/oauth/lock/log.write"],
"jans-config-api/lock/audit/health/bulk": ["https://jans.io/oauth/lock/health.readonly", "https://jans.io/oauth/lock/health.write"],
}.items():
if k in conf["endpointDetails"]:
continue
conf["endpointDetails"][k] = v
should_update = True

# return modified config (if any) and update flag
return conf, should_update

Expand Down
4 changes: 2 additions & 2 deletions docker-jans-casa/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ RUN wget -q https://repo1.maven.org/maven2/org/eclipse/jetty/jetty-home/${JETTY_
# ====

ENV CN_VERSION=1.1.5-SNAPSHOT
ENV CN_BUILD_DATE='2024-09-06 13:36'
ENV CN_BUILD_DATE='2024-09-11 08:59'

ENV CN_SOURCE_URL=https://jenkins.jans.io/maven/io/jans/casa/${CN_VERSION}/casa-${CN_VERSION}.war

Expand Down Expand Up @@ -60,7 +60,7 @@ RUN mkdir -p /usr/share/java \
# Assets sync
# ===========

ENV JANS_SOURCE_VERSION=b645f0bdb706b933bf5c93fc261a6f00ce5a1882
ENV JANS_SOURCE_VERSION=0f3838b05931401dbfcccd493ad8457435a56ed6
ARG JANS_SETUP_DIR=jans-linux-setup/jans_setup

# note that as we're pulling from a monorepo (with multiple project in it)
Expand Down
19 changes: 7 additions & 12 deletions docker-jans-casa/scripts/bootstrap.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
import json
import logging.config
import math
import os
import time
from uuid import uuid4
from string import Template
from functools import cached_property
Expand Down Expand Up @@ -40,6 +38,10 @@
from jans.pycloudlib.utils import get_server_certificate

from settings import LOGGING_CONFIG
from utils import generalized_time_utc
from utils import get_ads_project_base64
from utils import CASA_AGAMA_DEPLOYMENT_ID
from utils import CASA_AGAMA_ARCHIVE

logging.config.dictConfig(LOGGING_CONFIG)
logger = logging.getLogger("jans-casa")
Expand Down Expand Up @@ -234,7 +236,7 @@ def ctx(self):
"casa_redirect_uri": f"https://{hostname}/jans-casa",
"casa_redirect_logout_uri": f"https://{hostname}/jans-casa/bye.zul",
"casa_frontchannel_logout_uri": f"https://{hostname}/jans-casa/autologout",
"casa_agama_deployment_id": "202447d5-d44c-3125-b1f7-207cb33b6bf7",
"casa_agama_deployment_id": CASA_AGAMA_DEPLOYMENT_ID,
}

# Casa client
Expand All @@ -258,15 +260,8 @@ def ctx(self):
with open("/app/templates/jans-casa/casa-config.json") as f:
ctx["casa_config_base64"] = generate_base64_contents(f.read() % ctx)

# calculate start date
ts = time.time()
microseconds, _ = math.modf(ts)
gm_ts = time.gmtime(ts)
ctx["jans_start_date"] = time.strftime("%Y%m%d%H%M%S", gm_ts) + f"{microseconds:.3f}Z"[1:]

# casa agama project (requires agama script to be enabled)
with open("/usr/share/java/casa-agama-project.zip", "rb") as f:
ctx["ads_prj_assets_base64"] = generate_base64_contents(f.read())
ctx["jans_start_date"] = generalized_time_utc()
ctx["ads_prj_assets_base64"] = get_ads_project_base64(CASA_AGAMA_ARCHIVE)

# finalized contexts
return ctx
Expand Down
106 changes: 91 additions & 15 deletions docker-jans-casa/scripts/upgrade.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,12 @@
from jans.pycloudlib.utils import as_boolean

from settings import LOGGING_CONFIG
from utils import get_ads_project_base64
from utils import get_ads_project_md5sum
from utils import generalized_time_utc
from utils import utcnow
from utils import CASA_AGAMA_DEPLOYMENT_ID
from utils import CASA_AGAMA_ARCHIVE

logging.config.dictConfig(LOGGING_CONFIG)
logger = logging.getLogger("jans-casa")
Expand All @@ -30,36 +36,51 @@ def __init__(self, manager):
self.client = LdapClient(manager)
self.type = "ldap"

def format_attrs(self, attrs):
_attrs = {}
for k, v in attrs.items():
if len(v) < 2:
v = v[0]
_attrs[k] = v
return _attrs
def format_attrs(self, entry, raw_values=None):
raw_values = raw_values or []
attrs = {}

for attr in entry.entry_attributes:
if attr in raw_values:
values = entry[attr].raw_values
else:
values = entry[attr].values

if len(values) < 2:
v = values[0]
else:
v = values
attrs[attr] = v
return attrs

def get_entry(self, key, filter_="", attrs=None, **kwargs):
filter_ = filter_ or "(objectClass=*)"
raw_values = kwargs.get("raw_values")

entry = self.client.get(key, filter_=filter_, attributes=attrs)
if not entry:
return None
return Entry(entry.entry_dn, self.format_attrs(entry.entry_attributes_as_dict))
return Entry(entry.entry_dn, self.format_attrs(entry, raw_values))

def modify_entry(self, key, attrs=None, **kwargs):
attrs = attrs or {}
del_flag = kwargs.get("delete_attr", False)

if del_flag:
mod = self.client.MODIFY_DELETE
else:
mod = self.client.MODIFY_REPLACE
del_attrs = kwargs.get("delete_attrs") or []

for k, v in attrs.items():
if not isinstance(v, list):
v = [v]

if k in del_attrs:
mod = self.client.MODIFY_DELETE
else:
mod = self.client.MODIFY_REPLACE
attrs[k] = [(mod, v)]
return self.client.modify(key, attrs)

modified, _ = self.client.modify(key, attrs)
return modified

def delete_entry(self, key, **kwargs):
return self.client.delete(key)


class SQLBackend:
Expand All @@ -81,6 +102,10 @@ def modify_entry(self, key, attrs=None, **kwargs):
table_name = kwargs.get("table_name")
return self.client.update(table_name, key, attrs), ""

def delete_entry(self, key, **kwargs):
table_name = kwargs.get("table_name")
return self.client.delete(table_name, key)


class CouchbaseBackend:
def __init__(self, manager):
Expand Down Expand Up @@ -131,6 +156,10 @@ def modify_entry(self, key, attrs=None, **kwargs):
message = req.text or req.reason
return status, message

def delete_entry(self, key, **kwargs):
bucket = kwargs.get("bucket")
return self.client.delete(bucket, key)


class SpannerBackend:
def __init__(self, manager):
Expand All @@ -151,6 +180,10 @@ def modify_entry(self, key, attrs=None, **kwargs):
table_name = kwargs.get("table_name")
return self.client.update(table_name, key, attrs), ""

def delete_entry(self, key, **kwargs):
table_name = kwargs.get("table_name")
return self.client.delete(table_name, key)


BACKEND_CLASSES = {
"sql": SQLBackend,
Expand All @@ -175,6 +208,7 @@ def invoke(self):
self.update_client_uris()
self.update_conf_app()
self.update_agama_script()
self.update_agama_deployment()

def update_client_scopes(self):
kwargs = {}
Expand Down Expand Up @@ -324,6 +358,48 @@ def update_agama_script(self):
entry.attrs["jansRevision"] += 1
self.backend.modify_entry(entry.id, entry.attrs, **kwargs)

def update_agama_deployment(self):
casa_agama_deployment_id = CASA_AGAMA_DEPLOYMENT_ID
deploy_id = f"jansId={casa_agama_deployment_id},ou=deployments,ou=agama,o=jans"

if self.backend.type in ("sql", "spanner"):
kwargs = {"table_name": "adsPrjDeployment"}
deploy_id = doc_id_from_dn(deploy_id)
elif self.backend.type == "couchbase":
kwargs = {"bucket": os.environ.get("CN_COUCHBASE_BUCKET_PREFIX", "jans")}
deploy_id = id_from_dn(deploy_id)
else:
# for ldap, get the raw value of the following attribute so we get a precise value
kwargs = {"raw_values": ["jansEndDate"]}

entry = self.backend.get_entry(deploy_id, **kwargs)
proj_archive = CASA_AGAMA_ARCHIVE
assets_md5 = get_ads_project_md5sum(proj_archive)

# marker to determine whether we need to update persistence if asset is changed
if entry and assets_md5 != self.manager.config.get("casa_agama_md5sum"):
logger.info(f"Detected changes of casa-agama-project assets; synchronizing changes from {proj_archive} to persistence.")

entry.attrs["adsPrjDeplDetails"] = json.dumps({"projectMetadata": {"projectName": "casa"}})
entry.attrs["adsPrjAssets"] = get_ads_project_base64(proj_archive)
entry.attrs["jansActive"] = False
start_date = utcnow()

if self.backend.type in ("sql", "spanner"):
entry.attrs["jansStartDate"] = start_date
entry.attrs["jansEndDate"] = None
elif self.backend.type == "couchbase":
entry.attrs["jansStartDate"] = start_date.strftime("%Y-%m-%dT%H:%M:%SZ")
entry.attrs["jansEndDate"] = ""
entry.attrs["adsPrjDeplDetails"] = {"projectMetadata": {"projectName": "casa"}}
else: # ldap
# remove jansEndDate
kwargs["delete_attrs"] = ["jansEndDate"]
entry.attrs["jansStartDate"] = generalized_time_utc(start_date)

if self.backend.modify_entry(entry.id, entry.attrs, **kwargs):
self.manager.config.set("casa_agama_md5sum", assets_md5)


def main():
manager = get_manager()
Expand Down
33 changes: 33 additions & 0 deletions docker-jans-casa/scripts/utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
from datetime import datetime
from datetime import UTC
from hashlib import md5

from jans.pycloudlib.utils import exec_cmd


def utcnow():
return datetime.now(UTC)


def generalized_time_utc(dtime=None):
"""Calculate LDAP generalized time."""
if not dtime:
dtime = utcnow()
return dtime.strftime("%Y%m%d%H%M%SZ")


def get_ads_project_base64(path):
out, err, code = exec_cmd(f"base64 -w0 {path}")
if code != 0:
raise IOError(f"Unable to resolve contents of {path} as base64 strings; err={err.decode()}")
return out.decode()


def get_ads_project_md5sum(path):
with open(path, "rb") as f:
return md5(f.read()).hexdigest() # nosec: B324


CASA_AGAMA_DEPLOYMENT_ID = "202447d5-d44c-3125-b1f7-207cb33b6bf7"

CASA_AGAMA_ARCHIVE = "/usr/share/java/casa-agama-project.zip"
4 changes: 2 additions & 2 deletions docker-jans-config-api/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ RUN wget -q https://maven.jans.io/maven/io/jans/jython-installer/${JYTHON_VERSIO
# ==========

ENV CN_VERSION=1.1.5-SNAPSHOT
ENV CN_BUILD_DATE='2024-09-06 13:27'
ENV CN_BUILD_DATE='2024-09-14 08:45'

ENV CN_SOURCE_URL=https://jenkins.jans.io/maven/io/jans/jans-config-api-server/${CN_VERSION}/jans-config-api-server-${CN_VERSION}.war

Expand Down Expand Up @@ -78,7 +78,7 @@ RUN mkdir -p ${JETTY_BASE}/jans-config-api/_plugins \
# Assets sync
# ===========

ENV JANS_SOURCE_VERSION=b645f0bdb706b933bf5c93fc261a6f00ce5a1882
ENV JANS_SOURCE_VERSION=0f3838b05931401dbfcccd493ad8457435a56ed6
ARG JANS_SETUP_DIR=jans-linux-setup/jans_setup
ARG JANS_CONFIG_API_RESOURCES=jans-config-api/server/src/main/resources

Expand Down
2 changes: 1 addition & 1 deletion docker-jans-persistence-loader/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ RUN apk update \
# ===========

# janssenproject/jans SHA commit
ENV JANS_SOURCE_VERSION=b645f0bdb706b933bf5c93fc261a6f00ce5a1882
ENV JANS_SOURCE_VERSION=0f3838b05931401dbfcccd493ad8457435a56ed6
ARG JANS_SETUP_DIR=jans-linux-setup/jans_setup
ARG JANS_SCRIPT_CATALOG_DIR=docs/script-catalog
ARG JANS_CONFIG_API_RESOURCES=jans-config-api/server/src/main/resources
Expand Down

0 comments on commit 4b07e84

Please sign in to comment.