Module jmcore.paths
Shared path utilities for JoinMarket data directories.
This module provides consistent path handling across all JoinMarket components (maker, taker, wallet) for data directories, commitment blacklists, and history.
Functions
def get_all_nick_states(data_dir: Path | str | None = None) ‑> dict[str, str]-
Expand source code
def get_all_nick_states(data_dir: Path | str | None = None) -> dict[str, str]: """ Read all component nick state files from the data directory. Useful for discovering all running components and their nicks. Args: data_dir: Optional data directory (defaults to get_default_data_dir()) Returns: Dict mapping component names to their nicks (e.g., {'maker': 'J5XXX', 'taker': 'J5YYY'}) """ if data_dir is None: data_dir = get_default_data_dir() elif isinstance(data_dir, str): data_dir = Path(data_dir) state_dir = data_dir / "state" if not state_dir.exists(): return {} result: dict[str, str] = {} for path in state_dir.glob("*.nick"): component = path.stem # e.g., 'maker' from 'maker.nick' try: nick = path.read_text().strip() if nick: result[component] = nick except OSError: continue return resultRead all component nick state files from the data directory.
Useful for discovering all running components and their nicks.
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
Returns
Dict mapping component names to their nicks (e.g., {'maker': 'J5XXX', 'taker': 'J5YYY'})
def get_commitment_blacklist_path(data_dir: Path | None = None) ‑> pathlib.Path-
Expand source code
def get_commitment_blacklist_path(data_dir: Path | None = None) -> Path: """ Get the path to the commitment blacklist file. Args: data_dir: Optional data directory (defaults to get_default_data_dir()) Returns: Path to cmtdata/commitmentlist (compatible with reference JoinMarket) """ if data_dir is None: data_dir = get_default_data_dir() # Use cmtdata/ subdirectory for commitment data (matches reference implementation) cmtdata_dir = data_dir / "cmtdata" cmtdata_dir.mkdir(parents=True, exist_ok=True) return cmtdata_dir / "commitmentlist"Get the path to the commitment blacklist file.
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
Returns
Path to cmtdata/commitmentlist (compatible with reference JoinMarket)
def get_default_data_dir() ‑> pathlib.Path-
Expand source code
def get_default_data_dir() -> Path: """ Get the default JoinMarket data directory. Returns ~/.joinmarket-ng or $JOINMARKET_DATA_DIR if set. Creates the directory if it doesn't exist. For compatibility with reference JoinMarket in Docker, users can set JOINMARKET_DATA_DIR=/home/jm/.joinmarket-ng to share the same volume. """ env_path = os.getenv("JOINMARKET_DATA_DIR") data_dir = Path(env_path) if env_path else Path.home() / ".joinmarket-ng" data_dir.mkdir(parents=True, exist_ok=True) return data_dirGet the default JoinMarket data directory.
Returns ~/.joinmarket-ng or $JOINMARKET_DATA_DIR if set. Creates the directory if it doesn't exist.
For compatibility with reference JoinMarket in Docker, users can set JOINMARKET_DATA_DIR=/home/jm/.joinmarket-ng to share the same volume.
def get_ignored_makers_path(data_dir: Path | None = None) ‑> pathlib.Path-
Expand source code
def get_ignored_makers_path(data_dir: Path | None = None) -> Path: """ Get the path to the ignored makers file (for takers). Args: data_dir: Optional data directory (defaults to get_default_data_dir()) Returns: Path to ignored_makers.txt """ if data_dir is None: data_dir = get_default_data_dir() return data_dir / "ignored_makers.txt"Get the path to the ignored makers file (for takers).
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
Returns
Path to ignored_makers.txt
def get_nick_state_path(data_dir: Path | str | None = None, component: str = '') ‑> pathlib.Path-
Expand source code
def get_nick_state_path(data_dir: Path | str | None = None, component: str = "") -> Path: """ Get the path to a component's nick state file. The nick state file stores the current nick of a running component, allowing operators to easily identify the nick and enabling cross-component protection (e.g., taker excluding own maker nick from peer selection). Args: data_dir: Optional data directory (defaults to get_default_data_dir()) component: Component name (e.g., 'maker', 'taker', 'directory', 'orderbook') Returns: Path to state/<component>.nick (e.g., ~/.joinmarket-ng/state/maker.nick) """ if data_dir is None: data_dir = get_default_data_dir() elif isinstance(data_dir, str): data_dir = Path(data_dir) # Use state/ subdirectory to keep state files organized state_dir = data_dir / "state" state_dir.mkdir(parents=True, exist_ok=True) return state_dir / f"{component}.nick"Get the path to a component's nick state file.
The nick state file stores the current nick of a running component, allowing operators to easily identify the nick and enabling cross-component protection (e.g., taker excluding own maker nick from peer selection).
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
component- Component name (e.g., 'maker', 'taker', 'directory', 'orderbook')
Returns
Path to state/
.nick (e.g., ~/.joinmarket-ng/state/maker.nick) def get_used_commitments_path(data_dir: Path | None = None) ‑> pathlib.Path-
Expand source code
def get_used_commitments_path(data_dir: Path | None = None) -> Path: """ Get the path to the used commitments file (for takers). Args: data_dir: Optional data directory (defaults to get_default_data_dir()) Returns: Path to cmtdata/commitments.json (compatible with reference JoinMarket) """ if data_dir is None: data_dir = get_default_data_dir() # Use cmtdata/ subdirectory cmtdata_dir = data_dir / "cmtdata" cmtdata_dir.mkdir(parents=True, exist_ok=True) return cmtdata_dir / "commitments.json"Get the path to the used commitments file (for takers).
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
Returns
Path to cmtdata/commitments.json (compatible with reference JoinMarket)
def read_nick_state(data_dir: Path | str | None, component: str) ‑> str | None-
Expand source code
def read_nick_state(data_dir: Path | str | None, component: str) -> str | None: """ Read a component's nick from its state file. Args: data_dir: Optional data directory (defaults to get_default_data_dir()) component: Component name (e.g., 'maker', 'taker', 'directory', 'orderbook') Returns: The nick string if file exists and is readable, None otherwise """ if data_dir is None: data_dir = get_default_data_dir() elif isinstance(data_dir, str): data_dir = Path(data_dir) path = get_nick_state_path(data_dir, component) if path.exists(): try: return path.read_text().strip() except OSError: return None return NoneRead a component's nick from its state file.
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
component- Component name (e.g., 'maker', 'taker', 'directory', 'orderbook')
Returns
The nick string if file exists and is readable, None otherwise
def remove_nick_state(data_dir: Path | str | None, component: str) ‑> bool-
Expand source code
def remove_nick_state(data_dir: Path | str | None, component: str) -> bool: """ Remove a component's nick state file (e.g., on shutdown). Args: data_dir: Optional data directory (defaults to get_default_data_dir()) component: Component name (e.g., 'maker', 'taker', 'directory', 'orderbook') Returns: True if file was removed, False if it didn't exist or removal failed """ if data_dir is None: data_dir = get_default_data_dir() elif isinstance(data_dir, str): data_dir = Path(data_dir) path = get_nick_state_path(data_dir, component) if path.exists(): try: path.unlink() return True except OSError: return False return FalseRemove a component's nick state file (e.g., on shutdown).
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
component- Component name (e.g., 'maker', 'taker', 'directory', 'orderbook')
Returns
True if file was removed, False if it didn't exist or removal failed
def write_nick_state(data_dir: Path | str | None, component: str, nick: str) ‑> pathlib.Path-
Expand source code
def write_nick_state(data_dir: Path | str | None, component: str, nick: str) -> Path: """ Write a component's nick to its state file. Creates the state directory if it doesn't exist. Args: data_dir: Optional data directory (defaults to get_default_data_dir()) component: Component name (e.g., 'maker', 'taker', 'directory', 'orderbook') nick: The nick to write (e.g., 'J5XXXXXXXXX') Returns: Path to the written state file """ path = get_nick_state_path(data_dir, component) path.write_text(nick + "\n") return pathWrite a component's nick to its state file.
Creates the state directory if it doesn't exist.
Args
data_dir- Optional data directory (defaults to get_default_data_dir())
component- Component name (e.g., 'maker', 'taker', 'directory', 'orderbook')
nick- The nick to write (e.g., 'J5XXXXXXXXX')
Returns
Path to the written state file