Skip to content

Commit

Permalink
fix: unpin jsonschema and update tests
Browse files Browse the repository at this point in the history
In 034a5cd , we pinned jsonschema version due to failing tests. Test
failures were due to jsonschema library changing error messages.
This commit unpins the version and updates tests accordingly.

Fixes canonicalGH-4783

Co-authored-by: dermotbradley <[email protected]>
  • Loading branch information
TheRealFalcon and dermotbradley committed Feb 14, 2024
1 parent 7d605ea commit b5371a6
Show file tree
Hide file tree
Showing 17 changed files with 87 additions and 38 deletions.
2 changes: 1 addition & 1 deletion requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ requests
jsonpatch

# For validating cloud-config sections per schema definitions
jsonschema<=4.20.0
jsonschema

# Used by DataSourceVMware to inspect the host's network configuration during
# the "setup()" function.
Expand Down
2 changes: 1 addition & 1 deletion test-requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,6 @@ pytest!=7.3.2
pytest-cov
pytest-mock
setuptools
jsonschema<=4.20.0
jsonschema
responses
passlib
5 changes: 3 additions & 2 deletions tests/unittests/config/test_cc_apk_configure.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
validate_cloudconfig_schema,
)
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
FilesystemMockingTestCase,
mock,
skipUnlessJsonSchema,
Expand Down Expand Up @@ -355,7 +356,7 @@ class TestApkConfigureSchema:
(
{"apk_repos": {"alpine_repo": {}}},
"apk_repos.alpine_repo: 'version' is a required property,"
" apk_repos.alpine_repo: {} does not have enough properties",
f" apk_repos.alpine_repo: {{}} {SCHEMA_EMPTY_ERROR}",
),
(
{"apk_repos": {"alpine_repo": True}},
Expand All @@ -368,7 +369,7 @@ class TestApkConfigureSchema:
),
(
{"apk_repos": {}},
"apk_repos: {} does not have enough properties",
f"apk_repos: {{}} {SCHEMA_EMPTY_ERROR}",
),
(
{"apk_repos": {"local_repo_base_url": None}},
Expand Down
14 changes: 7 additions & 7 deletions tests/unittests/config/test_cc_apt_configure.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
get_schema,
validate_cloudconfig_schema,
)
from tests.unittests.helpers import skipUnlessJsonSchema
from tests.unittests.helpers import SCHEMA_EMPTY_ERROR, skipUnlessJsonSchema
from tests.unittests.util import get_cloud

M_PATH = "cloudinit.config.cc_apt_configure."
Expand All @@ -39,7 +39,7 @@ class TestAPTConfigureSchema:
" ('boguskey' was unexpected)"
),
),
({"apt": {}}, "apt: {} does not have enough properties"),
({"apt": {}}, f"apt: {{}} {SCHEMA_EMPTY_ERROR}"),
(
{"apt": {"preserve_sources_list": 1}},
"apt.preserve_sources_list: 1 is not of type 'boolean'",
Expand All @@ -50,7 +50,7 @@ class TestAPTConfigureSchema:
),
(
{"apt": {"disable_suites": []}},
re.escape("apt.disable_suites: [] is too short"),
re.escape("apt.disable_suites: [] ") + SCHEMA_EMPTY_ERROR,
),
(
{"apt": {"disable_suites": [1]}},
Expand All @@ -70,7 +70,7 @@ class TestAPTConfigureSchema:
),
(
{"apt": {"primary": []}},
re.escape("apt.primary: [] is too short"),
re.escape("apt.primary: [] ") + SCHEMA_EMPTY_ERROR,
),
(
{"apt": {"primary": ["nonobj"]}},
Expand Down Expand Up @@ -107,7 +107,7 @@ class TestAPTConfigureSchema:
),
(
{"apt": {"primary": [{"arches": ["amd64"], "search": []}]}},
re.escape("apt.primary.0.search: [] is too short"),
re.escape("apt.primary.0.search: [] ") + SCHEMA_EMPTY_ERROR,
),
(
{
Expand Down Expand Up @@ -139,7 +139,7 @@ class TestAPTConfigureSchema:
),
(
{"apt": {"debconf_selections": {}}},
"apt.debconf_selections: {} does not have enough properties",
f"apt.debconf_selections: {{}} {SCHEMA_EMPTY_ERROR}",
),
(
{"apt": {"sources_list": True}},
Expand Down Expand Up @@ -175,7 +175,7 @@ class TestAPTConfigureSchema:
),
(
{"apt": {"sources": {"opaquekey": {}}}},
"apt.sources.opaquekey: {} does not have enough properties",
f"apt.sources.opaquekey: {{}} {SCHEMA_EMPTY_ERROR}",
),
(
{"apt": {"sources": {"opaquekey": {"boguskey": True}}}},
Expand Down
17 changes: 12 additions & 5 deletions tests/unittests/config/test_cc_bootcmd.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,12 @@
get_schema,
validate_cloudconfig_schema,
)
from tests.unittests.helpers import CiTestCase, mock, skipUnlessJsonSchema
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
CiTestCase,
mock,
skipUnlessJsonSchema,
)
from tests.unittests.util import get_cloud


