From be201f906cfdb7dd3929244d5a0aa626e9ec436b Mon Sep 17 00:00:00 2001
From: daywalker90 <8257956+daywalker90@users.noreply.github.com>
Date: Tue, 2 Dec 2025 13:51:28 +0100
Subject: [PATCH 01/85] CI: add cargo test
---
.github/workflows/ci.yml | 1 +
1 file changed, 1 insertion(+)
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index f9e3ecb..8190192 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -140,6 +140,7 @@ jobs:
fi
cargo build
+ cargo test
fi
- name: Run tests
From d76ad4e89f9e7036d2f24f850fc621e10287c117 Mon Sep 17 00:00:00 2001
From: daywalker90 <8257956+daywalker90@users.noreply.github.com>
Date: Mon, 8 Dec 2025 23:13:41 +0100
Subject: [PATCH 02/85] CI: upgrade to CLN v25.12
---
.github/workflows/{latest_v24.11.yml => latest_v25.12.yml} | 6 +++---
.github/workflows/{main_v24.11.yml => main_v25.12.yml} | 6 +++---
2 files changed, 6 insertions(+), 6 deletions(-)
rename .github/workflows/{latest_v24.11.yml => latest_v25.12.yml} (51%)
rename .github/workflows/{main_v24.11.yml => main_v25.12.yml} (74%)
diff --git a/.github/workflows/latest_v24.11.yml b/.github/workflows/latest_v25.12.yml
similarity index 51%
rename from .github/workflows/latest_v24.11.yml
rename to .github/workflows/latest_v25.12.yml
index 7174254..268f5f6 100644
--- a/.github/workflows/latest_v24.11.yml
+++ b/.github/workflows/latest_v25.12.yml
@@ -1,4 +1,4 @@
-name: Latest release on CLN v24.11.x
+name: Latest release on CLN v25.12.x
on:
release:
@@ -9,6 +9,6 @@ jobs:
call-ci:
uses: ./.github/workflows/ci.yml
with:
- cln-version: "v24.11.2"
- pyln-version: "24.11.1"
+ cln-version: "v25.12"
+ pyln-version: "25.12"
tagged-release: true
\ No newline at end of file
diff --git a/.github/workflows/main_v24.11.yml b/.github/workflows/main_v25.12.yml
similarity index 74%
rename from .github/workflows/main_v24.11.yml
rename to .github/workflows/main_v25.12.yml
index 7078bd5..8327116 100644
--- a/.github/workflows/main_v24.11.yml
+++ b/.github/workflows/main_v25.12.yml
@@ -1,4 +1,4 @@
-name: main on CLN v24.11.x
+name: main on CLN v25.12.x
on:
push:
@@ -19,6 +19,6 @@ jobs:
call-ci:
uses: ./.github/workflows/ci.yml
with:
- cln-version: "v24.11.2"
- pyln-version: "24.11.1"
+ cln-version: "v25.12"
+ pyln-version: "25.12"
tagged-release: false
\ No newline at end of file
From 65ec4137535fc6a263683380c9c617d23a9fc10b Mon Sep 17 00:00:00 2001
From: daywalker90 <8257956+daywalker90@users.noreply.github.com>
Date: Mon, 8 Dec 2025 23:30:01 +0100
Subject: [PATCH 03/85] README: update for new CLN v25.12
---
README.md | 24 ++++++++++++------------
1 file changed, 12 insertions(+), 12 deletions(-)
diff --git a/README.md b/README.md
index 42fd960..8914b6e 100644
--- a/README.md
+++ b/README.md
@@ -1,16 +1,4 @@
From 7dff9f83e7286251e5b3bd4f2cc3a288c72694e0 Mon Sep 17 00:00:00 2001
From: daywalker90 <8257956+daywalker90@users.noreply.github.com>
Date: Tue, 9 Dec 2025 16:23:34 +0100
Subject: [PATCH 04/85] tests: move pyproject to tests
---
.github/workflows/ci.yml | 3 ++-
pyproject.toml => tests/pyproject.toml | 0
tests/util.py | 5 +++--
uv.lock => tests/uv.lock | 0
4 files changed, 5 insertions(+), 3 deletions(-)
rename pyproject.toml => tests/pyproject.toml (100%)
rename uv.lock => tests/uv.lock (100%)
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 8190192..9aa14a4 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -154,5 +154,6 @@ jobs:
export VALGRIND=0
export PYTEST_TIMEOUT=600
+ cd tests
uv add --dev pyln-testing==${{ inputs.pyln-version }} pyln-client==${{ inputs.pyln-version }} pyln-proto==${{ inputs.pyln-version }}
- uv run -v pytest -n=10 tests/test_*.py
+ uv run -v pytest -n=10
diff --git a/pyproject.toml b/tests/pyproject.toml
similarity index 100%
rename from pyproject.toml
rename to tests/pyproject.toml
diff --git a/tests/util.py b/tests/util.py
index 1f6fbf8..a3f69aa 100644
--- a/tests/util.py
+++ b/tests/util.py
@@ -7,8 +7,9 @@ from pathlib import Path
import pytest
RUST_PROFILE = os.environ.get("RUST_PROFILE", "debug")
-COMPILED_PATH = Path.cwd() / "target" / RUST_PROFILE / "cln-nip47"
-DOWNLOAD_PATH = Path.cwd() / "tests" / "cln-nip47"
+plugin_dir = Path(__file__).parent.parent.resolve()
+COMPILED_PATH = plugin_dir / "target" / RUST_PROFILE / "cln-nip47"
+DOWNLOAD_PATH = plugin_dir / "tests" / "cln-nip47"
@pytest.fixture
diff --git a/uv.lock b/tests/uv.lock
similarity index 100%
rename from uv.lock
rename to tests/uv.lock
From 727f71064636921abf2734d3746eca5923604ee9 Mon Sep 17 00:00:00 2001
From: daywalker90 <8257956+daywalker90@users.noreply.github.com>
Date: Wed, 31 Dec 2025 12:24:32 +0100
Subject: [PATCH 05/85] tests: use nostr-rs-relay instead of nostr_relay
---
.github/workflows/ci.yml | 19 +-
.gitignore | 1 +
tests/config.toml | 12 +
tests/conftest.py | 64 +
tests/nostr-rs-relay.tar.gz | Bin 0 -> 4366423 bytes
tests/pyproject.toml | 2 -
tests/setup.sh | 5 +
tests/test_cln-nip47.py | 648 ++++----
tests/uv.lock | 2930 +++++++++--------------------------
9 files changed, 1128 insertions(+), 2553 deletions(-)
create mode 100644 tests/config.toml
create mode 100644 tests/conftest.py
create mode 100644 tests/nostr-rs-relay.tar.gz
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 9aa14a4..1873eb9 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -27,14 +27,14 @@ jobs:
bitcoind-version: ["30.0"]
experimental: [1]
deprecated: [0]
- python-version: ["3.9", "3.13"]
+ python-version: ["3.9", "3.14"]
os: ["ubuntu-latest"]
runs-on: ${{ matrix.os }}
steps:
- name: Checkout code
- uses: actions/checkout@v4
+ uses: actions/checkout@v6
- name: Create cache paths
run: |
@@ -44,7 +44,7 @@ jobs:
sudo chown -R $USER /usr/local/libexec
- name: Set up Python ${{ matrix.python-version }}
- uses: actions/setup-python@v5
+ uses: actions/setup-python@v6
with:
python-version: ${{ matrix.python-version }}
@@ -60,7 +60,7 @@ jobs:
- name: Restore CLN cache
id: cache-cln
- uses: actions/cache/restore@v4
+ uses: actions/cache/restore@v5
with:
path: |
/usr/local/bin/lightning*
@@ -69,13 +69,13 @@ jobs:
- name: Restore bitcoind cache
id: cache-bitcoind
- uses: actions/cache/restore@v4
+ uses: actions/cache/restore@v5
with:
path: /usr/local/bin/bitcoin*
key: cache-bitcoind-${{ matrix.bitcoind-version }}-${{ steps.exact_versions.outputs.os_version }}
- name: Install uv
- uses: astral-sh/setup-uv@v6
+ uses: astral-sh/setup-uv@v7
with:
enable-cache: true
cache-dependency-glob: "**/pyproject.toml"
@@ -93,7 +93,7 @@ jobs:
- name: Save bitcoind cache
id: save-cache-bitcoind
if : ${{ always() && steps.cache-bitcoind.outputs.cache-hit != 'true'}}
- uses: actions/cache/save@v4
+ uses: actions/cache/save@v5
with:
path: /usr/local/bin/bitcoin*
key: ${{ steps.cache-bitcoind.outputs.cache-primary-key }}
@@ -111,7 +111,7 @@ jobs:
- name: Save CLN cache
id: save-cache-cln
if : ${{ always() && steps.cache-cln.outputs.cache-hit != 'true' }}
- uses: actions/cache/save@v4
+ uses: actions/cache/save@v5
with:
path: |
/usr/local/bin/lightning*
@@ -123,7 +123,7 @@ jobs:
uses: dtolnay/rust-toolchain@stable
- name: Set up protoc
- if: ${{ inputs.tagged-release == false}} && ${{ steps.cache-cln.outputs.cache-hit != 'true' }}
+ if: ${{ inputs.tagged-release == false}}
uses: arduino/setup-protoc@v3
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
@@ -155,5 +155,6 @@ jobs:
export PYTEST_TIMEOUT=600
cd tests
+ tar -xf nostr-rs-relay.tar.gz
uv add --dev pyln-testing==${{ inputs.pyln-version }} pyln-client==${{ inputs.pyln-version }} pyln-proto==${{ inputs.pyln-version }}
uv run -v pytest -n=10
diff --git a/.gitignore b/.gitignore
index c702af1..9f63775 100644
--- a/.gitignore
+++ b/.gitignore
@@ -4,3 +4,4 @@
/result/
/tests/holdinvoice
/tests/hold
+/tests/nostr-rs-relay
diff --git a/tests/config.toml b/tests/config.toml
new file mode 100644
index 0000000..062124b
--- /dev/null
+++ b/tests/config.toml
@@ -0,0 +1,12 @@
+
+[info]
+relay_url = "ws://127.0.0.1/"
+name = "nostr-rs-relay"
+description = "test relay"
+
+[options]
+reject_future_seconds = 1800
+[limits]
+limit_scrapers = false
+[network]
+address = "0.0.0.0"
diff --git a/tests/conftest.py b/tests/conftest.py
new file mode 100644
index 0000000..da7e80d
--- /dev/null
+++ b/tests/conftest.py
@@ -0,0 +1,64 @@
+import os
+import socket
+import pytest
+import tempfile
+import shutil
+from pathlib import Path
+import subprocess
+
+
+@pytest.fixture(scope="session")
+def nostr_relay(worker_id):
+ worker_index = int(worker_id[2:]) if worker_id and worker_id.startswith("gw") else 0
+ base_port = 50000 + (worker_index * 100)
+ port = get_free_port(base_port)
+
+ config_path = Path(__file__).parent / "config.toml"
+ if not config_path.exists():
+ raise FileNotFoundError(f"config.toml not found at {config_path}")
+
+ temp_dir = Path(tempfile.mkdtemp())
+
+ # Copy your original config.toml into it
+ original_config = Path(__file__).parent / "config.toml"
+ temp_config = temp_dir / "config.toml"
+ shutil.copy(original_config, temp_config)
+
+ with temp_config.open("a") as f:
+ f.write(f"port = {port}\n")
+
+ proc = subprocess.Popen(
+ ["./nostr-rs-relay", "--config", str(temp_config), "--db", str(temp_dir)],
+ cwd=Path(__file__).parent,
+ stdout=subprocess.PIPE,
+ stderr=subprocess.PIPE,
+ env=os.environ | {"RUST_LOG": "warn,nostr_rs_relay=debug"},
+ )
+
+ try:
+ import time
+
+ time.sleep(1.0)
+
+ ws_url = f"ws://127.0.0.1:{port}"
+ yield ws_url
+
+ finally:
+ proc.terminate()
+ try:
+ proc.wait(timeout=5)
+ except subprocess.TimeoutExpired:
+ proc.kill()
+ proc.wait()
+
+
+def get_free_port(start_port=50000):
+ for port in range(start_port, start_port + 100):
+ with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
+ try:
+ s.bind(("127.0.0.1", port))
+ s.listen(1)
+ return port
+ except OSError:
+ continue
+ raise RuntimeError(f"No free ports found starting from {start_port}")
diff --git a/tests/nostr-rs-relay.tar.gz b/tests/nostr-rs-relay.tar.gz
new file mode 100644
index 0000000000000000000000000000000000000000..705210ecbf241df769cae4587039585c1b57062e
GIT binary patch
literal 4366423
zcmZs?c{tSH`#+vkNHvzCBEyJDi>XwSSt>*+>ZMXCQ&iK25Qf>Pgk+gi2s5Qud6i0~
ztYb!&jL0NK)?o}|ofWgs{GPp+@AbK^-`nMSp5u?_^PF>^`+nSy$9)cPs{Xux{pkMe
zkG&D_t3XdU*|7h?Z6o8okVk6^69zwKS-bi`o-AD2{oq~7g1dWl_LC_a&xQQDbk1
z?DJ&(;mr+8?;EyL`q-)#Npro;0~cMgSMmRXfOqnHT~|9HIhaN@D4NOm=(
zqUb7#NgnuAL%7%f6_?O0+2T
z@9OcXZyi-tJ@RqRji8SXRmgPtvpL(3)Hu7`!5tq>daj&vChT%ZFS2RREt{AulzeYGmqG0$FP`MaI=!H4u3>t{2HMF!2w$*;
zh?}-JP;l^#c3Z%RfD#f%LA?CZt0^ydnSFOvrA(GCx%f$;H(?rijB~Q^M`y*sXNuRz
zWArGP_vL}t*EDdwQkxpO_oX}7s_Vla(?4#Xa~*?kBSrri*A-21_EU|6-^_j}m{9uh
zo<jTcVw&=oG!m|MmupZA_`rNQhcAh8r)K8e)saiBhzLDlRpo{
zs-x6y0?tQ=64=@fw05Sfnq4KWsR;-MeN(9?&DD)%o?6KS|2S^_11kw>OdBDutZneu
zL4#C~!6SnU2c73JmSR`Q2(`tvR9(#?At(VnaDl&La56q@KG90(ouC(gwKl7^WD#+x
z&>~)o5PBw{7UGx4ylc_A8l;dF&&s>V_tZg|$qoz_%}43V_6=fmLEhT?DNVaoD{7@W
z3J*zOB^`C1`DhP4Orl6|YvSi(MnzDU>FV7UA1AMxy7d77U_w=*wis2dxIp
zbr?&q`Z8-_alAkmcu@_Qh1j)GGOMyqCaspi5*Q2c^JTrYC>>;f5I-^@^~8;?-J8c+
z#=_EOCMqk4AAL}ZU)fS&nJEn)+P90>ncwB_NOwFqm14h_zUkE5)b1c_^OfJD|NeM(
zo8{8bCFgbh(Cmrs$NJEsuhAjaj}J~U7yUSS^8C(6OU{?JAFf#Q!437YRDV^|m4UYx
zBEsJkAe@XWTVLqz37LpBzZ84&?$*ql&!Q1d^Y@=ucC^6qOg^93
zYIK