Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ stompman takes care of cleaning up resources automatically. When you leave the c
Also, I want to pointed out that:

- Protocol parsing is inspired by [aiostomp](https://github.com/pedrokiefer/aiostomp/blob/3449dcb53f43e5956ccc7662bb5b7d76bc6ef36b/aiostomp/protocol.py) (meaning: consumed by me and refactored from).
- stompman is tested and used with [Artemis ActiveMQ](https://activemq.apache.org/components/artemis/).
- stompman is tested and used with [ActiveMQ Artemis](https://activemq.apache.org/components/artemis/) and [ActiveMQ Classic](https://activemq.apache.org/components/classic/).
- Specification says that headers in CONNECT and CONNECTED frames shouldn't be escaped for backwards compatibility. stompman escapes headers in CONNECT frame (outcoming), but does not unescape headers in CONNECTED (outcoming).

### Examples
Expand Down
14 changes: 10 additions & 4 deletions docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,16 +5,22 @@ services:
args:
PYTHON_IMAGE: ${PYTHON_IMAGE:-python:3.13-slim-bullseye}
depends_on:
artemis:
activemq-artemis:
condition: service_started
activemq-classic:
condition: service_started
environment:
ARTEMIS_HOST: artemis

artemis:
activemq-artemis:
image: apache/activemq-artemis:2.37.0-alpine
environment:
ARTEMIS_USER: admin
ARTEMIS_PASSWORD: ":=123"
ports:
- 8161:8161
- 61616:61616

activemq-classic:
image: apache/activemq-classic:6.1.2
environment:
ACTIVEMQ_CONNECTION_USER: admin
ACTIVEMQ_CONNECTION_PASSWORD: ":=123"
8 changes: 1 addition & 7 deletions examples/consumer.py
Original file line number Diff line number Diff line change
@@ -1,14 +1,8 @@
import asyncio
import os

import stompman

server = stompman.ConnectionParameters(
host=os.environ.get("ARTEMIS_HOST", "0.0.0.0"), # noqa: S104
port=61616,
login="admin",
passcode=":=123",
)
server = stompman.ConnectionParameters(host="0.0.0.0", port=61616, login="admin", passcode=":=123") # noqa: S104


async def handle_message(message_frame: stompman.MessageFrame) -> None:
Expand Down
8 changes: 1 addition & 7 deletions examples/producer.py
Original file line number Diff line number Diff line change
@@ -1,14 +1,8 @@
import asyncio
import os

import stompman

server = stompman.ConnectionParameters(
host=os.environ.get("ARTEMIS_HOST", "0.0.0.0"), # noqa: S104
port=61616,
login="admin",
passcode=":=123",
)
server = stompman.ConnectionParameters(host="0.0.0.0", port=61616, login="admin", passcode=":=123") # noqa: S104


async def main() -> None:
Expand Down
29 changes: 19 additions & 10 deletions tests/integration.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
import asyncio
import os
from collections.abc import AsyncGenerator, Callable
from contextlib import asynccontextmanager
from itertools import starmap
from typing import Final
from typing import Final, cast
from uuid import uuid4

import pytest
Expand All @@ -21,23 +20,29 @@
parse_header,
)

pytestmark = pytest.mark.anyio
DESTINATION: Final = "DLQ"


CONNECTION_PARAMETERS: Final = stompman.ConnectionParameters(
host=os.environ["ARTEMIS_HOST"], port=61616, login="admin", passcode=":=123"
@pytest.fixture(
params=[
stompman.ConnectionParameters(host="activemq-artemis", port=61616, login="admin", passcode=":=123"),
stompman.ConnectionParameters(host="activemq-classic", port=61613, login="admin", passcode=":=123"),
]
)
DESTINATION: Final = "DLQ"
def connection_parameters(request: pytest.FixtureRequest) -> stompman.ConnectionParameters:
return cast(stompman.ConnectionParameters, request.param)


@asynccontextmanager
async def create_client() -> AsyncGenerator[stompman.Client, None]:
async def create_client(connection_parameters: stompman.ConnectionParameters) -> AsyncGenerator[stompman.Client, None]:
async with stompman.Client(
servers=[CONNECTION_PARAMETERS], read_timeout=10, connection_confirmation_timeout=10
servers=[connection_parameters], read_timeout=10, connection_confirmation_timeout=10
) as client:
yield client


async def test_ok() -> None:
@pytest.mark.anyio
async def test_ok(connection_parameters: stompman.ConnectionParameters) -> None:
async def produce() -> None:
for message in messages[200:]:
await producer.send(body=message, destination=DESTINATION, headers={"hello": "from outside transaction"})
Expand Down Expand Up @@ -65,7 +70,11 @@ async def handle_message(frame: stompman.MessageFrame) -> None: # noqa: RUF029

messages = [str(uuid4()).encode() for _ in range(10000)]

async with create_client() as consumer, create_client() as producer, asyncio.TaskGroup() as task_group:
async with (
create_client(connection_parameters) as consumer,
create_client(connection_parameters) as producer,
asyncio.TaskGroup() as task_group,
):
task_group.create_task(consume())
task_group.create_task(produce())

Expand Down
Loading