Expand Down Expand Up @@ -128,12 +133,14 @@ class TestBootCMDSchema:
"Cloud config schema errors: bootcmd: 1 is not of type"
" 'array'",
),
({"bootcmd": []}, re.escape("bootcmd: [] is too short")),
(
{"bootcmd": []},
re.escape(
"Cloud config schema errors: bootcmd: [] is too short"
),
re.escape("bootcmd: [] ") + SCHEMA_EMPTY_ERROR,
),
(
{"bootcmd": []},
re.escape("Cloud config schema errors: bootcmd: [] ")
+ SCHEMA_EMPTY_ERROR,
),
(
{
Expand Down
10 changes: 7 additions & 3 deletions tests/unittests/config/test_cc_ca_certs.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,11 @@
get_schema,
validate_cloudconfig_schema,
)
from tests.unittests.helpers import TestCase, skipUnlessJsonSchema
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
TestCase,
skipUnlessJsonSchema,
)
from tests.unittests.util import get_cloud


Expand Down Expand Up @@ -396,7 +400,7 @@ class TestCACertsSchema:
),
(
{"ca_certs": {}},
re.escape("ca_certs: {} does not have enough properties"),
re.escape("ca_certs: {} ") + SCHEMA_EMPTY_ERROR,
),
(
{"ca_certs": {"boguskey": 1}},
Expand All @@ -415,7 +419,7 @@ class TestCACertsSchema:
),
(
{"ca_certs": {"trusted": []}},
re.escape("ca_certs.trusted: [] is too short"),
re.escape("ca_certs.trusted: [] ") + SCHEMA_EMPTY_ERROR,
),
),
)
Expand Down
5 changes: 3 additions & 2 deletions tests/unittests/config/test_cc_chef.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
)
from tests.helpers import cloud_init_project_dir
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
FilesystemMockingTestCase,
ResponsesTestCase,
mock,
Expand Down Expand Up @@ -306,7 +307,7 @@ class TestBootCMDSchema:
),
(
{"chef": {}},
re.escape(" chef: {} does not have enough properties"),
re.escape(" chef: {} ") + SCHEMA_EMPTY_ERROR,
),
(
{"chef": {"boguskey": True}},
Expand All @@ -321,7 +322,7 @@ class TestBootCMDSchema:
),
(
{"chef": {"directories": []}},
re.escape("chef.directories: [] is too short"),
re.escape("chef.directories: [] ") + SCHEMA_EMPTY_ERROR,
),
(
{"chef": {"directories": [1]}},
Expand Down
2 changes: 1 addition & 1 deletion tests/unittests/config/test_cc_lxd.py
Original file line number Diff line number Diff line change
Expand Up @@ -393,7 +393,7 @@ class TestLXDSchema:
# Require bridge.mode
({"lxd": {"bridge": {}}}, "bridge: 'mode' is a required property"),
# Require init or bridge keys
({"lxd": {}}, "lxd: {} does not have enough properties"),
({"lxd": {}}, f"lxd: {{}} {t_help.SCHEMA_EMPTY_ERROR}"),
# Require some non-empty preseed config of type string
({"lxd": {"preseed": {}}}, "not of type 'string'"),
({"lxd": {"preseed": ""}}, None),
Expand Down
10 changes: 8 additions & 2 deletions tests/unittests/config/test_cc_mounts.py
Original file line number Diff line number Diff line change
Expand Up @@ -583,9 +583,15 @@ class TestMountsSchema:
"config, error_msg",
[
# We expect to see one mount if provided in user-data.
({"mounts": []}, re.escape("mounts: [] is too short")),
(
{"mounts": []},
re.escape("mounts: [] ") + test_helpers.SCHEMA_EMPTY_ERROR,
),
# Disallow less than 1 item per mount entry
({"mounts": [[]]}, re.escape("mounts.0: [] is too short")),
(
{"mounts": [[]]},
re.escape("mounts.0: [] ") + test_helpers.SCHEMA_EMPTY_ERROR,
),
# Disallow more than 6 items per mount entry
({"mounts": [["1"] * 7]}, "mounts.0:.* is too long"),
# Disallow mount_default_fields will anything other than 6 items
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,11 @@
)
from cloudinit.distros import PackageInstallerError
from cloudinit.subp import SubpResult
from tests.unittests.helpers import does_not_raise, skipUnlessJsonSchema
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
does_not_raise,
skipUnlessJsonSchema,
)
from tests.unittests.util import get_cloud

