feat(rnpath): improve get_path_table method with filtering, sorting, and pagination; include additional stats for path entries
This commit is contained in:
@@ -5,10 +5,46 @@ class RNPathHandler:
|
||||
def __init__(self, reticulum_instance: RNS.Reticulum):
|
||||
self.reticulum = reticulum_instance
|
||||
|
||||
def get_path_table(self, max_hops: int = None):
|
||||
def get_path_table(
|
||||
self,
|
||||
max_hops: int = None,
|
||||
search: str = None,
|
||||
interface: str = None,
|
||||
hops: int = None,
|
||||
page: int = 1,
|
||||
limit: int = 0,
|
||||
):
|
||||
table = self.reticulum.get_path_table(max_hops=max_hops)
|
||||
formatted_table = []
|
||||
for entry in table:
|
||||
# Get additional data directly from Transport.path_table if available
|
||||
# to provide more stats as requested.
|
||||
dst_hash = entry["hash"]
|
||||
announce_hash = None
|
||||
state = RNS.Transport.STATE_UNKNOWN
|
||||
|
||||
if dst_hash in RNS.Transport.path_table:
|
||||
pt_entry = RNS.Transport.path_table[dst_hash]
|
||||
if len(pt_entry) > 6:
|
||||
announce_hash = pt_entry[6].hex() if pt_entry[6] else None
|
||||
|
||||
if dst_hash in RNS.Transport.path_states:
|
||||
state = RNS.Transport.path_states[dst_hash]
|
||||
|
||||
# Filtering
|
||||
if search:
|
||||
search = search.lower()
|
||||
hash_str = entry["hash"].hex().lower()
|
||||
via_str = entry["via"].hex().lower()
|
||||
if search not in hash_str and search not in via_str:
|
||||
continue
|
||||
|
||||
if interface and entry["interface"] != interface:
|
||||
continue
|
||||
|
||||
if hops is not None and entry["hops"] != hops:
|
||||
continue
|
||||
|
||||
formatted_table.append(
|
||||
{
|
||||
"hash": entry["hash"].hex(),
|
||||
@@ -16,9 +52,47 @@ class RNPathHandler:
|
||||
"via": entry["via"].hex(),
|
||||
"interface": entry["interface"],
|
||||
"expires": entry["expires"],
|
||||
"timestamp": entry.get("timestamp"),
|
||||
"announce_hash": announce_hash,
|
||||
"state": state,
|
||||
}
|
||||
)
|
||||
return sorted(formatted_table, key=lambda e: (e["interface"], e["hops"]))
|
||||
|
||||
# Sort: Responsive first, then by hops, then by interface
|
||||
formatted_table.sort(
|
||||
key=lambda e: (
|
||||
0 if e["state"] == RNS.Transport.STATE_RESPONSIVE else 1,
|
||||
e["hops"],
|
||||
e["interface"],
|
||||
)
|
||||
)
|
||||
|
||||
total = len(formatted_table)
|
||||
responsive_count = len(
|
||||
[e for e in formatted_table if e["state"] == RNS.Transport.STATE_RESPONSIVE]
|
||||
)
|
||||
unresponsive_count = len(
|
||||
[
|
||||
e
|
||||
for e in formatted_table
|
||||
if e["state"] == RNS.Transport.STATE_UNRESPONSIVE
|
||||
]
|
||||
)
|
||||
|
||||
# Pagination
|
||||
if limit > 0:
|
||||
start = (page - 1) * limit
|
||||
end = start + limit
|
||||
formatted_table = formatted_table[start:end]
|
||||
|
||||
return {
|
||||
"table": formatted_table,
|
||||
"total": total,
|
||||
"responsive": responsive_count,
|
||||
"unresponsive": unresponsive_count,
|
||||
"page": page,
|
||||
"limit": limit,
|
||||
}
|
||||
|
||||
def get_rate_table(self):
|
||||
table = self.reticulum.get_rate_table()
|
||||
|
||||
Reference in New Issue
Block a user