add run command to CLI
This commit is contained in:
parent
57fadd245a
commit
02eed8bf76
@ -97,4 +97,6 @@ def _(proc: CSIMatrix) -> None:
|
|||||||
cnt += 1
|
cnt += 1
|
||||||
|
|
||||||
|
|
||||||
app.start()
|
if __name__ == "__main__":
|
||||||
|
print("Starting app")
|
||||||
|
app.start()
|
||||||
|
|||||||
@ -166,9 +166,11 @@ class CSIApplication:
|
|||||||
self.raw_csi_callback(sample.matrix)
|
self.raw_csi_callback(sample.matrix)
|
||||||
if self.pre_merge_callback is not None:
|
if self.pre_merge_callback is not None:
|
||||||
self.pre_merge_callback(sample.frames)
|
self.pre_merge_callback(sample.frames)
|
||||||
processed = self.preprocessor.preprocess(sample.matrix, sample.frames)
|
processed = self.preprocessor.preprocess(
|
||||||
if self.visualise_raw:
|
sample.matrix, sample.frames, visualiser=self.visualise_data
|
||||||
self.visualise_data(processed, visualise.figures.Figure.PROCESSED_CSI)
|
)
|
||||||
|
# if self.visualise_raw:
|
||||||
|
# self.visualise_data(processed, visualise.figures.Figure.PROCESSED_CSI)
|
||||||
if self.preprocessed_csi_callback is not None:
|
if self.preprocessed_csi_callback is not None:
|
||||||
self.preprocessed_csi_callback(processed)
|
self.preprocessed_csi_callback(processed)
|
||||||
|
|
||||||
@ -197,17 +199,21 @@ class CSIApplication:
|
|||||||
self.buffer_thread.start()
|
self.buffer_thread.start()
|
||||||
self.webapp_thread.start()
|
self.webapp_thread.start()
|
||||||
|
|
||||||
if self.processing_callback is not None:
|
def get_proc_sample() -> None:
|
||||||
|
sample = self.preprocessor.last_sample
|
||||||
|
if self.visualise_raw and sample is not None:
|
||||||
|
self.visualise_data(
|
||||||
|
sample,
|
||||||
|
visualise.figures.Figure.PROCESSED_CSI,
|
||||||
|
)
|
||||||
|
if sample is not None and self.processing_callback is not None:
|
||||||
|
self.processing_callback(sample)
|
||||||
|
else:
|
||||||
|
self.logger.warning("No samples to process")
|
||||||
|
|
||||||
def get_proc_sample() -> None:
|
self.scheduler = Scheduler(config.processing_sample_rate, get_proc_sample)
|
||||||
sample = self.preprocessor.last_sample
|
self.scheduler.start()
|
||||||
if sample is not None and self.processing_callback is not None:
|
|
||||||
self.processing_callback(sample)
|
|
||||||
else:
|
|
||||||
self.logger.warning("No samples to process")
|
|
||||||
|
|
||||||
self.scheduler = Scheduler(config.processing_sample_rate, get_proc_sample)
|
|
||||||
self.scheduler.start()
|
|
||||||
try:
|
try:
|
||||||
self.webapp_thread.join()
|
self.webapp_thread.join()
|
||||||
except KeyboardInterrupt:
|
except KeyboardInterrupt:
|
||||||
|
|||||||
@ -1,4 +1,6 @@
|
|||||||
|
import importlib.util
|
||||||
import logging
|
import logging
|
||||||
|
from pathlib import Path
|
||||||
from queue import Queue
|
from queue import Queue
|
||||||
from typing import cast
|
from typing import cast
|
||||||
|
|
||||||
@ -7,11 +9,11 @@ import numpy.typing as npt
|
|||||||
import torch
|
import torch
|
||||||
import typer
|
import typer
|
||||||
|
|
||||||
|
from where_fi.application import CSIApplication
|
||||||
from where_fi.collection import CSIMatrix
|
from where_fi.collection import CSIMatrix
|
||||||
|
from where_fi.config import config
|
||||||
|
from where_fi.processing.aoa import AoA
|
||||||
|
|
||||||
from ..application import CSIApplication
|
|
||||||
from ..config import config
|
|
||||||
from ..processing.aoa import AoA
|
|
||||||
from ..visualise import server as visualise
|
from ..visualise import server as visualise
|
||||||
from . import file, globals
|
from . import file, globals
|
||||||
|
|
||||||
@ -53,44 +55,43 @@ def heatmap() -> None:
|
|||||||
|
|
||||||
|
|
||||||
@cli.command()
|
@cli.command()
|
||||||
def phase_analysis(
|
def run(file: Path, app_name: str = "app") -> None:
|
||||||
subcarriers: list[int] = [0], rx_antenna: int = 0, tx_antenna: int = 0
|
|
||||||
) -> None:
|
|
||||||
"""
|
"""
|
||||||
Visualise the phase information in the CSI data received from the antennas.
|
Run the application with the given file.
|
||||||
|
|
||||||
The data goes through the same preprocessing steps as the heatmap command, but
|
Can be used for running arbitrary CSI applications with non-default data streams
|
||||||
instead of going through the AoA estimation, we simply analyse the phase of the
|
(e.g. from file or environment simulation).
|
||||||
selected subcarrier and antenna.
|
|
||||||
"""
|
"""
|
||||||
|
print(file.absolute())
|
||||||
|
if not file.exists():
|
||||||
|
print(f"Error: File '{file}' does not exist.")
|
||||||
|
raise typer.Exit(1)
|
||||||
|
module_name = file.stem
|
||||||
|
|
||||||
app = CSIApplication(globals.csi_producer)
|
spec = importlib.util.spec_from_file_location(module_name, str(file))
|
||||||
|
if spec is None:
|
||||||
|
print(f"Could not load spec from {file}")
|
||||||
|
raise typer.Exit(1)
|
||||||
|
|
||||||
if isinstance(subcarriers, int):
|
module = importlib.util.module_from_spec(spec)
|
||||||
subcarriers = [subcarriers]
|
if spec.loader is None:
|
||||||
print("Starting phase analysis on subcarriers: ", subcarriers)
|
print(f"Could not load module from {file}")
|
||||||
|
raise typer.Exit(1)
|
||||||
|
try:
|
||||||
|
spec.loader.exec_module(module)
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Failed to execute {file}: {e}")
|
||||||
|
raise typer.Exit(1) from e
|
||||||
|
|
||||||
subcarrier_phase: dict[int, Queue[float]] = {
|
if not hasattr(module, app_name):
|
||||||
x: Queue(config.collection_sample_rate) for x in subcarriers
|
print(f"Error: '{app_name}' not defined in the module.")
|
||||||
}
|
raise typer.Exit(1)
|
||||||
|
if not isinstance(module.app, CSIApplication):
|
||||||
|
print(f"Error: '{app_name}' is not a CSIApplication.")
|
||||||
|
raise typer.Exit(1)
|
||||||
|
|
||||||
@app.on_sample
|
module.app.producer = globals.csi_producer
|
||||||
def _(sample: CSIMatrix) -> None:
|
module.app.start()
|
||||||
for subcarrier in subcarriers:
|
|
||||||
phase = cast(float, np.angle(sample[subcarrier, rx_antenna, tx_antenna]))
|
|
||||||
if subcarrier_phase[subcarrier].full():
|
|
||||||
subcarrier_phase[subcarrier].get()
|
|
||||||
subcarrier_phase[subcarrier].put(phase)
|
|
||||||
|
|
||||||
@app.on_process
|
|
||||||
def _(_: CSIMatrix) -> None:
|
|
||||||
logger.info("Updating phase visualisation")
|
|
||||||
app.visualise_data(
|
|
||||||
np.array([x.queue for x in subcarrier_phase.values()]),
|
|
||||||
visualise.figures.Figure.PHASE_ANALYSIS,
|
|
||||||
)
|
|
||||||
|
|
||||||
app.start()
|
|
||||||
|
|
||||||
|
|
||||||
cli.add_typer(file.app, name="file", help="Commands for working with CSI files")
|
cli.add_typer(file.app, name="file", help="Commands for working with CSI files")
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user