Skip to content

Commit

Permalink
docs: make requested changes
Browse files Browse the repository at this point in the history
  • Loading branch information
tmihoc committed Dec 17, 2024
1 parent f2538b9 commit 9454b1c
Show file tree
Hide file tree
Showing 38 changed files with 292 additions and 271 deletions.
6 changes: 3 additions & 3 deletions docs/custom_conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,9 +59,9 @@

# FIXME: temporarily disable missing xrefs in this branch, until the missing
# links to Juju and Charmcraft are added.
suppress_warnings = [
'myst.xref_missing',
]
#suppress_warnings = [
# 'myst.xref_missing',
#]

############################################################
### Project information
Expand Down
File renamed without changes.
3 changes: 3 additions & 0 deletions docs/explanation/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@
```{toctree}
:maxdepth: 1
charm-relation-interfaces
testing
interface-tests
holistic-vs-delta-charms
how-and-when-to-defer-events
storedstate-uses-limitations
Expand Down
File renamed without changes.
22 changes: 22 additions & 0 deletions docs/reference/testing.md → docs/explanation/testing.md
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,28 @@ When writing an integration test, it is not sufficient to simply check that Juju
- [pytest-operator](https://github.com/charmed-kubernetes/pytest-operator) and/or [`zaza`](https://github.com/openstack-charmers/zaza)


(pytest-operator)=
### `pytest-operator`

`pytest-operator` is a Python library that provides Juju plugins for the generic Python library `pytest` to facilitate the {ref}`integration testing <integration-testing>` of charms.

> See more: [`pytest-operator`](https://github.com/charmed-kubernetes/pytest-operator)
It builds a fixture called `ops_test` that helps you interact with Juju through constructs that wrap around [`python-libjuju` ](https://pypi.org/project/juju/).

> See more:
> - [`pytest-operator` > `ops_test`](https://github.com/charmed-kubernetes/pytest-operator/blob/main/docs/reference.md#ops_test)
> - [`pytest` > Fixtures](https://docs.pytest.org/en/6.2.x/fixture.html)
It also provides convenient markers and command line parameters (e.g., the `@pytest.mark.skip_if_deployed` marker in combination with the `--no-deploy` configuration helps you skip, e.g., a deployment test in the case where you already have a deployment).


> See more:
> - [`pytest-operator` > Markers](https://github.com/charmed-kubernetes/pytest-operator/blob/main/docs/reference.md#markers)
> - [`pytest-operator` > Command line parameters](https://github.com/charmed-kubernetes/pytest-operator/blob/main/docs/reference.md#command-line-parameters)


**Examples.**

- [https://github.com/canonical/prometheus-k8s-operator/blob/main/tests/integration/test_charm.py](https://github.com/canonical/prometheus-k8s-operator/blob/main/tests/integration/test_charm.py)
Expand Down
6 changes: 5 additions & 1 deletion docs/howto/get-started-with-charm-testing.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ Testing charm code is an essential part of charming. Here we will see how to get
**What you'll need:**
- knowledge of testing in general
- knowledge of Juju and charms
- knowledge of the Juju models and events, esp. the data involved in a charm's lifecycle (e.g. see [Talking to a workload control flow from A to Z]())
- knowledge of the Juju models and events, esp. the data involved in a charm's lifecycle

**What you will learn:**
- What are the starting points for adding tests to a charm?
Expand Down Expand Up @@ -77,7 +77,9 @@ If the charm is a machine charm, workload operation calls can be done directly,

"Juju operations" are the most 'meta' of them all: they do not affect the workload in and of itself, but they share data which is meant to affect the operation of *other* charms that this charm is integrated with.

<!-- UPDATE LINKS:
> See more: [Talking to a workload: control flow from A to Z](), [Charm lifecycle]()
-->

### What we are testing when we unit-test

Expand Down Expand Up @@ -120,7 +122,9 @@ There are two ways to initialize a harnessed charm:
* When a charm is deployed, it goes through the Setup phase, a fixed sequence of events. `Harness` has a method, `begin_with_initial_hooks()`, that runs this sequence.
* Alternatively, you can initialise the charm by calling `begin()`. This will instantiate the charm without firing any Setup phase event.

<!-- UPDATE LINKS:
> See more: [A charm's life](), [`ops.testing.Harness.begin_with_initial_hooks()`](https://ops.readthedocs.io/en/latest/harness.html#ops.testing.Harness.begin_with_initial_hooks), [`ops.testing.Harness.begin()`](https://ops.readthedocs.io/en/latest/harness.html#ops.testing.Harness.begin)
-->

After the Setup phase, the charm goes into Operation. To test operation-phase-related events, the harness provides some methods to simulate the most common scenarios. For example:

Expand Down
3 changes: 1 addition & 2 deletions docs/howto/index.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
(howto-guides)=
(how-to-guides)=
# How-to guides

```{toctree}
Expand All @@ -22,7 +22,6 @@ Get started with charm testing <get-started-with-charm-testing>
Write unit tests for a charm <write-unit-tests-for-a-charm>
Write scenario tests for a charm <write-scenario-tests-for-a-charm>
Write integration tests for a charm <write-integration-tests-for-a-charm>
Instrument your charm with tracing telemetry <instrument-your-charm-with-tracing-telemetry>
Turn a hooks-based charm into an ops charm <turn-a-hooks-based-charm-into-an-ops-charm>
```
Expand Down
146 changes: 0 additions & 146 deletions docs/howto/instrument-your-charm-with-tracing-telemetry.md

This file was deleted.

3 changes: 2 additions & 1 deletion docs/howto/manage-actions.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
(manage-actions)=
# How to manage actions

<!-- UPDATE LINKS
> See first: [`juju` | Action](https://juju.is/docs/juju/action), [`juju` | Manage actions](https://juju.is/docs/juju/manage-actions), [`charmcraft` | Manage actions]()
-->

## Implement the feature

Expand Down
2 changes: 2 additions & 0 deletions docs/howto/manage-configurations.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
(manage-configurations)=
# Manage configurations

<!-- UPDATE LINKS:
> See first: [`juju` | Application configuration](https://juju.is/docs/juju/configuration#heading--application-configuration), [`juju` | Manage application configurations](https://juju.is/docs/juju/manage-applications#heading--configure-an-application), [`charmcraft` | Manage configurations]()
-->


## Implement the feature
Expand Down
4 changes: 2 additions & 2 deletions docs/howto/manage-interfaces.md
Original file line number Diff line number Diff line change
Expand Up @@ -332,7 +332,7 @@ You should see:
In particular, pay attention to the `provider` field. If it says `<no tests>` then there is something wrong with your setup, and the collector isn't able to find your test or identify it as a valid test.

Similarly, you can add tests for requirer in `./interfaces/my_fancy_database/v0/interface_tests/test_requirer.py`. Don't forget to edit the `interface.yaml` file in the "requirers" section to add the name of the charm and the URL. See the "Edit `interface.yaml`" section in the previous how-to guide [How to register an interface]() for more detail on editing `interface.yaml`. [Here](https://github.com/IronCore864/charm-relation-interfaces/tree/my-fancy-database/interfaces/my_fancy_database/v0) is an example of tests for requirers added.
Similarly, you can add tests for requirer in `./interfaces/my_fancy_database/v0/interface_tests/test_requirer.py`. Don't forget to edit the `interface.yaml` file in the "requirers" section to add the name of the charm and the URL. See the "Edit `interface.yaml`" section in the previous how-to guide "How to register an interface" for more detail on editing `interface.yaml`. [Here](https://github.com/IronCore864/charm-relation-interfaces/tree/my-fancy-database/interfaces/my_fancy_database/v0) is an example of tests for requirers added.

### Merge in charm-relation-interfaces

Expand Down Expand Up @@ -451,7 +451,7 @@ INFO:root:Running tests for role: provider
}
```

