Skip to content
This repository was archived by the owner on Feb 26, 2025. It is now read-only.

Commit 546b801

Browse files
nico-cantaChristos KotsalosStephLisa
authored
Archngv (#40)
Merge ArchNGV branch. - 'load_graph_archngv.py' loads archngv graphs and saves them in pickle binary format - replace m2r2 with sphinx_mdinclude - install joblib and archngv in the venv - setup.sh and sbatch files can be run from any directory --------- Co-authored-by: Christos Kotsalos <christos.kotsalos@epfl.ch> Co-authored-by: StephLisa <57900635+StephLisa@users.noreply.github.com>
1 parent 2dd34a4 commit 546b801

File tree

9 files changed

+200
-14
lines changed

9 files changed

+200
-14
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
*py~
77
*~
88
*.egg-info
9+
examples/data/graphs_folder/dumped_graph.bin
910

1011
# Mac related stuff
1112
.DS_Store

README.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,13 @@ The code can be run using
4646

4747
python3 compute_static_flow_pressure.py
4848

49+
### Load Archngv graph
50+
51+
An archngv graph can be loaded and converted to a pickle binary format, using the script `load_graph_archngv.py` inside the folder `examples`.
52+
Run the script as
53+
54+
python3 load_graph_archngv.py --filename_ngv "path_to_ngv_circuit" --output_graph "output_graph_name.bin"
55+
4956
### Sonata reports
5057

5158
Structure of the reports:

astrovascpy/bloodflow.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838

3939
# PETSc is compiled with complex number support
4040
# -> many warnings from/to PETSc to/from NumPy/SciPy
41-
warnings.filterwarnings(action="ignore", category=np.ComplexWarning)
41+
warnings.filterwarnings(action="ignore", category=np.exceptions.ComplexWarning)
4242

4343
print = partial(print, flush=True)
4444

docs/source/conf.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@
3535
"sphinx.ext.napoleon",
3636
"sphinx.ext.todo",
3737
"sphinx_click",
38-
"m2r2",
38+
"sphinx_mdinclude",
3939
]
4040

4141
todo_include_todos = True

examples/job_script.sbatch

Lines changed: 12 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -15,12 +15,19 @@
1515
#SBATCH --mem=0
1616
#SBATCH --output="%x-%j.log"
1717

18-
pushd ..
19-
source setup.sh
20-
popd
18+
JOB_SCRIPT=$(scontrol show job ${SLURM_JOB_ID} | awk -F= '/Command=/{print $2}')
19+
JOB_SCRIPT_DIR=$(dirname ${JOB_SCRIPT})
20+
21+
SETUP_SCRIPT="${JOB_SCRIPT_DIR}/../setup.sh"
22+
if [[ ! -f ${SETUP_SCRIPT} ]]; then
23+
>&2 echo "[ERROR] The 'setup.sh' script could not be found!"
24+
exit -1
25+
fi
26+
27+
source ${SETUP_SCRIPT}
2128

2229
echo
2330
echo "### Simulation Start"
2431
echo
25-
# time srun dplace python compute_static_flow_pressure.py
26-
time srun dplace python simulate_OU_process.py
32+
# time srun dplace python "${JOB_SCRIPT_DIR}/compute_static_flow_pressure.py"
33+
time srun dplace python "${JOB_SCRIPT_DIR}/simulate_OU_process.py"

examples/load_graph_archngv.py