M_PATH = "cloudinit.config.cc_package_update_upgrade_install."
Expand Down Expand Up @@ -284,7 +288,7 @@ class TestPackageUpdateUpgradeSchema:
# packages list with three entries (2 required)
({"packages": ["p1", ["p2", "p3", "p4"]]}, ""),
# empty packages list
({"packages": []}, "is too short"),
({"packages": []}, SCHEMA_EMPTY_ERROR),
(
{"apt_update": False},
(
Expand Down
3 changes: 2 additions & 1 deletion tests/unittests/config/test_cc_runcmd.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
validate_cloudconfig_schema,
)
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
FilesystemMockingTestCase,
skipUnlessJsonSchema,
)
Expand Down Expand Up @@ -92,7 +93,7 @@ class TestRunCmdSchema:
({"runcmd": ["echo bye", "echo bye"]}, None),
# Invalid schemas
({"runcmd": 1}, "1 is not of type 'array'"),
({"runcmd": []}, r"runcmd: \[\] is too short"),
({"runcmd": []}, rf"runcmd: \[\] {SCHEMA_EMPTY_ERROR}"),
(
{
"runcmd": [
Expand Down
9 changes: 7 additions & 2 deletions tests/unittests/config/test_cc_set_passwords.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,11 @@
get_schema,
validate_cloudconfig_schema,
)
from tests.unittests.helpers import does_not_raise, skipUnlessJsonSchema
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
does_not_raise,
skipUnlessJsonSchema,
)
from tests.unittests.util import get_cloud

MODPATH = "cloudinit.config.cc_set_passwords."
Expand Down Expand Up @@ -718,7 +722,8 @@ class TestSetPasswordsSchema:
(
{"chpasswd": {"list": []}},
pytest.raises(
SchemaValidationError, match=r"\[\] is too short"
SchemaValidationError,
match=rf"\[\] {SCHEMA_EMPTY_ERROR}",
),
),
],
Expand Down
20 changes: 14 additions & 6 deletions tests/unittests/config/test_cc_snap.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,12 @@
get_schema,
validate_cloudconfig_schema,
)
from tests.unittests.helpers import CiTestCase, mock, skipUnlessJsonSchema
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
CiTestCase,
mock,
skipUnlessJsonSchema,
)
from tests.unittests.util import get_cloud