For reference, [here](https://github.com/IronCore864/my-fancy-database-operator) is an example of a bare minimum `my-fancy-database-operator` charm to make the test pass. In the charm, application relation data and unit relation data are set according to our definition (see the beginning part of the previous how-to guide [How to register an interface]().
For reference, [here](https://github.com/IronCore864/my-fancy-database-operator) is an example of a bare minimum `my-fancy-database-operator` charm to make the test pass. In the charm, application relation data and unit relation data are set according to our definition (see the beginning part of the previous how-to guide "How to register an interface".

### Troubleshooting and debugging the tests

Expand Down
3 changes: 2 additions & 1 deletion docs/howto/manage-leadership-changes.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
(manage-leadership-changes)=
# Manage leadership changes

<!-- UPDATE LINKS:
> See first: [`juju` | Leader](https://juju.is/docs/juju/leader)
-->

## Implement response to leadership changes

Expand Down
7 changes: 5 additions & 2 deletions docs/howto/manage-libraries.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
(manage-libraries)=
# Manage libraries
> See first: [`juju` | Library](), [`charmcraft` | Manage libraries]()

<!-- UPDATE LINKS:
> See first: [`juju` | Library](), [`charmcraft` | Manage libraries]()
-->
## Write a library

When you're writing libraries, instead of callbacks, you can use custom events; that'll result in a more `ops`-native-feeling API. A custom event is, from a technical standpoint, an EventBase subclass that can be emitted at any point throughout the charm's lifecycle. These events are therefore totally unknown to Juju. They are essentially charm-internal, and can be useful to abstract certain conditional workflows and wrap the toplevel Juju event so it can be observed independently.
Expand Down Expand Up @@ -209,7 +210,9 @@ def test_my_object_data(context, endpoint, n_relations):

Fetch the library.

<!-- UPDATE LINKS:
> See more: [`charmcraft` | Manage libraries]()
-->

In your `src/charm.py`, observe the custom events it puts at your disposal. For example, a database library may have provided a `database_relation_ready` event -- a high-level wrapper around the relevant `juju` relation events -- so you use it to manage the database integration in your charm as below:

Expand Down
2 changes: 2 additions & 0 deletions docs/howto/manage-logs.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
(how-to-log-a-message-in-a-charm)=
# How to log a message in a charm

<!-- UPDATE LINKS:
> See first: [`juju` | Log](https://juju.is/docs/juju/log), [`juju` | How to manage logs > Manage the logging configuration](https://juju.is/docs/juju/manage-logs#heading--manage-the-logging-configuration)
-->

<!--
>
Expand Down
2 changes: 2 additions & 0 deletions docs/howto/manage-relations.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,9 @@

To add integration capabilities to a charm, you’ll have to define the relation in your charm’s charmcraft.yaml file and then add relation event handlers in your charm’s `src/charm.py` file.

<!-- UPDATE LINKS
> See first: [`juju` | Relation (integration)](https://juju.is/docs/juju/relation), [`juju` | Manage relations](https://juju.is/docs/juju/manage-relations), [`charmcraft` | Manage relations]()
-->

## Implement the feature

Expand Down
2 changes: 2 additions & 0 deletions docs/howto/manage-resources.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
(manage-resources)=
# How to manage resources

<!-- UPDATE LINKS:
> See also: [`juju` | Resource (charm)](https://juju.is/docs/juju/charm-resource), [`juju` | Manage resources](https://juju.is/docs/juju/manage-charm-resources), [`charmcraft` | Manage resources]()
-->

## Implement the feature

Expand Down
2 changes: 2 additions & 0 deletions docs/howto/manage-secrets.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
(manage-secrets)=
# How to manage secrets

<!-- UPDATE LINKS:
> See first: [`juju` | Secret](https://juju.is/docs/juju/secret), [`juju` | Manage secrets](https://juju.is/docs/juju/manage-secrets), [`charmcraft` | Manage secrets]()
-->

> Added in `ops 2.0.0`, `juju 3.0.2`
Expand Down
2 changes: 2 additions & 0 deletions docs/howto/manage-storage.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
(manage-storage)=
# How to manage storage

<!-- UPDATE LINKS:
> See first: [`juju` | Storage](https://juju.is/docs/juju/storage), [`juju` | Manage storage](https://juju.is/docs/juju/manage-storage), [`charmcraft | Manage storage]()
-->

## Implement the feature

Expand Down
2 changes: 1 addition & 1 deletion docs/howto/run-workloads-with-a-charm-kubernetes.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ The recommended way to create charms for Kubernetes is using the sidecar pattern

Pebble is a lightweight, API-driven process supervisor designed for use with charms. If you specify the `containers` field in a charm's `charmcraft.yaml`, Juju will deploy the charm code in a sidecar container, with Pebble running as the workload container's `ENTRYPOINT`.

When the workload container starts up, Juju fires a [`PebbleReadyEvent`](https://ops.readthedocs.io/en/latest/#ops.PebbleReadyEvent), which can be handled using [`Framework.observe`](https://ops.readthedocs.io/en/latest/#ops.Framework.observe) as shown in [Framework Constructs under "Containers"](). This gives the charm author access to `event.workload`, a [`Container`](https://ops.readthedocs.io/en/latest/#ops.Container) instance.
When the workload container starts up, Juju fires a [`PebbleReadyEvent`](https://ops.readthedocs.io/en/latest/#ops.PebbleReadyEvent), which can be handled using [`Framework.observe`](https://ops.readthedocs.io/en/latest/#ops.Framework.observe). This gives the charm author access to `event.workload`, a [`Container`](https://ops.readthedocs.io/en/latest/#ops.Container) instance.

The `Container` class has methods to modify the Pebble configuration "plan", start and stop services, read and write files, and run commands. These methods use the Pebble API, which communicates from the charm container to the workload container using HTTP over a Unix domain socket.

Expand Down
4 changes: 3 additions & 1 deletion docs/howto/turn-a-hooks-based-charm-into-an-ops-charm.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
(turn-a-hooks-based-charm-into-an-ops-charm)=
# How to turn a hooks-based charm into an ops charm

<!-- UPDATE LINKS:
> See first: [`juju` | Charm taxonomy]()
-->

Suppose you have a hooks-based charm and you decide to rewrite it using the Ops framework in Python.

Expand All @@ -24,7 +26,7 @@ We start by looking at the charm we intend to translate; as an example, we will

From the charm root directory we see:

```bash
```text
$ tree .
.
├── charmcraft.yaml
Expand Down
Loading

0 comments on commit 9454b1c

Please sign in to comment.