diff --git a/scenario/context.py b/scenario/context.py index 6dcf910a..5cf51635 100644 --- a/scenario/context.py +++ b/scenario/context.py @@ -154,11 +154,10 @@ def _get_output(self): class _ActionManager(_Manager): - if TYPE_CHECKING: # pragma: no cover - output: ActionOutput # pyright: ignore[reportIncompatibleVariableOverride] + output: ActionOutput # pyright: ignore[reportIncompatibleVariableOverride] - def run(self) -> "ActionOutput": - return cast("ActionOutput", super().run()) + def run_action(self) -> "ActionOutput": + return cast("ActionOutput", super().run()) @property def _runner(self): @@ -600,38 +599,30 @@ def _record_status(self, state: "State", is_app: bool): else: self.unit_status_history.append(state.unit_status) - def manager(self, event: "_Event", state: "State"): + def __call__(self, event: Union["_Event", "Action"], state: "State"): """Context manager to introspect live charm object before and after the event is emitted. Usage:: ctx = Context(MyCharm) - with ctx.manager(ctx.on.start(), State()) as manager: - assert manager.charm._some_private_attribute == "foo" # noqa - manager.run() # this will fire the event - assert manager.charm._some_private_attribute == "bar" # noqa + with ctx(ctx.on.start(), State()) as event: + event.charm._some_private_setup() + event.run() # this will fire the event + assert event.charm._some_private_attribute == "bar" # noqa + + with ctx(Action("foo"), State()) as event: + event.charm._some_private_setup() + event.run_action() # this will fire the event + assert event.charm._some_private_attribute == "bar" # noqa Args: - event: the :class:`Event` that the charm will respond to. + event: the :class:`Event` or :class:`Action` that the charm will respond to. state: the :class:`State` instance to use when handling the Event. """ + if isinstance(event, Action) or event.action: + return _ActionManager(self, event, state) return _EventManager(self, event, state) - def action_manager(self, action: "_Action", state: "State"): - """Context manager to introspect live charm object before and after the event is emitted. - - Usage: - >>> with Context().action_manager(Action("foo"), State()) as manager: - >>> assert manager.charm._some_private_attribute == "foo" # noqa - >>> manager.run() # this will fire the event - >>> assert manager.charm._some_private_attribute == "bar" # noqa - - :arg action: the Action that the charm will execute. - :arg state: the State instance to use as data source for the hook tool calls that the - charm will invoke when handling the Action (event). - """ - return _ActionManager(self, action, state) - @contextmanager def _run_event(self, event: "_Event", state: "State"): with self._run(event=event, state=state) as ops: diff --git a/tests/helpers.py b/tests/helpers.py index c8060d1c..089ba1e1 100644 --- a/tests/helpers.py +++ b/tests/helpers.py @@ -58,12 +58,12 @@ def trigger( event = getattr(ctx.on, event)(tuple(state.containers)[0]) else: event = getattr(ctx.on, event)() - with ctx.manager(event, state=state) as mgr: + with ctx(event, state=state) as event: if pre_event: - pre_event(mgr.charm) - state_out = mgr.run() + pre_event(event.charm) + state_out = event.run() if post_event: - post_event(mgr.charm) + post_event(event.charm) return state_out diff --git a/tests/test_charm_spec_autoload.py b/tests/test_charm_spec_autoload.py index fb738f87..527510dc 100644 --- a/tests/test_charm_spec_autoload.py +++ b/tests/test_charm_spec_autoload.py @@ -162,6 +162,6 @@ def test_config_defaults(tmp_path, legacy): ) as charm: # this would fail if there were no 'cuddles' relation defined in meta ctx = Context(charm) - with ctx.manager(ctx.on.start(), State()) as mgr: - mgr.run() - assert mgr.charm.config["foo"] is True + with ctx(ctx.on.start(), State()) as event: + event.run() + assert event.charm.config["foo"] is True diff --git a/tests/test_context.py b/tests/test_context.py index 2ca8b93a..f3ad4d16 100644 --- a/tests/test_context.py +++ b/tests/test_context.py @@ -53,9 +53,21 @@ def test_run_action(): @pytest.mark.parametrize("unit_id", (1, 2, 42)) def test_app_name(app_name, unit_id): ctx = Context(MyCharm, meta={"name": "foo"}, app_name=app_name, unit_id=unit_id) - with ctx.manager(ctx.on.start(), State()) as mgr: - assert mgr.charm.app.name == app_name - assert mgr.charm.unit.name == f"{app_name}/{unit_id}" + with ctx(ctx.on.start(), State()) as event: + assert event.charm.app.name == app_name + assert event.charm.unit.name == f"{app_name}/{unit_id}" + + +def test_context_manager(): + ctx = Context(MyCharm, meta={"name": "foo"}, actions={"act": {}}) + state = State() + with ctx(ctx.on.start(), state) as event: + event.run() + assert event.charm.meta.name == "foo" + + with ctx(Action("act"), state) as event: + event.run_action() + assert event.charm.meta.name == "foo" def test_action_output_no_positional_arguments(): diff --git a/tests/test_context_on.py b/tests/test_context_on.py index 151bc303..a8a945ac 100644 --- a/tests/test_context_on.py +++ b/tests/test_context_on.py @@ -64,7 +64,7 @@ def test_simple_events(event_name, event_kind): ctx = scenario.Context(ContextCharm, meta=META, actions=ACTIONS) # These look like: # ctx.run(ctx.on.install(), state) - with ctx.manager(getattr(ctx.on, event_name)(), scenario.State()) as mgr: + with ctx(getattr(ctx.on, event_name)(), scenario.State()) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -95,7 +95,7 @@ def test_simple_secret_events(as_kwarg, event_name, event_kind, owner): else: args = (secret,) kwargs = {} - with ctx.manager(getattr(ctx.on, event_name)(*args, **kwargs), state_in) as mgr: + with ctx(getattr(ctx.on, event_name)(*args, **kwargs), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -123,7 +123,7 @@ def test_revision_secret_events(event_name, event_kind): # ctx.run(ctx.on.secret_expired(secret=secret, revision=revision), state) # The secret and revision must always be passed because the same event name # is used for all secrets. - with ctx.manager(getattr(ctx.on, event_name)(secret, revision=42), state_in) as mgr: + with ctx(getattr(ctx.on, event_name)(secret, revision=42), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -159,7 +159,7 @@ def test_storage_events(event_name, event_kind): state_in = scenario.State(storages=[storage]) # These look like: # ctx.run(ctx.on.storage_attached(storage), state) - with ctx.manager(getattr(ctx.on, event_name)(storage), state_in) as mgr: + with ctx(getattr(ctx.on, event_name)(storage), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -173,8 +173,8 @@ def test_action_event_no_params(): ctx = scenario.Context(ContextCharm, meta=META, actions=ACTIONS) # These look like: # ctx.run_action(ctx.on.action(action), state) - with ctx.action_manager(ctx.on.action("act"), scenario.State()) as mgr: - mgr.run() + with ctx(ctx.on.action("act"), scenario.State()) as mgr: + mgr.run_action() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) event = mgr.charm.observed[0] @@ -187,8 +187,8 @@ def test_action_event_with_params(): # ctx.run_action(ctx.on.action(action=action), state) # So that any parameters can be included and the ID can be customised. call_event = ctx.on.action("act", params={"param": "hello"}) - with ctx.action_manager(call_event, scenario.State()) as mgr: - mgr.run() + with ctx(call_event, scenario.State()) as mgr: + mgr.run_action() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) event = mgr.charm.observed[0] @@ -203,7 +203,7 @@ def test_pebble_ready_event(): state_in = scenario.State(containers=[container]) # These look like: # ctx.run(ctx.on.pebble_ready(container), state) - with ctx.manager(ctx.on.pebble_ready(container), state_in) as mgr: + with ctx(ctx.on.pebble_ready(container), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -232,7 +232,7 @@ def test_relation_app_events(as_kwarg, event_name, event_kind): else: args = (relation,) kwargs = {} - with ctx.manager(getattr(ctx.on, event_name)(*args, **kwargs), state_in) as mgr: + with ctx(getattr(ctx.on, event_name)(*args, **kwargs), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -249,7 +249,7 @@ def test_relation_complex_name(): ctx = scenario.Context(ContextCharm, meta=meta, actions=ACTIONS) relation = scenario.Relation("foo-bar-baz") state_in = scenario.State(relations=[relation]) - with ctx.manager(ctx.on.relation_created(relation), state_in) as mgr: + with ctx(ctx.on.relation_created(relation), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 event = mgr.charm.observed[0] @@ -282,7 +282,7 @@ def test_relation_unit_events_default_unit(event_name, event_kind): # These look like: # ctx.run(ctx.on.baz_relation_changed, state) # The unit is chosen automatically. - with ctx.manager(getattr(ctx.on, event_name)(relation), state_in) as mgr: + with ctx(getattr(ctx.on, event_name)(relation), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -308,9 +308,7 @@ def test_relation_unit_events(event_name, event_kind): state_in = scenario.State(relations=[relation]) # These look like: # ctx.run(ctx.on.baz_relation_changed(unit=unit_ordinal), state) - with ctx.manager( - getattr(ctx.on, event_name)(relation, remote_unit=2), state_in - ) as mgr: + with ctx(getattr(ctx.on, event_name)(relation, remote_unit=2), state_in) as mgr: mgr.run() assert len(mgr.charm.observed) == 2 assert isinstance(mgr.charm.observed[1], ops.CollectStatusEvent) @@ -327,7 +325,7 @@ def test_relation_departed_event(): state_in = scenario.State(relations=[relation]) # These look like: # ctx.run(ctx.on.baz_relation_departed(unit=unit_ordinal, departing_unit=unit_ordinal), state) - with ctx.manager( + with ctx( ctx.on.relation_departed(relation, remote_unit=2, departing_unit=1), state_in ) as mgr: mgr.run() diff --git a/tests/test_e2e/test_cloud_spec.py b/tests/test_e2e/test_cloud_spec.py index 1834b3da..c3a09248 100644 --- a/tests/test_e2e/test_cloud_spec.py +++ b/tests/test_e2e/test_cloud_spec.py @@ -47,14 +47,14 @@ def test_get_cloud_spec(): name="lxd-model", type="lxd", cloud_spec=scenario_cloud_spec ), ) - with ctx.manager(ctx.on.start(), state=state) as mgr: + with ctx(ctx.on.start(), state=state) as mgr: assert mgr.charm.model.get_cloud_spec() == expected_cloud_spec def test_get_cloud_spec_error(): ctx = scenario.Context(MyCharm, meta={"name": "foo"}) state = scenario.State(model=scenario.Model(name="lxd-model", type="lxd")) - with ctx.manager(ctx.on.start(), state) as mgr: + with ctx(ctx.on.start(), state) as mgr: with pytest.raises(ops.ModelError): mgr.charm.model.get_cloud_spec() @@ -65,6 +65,6 @@ def test_get_cloud_spec_untrusted(): state = scenario.State( model=scenario.Model(name="lxd-model", type="lxd", cloud_spec=cloud_spec), ) - with ctx.manager(ctx.on.start(), state) as mgr: + with ctx(ctx.on.start(), state) as mgr: with pytest.raises(ops.ModelError): mgr.charm.model.get_cloud_spec() diff --git a/tests/test_e2e/test_manager.py b/tests/test_e2e/test_manager.py index 3f99ffd0..2b401eb6 100644 --- a/tests/test_e2e/test_manager.py +++ b/tests/test_e2e/test_manager.py @@ -65,7 +65,7 @@ def test_manager_reemit_fails(mycharm): def test_context_manager(mycharm): ctx = Context(mycharm, meta=mycharm.META) - with ctx.manager(ctx.on.start(), State()) as manager: + with ctx(ctx.on.start(), State()) as manager: state_out = manager.run() assert isinstance(state_out, State) assert ctx.emitted_events[0].handle.kind == "start" @@ -73,7 +73,7 @@ def test_context_manager(mycharm): def test_context_action_manager(mycharm): ctx = Context(mycharm, meta=mycharm.META, actions=mycharm.ACTIONS) - with ctx.action_manager(ctx.on.action("do-x"), State()) as manager: - ao = manager.run() + with ctx(ctx.on.action("do-x"), State()) as manager: + ao = manager.run_action() assert isinstance(ao, ActionOutput) assert ctx.emitted_events[0].handle.kind == "do_x_action" diff --git a/tests/test_e2e/test_network.py b/tests/test_e2e/test_network.py index e2b70ea4..369e3f5e 100644 --- a/tests/test_e2e/test_network.py +++ b/tests/test_e2e/test_network.py @@ -40,7 +40,7 @@ def test_ip_get(mycharm): }, ) - with ctx.manager( + with ctx( ctx.on.update_status(), State( relations=[ @@ -77,7 +77,7 @@ def test_no_sub_binding(mycharm): }, ) - with ctx.manager( + with ctx( ctx.on.update_status(), State( relations=[ @@ -102,7 +102,7 @@ def test_no_relation_error(mycharm): }, ) - with ctx.manager( + with ctx( ctx.on.update_status(), State( relations=[ diff --git a/tests/test_e2e/test_pebble.py b/tests/test_e2e/test_pebble.py index da40cf5d..119d8ec0 100644 --- a/tests/test_e2e/test_pebble.py +++ b/tests/test_e2e/test_pebble.py @@ -128,9 +128,9 @@ def callback(self: CharmBase): charm_type=charm_cls, meta={"name": "foo", "containers": {"foo": {}}}, ) - with ctx.manager(ctx.on.start(), state=state) as mgr: - out = mgr.run() - callback(mgr.charm) + with ctx(ctx.on.start(), state=state) as event: + out = event.run() + callback(event.charm) if make_dirs: # file = (out.get_container("foo").mounts["foo"].source + "bar/baz.txt").open("/foo/bar/baz.txt") @@ -318,8 +318,8 @@ def test_exec_wait_error(charm_cls): ) ctx = Context(charm_cls, meta={"name": "foo", "containers": {"foo": {}}}) - with ctx.manager(ctx.on.start(), state) as mgr: - container = mgr.charm.unit.get_container("foo") + with ctx(ctx.on.start(), state) as event: + container = event.charm.unit.get_container("foo") proc = container.exec(["foo"]) with pytest.raises(ExecError): proc.wait() @@ -340,8 +340,8 @@ def test_exec_wait_output(charm_cls): ) ctx = Context(charm_cls, meta={"name": "foo", "containers": {"foo": {}}}) - with ctx.manager(ctx.on.start(), state) as mgr: - container = mgr.charm.unit.get_container("foo") + with ctx(ctx.on.start(), state) as event: + container = event.charm.unit.get_container("foo") proc = container.exec(["foo"]) out, err = proc.wait_output() assert out == "hello pebble" @@ -360,8 +360,8 @@ def test_exec_wait_output_error(charm_cls): ) ctx = Context(charm_cls, meta={"name": "foo", "containers": {"foo": {}}}) - with ctx.manager(ctx.on.start(), state) as mgr: - container = mgr.charm.unit.get_container("foo") + with ctx(ctx.on.start(), state) as event: + container = event.charm.unit.get_container("foo") proc = container.exec(["foo"]) with pytest.raises(ExecError): proc.wait_output() @@ -381,10 +381,10 @@ def test_pebble_custom_notice(charm_cls): state = State(containers=[container]) ctx = Context(charm_cls, meta={"name": "foo", "containers": {"foo": {}}}) - with ctx.manager( + with ctx( ctx.on.pebble_custom_notice(container=container, notice=notices[-1]), state - ) as mgr: - container = mgr.charm.unit.get_container("foo") + ) as event: + container = event.charm.unit.get_container("foo") assert container.get_notices() == [n._to_ops() for n in notices] diff --git a/tests/test_e2e/test_relations.py b/tests/test_e2e/test_relations.py index 9ba0ed61..be877203 100644 --- a/tests/test_e2e/test_relations.py +++ b/tests/test_e2e/test_relations.py @@ -417,8 +417,8 @@ def test_broken_relation_not_in_model_relations(mycharm): ctx = Context( mycharm, meta={"name": "local", "requires": {"foo": {"interface": "foo"}}} ) - with ctx.manager(ctx.on.relation_broken(rel), state=State(relations={rel})) as mgr: - charm = mgr.charm + with ctx(ctx.on.relation_broken(rel), state=State(relations={rel})) as event: + charm = event.charm assert charm.model.get_relation("foo") is None assert charm.model.relations["foo"] == [] diff --git a/tests/test_e2e/test_resource.py b/tests/test_e2e/test_resource.py index c4237ea6..71950906 100644 --- a/tests/test_e2e/test_resource.py +++ b/tests/test_e2e/test_resource.py @@ -25,10 +25,10 @@ def test_get_resource(): ) resource1 = Resource(name="foo", path=pathlib.Path("/tmp/foo")) resource2 = Resource(name="bar", path=pathlib.Path("~/bar")) - with ctx.manager( + with ctx( ctx.on.update_status(), state=State(resources={resource1, resource2}) - ) as mgr: - assert mgr.charm.model.resources.fetch("foo") == resource1.path - assert mgr.charm.model.resources.fetch("bar") == resource2.path + ) as event: + assert event.charm.model.resources.fetch("foo") == resource1.path + assert event.charm.model.resources.fetch("bar") == resource2.path with pytest.raises(NameError): - mgr.charm.model.resources.fetch("baz") + event.charm.model.resources.fetch("baz") diff --git a/tests/test_e2e/test_secrets.py b/tests/test_e2e/test_secrets.py index 85fda55c..a11c9fa2 100644 --- a/tests/test_e2e/test_secrets.py +++ b/tests/test_e2e/test_secrets.py @@ -29,26 +29,26 @@ def _on_event(self, event): def test_get_secret_no_secret(mycharm): ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager(ctx.on.update_status(), State()) as mgr: + with ctx(ctx.on.update_status(), State()) as event: with pytest.raises(SecretNotFoundError): - assert mgr.charm.model.get_secret(id="foo") + assert event.charm.model.get_secret(id="foo") with pytest.raises(SecretNotFoundError): - assert mgr.charm.model.get_secret(label="foo") + assert event.charm.model.get_secret(label="foo") def test_get_secret(mycharm): ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( state=State(secrets={Secret(id="foo", contents={0: {"a": "b"}})}), event=ctx.on.update_status(), - ) as mgr: - assert mgr.charm.model.get_secret(id="foo").get_content()["a"] == "b" + ) as event: + assert event.charm.model.get_secret(id="foo").get_content()["a"] == "b" @pytest.mark.parametrize("owner", ("app", "unit")) def test_get_secret_get_refresh(mycharm, owner): ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State( secrets={ @@ -62,15 +62,15 @@ def test_get_secret_get_refresh(mycharm, owner): ) } ), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm assert charm.model.get_secret(id="foo").get_content(refresh=True)["a"] == "c" @pytest.mark.parametrize("app", (True, False)) def test_get_secret_nonowner_peek_update(mycharm, app): ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State( leader=app, @@ -84,8 +84,8 @@ def test_get_secret_nonowner_peek_update(mycharm, app): ), }, ), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm assert charm.model.get_secret(id="foo").get_content()["a"] == "b" assert charm.model.get_secret(id="foo").peek_content()["a"] == "c" assert charm.model.get_secret(id="foo").get_content()["a"] == "b" @@ -97,7 +97,7 @@ def test_get_secret_nonowner_peek_update(mycharm, app): @pytest.mark.parametrize("owner", ("app", "unit")) def test_get_secret_owner_peek_update(mycharm, owner): ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State( secrets={ @@ -111,8 +111,8 @@ def test_get_secret_owner_peek_update(mycharm, owner): ) } ), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm assert charm.model.get_secret(id="foo").get_content()["a"] == "b" assert charm.model.get_secret(id="foo").peek_content()["a"] == "c" assert charm.model.get_secret(id="foo").get_content(refresh=True)["a"] == "c" @@ -160,18 +160,18 @@ def test_consumer_events_failures(mycharm, evt_suffix, revision): @pytest.mark.parametrize("app", (True, False)) def test_add(mycharm, app): ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State(leader=app), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm if app: charm.app.add_secret({"foo": "bar"}, label="mylabel") else: charm.unit.add_secret({"foo": "bar"}, label="mylabel") - assert mgr.output.secrets - secret = mgr.output.get_secret(label="mylabel") + assert event.output.secrets + secret = event.output.get_secret(label="mylabel") assert secret.contents[0] == {"foo": "bar"} assert secret.label == "mylabel" @@ -181,11 +181,11 @@ def test_set_legacy_behaviour(mycharm): # ref: https://bugs.launchpad.net/juju/+bug/2037120 rev1, rev2, rev3 = {"foo": "bar"}, {"foo": "baz"}, {"foo": "baz", "qux": "roz"} ctx = Context(mycharm, meta={"name": "local"}, juju_version="3.1.6") - with ctx.manager( + with ctx( ctx.on.update_status(), State(), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm secret: ops_Secret = charm.unit.add_secret(rev1, label="mylabel") assert ( secret.get_content() @@ -206,7 +206,7 @@ def test_set_legacy_behaviour(mycharm): ) secret.set_content(rev3) - state_out = mgr.run() + state_out = event.run() secret = charm.model.get_secret(label="mylabel") assert ( secret.get_content() @@ -225,11 +225,11 @@ def test_set_legacy_behaviour(mycharm): def test_set(mycharm): rev1, rev2, rev3 = {"foo": "bar"}, {"foo": "baz"}, {"foo": "baz", "qux": "roz"} ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State(), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm secret: ops_Secret = charm.unit.add_secret(rev1, label="mylabel") assert ( secret.get_content() @@ -243,7 +243,7 @@ def test_set(mycharm): assert secret.peek_content() == secret.get_content(refresh=True) == rev2 secret.set_content(rev3) - state_out = mgr.run() + state_out = event.run() assert secret.get_content() == rev2 assert secret.peek_content() == secret.get_content(refresh=True) == rev3 @@ -257,11 +257,11 @@ def test_set(mycharm): def test_set_juju33(mycharm): rev1, rev2, rev3 = {"foo": "bar"}, {"foo": "baz"}, {"foo": "baz", "qux": "roz"} ctx = Context(mycharm, meta={"name": "local"}, juju_version="3.3.1") - with ctx.manager( + with ctx( ctx.on.update_status(), State(), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm secret: ops_Secret = charm.unit.add_secret(rev1, label="mylabel") assert secret.get_content() == rev1 @@ -271,7 +271,7 @@ def test_set_juju33(mycharm): assert secret.get_content(refresh=True) == rev2 secret.set_content(rev3) - state_out = mgr.run() + state_out = event.run() assert secret.get_content() == rev2 assert secret.peek_content() == rev3 assert secret.get_content(refresh=True) == rev3 @@ -286,7 +286,7 @@ def test_set_juju33(mycharm): @pytest.mark.parametrize("app", (True, False)) def test_meta(mycharm, app): ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State( leader=True, @@ -303,8 +303,8 @@ def test_meta(mycharm, app): ) }, ), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm assert charm.model.get_secret(label="mylabel") secret = charm.model.get_secret(id="foo") @@ -326,7 +326,7 @@ def test_secret_permission_model(mycharm, leader, owner): ) ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State( leader=leader, @@ -343,14 +343,14 @@ def test_secret_permission_model(mycharm, leader, owner): ) }, ), - ) as mgr: - secret = mgr.charm.model.get_secret(id="foo") + ) as event: + secret = event.charm.model.get_secret(id="foo") assert secret.get_content()["a"] == "b" assert secret.peek_content() assert secret.get_content(refresh=True) # can always view - secret: ops_Secret = mgr.charm.model.get_secret(id="foo") + secret: ops_Secret = event.charm.model.get_secret(id="foo") if expect_manage: assert secret.get_content() @@ -379,7 +379,7 @@ def test_grant(mycharm, app): ctx = Context( mycharm, meta={"name": "local", "requires": {"foo": {"interface": "bar"}}} ) - with ctx.manager( + with ctx( ctx.on.update_status(), State( relations=[Relation("foo", "remote")], @@ -396,15 +396,15 @@ def test_grant(mycharm, app): ) }, ), - ) as mgr: - charm = mgr.charm + ) as event: + charm = event.charm secret = charm.model.get_secret(label="mylabel") foo = charm.model.get_relation("foo") if app: secret.grant(relation=foo) else: secret.grant(relation=foo, unit=foo.units.pop()) - vals = list(mgr.output.get_secret(label="mylabel").remote_grants.values()) + vals = list(event.output.get_secret(label="mylabel").remote_grants.values()) assert vals == [{"remote"}] if app else [{"remote/0"}] @@ -412,7 +412,7 @@ def test_update_metadata(mycharm): exp = datetime.datetime(2050, 12, 12) ctx = Context(mycharm, meta={"name": "local"}) - with ctx.manager( + with ctx( ctx.on.update_status(), State( secrets={ @@ -426,8 +426,8 @@ def test_update_metadata(mycharm): ) }, ), - ) as mgr: - secret = mgr.charm.model.get_secret(label="mylabel") + ) as event: + secret = event.charm.model.get_secret(label="mylabel") secret.set_info( label="babbuccia", description="blu", @@ -435,7 +435,7 @@ def test_update_metadata(mycharm): rotate=SecretRotate.DAILY, ) - secret_out = mgr.output.get_secret(label="babbuccia") + secret_out = event.output.get_secret(label="babbuccia") assert secret_out.label == "babbuccia" assert secret_out.rotate == SecretRotate.DAILY assert secret_out.description == "blu" @@ -513,31 +513,31 @@ def __init__(self, *args): }, ) - with ctx.manager(ctx.on.start(), state) as mgr: - charm = mgr.charm + with ctx(ctx.on.start(), state) as event: + charm = event.charm secret = charm.app.add_secret({"foo": "bar"}, label="mylabel") bar_relation = charm.model.relations["bar"][0] secret.grant(bar_relation) - assert mgr.output.secrets - scenario_secret = mgr.output.get_secret(label="mylabel") + assert event.output.secrets + scenario_secret = event.output.get_secret(label="mylabel") assert relation_remote_app in scenario_secret.remote_grants[relation_id] - with ctx.manager(ctx.on.start(), mgr.output) as mgr: - charm: GrantingCharm = mgr.charm + with ctx(ctx.on.start(), event.output) as event: + charm: GrantingCharm = event.charm secret = charm.model.get_secret(label="mylabel") secret.revoke(bar_relation) - scenario_secret = mgr.output.get_secret(label="mylabel") + scenario_secret = event.output.get_secret(label="mylabel") assert scenario_secret.remote_grants == {} - with ctx.manager(ctx.on.start(), mgr.output) as mgr: - charm: GrantingCharm = mgr.charm + with ctx(ctx.on.start(), event.output) as event: + charm: GrantingCharm = event.charm secret = charm.model.get_secret(label="mylabel") secret.remove_all_revisions() - assert not mgr.output.get_secret(label="mylabel").contents # secret wiped + assert not event.output.get_secret(label="mylabel").contents # secret wiped def test_no_additional_positional_arguments(): diff --git a/tests/test_e2e/test_storage.py b/tests/test_e2e/test_storage.py index 3e6912fb..8f65fe5c 100644 --- a/tests/test_e2e/test_storage.py +++ b/tests/test_e2e/test_storage.py @@ -23,38 +23,38 @@ def no_storage_ctx(): def test_storage_get_null(no_storage_ctx): - with no_storage_ctx.manager(no_storage_ctx.on.update_status(), State()) as mgr: - storages = mgr.charm.model.storages + with no_storage_ctx(no_storage_ctx.on.update_status(), State()) as event: + storages = event.charm.model.storages assert not len(storages) def test_storage_get_unknown_name(storage_ctx): - with storage_ctx.manager(storage_ctx.on.update_status(), State()) as mgr: - storages = mgr.charm.model.storages + with storage_ctx(storage_ctx.on.update_status(), State()) as event: + storages = event.charm.model.storages # not in metadata with pytest.raises(KeyError): storages["bar"] def test_storage_request_unknown_name(storage_ctx): - with storage_ctx.manager(storage_ctx.on.update_status(), State()) as mgr: - storages = mgr.charm.model.storages + with storage_ctx(storage_ctx.on.update_status(), State()) as event: + storages = event.charm.model.storages # not in metadata with pytest.raises(ModelError): storages.request("bar") def test_storage_get_some(storage_ctx): - with storage_ctx.manager(storage_ctx.on.update_status(), State()) as mgr: - storages = mgr.charm.model.storages + with storage_ctx(storage_ctx.on.update_status(), State()) as event: + storages = event.charm.model.storages # known but none attached assert storages["foo"] == [] @pytest.mark.parametrize("n", (1, 3, 5)) def test_storage_add(storage_ctx, n): - with storage_ctx.manager(storage_ctx.on.update_status(), State()) as mgr: - storages = mgr.charm.model.storages + with storage_ctx(storage_ctx.on.update_status(), State()) as event: + storages = event.charm.model.storages storages.request("foo", n) assert storage_ctx.requested_storages["foo"] == n @@ -65,10 +65,10 @@ def test_storage_usage(storage_ctx): # setup storage with some content (storage.get_filesystem(storage_ctx) / "myfile.txt").write_text("helloworld") - with storage_ctx.manager( + with storage_ctx( storage_ctx.on.update_status(), State(storages={storage}) - ) as mgr: - foo = mgr.charm.model.storages["foo"][0] + ) as event: + foo = event.charm.model.storages["foo"][0] loc = foo.location path = loc / "myfile.txt" assert path.exists() diff --git a/tests/test_e2e/test_vroot.py b/tests/test_e2e/test_vroot.py index c8702611..5ba94a7b 100644 --- a/tests/test_e2e/test_vroot.py +++ b/tests/test_e2e/test_vroot.py @@ -56,16 +56,16 @@ def test_charm_virtual_root_cleanup_if_exists(charm_virtual_root): meta_file.write_text(raw_ori_meta) ctx = Context(MyCharm, meta=MyCharm.META, charm_root=charm_virtual_root) - with ctx.manager( + with ctx( ctx.on.start(), State(), - ) as mgr: + ) as event: assert meta_file.exists() assert meta_file.read_text() == yaml.safe_dump({"name": "my-charm"}) assert ( - mgr.charm.meta.name == "my-charm" + event.charm.meta.name == "my-charm" ) # not karl! Context.meta takes precedence - mgr.run() + event.run() assert meta_file.exists() # meta file was restored to its previous contents @@ -79,13 +79,13 @@ def test_charm_virtual_root_cleanup_if_not_exists(charm_virtual_root): assert not meta_file.exists() ctx = Context(MyCharm, meta=MyCharm.META, charm_root=charm_virtual_root) - with ctx.manager( + with ctx( ctx.on.start(), State(), - ) as mgr: + ) as event: assert meta_file.exists() assert meta_file.read_text() == yaml.safe_dump({"name": "my-charm"}) - mgr.run() + event.run() assert not meta_file.exists() assert not meta_file.exists()