M_PATH = "cloudinit.config.cc_snap."
Expand Down Expand Up @@ -253,15 +258,18 @@ class TestSnapSchema:
{"snap": {"commands": ["ls"], "invalid-key": ""}},
"Additional properties are not allowed",
),
({"snap": {}}, "{} does not have enough properties"),
({"snap": {}}, f"{{}} {SCHEMA_EMPTY_ERROR}"),
(
{"snap": {"commands": "broken"}},
"'broken' is not of type 'object', 'array'",
),
({"snap": {"commands": []}}, r"snap.commands: \[\] is too short"),
(
{"snap": {"commands": []}},
rf"snap.commands: \[\] {SCHEMA_EMPTY_ERROR}",
),
(
{"snap": {"commands": {}}},
r"snap.commands: {} does not have enough properties",
rf"snap.commands: {{}} {SCHEMA_EMPTY_ERROR}",
),
({"snap": {"commands": [123]}}, ""),
({"snap": {"commands": {"01": 123}}}, ""),
Expand All @@ -276,10 +284,10 @@ class TestSnapSchema:
{"snap": {"assertions": "broken"}},
"'broken' is not of type 'object', 'array'",
),
({"snap": {"assertions": []}}, r"\[\] is too short"),
({"snap": {"assertions": []}}, rf"\[\] {SCHEMA_EMPTY_ERROR}"),
(
{"snap": {"assertions": {}}},
r"\{} does not have enough properties",
rf"\{{}} {SCHEMA_EMPTY_ERROR}",
),
],
)
Expand Down
6 changes: 5 additions & 1 deletion tests/unittests/config/test_cc_write_files.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
validate_cloudconfig_schema,
)
from tests.unittests.helpers import (
SCHEMA_EMPTY_ERROR,
CiTestCase,
FilesystemMockingTestCase,
skipUnlessJsonSchema,
Expand Down Expand Up @@ -222,7 +223,10 @@ class TestWriteFilesSchema:
[
# Top-level write_files type validation
({"write_files": 1}, "write_files: 1 is not of type 'array'"),
({"write_files": []}, re.escape("write_files: [] is too short")),
(
{"write_files": []},
re.escape("write_files: [] ") + SCHEMA_EMPTY_ERROR,
),
(
{"write_files": [{}]},
"write_files.0: 'path' is a required property",
Expand Down
2 changes: 1 addition & 1 deletion tests/unittests/config/test_cc_yum_add_repo.py
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,7 @@ class TestAddYumRepoSchema:
),
(
{"yum_repos": {}},
re.escape("yum_repos: {} does not have enough properties"),
re.escape("yum_repos: {} ") + helpers.SCHEMA_EMPTY_ERROR,
),
# baseurl required
(
Expand Down
8 changes: 8 additions & 0 deletions tests/unittests/helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,14 @@
HAS_APT_PKG = False


# Used by tests to verify the error message when a jsonschema structure
# is empty but should not be.
# Version 4.20.0 of jsonschema changed the error messages for empty structures.
SCHEMA_EMPTY_ERROR = (
"(is too short|should be non-empty|does not have enough properties)"
)


# Makes the old path start
# with new base instead of whatever
# it previously had
Expand Down
2 changes: 1 addition & 1 deletion tests/unittests/test_merging.py
Original file line number Diff line number Diff line change
Expand Up @@ -270,7 +270,7 @@ class TestMergingSchema:
[
({"merge_how": "list()+dict()+str()"}, None),
({"merge_type": "list()+dict()+str()"}, None),
({"merge_how": []}, "\\[\\] is too short"),
({"merge_how": []}, f"\\[\\] {helpers.SCHEMA_EMPTY_ERROR}"),
(
{"merge_how": {"name": "list", "settings": ["append"]}},
"is not of type",
Expand Down

0 comments on commit b5371a6

Please sign in to comment.