Lines changed: 133 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,133 @@
1+
import argparse
2+
import multiprocessing
3+
import pickle
4+
from functools import partial
5+
from pathlib import Path
6+
7+
import numpy as np
8+
import pandas as pd
9+
import psutil
10+
from archngv import NGVCircuit
11+
from joblib import Parallel, delayed, parallel_config
12+
from tqdm import tqdm
13+
14+
from astrovascpy import bloodflow
15+
from astrovascpy.exceptions import BloodFlowError
16+
from astrovascpy.utils import Graph
17+
18+
19+
def load_graph_archngv_parallel(
20+
filename, n_workers, n_astro=None, parallelization_backend="multiprocessing"
21+
):
22+
"""Load a vasculature from an NGV circuit.
23+
24+
Args:
25+
filename (str): vasculature dataset.
26+
n_workers (int): number of processes to set endfeet on edges.
27+
n_astro (int): for testing, if not None, it will reduce the number of astrocytes used
28+
parallelization_backend (str): Either multiprocessing or joblib
29+
30+
Returns:
31+
vasculatureAPI.PointVasculature: graph containing point vasculature skeleton.
32+
33+
Raises:
34+
BloodFlowError: if the file object identified by filename is not in h5 format.
35+
"""
36+
if not Path(filename).exists():
37+
raise BloodFlowError("File provided does not exist")
38+
circuit = NGVCircuit(filename)
39+
pv = circuit.vasculature.point_graph
40+
graph = Graph.from_point_vasculature(pv)
41+
graph.edge_properties.index = pd.MultiIndex.from_frame(
42+
graph.edge_properties.loc[:, ["section_id", "segment_id"]]
43+
)
44+
gv_conn = circuit.gliovascular_connectome
45+
worker = partial(bloodflow.get_closest_edges, graph=graph)
46+
47+
args = (
48+
(
49+
gv_conn.vasculature_sections_segments(endfoot_id).vasculature_section_id.values[0],
50+
gv_conn.vasculature_sections_segments(endfoot_id).vasculature_segment_id.values[0],
51+
gv_conn.get(endfoot_id, ["endfoot_compartment_length"]).values[0],
52+
)
53+
for astro_id in np.arange(n_astro or circuit.astrocytes.size)
54+
for endfoot_id in gv_conn.astrocyte_endfeet(astro_id)
55+
)
56+
endfoot_ids = [
57+
endfoot_id
58+
for astro_id in np.arange(n_astro or circuit.astrocytes.size)
59+
for endfoot_id in gv_conn.astrocyte_endfeet(astro_id)
60+
]
61+
62+
if parallelization_backend == "multiprocessing":
63+
with multiprocessing.Pool(n_workers) as pool:
64+
for result_ids, result_endfeet in zip(
65+
tqdm(
66+
pool.imap(worker, args, chunksize=max(1, int(len(endfoot_ids) / n_workers))),
67+
total=len(endfoot_ids),
68+
),
69+
endfoot_ids,
70+
):
71+
# Only the main process executes this part, i.e. as soon as it receives the parallelly generated data
72+
graph.edge_properties.loc[pd.MultiIndex.from_arrays(result_ids.T), "endfeet_id"] = (
73+
result_endfeet
74+
)
75+
76+
elif parallelization_backend == "joblib":
77+
with parallel_config(
78+
backend="loky", prefer="processes", n_jobs=n_workers, inner_max_num_threads=1
79+
):
80+
parallel = Parallel(return_as="generator", batch_size="auto")
81+
parallelized_region = parallel(
82+
delayed(worker)(arg) for arg in tqdm(args, total=len(endfoot_ids))
83+
)
84+
85+
for result_ids, result_endfeet in zip(parallelized_region, endfoot_ids):
86+
# Only the main process executes this part, i.e. as soon as it receives the parallelly generated data
87+
graph.edge_properties.loc[pd.MultiIndex.from_arrays(result_ids.T), "endfeet_id"] = (
88+
result_endfeet
89+
)
90+
91+
else:
92+
raise BloodFlowError(
93+
f"parallelization_backend={parallelization_backend} invalid option. Use 'joblib' or 'multiprocessing'."
94+
)
95+
96+
return graph
97+
98+
99+
def main():
100+
global print
101+
print = partial(print, flush=True)
102+
103+
parser = argparse.ArgumentParser(description="File paths for NGVCircuits and output graph.")
104+
parser.add_argument(
105+
"--filename_ngv", type=str, required=True, help="Path to the NGV circuits file"
106+
)
107+
parser.add_argument(
108+
"--output_graph", type=str, required=True, help="Path to the output graph file"
109+
)
110+
args = parser.parse_args()
111+
112+
filename_ngv = args.filename_ngv
113+
output_graph = args.output_graph
114+
115+
n_cores = psutil.cpu_count(logical=False)
116+
print(f"number of physical CPU cores = {n_cores}")
117+
118+
print(f"NGV Circuits file: {filename_ngv}")
119+
print("loading circuit : start")
120+
graph = load_graph_archngv_parallel(
121+
filename_ngv, n_workers=n_cores
122+
) # n_astro=50 for debugging (smaller processing needs)
123+
print("loading circuit : finish")
124+
125+
print("pickle graph : start")
126+
filehandler = open(output_graph, "wb")
127+
pickle.dump(graph, filehandler)
128+
print("pickle graph : finish")
129+
print(f"Graph file: {output_graph}")
130+
131+
132+
if __name__ == "__main__":
133+
main()

