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

test_: Test private chat messages #6259

Open
wants to merge 19 commits into
base: develop
Choose a base branch
from
Open
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 .github/workflows/test-reliability.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ jobs:
run: cd tests-functional; docker compose -f docker-compose.anvil.yml -f docker-compose.test.status-go.yml -f docker-compose.status-go.local.yml up --build --remove-orphans -d

- name: Run tests
run: pytest -m "reliability" -c tests-functional/pytest.ini --alluredir=allure-results
run: pytest -n auto -m "reliability" -c tests-functional/pytest.ini --alluredir=allure-results

- name: Get allure history
if: always()
Expand Down
5 changes: 5 additions & 0 deletions tests-functional/clients/services/wakuext.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,3 +38,8 @@ def create_group_chat_with_members(self, pubkey_list: list, group_chat_name: str
params = [None, group_chat_name, pubkey_list]
response = self.rpc_request("createGroupChatWithMembers", params)
return response.json()

def send_group_chat_message(self, group_id: str, message: str):
params = [{"id": group_id, "message": message}]
response = self.rpc_request("sendGroupChatMessage", params)
return response.json()
41 changes: 33 additions & 8 deletions tests-functional/clients/status_backend.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,13 @@
import time
import random
import threading
from uuid import uuid4
import requests
import docker
import docker.errors
import os

from tenacity import retry, stop_after_delay, wait_fixed
from clients.services.wallet import WalletService
from clients.services.wakuext import WakuextService
from clients.services.accounts import AccountService
Expand All @@ -29,16 +32,24 @@ class StatusBackend(RpcClient, SignalClient):
container = None

def __init__(self, await_signals=[], privileged=False):

if option.status_backend_url:
url = option.status_backend_url
else:
self.docker_client = docker.from_env()
host_port = random.choice(option.status_backend_port_range)

self.container = self._start_container(host_port, privileged)
url = f"http://127.0.0.1:{host_port}"
option.status_backend_port_range.remove(host_port)
retries = 5
ports_tried = []
for _ in range(retries):
try:
host_port = random.choice(option.status_backend_port_range)
ports_tried.append(host_port)
self.container = self._start_container(host_port, privileged)
url = f"http://127.0.0.1:{host_port}"
option.status_backend_port_range.remove(host_port)
break
except Exception:
continue
else:
raise RuntimeError(f"Failed to start container on ports: {ports_tried}")

self.base_url = url
self.api_url = f"{url}/statusgo"
Expand All @@ -64,8 +75,9 @@ def _start_container(self, host_port, privileged):
docker_project_name = option.docker_project_name

timestamp = int(time.time() * 1000) # Keep in sync with run_functional_tests.sh
unique_id = uuid4().hex[:8] # Add a unique suffix
image_name = f"{docker_project_name}-status-backend:latest"
container_name = f"{docker_project_name}-status-backend-{timestamp}"
container_name = f"{docker_project_name}-status-backend-{timestamp}-{unique_id}"

coverage_path = option.codecov_dir if option.codecov_dir else os.path.abspath("./coverage/binary")

Expand Down Expand Up @@ -99,7 +111,7 @@ def _start_container(self, host_port, privileged):
network = self.docker_client.networks.get(f"{docker_project_name}_default")
network.connect(container)

option.status_backend_containers.append(container.id)
option.status_backend_containers.append(self)
return container

def wait_for_healthy(self, timeout=10):
Expand Down Expand Up @@ -303,3 +315,16 @@ def container_exec(self, command):

def find_public_key(self):
self.public_key = self.node_login_event.get("event", {}).get("settings", {}).get("public-key")

@retry(stop=stop_after_delay(5), wait=wait_fixed(0.1), reraise=True)
def kill(self):
if self.container:
logging.info(f"Killing container with id {self.container.short_id}")
self.container.kill()
try:
self.container.remove()
except Exception as e:
logging.warning(f"Failed to remove container {self.container.short_id}: {e}")
finally:
self.container = None
logging.info("Container stopped.")
22 changes: 9 additions & 13 deletions tests-functional/conftest.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
import os
import docker

from dataclasses import dataclass, field
from typing import List
import pytest


def pytest_addoption(parser):
Expand Down Expand Up @@ -63,19 +62,16 @@ def pytest_configure(config):
range_size = 100

start_port = base_port + (executor_number * range_size)

option.status_backend_port_range = list(range(start_port, start_port + range_size - 1))
end_port = 20000
option.status_backend_port_range = list(range(start_port, end_port))
option.status_backend_containers = []

option.base_dir = os.path.dirname(os.path.abspath(__file__))


def pytest_unconfigure():
docker_client = docker.from_env()
for container_id in option.status_backend_containers:
try:
container = docker_client.containers.get(container_id)
container.stop(timeout=30)
container.remove()
except Exception as e:
print(e)
@pytest.fixture(scope="function", autouse=True)
def close_status_backend_containers():
option.status_backend_containers = []
yield
for container in option.status_backend_containers:
container.kill()
19 changes: 10 additions & 9 deletions tests-functional/requirements.txt
Original file line number Diff line number Diff line change
@@ -1,14 +1,15 @@
deepdiff==5.5.0
deepdiff~=5.5.0
jsonschema~=3.2.0
pytest==6.2.4
requests==2.31.0
pytest~=7.0.0
requests~=2.31.0
genson~=1.2.2
websocket-client~=1.4.2
tenacity~=9.0.0
pytest-dependency~=0.6.0
docker==7.1.0
pyright==1.1.388
black==24.10.0
pre-commit==3.6.2
allure-pytest==2.13.5
allure-python-commons==2.13.5
docker~=7.1.0
pyright~=1.1.388
black~=24.10.0
pre-commit~=3.6.2
allure-pytest~=2.13.5
allure-python-commons~=2.13.5
pytest-xdist~=3.6.1
42 changes: 10 additions & 32 deletions tests-functional/tests/reliability/test_contact_request.py
Original file line number Diff line number Diff line change
@@ -1,17 +1,15 @@
from time import sleep
from uuid import uuid4
import pytest
from test_cases import MessengerTestCase
from tests.test_cases import MessengerTestCase
from clients.signals import SignalType
from resources.enums import MessageContentType


@pytest.mark.reliability
class TestContactRequests(MessengerTestCase):

@pytest.mark.rpc # until we have dedicated functional tests for this we can still run this test as part of the functional tests suite
@pytest.mark.dependency(name="test_contact_request_baseline")
def test_contact_request_baseline(self, execution_number=1):
def test_contact_request_baseline(self, execution_number=1, network_condition=None):
message_text = f"test_contact_request_{execution_number}_{uuid4()}"
sender = self.initialize_backend(await_signals=self.await_signals)
receiver = self.initialize_backend(await_signals=self.await_signals)
Expand All @@ -21,6 +19,9 @@ def test_contact_request_baseline(self, execution_number=1):
if sender.public_key in str(existing_contacts):
pytest.skip("Contact request was already sent for this sender<->receiver. Skipping test!!")

if network_condition:
network_condition(receiver)

response = sender.wakuext_service.send_contact_request(receiver.public_key, message_text)
expected_message = self.get_message_by_content_type(response, content_type=MessageContentType.CONTACT_REQUEST.value)[0]

Expand All @@ -44,43 +45,20 @@ def test_contact_request_baseline(self, execution_number=1):
expected_message=expected_message,
)

