Skip to content

Commit

Permalink
Run integration tests on arm64 (#278)
Browse files Browse the repository at this point in the history
  • Loading branch information
carlcsaposs-canonical authored Jul 3, 2024
1 parent 156da2d commit ee5d2ff
Show file tree
Hide file tree
Showing 8 changed files with 93 additions and 39 deletions.
16 changes: 12 additions & 4 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -75,21 +75,29 @@ jobs:
juju:
- agent: 2.9.49 # renovate: juju-agent-pin-minor
libjuju: ^2
allure: false
allure_on_amd64: false
- agent: 3.4.3 # renovate: juju-agent-pin-minor
allure: true
name: Integration test charm | ${{ matrix.juju.agent }}
allure_on_amd64: true
architecture:
- amd64
include:
- juju:
agent: 3.4.3 # renovate: juju-agent-pin-minor
allure_on_amd64: true
architecture: arm64
name: Integration test charm | ${{ matrix.juju.agent }} | ${{ matrix.architecture }}
needs:
- lint
- unit-test
- build
uses: canonical/data-platform-workflows/.github/workflows/[email protected]
with:
artifact-prefix: ${{ needs.build.outputs.artifact-prefix }}
architecture: ${{ matrix.architecture }}
cloud: microk8s
microk8s-snap-channel: 1.28-strict/stable
juju-agent-version: ${{ matrix.juju.agent }}
libjuju-version-constraint: ${{ matrix.juju.libjuju }}
_beta_allure_report: ${{ matrix.juju.allure }}
_beta_allure_report: ${{ matrix.juju.allure_on_amd64 && matrix.architecture == 'amd64' }}
permissions:
contents: write # Needed for Allure Report beta
7 changes: 7 additions & 0 deletions tests/integration/architecture.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
# Copyright 2024 Canonical Ltd.
# See LICENSE file for licensing details.
import subprocess

architecture = subprocess.run(
["dpkg", "--print-architecture"], capture_output=True, check=True, encoding="utf-8"
).stdout.strip()
11 changes: 6 additions & 5 deletions tests/integration/helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import itertools
import json
import logging
import pathlib
import subprocess
import tempfile
from typing import Dict, List, Optional
Expand Down Expand Up @@ -205,13 +206,13 @@ async def write_content_to_file_in_unit(
"""
pod_name = unit.name.replace("/", "-")

with tempfile.NamedTemporaryFile(mode="w") as temp_file:
with tempfile.NamedTemporaryFile(mode="w", dir=pathlib.Path.home()) as temp_file:
temp_file.write(content)
temp_file.flush()

subprocess.run(
[
"kubectl",
"microk8s.kubectl",
"cp",
"-n",
ops_test.model.info.name,
Expand Down Expand Up @@ -240,10 +241,10 @@ async def read_contents_from_file_in_unit(
"""
pod_name = unit.name.replace("/", "-")

with tempfile.NamedTemporaryFile(mode="r+") as temp_file:
with tempfile.NamedTemporaryFile(mode="r+", dir=pathlib.Path.home()) as temp_file:
subprocess.run(
[
"kubectl",
"microk8s.kubectl",
"cp",
"-n",
ops_test.model.info.name,
Expand Down Expand Up @@ -351,7 +352,7 @@ async def rotate_mysqlrouter_logs(ops_test: OpsTest, unit_name: str) -> None:

subprocess.run(
[
"kubectl",
"microk8s.kubectl",
"exec",
"-n",
ops_test.model.info.name,
Expand Down
8 changes: 7 additions & 1 deletion tests/integration/markers.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,15 @@

import pytest

from . import juju_
from . import architecture, juju_

skip_if_lower_than_3_1 = pytest.mark.skipif(
not juju_.is_3_1_or_higher,
reason="Skips juju <3.1.x as we have a dependency for self-signed-certificates",
)
amd64_only = pytest.mark.skipif(
architecture.architecture != "amd64", reason="Requires amd64 architecture"
)
arm64_only = pytest.mark.skipif(
architecture.architecture != "arm64", reason="Requires arm64 architecture"
)
5 changes: 5 additions & 0 deletions tests/integration/test_exporter.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
import yaml
from pytest_operator.plugin import OpsTest

from . import markers
from .helpers import (
APPLICATION_DEFAULT_APP_NAME,
MYSQL_DEFAULT_APP_NAME,
Expand All @@ -32,6 +33,10 @@


@pytest.mark.group(1)
# TODO: remove amd64_only after these issues fixed:
# https://github.com/canonical/mysql-router-k8s-operator/issues/282
# https://github.com/canonical/grafana-agent-k8s-operator/issues/309
@markers.amd64_only
@pytest.mark.abort_on_fail
async def test_exporter_endpoint(ops_test: OpsTest) -> None:
"""Test that exporter endpoint is functional."""
Expand Down
44 changes: 28 additions & 16 deletions tests/integration/test_exporter_with_tls.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
import yaml
from pytest_operator.plugin import OpsTest

from . import juju_
from . import architecture, juju_, markers
from .helpers import (
APPLICATION_DEFAULT_APP_NAME,
MYSQL_DEFAULT_APP_NAME,
Expand All @@ -33,14 +33,26 @@
RETRY_TIMEOUT = 3 * 60

if juju_.is_3_or_higher:
TLS_APP_NAME = "self-signed-certificates"
TLS_CONFIG = {"ca-common-name": "Test CA"}
tls_app_name = "self-signed-certificates"
if architecture.architecture == "arm64":
tls_channel = "latest/edge"
else:
tls_channel = "latest/stable"
tls_config = {"ca-common-name": "Test CA"}
else:
TLS_APP_NAME = "tls-certificates-operator"
TLS_CONFIG = {"generate-self-signed-certificates": "true", "ca-common-name": "Test CA"}
tls_app_name = "tls-certificates-operator"
if architecture.architecture == "arm64":
tls_channel = "legacy/edge"
else:
tls_channel = "legacy/stable"
tls_config = {"generate-self-signed-certificates": "true", "ca-common-name": "Test CA"}


@pytest.mark.group(1)
# TODO: remove amd64_only after these issues fixed:
# https://github.com/canonical/mysql-router-k8s-operator/issues/282
# https://github.com/canonical/grafana-agent-k8s-operator/issues/309
@markers.amd64_only
@pytest.mark.abort_on_fail
async def test_exporter_endpoint(ops_test: OpsTest) -> None:
"""Test that the exporter endpoint works when related with TLS"""
Expand Down Expand Up @@ -125,21 +137,21 @@ async def test_exporter_endpoint(ops_test: OpsTest) -> None:
"Issuer: CN = MySQL_Router_Auto_Generated_CA_Certificate" in issuer
), "Expected mysqlrouter autogenerated certificate"

logger.info(f"Deploying {TLS_APP_NAME}")
logger.info(f"Deploying {tls_app_name}")
await ops_test.model.deploy(
TLS_APP_NAME,
application_name=TLS_APP_NAME,
channel="stable",
config=TLS_CONFIG,
tls_app_name,
application_name=tls_app_name,
channel=tls_channel,
config=tls_config,
series="jammy",
)

await ops_test.model.wait_for_idle([TLS_APP_NAME], status="active", timeout=SLOW_TIMEOUT)
await ops_test.model.wait_for_idle([tls_app_name], status="active", timeout=SLOW_TIMEOUT)

logger.info(f"Relating mysqlrouter with {TLS_APP_NAME}")
logger.info(f"Relating mysqlrouter with {tls_app_name}")

await ops_test.model.relate(
f"{MYSQL_ROUTER_APP_NAME}:certificates", f"{TLS_APP_NAME}:certificates"
f"{MYSQL_ROUTER_APP_NAME}:certificates", f"{tls_app_name}:certificates"
)

unit_address = await get_unit_address(ops_test, mysql_router_app.units[0].name)
Expand Down Expand Up @@ -198,7 +210,7 @@ async def test_exporter_endpoint(ops_test: OpsTest) -> None:
)
assert (
"CN = Test CA" in issuer
), f"Expected mysqlrouter certificate from {TLS_APP_NAME}"
), f"Expected mysqlrouter certificate from {tls_app_name}"

logger.info("Removing relation between mysqlrouter and grafana agent")
await mysql_router_app.remove_relation(
Expand All @@ -220,9 +232,9 @@ async def test_exporter_endpoint(ops_test: OpsTest) -> None:
else:
assert False, "❌ can connect to metrics endpoint without relation with cos"

logger.info(f"Removing relation between mysqlrouter and {TLS_APP_NAME}")
logger.info(f"Removing relation between mysqlrouter and {tls_app_name}")
await mysql_router_app.remove_relation(
f"{MYSQL_ROUTER_APP_NAME}:certificates", f"{TLS_APP_NAME}:certificates"
f"{MYSQL_ROUTER_APP_NAME}:certificates", f"{tls_app_name}:certificates"
)

for attempt in tenacity.Retrying(
Expand Down
9 changes: 8 additions & 1 deletion tests/integration/test_node_port.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
import yaml
from pytest_operator.plugin import OpsTest

from . import markers
from . import architecture, markers
from .helpers import (
APPLICATION_DEFAULT_APP_NAME,
MYSQL_DEFAULT_APP_NAME,
Expand All @@ -35,6 +35,11 @@
DATA_INTEGRATOR = "data-integrator"
SLOW_TIMEOUT = 15 * 60
MODEL_CONFIG = {"logging-config": "<root>=INFO;unit=DEBUG"}
if architecture.architecture == "arm64":
tls_channel = "latest/edge"
else:
tls_channel = "latest/stable"
TLS_CONFIG = {"ca-common-name": "Test CA"}


@pytest.mark.group(1)
Expand Down Expand Up @@ -86,7 +91,9 @@ async def test_build_and_deploy(ops_test: OpsTest):
),
ops_test.model.deploy(
SELF_SIGNED_CERTIFICATE_NAME,
channel=tls_channel,
application_name=SELF_SIGNED_CERTIFICATE_NAME,
config=TLS_CONFIG,
series="jammy",
num_units=1,
),
Expand Down
32 changes: 20 additions & 12 deletions tests/integration/test_tls.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
import yaml
from pytest_operator.plugin import OpsTest

from . import juju_
from . import architecture, juju_
from .helpers import (
APPLICATION_DEFAULT_APP_NAME,
MYSQL_DEFAULT_APP_NAME,
Expand All @@ -29,11 +29,19 @@
RETRY_TIMEOUT = 2 * 60

if juju_.is_3_or_higher:
TLS_APP_NAME = "self-signed-certificates"
TLS_CONFIG = {"ca-common-name": "Test CA"}
tls_app_name = "self-signed-certificates"
if architecture.architecture == "arm64":
tls_channel = "latest/edge"
else:
tls_channel = "latest/stable"
tls_config = {"ca-common-name": "Test CA"}
else:
TLS_APP_NAME = "tls-certificates-operator"
TLS_CONFIG = {"generate-self-signed-certificates": "true", "ca-common-name": "Test CA"}
tls_app_name = "tls-certificates-operator"
if architecture.architecture == "arm64":
tls_channel = "legacy/edge"
else:
tls_channel = "legacy/stable"
tls_config = {"generate-self-signed-certificates": "true", "ca-common-name": "Test CA"}


@pytest.mark.group(1)
Expand Down Expand Up @@ -71,10 +79,10 @@ async def test_build_deploy_and_relate(ops_test: OpsTest) -> None:
trust=True,
),
ops_test.model.deploy(
TLS_APP_NAME,
application_name=TLS_APP_NAME,
channel="stable",
config=TLS_CONFIG,
tls_app_name,
application_name=tls_app_name,
channel=tls_channel,
config=tls_config,
series="jammy",
),
ops_test.model.deploy(
Expand Down Expand Up @@ -121,7 +129,7 @@ async def test_connected_encryption(ops_test: OpsTest) -> None:
), "Expected mysqlrouter autogenerated certificate"

logger.info("Relating TLS with mysqlrouter")
await ops_test.model.relate(TLS_APP_NAME, MYSQL_ROUTER_APP_NAME)
await ops_test.model.relate(tls_app_name, MYSQL_ROUTER_APP_NAME)

logger.info("Getting certificate issuer after relating with tls operator")
for attempt in tenacity.Retrying(
Expand All @@ -138,11 +146,11 @@ async def test_connected_encryption(ops_test: OpsTest) -> None:
)
assert (
"CN = Test CA" in issuer
), f"Expected mysqlrouter certificate from {TLS_APP_NAME}"
), f"Expected mysqlrouter certificate from {tls_app_name}"

logger.info("Removing relation TLS with mysqlrouter")
await ops_test.model.applications[MYSQL_ROUTER_APP_NAME].remove_relation(
f"{TLS_APP_NAME}:certificates", f"{MYSQL_ROUTER_APP_NAME}:certificates"
f"{tls_app_name}:certificates", f"{MYSQL_ROUTER_APP_NAME}:certificates"
)

for attempt in tenacity.Retrying(
Expand Down

0 comments on commit ee5d2ff

Please sign in to comment.