@@ -100,20 +100,15 @@ def blog_add_posts(context):
100
100
posts = []
101
101
# posts from the file system
102
102
if context ["blog" ]["posts_path" ]:
103
- posts_path = os .path .join (
104
- context ["source_path" ], * context ["blog" ]["posts_path" ].split ("/" )
105
- )
106
- for fname in os .listdir (posts_path ):
107
- if fname .startswith ("index." ):
103
+ posts_path = context ["source_path" ] / context ["blog" ]["posts_path" ]
104
+ for fname in posts_path .iterdir ():
105
+ if fname .name .startswith ("index." ):
108
106
continue
109
- link = (
110
- f"/{ context ['blog' ]['posts_path' ]} "
111
- f"/{ os .path .splitext (fname )[0 ]} .html"
112
- )
107
+ link = f"/{ context ['blog' ]['posts_path' ]} /{ fname .stem } .html"
113
108
md = markdown .Markdown (
114
109
extensions = context ["main" ]["markdown_extensions" ]
115
110
)
116
- with open (os . path . join ( posts_path , fname ), encoding = "utf-8" ) as f :
111
+ with fname . open (encoding = "utf-8" ) as f :
117
112
html = md .convert (f .read ())
118
113
title = md .Meta ["title" ][0 ]
119
114
summary = re .sub (tag_expr , "" , html )
@@ -386,15 +381,15 @@ def get_callable(obj_as_str: str) -> object:
386
381
return obj
387
382
388
383
389
- def get_context (config_fname : str , ** kwargs ):
384
+ def get_context (config_fname : pathlib . Path , ** kwargs ):
390
385
"""
391
386
Load the config yaml as the base context, and enrich it with the
392
387
information added by the context preprocessors defined in the file.
393
388
"""
394
- with open (config_fname , encoding = "utf-8" ) as f :
389
+ with config_fname . open (encoding = "utf-8" ) as f :
395
390
context = yaml .safe_load (f )
396
391
397
- context ["source_path" ] = os . path . dirname ( config_fname )
392
+ context ["source_path" ] = config_fname . parent
398
393
context .update (kwargs )
399
394
400
395
preprocessors = (
@@ -409,14 +404,13 @@ def get_context(config_fname: str, **kwargs):
409
404
return context
410
405
411
406
412
- def get_source_files (source_path : str ) -> typing .Generator [str , None , None ]:
407
+ def get_source_files (source_path : pathlib . Path ) -> typing .Generator [str , None , None ]:
413
408
"""
414
409
Generate the list of files present in the source directory.
415
410
"""
416
- for root , dirs , fnames in os .walk (source_path ):
417
- root_rel_path = os .path .relpath (root , source_path )
418
- for fname in fnames :
419
- yield os .path .join (root_rel_path , fname )
411
+ for path in source_path .rglob ("*" ):
412
+ if path .is_file ():
413
+ yield path .relative_to (source_path )
420
414
421
415
422
416
def extend_base_template (content : str , base_template : str ) -> str :
@@ -432,26 +426,27 @@ def extend_base_template(content: str, base_template: str) -> str:
432
426
433
427
434
428
def main (
435
- source_path : str ,
436
- target_path : str ,
429
+ source_path : pathlib . Path ,
430
+ target_path : pathlib . Path ,
437
431
) -> int :
438
432
"""
439
433
Copy every file in the source directory to the target directory.
440
434
441
435
For ``.md`` and ``.html`` files, render them with the context
442
436
before copying them. ``.md`` files are transformed to HTML.
443
437
"""
438
+
444
439
# Sanity check: validate that versions.json is valid JSON
445
- versions_path = os . path . join ( source_path , "versions.json" )
446
- with open (versions_path , encoding = "utf-8" ) as f :
440
+ versions_path = source_path / "versions.json"
441
+ with versions_path . open (encoding = "utf-8" ) as f :
447
442
try :
448
443
json .load (f )
449
444
except json .JSONDecodeError as e :
450
445
raise RuntimeError (
451
446
f"Invalid versions.json: { e } . Ensure it is valid JSON."
452
447
) from e
453
448
454
- config_fname = os . path . join ( source_path , "config.yml" )
449
+ config_fname = source_path / "config.yml"
455
450
456
451
shutil .rmtree (target_path , ignore_errors = True )
457
452
os .makedirs (target_path , exist_ok = True )
@@ -460,23 +455,22 @@ def main(
460
455
context = get_context (config_fname , target_path = target_path )
461
456
sys .stderr .write ("Context generated\n " )
462
457
463
- templates_path = os . path . join ( source_path , context ["main" ]["templates_path" ])
458
+ templates_path = source_path / context ["main" ]["templates_path" ]
464
459
jinja_env = jinja2 .Environment (loader = jinja2 .FileSystemLoader (templates_path ))
465
460
466
461
for fname in get_source_files (source_path ):
467
- if os . path . normpath ( fname ) in context ["main" ]["ignore" ]:
462
+ if fname . as_posix ( ) in context ["main" ]["ignore" ]:
468
463
continue
469
-
470
464
sys .stderr .write (f"Processing { fname } \n " )
471
- dirname = os . path . dirname ( fname )
472
- os . makedirs ( os . path . join ( target_path , dirname ), exist_ok = True )
465
+ dirname = fname . parent
466
+ ( target_path / dirname ). mkdir ( parents = True , exist_ok = True )
473
467
474
- extension = os . path . splitext ( fname )[ - 1 ]
468
+ extension = fname . suffix
475
469
if extension in (".html" , ".md" ):
476
- with open ( os . path . join ( source_path , fname ), encoding = "utf-8" ) as f :
470
+ with ( source_path / fname ). open ( encoding = "utf-8" ) as f :
477
471
content = f .read ()
478
472
if extension == ".md" :
479
- if "pdeps/" in fname :
473
+ if len ( fname . parts ) > 1 and fname . parts [ 1 ] == "pdeps" :
480
474
from markdown .extensions .toc import TocExtension
481
475
482
476
body = markdown .markdown (
@@ -503,17 +497,13 @@ def main(
503
497
# Python-Markdown doesn't let us config table attributes by hand
504
498
body = body .replace ("<table>" , '<table class="table table-bordered">' )
505
499
content = extend_base_template (body , context ["main" ]["base_template" ])
506
- context ["base_url" ] = "" . join ([ "../" ] * os . path . normpath ( fname ). count ( "/" ) )
500
+ context ["base_url" ] = "../" * ( len ( fname . parents ) - 1 )
507
501
content = jinja_env .from_string (content ).render (** context )
508
- fname_html = os .path .splitext (fname )[0 ] + ".html"
509
- with open (
510
- os .path .join (target_path , fname_html ), "w" , encoding = "utf-8"
511
- ) as f :
502
+ fname_html = fname .with_suffix (".html" ).name
503
+ with (target_path / dirname / fname_html ).open ("w" , encoding = "utf-8" ) as f :
512
504
f .write (content )
513
505
else :
514
- shutil .copy (
515
- os .path .join (source_path , fname ), os .path .join (target_path , dirname )
516
- )
506
+ shutil .copy (source_path / fname , target_path / fname )
517
507
518
508
519
509
if __name__ == "__main__" :
@@ -525,4 +515,4 @@ def main(
525
515
"--target-path" , default = "build" , help = "directory where to write the output"
526
516
)
527
517
args = parser .parse_args ()
528
- sys .exit (main (args .source_path , args .target_path ))
518
+ sys .exit (main (pathlib . Path ( args .source_path ), pathlib . Path ( args .target_path ) ))
0 commit comments