@pytest.mark.skip(
reason=(
"Skipping because of error 'Not enough status-backend containers, "
"please add more'. Unkipping when we merge "
"https://github.com/status-im/status-go/pull/6159"
)
)
@pytest.mark.parametrize("execution_number", range(10))
@pytest.mark.dependency(depends=["test_contact_request_baseline"])
def test_multiple_contact_requests(self, execution_number):
self.test_contact_request_baseline(execution_number=execution_number)

@pytest.mark.dependency(depends=["test_contact_request_baseline"])
@pytest.mark.skip(reason="Skipping until add_latency is implemented")
def test_contact_request_with_latency(self):
# with self.add_latency():
# self.test_contact_request_baseline()
# to be done in the next PR
pass
@pytest.mark.parametrize("execution_number", range(10))
def test_contact_request_with_latency(self, execution_number):
self.test_contact_request_baseline(execution_number=execution_number, network_condition=self.add_latency)

@pytest.mark.dependency(depends=["test_contact_request_baseline"])
@pytest.mark.skip(reason="Skipping until add_packet_loss is implemented")
def test_contact_request_with_packet_loss(self):
# with self.add_packet_loss():
# self.test_contact_request_baseline()
# to be done in the next PR
pass
self.test_contact_request_baseline(execution_number=10, network_condition=self.add_packet_loss)

@pytest.mark.dependency(depends=["test_contact_request_baseline"])
@pytest.mark.skip(reason="Skipping until add_low_bandwith is implemented")
def test_contact_request_with_low_bandwidth(self):
# with self.add_low_bandwith():
# self.test_contact_request_baseline()
# to be done in the next PR
pass
self.test_contact_request_baseline(execution_number=10, network_condition=self.add_low_bandwith)

@pytest.mark.dependency(depends=["test_contact_request_baseline"])
def test_contact_request_with_node_pause_30_seconds(self):
sender = self.initialize_backend(await_signals=self.await_signals)
receiver = self.initialize_backend(await_signals=self.await_signals)
Expand Down
30 changes: 1 addition & 29 deletions tests-functional/tests/reliability/test_create_private_groups.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
from time import sleep
from uuid import uuid4
import pytest
from test_cases import MessengerTestCase
from tests.test_cases import MessengerTestCase
from clients.signals import SignalType
from resources.enums import MessageContentType

