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

Commit 5dd7b1c

Browse files
committed
document process
1 parent b3762a2 commit 5dd7b1c

9 files changed

Lines changed: 69 additions & 46 deletions

File tree

Lines changed: 30 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -130,7 +130,7 @@ def get_running_torch_version():
130130
)
131131

132132

133-
class HelperCLI:
133+
class AssistantCLI:
134134

135135
DIR_NOTEBOOKS = ".notebooks"
136136
META_REQUIRED_FIELDS = ("title", "author", "license", "description")
@@ -158,7 +158,7 @@ class HelperCLI:
158158

159159
@staticmethod
160160
def _meta_file(folder: str) -> str:
161-
files = glob.glob(os.path.join(folder, HelperCLI.META_FILE_REGEX), flags=glob.BRACE)
161+
files = glob.glob(os.path.join(folder, AssistantCLI.META_FILE_REGEX), flags=glob.BRACE)
162162
if len(files) == 1:
163163
return files[0]
164164

@@ -171,9 +171,9 @@ def augment_script(fpath: str):
171171
"""
172172
with open(fpath) as fp:
173173
py_file = fp.readlines()
174-
fpath_meta = HelperCLI._meta_file(os.path.dirname(fpath))
174+
fpath_meta = AssistantCLI._meta_file(os.path.dirname(fpath))
175175
meta = yaml.safe_load(open(fpath_meta))
176-
meta_miss = [fl for fl in HelperCLI.META_REQUIRED_FIELDS if fl not in meta]
176+
meta_miss = [fl for fl in AssistantCLI.META_REQUIRED_FIELDS if fl not in meta]
177177
if meta_miss:
178178
raise ValueError(f"Meta file '{fpath_meta}' is missing the following fields: {meta_miss}")
179179
meta.update(
@@ -188,7 +188,7 @@ def augment_script(fpath: str):
188188
setup = TEMPLATE_SETUP % dict(requirements=" ".join([f'"{req}"' for req in requires]))
189189
py_file = [header + setup] + py_file + [TEMPLATE_FOOTER]
190190

191-
py_file = HelperCLI._replace_images(py_file, os.path.dirname(fpath))
191+
py_file = AssistantCLI._replace_images(py_file, os.path.dirname(fpath))
192192

193193
with open(fpath, "w") as fp:
194194
fp.writelines(py_file)
@@ -226,10 +226,10 @@ def _replace_images(lines: list, local_dir: str) -> list:
226226

227227
@staticmethod
228228
def _is_ipynb_parent_dir(dir_path: str) -> bool:
229-
if HelperCLI._meta_file(dir_path):
229+
if AssistantCLI._meta_file(dir_path):
230230
return True
231231
sub_dirs = [d for d in glob.glob(os.path.join(dir_path, "*")) if os.path.isdir(d)]
232-
return any(HelperCLI._is_ipynb_parent_dir(d) for d in sub_dirs)
232+
return any(AssistantCLI._is_ipynb_parent_dir(d) for d in sub_dirs)
233233

234234
@staticmethod
235235
def group_folders(
@@ -255,7 +255,7 @@ def group_folders(
255255
root_path: path to the root tobe added for all local folder paths in files
256256
257257
Example:
258-
>> python helpers.py group-folders ../target-diff.txt --fpaths_actual_dirs "['../dirs-main.txt', '../dirs-publication.txt']"
258+
>> python assistant.py group-folders ../target-diff.txt --fpaths_actual_dirs "['../dirs-main.txt', '../dirs-publication.txt']"
259259
"""
260260
with open(fpath_gitdiff) as fp:
261261
changed = [ln.strip() for ln in fp.readlines()]
@@ -275,19 +275,19 @@ def group_folders(
275275
# unique folders
276276
dirs = set(dirs)
277277
# drop folder with skip folder
278-
dirs = [pd for pd in dirs if not any(nd in HelperCLI.SKIP_DIRS for nd in pd.split(os.path.sep))]
278+
dirs = [pd for pd in dirs if not any(nd in AssistantCLI.SKIP_DIRS for nd in pd.split(os.path.sep))]
279279
# valid folder has meta
280280
dirs_exist = [d for d in dirs if os.path.isdir(d)]
281-
dirs_invalid = [d for d in dirs_exist if not HelperCLI._meta_file(d)]
281+
dirs_invalid = [d for d in dirs_exist if not AssistantCLI._meta_file(d)]
282282
if strict and dirs_invalid:
283-
msg = f"Following folders do not have valid `{HelperCLI.META_FILE_REGEX}`"
283+
msg = f"Following folders do not have valid `{AssistantCLI.META_FILE_REGEX}`"
284284
warn(f"{msg}: \n {os.linesep.join(dirs_invalid)}")
285285
# check if there is other valid folder in its tree
286-
dirs_invalid = [pd for pd in dirs_invalid if not HelperCLI._is_ipynb_parent_dir(pd)]
286+
dirs_invalid = [pd for pd in dirs_invalid if not AssistantCLI._is_ipynb_parent_dir(pd)]
287287
if dirs_invalid:
288288
raise FileNotFoundError(f"{msg} nor sub-folder: \n {os.linesep.join(dirs_invalid)}")
289289

290-
dirs_change = [d for d in dirs_exist if HelperCLI._meta_file(d)]
290+
dirs_change = [d for d in dirs_exist if AssistantCLI._meta_file(d)]
291291
with open(fpath_change_folders, "w") as fp:
292292
fp.write(os.linesep.join(sorted(dirs_change)))
293293

@@ -301,19 +301,21 @@ def parse_requirements(dir_path: str):
301301
Args:
302302
dir_path: path to the folder
303303
"""
304-
fpath = HelperCLI._meta_file(dir_path)
304+
fpath = AssistantCLI._meta_file(dir_path)
305305
assert fpath, f"Missing Meta file in {dir_path}"
306306
meta = yaml.safe_load(open(fpath))
307307
pprint(meta)
308308

309309
req = meta.get("requirements", [])
310-
fname = os.path.join(dir_path, HelperCLI.REQUIREMENTS_FILE)
310+
fname = os.path.join(dir_path, AssistantCLI.REQUIREMENTS_FILE)
311311
print(f"File for requirements: {fname}")
312312
with open(fname, "w") as fp:
313313
fp.write(os.linesep.join(req))
314314

315315
pip_args = {
316-
k.replace(HelperCLI.META_PIP_KEY, ""): v for k, v in meta.items() if k.startswith(HelperCLI.META_PIP_KEY)
316+
k.replace(AssistantCLI.META_PIP_KEY, ""): v
317+
for k, v in meta.items()
318+
if k.startswith(AssistantCLI.META_PIP_KEY)
317319
}
318320
cmd_args = []
319321
for pip_key in pip_args:
@@ -323,7 +325,7 @@ def parse_requirements(dir_path: str):
323325
arg = arg % RUNTIME_VERSIONS
324326
cmd_args.append(f"--{pip_key} {arg}")
325327

326-
fname = os.path.join(dir_path, HelperCLI.PIP_ARGS_FILE)
328+
fname = os.path.join(dir_path, AssistantCLI.PIP_ARGS_FILE)
327329
print(f"File for PIP arguments: {fname}")
328330
with open(fname, "w") as fp:
329331
fp.write(" ".join(cmd_args))
@@ -349,7 +351,7 @@ def _get_card_item_cell(path_ipynb: str, path_meta: str, path_thumb: Optional[st
349351

350352
dirname = os.path.basename(os.path.dirname(path_ipynb))
351353
if dirname != ".notebooks":
352-
meta["tags"].append(HelperCLI.DIR_TO_TAG.get(dirname, dirname))
354+
meta["tags"].append(AssistantCLI.DIR_TO_TAG.get(dirname, dirname))
353355

354356
meta["tags"] = [tag.replace(" ", "-") for tag in meta["tags"]]
355357
meta["tags"] = ",".join(meta["tags"])
@@ -379,7 +381,7 @@ def _resolve_path_thumb(path_ipynb: str, path_meta: str) -> Optional[str]:
379381
assert len(paths) == 1, f"Found multiple possible thumbnail paths for notebook: {path_ipynb}."
380382
path_thumb = paths[0]
381383
path_thumb = path_thumb.split(os.path.sep)
382-
path_thumb = os.path.sep.join(path_thumb[path_thumb.index(HelperCLI.DIR_NOTEBOOKS) + 1 :])
384+
path_thumb = os.path.sep.join(path_thumb[path_thumb.index(AssistantCLI.DIR_NOTEBOOKS) + 1 :])
383385
return path_thumb
384386

385387
@staticmethod
@@ -401,22 +403,22 @@ def copy_notebooks(
401403
"""
402404
ls_ipynb = []
403405
for sub in patterns:
404-
ls_ipynb += glob.glob(os.path.join(path_root, HelperCLI.DIR_NOTEBOOKS, sub, "*.ipynb"))
406+
ls_ipynb += glob.glob(os.path.join(path_root, AssistantCLI.DIR_NOTEBOOKS, sub, "*.ipynb"))
405407

406408
os.makedirs(os.path.join(docs_root, path_docs_ipynb), exist_ok=True)
407409
ipynb_content = []
408410
for path_ipynb in tqdm.tqdm(ls_ipynb):
409411
ipynb = path_ipynb.split(os.path.sep)
410-
sub_ipynb = os.path.sep.join(ipynb[ipynb.index(HelperCLI.DIR_NOTEBOOKS) + 1 :])
412+
sub_ipynb = os.path.sep.join(ipynb[ipynb.index(AssistantCLI.DIR_NOTEBOOKS) + 1 :])
411413
new_ipynb = os.path.join(docs_root, path_docs_ipynb, sub_ipynb)
412414
os.makedirs(os.path.dirname(new_ipynb), exist_ok=True)
413415

414416
path_meta = path_ipynb.replace(".ipynb", ".yaml")
415-
path_thumb = HelperCLI._resolve_path_thumb(path_ipynb, path_meta)
417+
path_thumb = AssistantCLI._resolve_path_thumb(path_ipynb, path_meta)
416418

417419
if path_thumb is not None:
418420
new_thumb = os.path.join(docs_root, path_docs_images, path_thumb)
419-
old_path_thumb = os.path.join(path_root, HelperCLI.DIR_NOTEBOOKS, path_thumb)
421+
old_path_thumb = os.path.join(path_root, AssistantCLI.DIR_NOTEBOOKS, path_thumb)
420422
os.makedirs(os.path.dirname(new_thumb), exist_ok=True)
421423
copyfile(old_path_thumb, new_thumb)
422424
path_thumb = os.path.join(path_docs_images, path_thumb)
@@ -426,7 +428,7 @@ def copy_notebooks(
426428
with open(path_ipynb) as f:
427429
ipynb = json.load(f)
428430

429-
ipynb["cells"].append(HelperCLI._get_card_item_cell(path_ipynb, path_meta, path_thumb))
431+
ipynb["cells"].append(AssistantCLI._get_card_item_cell(path_ipynb, path_meta, path_thumb))
430432

431433
with open(new_ipynb, "w") as f:
432434
json.dump(ipynb, f)
@@ -439,7 +441,7 @@ def valid_accelerator(dir_path: str):
439441
Args:
440442
dir_path: path to the folder
441443
"""
442-
fpath = HelperCLI._meta_file(dir_path)
444+
fpath = AssistantCLI._meta_file(dir_path)
443445
assert fpath, f"Missing Meta file in {dir_path}"
444446
meta = yaml.safe_load(open(fpath))
445447
# default is CPU runtime
@@ -453,7 +455,7 @@ def update_env_details(dir_path: str):
453455
Args:
454456
dir_path: path to the folder
455457
"""
456-
fpath = HelperCLI._meta_file(dir_path)
458+
fpath = AssistantCLI._meta_file(dir_path)
457459
assert fpath, f"Missing Meta file in {dir_path}"
458460
meta = yaml.safe_load(open(fpath))
459461
# default is COU runtime
@@ -474,9 +476,9 @@ def _parse(pkg: str, keys: str = " <=>[]") -> str:
474476
meta["environment"] = [env[r] for r in require]
475477
meta["published"] = datetime.now().isoformat()
476478

477-
fmeta = os.path.join(HelperCLI.DIR_NOTEBOOKS, dir_path) + ".yaml"
479+
fmeta = os.path.join(AssistantCLI.DIR_NOTEBOOKS, dir_path) + ".yaml"
478480
yaml.safe_dump(meta, stream=open(fmeta, "w"), sort_keys=False)
479481

480482

481483
if __name__ == "__main__":
482-
fire.Fire(HelperCLI)
484+
fire.Fire(AssistantCLI)

.actions/git-diff-sync.sh

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ cat "dirs-$b2.txt"
3030
printf "\n\n"
3131
git merge --ff -s resolve origin/$1
3232

33-
python .actions/helpers.py group-folders target-diff.txt --fpaths_actual_dirs "['dirs-$b1.txt', 'dirs-$b2.txt']"
33+
python .actions/assistant.py group-folders target-diff.txt --fpaths_actual_dirs "['dirs-$b1.txt', 'dirs-$b2.txt']"
3434
printf "\n\nChanged folders:\n"
3535
cat changed-folders.txt
3636
printf "\n\nDropped folders:\n"

.actions/ipynb-generate.sh

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,13 @@ printf "Converting: $1\n\n"
55

66
# check that there is only one python script
77
python -c "import os, glob ; assert(len(glob.glob(os.path.join('$1', '*.py'))) == 1)"
8-
# check that there is meta file
9-
python -c "import os ; assert any(os.path.isfile(os.path.join('$1', f'.meta{ext}')) for ext in ['.yml', '.yaml'])"
8+
# check that there is exactly one meta recipe
9+
python -c "import os ; assert sum(os.path.isfile(os.path.join('$1', f'.meta{ext}')) for ext in ['.yml', '.yaml']) == 1"
1010
py_file=( $(ls "$1"/*.py) )
1111
printf $py_file
1212

13-
python .actions/helpers.py augment-script $py_file
13+
# add header and footer to the python script
14+
python .actions/assistant.py augment-script $py_file
1415

16+
# generate notebook from given script
1517
python -m jupytext --set-formats "ipynb,py:percent" $py_file

.actions/ipynb-render.sh

Lines changed: 16 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,17 @@
33
set -e
44
printf "Rendering: $1\n\n"
55

6+
# check that there is no ipython file in the folder
67
python -c "import os, glob ; assert(len(glob.glob(os.path.join('$1', '*.ipynb'))) == 1)"
78
ipynb_file=( $(ls "$1"/*.ipynb) )
89
printf $ipynb_file
910

10-
python -c "import os ; assert any(os.path.isfile(os.path.join('$1', f'.meta{ext}')) for ext in ['.yml', '.yaml'])"
11+
# check that there i exactly one meta recipe
12+
python -c "import os ; assert sum(os.path.isfile(os.path.join('$1', f'.meta{ext}')) for ext in ['.yml', '.yaml']) == 1"
1113
meta_file=( $(ls "$1"/.meta.*) )
1214
printf $meta_file
1315

16+
# check that folder has at most one thumb file
1417
python -c "import os, glob ; assert(len(glob.glob(os.path.join('$1', '.thumb.*'))) <= 1)"
1518
thumb_file=( $(ls "$1"/.thumb.* 2>/dev/null || echo "") ) || true
1619
[ ! -z $thumb_file ] && printf $thumb_file
@@ -21,6 +24,7 @@ printf $pub_file
2124
pub_meta_file=".notebooks/$1.yaml"
2225
printf $pub_meta_file
2326

27+
# if a notebook has thumb image gets its path
2428
if [ ! -z $thumb_file ]; then
2529
pub_thumb_file=".notebooks/"${thumb_file/"$1"\/.thumb/$1}
2630
printf $pub_thumb_file
@@ -29,18 +33,22 @@ fi
2933
pub_dir=$(dirname "$pub_file")
3034
mkdir -p $pub_dir
3135

32-
python .actions/helpers.py parse-requirements $1
36+
# just in case reinstall the global
3337
pip install --quiet --requirement requirements.txt --upgrade-strategy only-if-needed
38+
# prepare the requirements specific for the particular notebook
39+
python .actions/assistant.py parse-requirements $1
3440
cat "$1/requirements.txt"
3541
pip_args=$(cat "$1/pip_arguments.txt")
3642
printf "pip arguments:\n $pip_args\n\n"
43+
# and install specific packages
3744
pip install --requirement "$1/requirements.txt" $pip_args
3845

46+
# dry run does not execute the notebooks just takes them as they are
3947
if [ ! -z "${DRY_RUN}" ] && [ "${DRY_RUN}" == "1" ]; then
4048
cp $ipynb_file $pub_file
4149
else
4250
printf "available: $ACCELERATOR\n"
43-
accel=$(python .actions/helpers.py valid-accelerator $1 2>&1)
51+
accel=$(python .actions/assistant.py valid-accelerator $1 2>&1)
4452
if [ $accel == 1 ]
4553
then
4654
printf "Processing: $ipynb_file\n"
@@ -51,14 +59,18 @@ else
5159
fi
5260
fi
5361

54-
python .actions/helpers.py update-env-details $1
62+
# Export the actual packages used in runtime
63+
python .actions/assistant.py update-env-details $1
5564

65+
# copy and add to version the enriched meta config
5666
cp $meta_file $pub_meta_file
5767
git add $pub_meta_file
5868

69+
# if thumb image is linked to to the notebook, copy and version it too
5970
if [ ! -z $thumb_file ]; then
6071
cp $thumb_file $pub_thumb_file
6172
git add $pub_thumb_file
6273
fi
6374

75+
# add the generated notebook to version
6476
git add $pub_file

.actions/ipynb-test.sh

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,27 +3,32 @@
33
set -e
44
printf "Testing: $1\n\n"
55

6+
# check that there is no ipython file in the folder
67
python -c "import glob ; assert(len(glob.glob('$1/*.ipynb')) == 1)"
78
ipynb_file=( $(ls "$1"/*.ipynb) )
89
py_file=( $(ls "$1"/*.py) )
910
printf $ipynb_file
1011

1112
pip install --quiet --requirement requirements.txt --upgrade-strategy only-if-needed
1213

13-
python .actions/helpers.py parse-requirements $1
14+
# prepare the requirements specific for the particular notebook
15+
python .actions/assistant.py parse-requirements $1
1416
cat "$1/requirements.txt"
1517

18+
# prepare isolated environment with inheriting the global packages
1619
python -m virtualenv --system-site-packages "$1/venv"
1720
source "$1/venv/bin/activate"
1821
pip --version
22+
# just in case reinstall the global
1923
pip install --quiet --requirement requirements.txt --upgrade-strategy only-if-needed
2024
pip_args=$(cat "$1/pip_arguments.txt")
2125
printf "pip arguments:\n $pip_args\n\n"
26+
# and install specific packages
2227
pip install --requirement "$1/requirements.txt" $pip_args
2328
pip list
2429

2530
printf "available: $ACCELERATOR\n"
26-
accel=$(python .actions/helpers.py valid-accelerator $1 2>&1)
31+
accel=$(python .actions/assistant.py valid-accelerator $1 2>&1)
2732
if [ $accel == 1 ]
2833
then
2934
#python $py_file
@@ -33,4 +38,6 @@ else
3338
printf "WARNING: not valid accelerator so no tests will be run.\n"
3439
fi
3540

41+
# deactivate and clean local environment
3642
deactivate
43+
rm -rf "$1/venv"

.azure-pipelines/ipynb-tests.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ jobs:
4848
head=$(git rev-parse origin/main)
4949
printf "Head: $head\n"
5050
git diff --name-only $head --output=target-diff.txt
51-
python .actions/helpers.py group-folders target-diff.txt
51+
python .actions/assistant.py group-folders target-diff.txt
5252
printf "Changed folders:\n"
5353
cat changed-folders.txt
5454
displayName: 'Process folders'

.github/workflows/ci_docs.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ jobs:
4040
run: |
4141
head=$(git rev-parse origin/"${{ github.base_ref }}")
4242
git diff --name-only $head --output=master-diff.txt
43-
python .actions/helpers.py group-folders master-diff.txt
43+
python .actions/assistant.py group-folders master-diff.txt
4444
printf "Changed folders:\n"
4545
cat changed-folders.txt
4646
shell: bash

.github/workflows/ci_testing.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ jobs:
5757
run: |
5858
head=$(git rev-parse origin/${{ github.base_ref }})
5959
git diff --name-only $head --output=target-diff.txt
60-
python .actions/helpers.py group-folders target-diff.txt
60+
python .actions/assistant.py group-folders target-diff.txt
6161
printf "Changed folders:\n"
6262
cat changed-folders.txt
6363
shell: bash

0 commit comments

Comments
 (0)