Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(network): Add network context manager #367

Merged
merged 23 commits into from
Apr 16, 2024
Merged

Conversation

mloesch
Copy link
Contributor

@mloesch mloesch commented Jul 5, 2023

This PR adds a Network helper class that allows to create networks and connect containers programmatically.

The networks are context-managed resources like containers created via DockerContainer.

Please also see tests for a usage example :)

@VerdantForge
Copy link

I'm interested in this feature. But I see progress has been dropped. Is there a reason?

@mloesch
Copy link
Contributor Author

mloesch commented Nov 10, 2023

I'm interested in this feature. But I see progress has been dropped. Is there a reason?

The build is failing due to cython/cython#4568

I created #376 to fix it, but it hasn't been approved yet.

@kiview
Copy link
Member

kiview commented Nov 24, 2023

Hey @mloesch, thanks for providing this PR for the feature. I see you decided to allow specifying a name for the Network. In Testcontainers for Java, we made the design decision to only generate networks with random names, to avoid the potential for naming conflicts with existing networks. This is a general design approach of Testcontainers and it should be fine for the Testcontainers use cases.

Would you like to adapt the implementation accordingly?

See https://github.com/testcontainers/testcontainers-java/blob/1a3b23385f9a595576246a4c7f5dc54d244dd69d/core/src/main/java/org/testcontainers/containers/Network.java for the Java implementation.

@mloesch
Copy link
Contributor Author

mloesch commented Nov 27, 2023

Hey @kiview, thanks for the review, I changed the implementation to use random names in c10223f

Copy link
Member

@kiview kiview left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @mloesch, that change for the random id looks good. I did another pass and compared it with the implementation in tc-java (which I consider our reference implementation) and had some more suggestions.

I am still getting up to speed with the internals of tc-python, so we can discuss whether my suggestions make sense in this context.


def test_containers_can_communicate_over_network():
with Network() as network:
with DockerContainer("nginx:alpine-slim").with_name(
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Instead of using with_name (which can lead to naming conflicts when parallelizing tests or accidentally reusing names), can we add an API with_network_aliases(string[]), similar to tc-java, that uses Docker's --network-alias mechanism?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@kiview thanks for the pointer! Added this in c757142

def test_containers_can_communicate_over_network():
with Network() as network:
with DockerContainer("nginx:alpine-slim").with_name(
"alpine1").with_kwargs(network=network.name) as alpine1:
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does it make sense to use with_kwargs here and not have an explicit API with_network(Network)?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍 added in e4d9c19

@mloesch
Copy link
Contributor Author

mloesch commented Feb 6, 2024

@kiview is there anything else required for this PR to be merged? :)

@alexanderankin alexanderankin changed the title Add network context manager feat: Add network context manager Mar 20, 2024
Copy link
Collaborator

@santi santi left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I went through your PR now and have some final remarks that should be addressed before we are ready to merge. Very good work so far, this is feature is awesome! 🚀

core/testcontainers/core/container.py Show resolved Hide resolved
@@ -42,6 +43,8 @@ def __init__(
self._container = None
self._command = None
self._name = None
self._network: Optional[Network] = None
self._network_aliases: Optional[list] = None
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you further specify the list to list[str]?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in cac19d3

@@ -57,6 +60,14 @@ def with_exposed_ports(self, *ports: int) -> "DockerContainer":
self.ports[port] = None
return self

def with_network(self, network: Network) -> "DockerContainer":
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Latest version of this file has return type Self from typing_extensions for these methods. Could you sync it with main and update the signature to use Self?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in 1c8ebdc

Network context manager for programmatically connecting containers.
"""

def __init__(self, docker_client_kw: Optional[dict] = None, **kwargs) -> None:
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From an API users' point of view, it is not really clear what the kwargs arguments are meant for. Could you update the signature to be def __init__(self, docker_client_kw: Optional[dict] = None, docker_network_kw: Optional[dict] = None) -> None:?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in b392ca6

def __exit__(self, exc_type, exc_val, exc_tb) -> None:
self.remove()

def __del__(self) -> None:
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We've had some bad experiences with external resource cleanup through the __del__ method, so we have decided to move away from this. Having the context manager and the remove method provides sufficient means to cleanup the resource. __del__ hook can be removed 👍

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in 8c8b6e2

from testcontainers.core.docker_client import DockerClient
from testcontainers.core.network import Network

NGINX_ALPINE_SLIM_IMAGE = "nginx:alpine-slim"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you pin this dpenendency to a specific, versioned tag? We are currently working on making our tests more reproducible, and specific version tags for images used in tests are a part of this.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in 9db1080

mloesch and others added 8 commits April 4, 2024 17:38
…estcontainers#529)

Changed pre-commit config. Some files became re-formatted.
…ners#532)

see testcontainers#531:

I am using testcontainers within a library that provides some
pytest-fixtures.
In order for this to work I have change some settings.

As I can not guarantee that that my lib is imported before
testcontainers I need to monkeypatch the settings.
This is much easier if I only need to monkeypatch the config file and
not all modules that use configurations.

I would argue that for a potential library as this, this is a better
design.

Also one can easier see that the given UPERCASE variable is not a
constant but rather a setting.

Co-authored-by: Carli* Freudenberg <[email protected]>
github-actions bot and others added 3 commits April 8, 2024 11:39
🤖 I have created a release *beep* *boop*
---


##
[4.3.2](testcontainers/testcontainers-python@testcontainers-v4.3.1...testcontainers-v4.3.2)
(2024-04-08)


### Bug Fixes

* **core:** Improve typing for common container usage scenarios
([testcontainers#523](testcontainers#523))
([d5b8553](testcontainers@d5b8553))
* **core:** make config editable to avoid monkeypatching.1
([testcontainers#532](testcontainers#532))
([3be6da3](testcontainers@3be6da3))
* **vault:** add support for HashiCorp Vault container
([testcontainers#366](testcontainers#366))
([1326278](testcontainers@1326278))

---
This PR was generated with [Release
Please](https://github.com/googleapis/release-please). See
[documentation](https://github.com/googleapis/release-please#release-please).

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
@santi santi changed the title feat: Add network context manager feat(network): Add network context manager Apr 15, 2024
@santi
Copy link
Collaborator

santi commented Apr 16, 2024

Thank you for this @mloesch! 🙌 Really appreciate your contribution, this will benefit a lot of users 💯

@santi santi merged commit 11964de into testcontainers:main Apr 16, 2024
7 checks passed
alexanderankin pushed a commit that referenced this pull request Apr 17, 2024
🤖 I have created a release *beep* *boop*
---


##
[4.4.0](testcontainers-v4.3.3...testcontainers-v4.4.0)
(2024-04-17)


### Features

* **labels:** Add common testcontainers labels
([#519](#519))
([e04b7ac](e04b7ac))
* **network:** Add network context manager
([#367](#367))
([11964de](11964de))


### Bug Fixes

* **core:**
[#486](#486)
for colima delay for port avail for connect
([#543](#543))
([90bb780](90bb780))
* **core:** add TESTCONTAINERS_HOST_OVERRIDE as alternative to TC_HOST
([#384](#384))
([8073874](8073874))
* **dependencies:** remove usage of `sqlalchemy` in DB extras. Add
default wait timeout for `wait_for_logs`
([#525](#525))
([fefb9d0](fefb9d0))
* tests for Kafka container running on ARM64 CPU
([#536](#536))
([29b5179](29b5179))

---
This PR was generated with [Release
Please](https://github.com/googleapis/release-please). See
[documentation](https://github.com/googleapis/release-please#release-please).

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

8 participants