examples/load_graph_archngv.sbatch

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
#!/bin/bash
2+
3+
#SBATCH --job-name="archngv"
4+
#SBATCH --nodes=1
5+
6+
#SBATCH --account=proj16
7+
#SBATCH --partition=prod
8+
#SBATCH --constraint=cpu
9+
#SBATCH --time=00:30:00
10+
11+
#SBATCH --cpus-per-task=2
12+
#SBATCH --exclusive
13+
#SBATCH --mem=0
14+
#SBATCH --output="%x-%j.log"
15+
16+
JOB_SCRIPT=$(scontrol show job ${SLURM_JOB_ID} | awk -F= '/Command=/{print $2}')
17+
JOB_SCRIPT_DIR=$(dirname ${JOB_SCRIPT})
18+
19+
SETUP_SCRIPT="${JOB_SCRIPT_DIR}/../setup.sh"
20+
if [[ ! -f ${SETUP_SCRIPT} ]]; then
21+
>&2 echo "[ERROR] The 'setup.sh' script could not be found!"
22+
exit 2
23+
fi
24+
25+
source ${SETUP_SCRIPT}
26+
27+
FILENAME_NGV="/gpfs/bbp.cscs.ch/project/proj137/NGVCircuits/rat_O1"
28+
29+
GRAPH_PATH="./data/graphs_folder/dumped_graph.bin"
30+
31+
echo
32+
echo "### Loading graph"
33+
echo
34+
# It is imperative to use srun and dplace, otherwise the Python processes
35+
# do not work properly (possible deadlocks and/or performance degradation)
36+
time srun -n 1 --mpi=none dplace python ${JOB_SCRIPT_DIR}/load_graph_archngv.py --filename_ngv ${FILENAME_NGV} --output_graph ${GRAPH_PATH}

setup.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@
3737
]
3838

3939
doc_reqs = [
40-
"m2r2",
40+
"sphinx-mdinclude",
4141
"sphinx",
4242
"sphinx-bluebrain-theme",
4343
"sphinx-click",

setup.sh

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@ echo
22
echo "### setup/set env started"
33
echo
44

5+
SETUP_DIR=$(dirname ${BASH_SOURCE[0]})
6+
57
if command -v module &> /dev/null
68
then
79
module purge
@@ -26,7 +28,7 @@ else
2628
conda install -y pip
2729

2830
conda install -y -c conda-forge mpi mpi4py petsc petsc4py
29-
"$CONDA_PREFIX/bin/pip" install tox
31+
"$CONDA_PREFIX/bin/pip" install tox joblib archngv
3032
# If complex number support is needed
3133
#conda install -y -c conda-forge mpi mpi4py "petsc=*=*complex*" "petsc4py=*=*complex*"
3234
fi
@@ -58,15 +60,15 @@ then
5860
echo "python-venv already set"
5961
source python-venv/bin/activate
6062
else
61-
python3 -m venv --prompt astrovascpy python-venv
62-
source python-venv/bin/activate
63+
python3 -m venv --prompt astrovascpy ${SETUP_DIR}/python-venv
64+
source ${SETUP_DIR}/python-venv/bin/activate
6365
python3 -m pip install --upgrade pip
6466
fi
65-
pip3 install -e .
66-
pip3 install tox
67+
pip3 install -e ${SETUP_DIR}
68+
pip3 install tox joblib archngv
6769
else
6870
conda_bin=`conda info | grep "active env location" | grep -o "/.*"`/bin
69-
$conda_bin/pip install -e .
71+
$conda_bin/pip install -e ${SETUP_DIR}
7072
fi
7173

7274
# Backend solver/library for the linear systems

0 commit comments

Comments
 (0)