Expand All @@ -10,8 +10,6 @@
@pytest.mark.reliability
class TestCreatePrivateGroups(MessengerTestCase):

@pytest.mark.rpc # until we have dedicated functional tests for this we can still run this test as part of the functional tests suite
@pytest.mark.dependency(name="test_create_private_group_baseline")
def test_create_private_group_baseline(self, private_groups_count=1):
self.make_contacts()

Expand All @@ -38,35 +36,9 @@ def test_create_private_group_baseline(self, private_groups_count=1):
fields_to_validate={"text": "text"},
)

@pytest.mark.dependency(depends=["test_create_private_group_baseline"])
def test_multiple_one_create_private_groups(self):
self.test_create_private_group_baseline(private_groups_count=50)

@pytest.mark.dependency(depends=["test_create_private_group_baseline"])
@pytest.mark.skip(reason="Skipping until add_latency is implemented")
def test_create_private_groups_with_latency(self):
# with self.add_latency():
# self.test_create_private_group_baseline()
# to be done in the next PR
pass

@pytest.mark.dependency(depends=["test_create_private_group_baseline"])
@pytest.mark.skip(reason="Skipping until add_packet_loss is implemented")
def test_create_private_groups_with_packet_loss(self):
# with self.add_packet_loss():
# self.test_create_private_group_baseline()
# to be done in the next PR
pass

@pytest.mark.dependency(depends=["test_create_private_group_baseline"])
@pytest.mark.skip(reason="Skipping until add_low_bandwith is implemented")
def test_create_private_groups_with_low_bandwidth(self):
# with self.add_low_bandwith():
# self.test_create_private_group_baseline()
# to be done in the next PR
pass

@pytest.mark.dependency(depends=["test_create_private_group_baseline"])
def test_create_private_groups_with_node_pause_30_seconds(self):
self.make_contacts()

Expand Down
30 changes: 7 additions & 23 deletions tests-functional/tests/reliability/test_one_to_one_messages.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
from time import sleep
from uuid import uuid4
import pytest
from test_cases import MessengerTestCase
from tests.test_cases import MessengerTestCase
from clients.signals import SignalType
from resources.enums import MessageContentType

Expand All @@ -10,8 +10,6 @@
@pytest.mark.reliability
class TestOneToOneMessages(MessengerTestCase):

@pytest.mark.rpc # until we have dedicated functional tests for this we can still run this test as part of the functional tests suite
@pytest.mark.dependency(name="test_one_to_one_message_baseline")
def test_one_to_one_message_baseline(self, message_count=1):
sent_messages = []
for i in range(message_count):
Expand All @@ -33,35 +31,21 @@ def test_one_to_one_message_baseline(self, message_count=1):
expected_message=expected_message,
)

@pytest.mark.dependency(depends=["test_one_to_one_message_baseline"])
def test_multiple_one_to_one_messages(self):
self.test_one_to_one_message_baseline(message_count=50)

@pytest.mark.dependency(depends=["test_one_to_one_message_baseline"])
@pytest.mark.skip(reason="Skipping until add_latency is implemented")
def test_one_to_one_message_with_latency(self):
# with self.add_latency():
# self.test_one_to_one_message_baseline()
# to be done in the next PR
pass
with self.add_latency(self.receiver):
self.test_one_to_one_message_baseline(message_count=50)

@pytest.mark.dependency(depends=["test_one_to_one_message_baseline"])
@pytest.mark.skip(reason="Skipping until add_packet_loss is implemented")
def test_one_to_one_message_with_packet_loss(self):
# with self.add_packet_loss():
# self.test_one_to_one_message_baseline()
# to be done in the next PR
pass
with self.add_packet_loss(self.receiver):
self.test_one_to_one_message_baseline(message_count=50)

@pytest.mark.dependency(depends=["test_one_to_one_message_baseline"])
@pytest.mark.skip(reason="Skipping until add_low_bandwith is implemented")
def test_one_to_one_message_with_low_bandwidth(self):
# with self.add_low_bandwith():
# self.test_one_to_one_message_baseline()
# to be done in the next PR
pass
with self.add_low_bandwith(self.receiver):
self.test_one_to_one_message_baseline(message_count=50)

@pytest.mark.dependency(depends=["test_one_to_one_message_baseline"])
def test_one_to_one_message_with_node_pause_30_seconds(self):
with self.node_pause(self.receiver):
message_text = f"test_message_{uuid4()}"
Expand Down
Loading
Loading