Skip to content

Commit

Permalink
breaking(release_charm.yaml): Remove support for upstream-sources (#…
Browse files Browse the repository at this point in the history
…158)

`upstream-source` is sufficient if multi-architecture images are used
(#155)
  • Loading branch information
carlcsaposs-canonical committed Mar 14, 2024
1 parent c4494b6 commit b662fd7
Showing 1 changed file with 47 additions and 80 deletions.
127 changes: 47 additions & 80 deletions python/cli/data_platform_workflows_cli/craft_tools/release.py
Expand Up @@ -148,108 +148,75 @@ def charm():
directory = pathlib.Path(args.directory)

# Upload charm file(s) & store revision
charm_revisions: dict[craft.Architecture, list[int]] = {}
charm_revisions: list[int] = []
for charm_file in directory.glob("*.charm"):
# Examples of `charm_file.name`:
# - "mysql-router-k8s_ubuntu-22.04-amd64.charm"
# - "mysql-router-k8s_ubuntu-22.04-amd64-arm64.charm"
architectures = (
charm_file.name.split("_")[-1].removesuffix(".charm").split("-")[2:]
)
assert (
len(architectures) == 1
), f"Multiple architectures ({architectures}) in one (charmcraft.yaml) base not supported. Use one base per architecture"
architecture = craft.Architecture(architectures[0])
logging.info(f"Uploading {charm_file=} {architecture=}")
logging.info(f"Uploading {charm_file=}")
output = run(["charmcraft", "upload", "--format", "json", charm_file])
revision: int = json.loads(output)["revision"]
logging.info(f"Uploaded charm {revision=}")
charm_revisions.setdefault(architecture, []).append(revision)
charm_revisions.append(revision)
assert len(charm_revisions) > 0, "No charm packages found"

metadata_file = yaml.safe_load((directory / "metadata.yaml").read_text())
charm_name = metadata_file["name"]

# (Only for Kubernetes charms) upload OCI image(s) & store revision
oci_resources: dict[craft.Architecture, list[OCIResource]] = {}
oci_resources: list[OCIResource] = []
resources = metadata_file.get("resources", {})
for resource_name, resource in resources.items():
if resource["type"] != "oci-image":
continue
for architecture in charm_revisions.keys():
# Format: ST111 - Multi-architecture `upstream-source` in charm OCI resources
# https://docs.google.com/document/d/19pzpza7zj7qswDRSHBlpqdBrA7Ndcnyh6_75cCxMKSo/edit
upstream_source = resource.get("upstream-source")
if upstream_source is not None and "upstream-sources" in resource:
raise ValueError(
"`upstream-sources` and `upstream-source` cannot be used simultaneously. Use only `upstream-sources`"
)
elif upstream_source:
# Default to X64
upstream_sources = {craft.Architecture.X64.value: upstream_source}
else:
upstream_sources = resource["upstream-sources"]
image_name = upstream_sources[architecture.value]
logging.info(f"Downloading OCI image ({architecture=}): {image_name}")
run(["docker", "pull", image_name])
image_id = run(
["docker", "image", "inspect", image_name, "--format", "'{{.Id}}'"]
)
image_id = image_id.rstrip("\n").strip("'").removeprefix("sha256:")
assert "\n" not in image_id, f"Multiple local images found for {image_name}"
logging.info(f"Uploading charm resource: {resource_name}")
output = run(
[
"charmcraft",
"upload-resource",
"--format",
"json",
charm_name,
resource_name,
"--image",
image_id,
]
)
revision: int = json.loads(output)["revision"]
logging.info(f"Uploaded charm resource {revision=}")
oci_resources.setdefault(architecture, []).append(
OCIResource(resource_name, revision)
)

# Release charm file(s)
for architecture, revisions in charm_revisions.items():
for charm_revision in revisions:
logging.info(f"Releasing {charm_revision=} {architecture=}")
command = [
image_name = resource["upstream-source"]
logging.info(f"Downloading OCI image: {image_name}")
run(["docker", "pull", image_name])
image_id = run(
["docker", "image", "inspect", image_name, "--format", "'{{.Id}}'"]
)
image_id = image_id.rstrip("\n").strip("'").removeprefix("sha256:")
assert "\n" not in image_id, f"Multiple local images found for {image_name}"
logging.info(f"Uploading charm resource: {resource_name}")
output = run(
[
"charmcraft",
"release",
"upload-resource",
"--format",
"json",
charm_name,
"--revision",
str(charm_revision),
"--channel",
args.channel,
resource_name,
"--image",
image_id,
]
if oci_resources:
for oci in oci_resources[architecture]:
command += ["--resource", f"{oci.resource_name}:{oci.revision}"]
run(command)
)
revision: int = json.loads(output)["revision"]
logging.info(f"Uploaded charm resource {revision=}")
oci_resources.append(OCIResource(resource_name, revision))

# Release charm file(s)
for charm_revision in charm_revisions:
logging.info(f"Releasing {charm_revision=}")
command = [
"charmcraft",
"release",
charm_name,
"--revision",
str(charm_revision),
"--channel",
args.channel,
]
for oci in oci_resources:
command += ["--resource", f"{oci.resource_name}:{oci.revision}"]
run(command)

# Output GitHub release info
revisions = []
for revs in charm_revisions.values():
revisions.extend(revs)
release_tag = f"rev{max(revisions)}"
if len(revisions) == 1:
release_tag = f"rev{max(charm_revisions)}"
if len(charm_revisions) == 1:
release_title = "Revision "
else:
release_title = "Revisions "
release_title += ", ".join(str(revision) for revision in revisions)
oci_info = "OCI images:"
for architecture, resources in oci_resources.items():
oci_info += f"\n- {architecture}:"
for oci in resources:
oci_info += f"\n - {dataclasses.asdict(oci)}"
release_notes = f"Released to {args.channel}\n{oci_info}"
release_title += ", ".join(str(revision) for revision in charm_revisions)
release_notes = f"Released to {args.channel}\nOCI images:\n" + "\n".join(
f"- {dataclasses.asdict(oci)}" for oci in oci_resources
)
with open("release_notes.txt", "w") as file:
file.write(release_notes)
output = f"release_tag={release_tag}\nrelease_title={release_title}"
Expand Down

0 comments on commit b662fd7

Please sign in to comment.