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 .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
// README at: https://github.com/devcontainers/templates/tree/main/src/docker-existing-dockerfile
{
"name": "dev",
"image": "ghcr.io/ten-framework/ten_agent_build:0.3.3",
"image": "ghcr.io/ten-framework/ten_agent_build:0.3.5",
"customizations": {
"vscode": {
"extensions": [
Expand Down
7 changes: 5 additions & 2 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ jobs:
ci:
runs-on: ubuntu-latest
container:
image: ghcr.io/ten-framework/ten_agent_build:0.3.3
image: ghcr.io/ten-framework/ten_agent_build:0.3.5
steps:
- uses: actions/checkout@v4
with:
Expand All @@ -34,7 +34,10 @@ jobs:
- name: Check ten dependencies
run: |
task install
task test

- name: Run tests
run: |
task test -- -s -v

- name: Release
if: startsWith(github.ref, 'refs/tags/')
Expand Down
3 changes: 2 additions & 1 deletion tests/bin/start
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ set -e
cd "$(dirname "${BASH_SOURCE[0]}")/../.."

export PYTHONPATH=.ten/app/ten_packages/system/ten_runtime_python/lib:.ten/app/ten_packages/system/ten_runtime_python/interface
export TEN_DISABLE_ADDON_UNREGISTER_AFTER_APP_CLOSE=true

# If the Python app imports some modules that are compiled with a different
# version of libstdc++ (ex: PyTorch), the Python app may encounter confusing
Expand All @@ -18,4 +19,4 @@ export PYTHONPATH=.ten/app/ten_packages/system/ten_runtime_python/lib:.ten/app/t
#
# Refer to https://github.com/pytorch/pytorch/issues/102360?from_wecom=1#issuecomment-1708989096

pytest -s tests/ "$@"
pytest tests/ "$@"
23 changes: 11 additions & 12 deletions tests/test_invalid_path.py → tests/test_404.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
import httpx


class ExtensionTesterInvalidPathCase1(ExtensionTester):
class ExtensionTesterNotFound1(ExtensionTester):
def on_start(self, ten_env: TenEnvTester) -> None:
ten_env.on_start_done()

Expand All @@ -28,7 +28,7 @@ def on_start(self, ten_env: TenEnvTester) -> None:
ten_env.stop_test()


class ExtensionTesterInvalidPathCase2(ExtensionTester):
class ExtensionTesterNotFound2(ExtensionTester):
def on_start(self, ten_env: TenEnvTester) -> None:
ten_env.on_start_done()

Expand All @@ -39,14 +39,13 @@ def on_start(self, ten_env: TenEnvTester) -> None:
ten_env.stop_test()


# TODO: disable it currently since second tester seems can not run. enable it once fixed
# def test_invalid_path():
# tester = ExtensionTesterInvalidPathCase1()
# tester.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
# tester.set_test_mode_single("http_server_python")
# tester.run()
def test_404():
tester = ExtensionTesterNotFound1()
tester.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
tester.set_test_mode_single("http_server_python")
tester.run()

# tester2 = ExtensionTesterInvalidPathCase2()
# tester2.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
# tester2.set_test_mode_single("http_server_python")
# tester2.run()
tester2 = ExtensionTesterNotFound2()
tester2.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
tester2.set_test_mode_single("http_server_python")
tester2.run()
60 changes: 60 additions & 0 deletions tests/test_5xx.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
#
# Copyright © 2025 Agora
# This file is part of TEN Framework, an open source project.
# Licensed under the Apache License, Version 2.0, with certain conditions.
# Refer to the "LICENSE" file in the root directory for more information.
#
from pathlib import Path
from typing import Optional
from ten import (
ExtensionTester,
TenEnvTester,
Cmd,
CmdResult,
StatusCode,
TenError,
)
import httpx
import threading


class ExtensionTester5xx(ExtensionTester):
def __init__(self):
super().__init__()
self.thread = None
self.event = threading.Event()

def on_cmd(self, ten_env: TenEnvTester, cmd: Cmd) -> None:
print(f"on_cmd name {cmd.get_name()}")
ten_env.return_result(CmdResult.create(StatusCode.ERROR), cmd)

event_got = self.event.wait(timeout=5)
if not event_got: # timeout
print("test error")
else:
ten_env.stop_test()

def on_start(self, ten_env: TenEnvTester) -> None:

self.thread = threading.Thread(target=self._async_request, args=[])
self.thread.start()

ten_env.on_start_done()

def _async_request(self) -> None:
property_json = {"num": 1, "str": "111"}
r = httpx.post("http://127.0.0.1:8888/cmd/abc",
json=property_json, timeout=5)
print(r)

if r.status_code >= 500:
# TODO: stop test directly once albe to call it in separate thread
# ten_env.stop_test()
self.event.set()


def test_5xx():
tester = ExtensionTester5xx()
tester.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
tester.set_test_mode_single("http_server_python")
tester.run()
58 changes: 58 additions & 0 deletions tests/test_basic.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
#
# Copyright © 2025 Agora
# This file is part of TEN Framework, an open source project.
# Licensed under the Apache License, Version 2.0, with certain conditions.
# Refer to the "LICENSE" file in the root directory for more information.
#
from pathlib import Path
from ten import (
ExtensionTester,
TenEnvTester,
Cmd,
CmdResult,
StatusCode,
)
import httpx
import threading


class ExtensionTesterBasic(ExtensionTester):
def __init__(self):
super().__init__()
self.thread = None
self.event = threading.Event()

def on_cmd(self, ten_env: TenEnvTester, cmd: Cmd) -> None:
print(f"on_cmd name {cmd.get_name()}")
ten_env.return_result(CmdResult.create(StatusCode.OK), cmd)

event_got = self.event.wait(timeout=5)
if not event_got: # timeout
print("test error")
else:
ten_env.stop_test()

def on_start(self, ten_env: TenEnvTester) -> None:

self.thread = threading.Thread(target=self._async_request, args=[])
self.thread.start()

ten_env.on_start_done()

def _async_request(self) -> None:
property_json = {"num": 1, "str": "111"}
r = httpx.post("http://127.0.0.1:8888/cmd/abc",
json=property_json, timeout=5)
print(r)

if r.status_code == httpx.codes.OK:
# TODO: stop test directly once albe to call it in separate thread
# ten_env.stop_test()
self.event.set()


def test_basic():
tester = ExtensionTesterBasic()
tester.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
tester.set_test_mode_single("http_server_python")
tester.run()
75 changes: 75 additions & 0 deletions tests/test_set_property.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
#
# Copyright © 2025 Agora
# This file is part of TEN Framework, an open source project.
# Licensed under the Apache License, Version 2.0, with certain conditions.
# Refer to the "LICENSE" file in the root directory for more information.
#
from pathlib import Path
from ten import (
ExtensionTester,
TenEnvTester,
Cmd,
CmdResult,
StatusCode,
)
import httpx
import threading


class ExtensionTesterSetProperty(ExtensionTester):
def __init__(self):
super().__init__()
self.thread = None
self.event = threading.Event()

def on_cmd(self, ten_env: TenEnvTester, cmd: Cmd) -> None:
print(f"on_cmd name {cmd.get_name()}")
ten_env.return_result(CmdResult.create(StatusCode.OK), cmd)

event_got = self.event.wait(timeout=5)
if not event_got: # timeout
print("test error")
else:
ten_env.stop_test()

def on_start(self, ten_env: TenEnvTester) -> None:

self.thread = threading.Thread(target=self._async_request, args=[])
self.thread.start()

ten_env.on_start_done()

def _async_request(self) -> None:
property_json = {"num": 1, "str": "111"}
r = httpx.post("http://127.0.0.1:8899/cmd/abc",
json=property_json, timeout=5)
print(r)

if r.status_code == httpx.codes.OK:
# TODO: stop test directly once albe to call it in separate thread
# ten_env.stop_test()
self.event.set()


def test_set_property():

# change port
property_json_1 = '{"listen_port":8899}'
tester_1 = ExtensionTesterSetProperty()
tester_1.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
tester_1.set_test_mode_single("http_server_python", property_json_1)
tester_1.run()

# change port with localhost
property_json_2 = '{"listen_addr":"127.0.0.1","listen_port":8899}'
tester_2 = ExtensionTesterSetProperty()
tester_2.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
tester_2.set_test_mode_single("http_server_python", property_json_2)
tester_2.run()

# change port with any addr
property_json_3 = '{"listen_addr":"0.0.0.0","listen_port":8899}'
tester_3 = ExtensionTesterSetProperty()
tester_3.add_addon_base_dir(str(Path(__file__).resolve().parent.parent))
tester_3.set_test_mode_single("http_server_python", property_json_3)
tester_3.run()
3 changes: 2 additions & 1 deletion tests/test_timeout.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,8 @@ def on_start(self, ten_env: TenEnvTester) -> None:
ten_env.on_start_done()

property_json = {"num": 1, "str": "111"}
r = httpx.post("http://127.0.0.1:8888/cmd/abc", json=property_json, timeout=10)
r = httpx.post("http://127.0.0.1:8888/cmd/abc",
json=property_json, timeout=10)
print(r)
if r.status_code == httpx.codes.GATEWAY_TIMEOUT:
ten_env.stop_test()
Expand Down
Loading