tinyssg 1.2.0__py3-none-any.whl → 1.3.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- tinyssg/__init__.py +73 -62
- {tinyssg-1.2.0.dist-info → tinyssg-1.3.0.dist-info}/METADATA +8 -9
- tinyssg-1.3.0.dist-info/RECORD +6 -0
- tinyssg-1.2.0.dist-info/RECORD +0 -6
- {tinyssg-1.2.0.dist-info → tinyssg-1.3.0.dist-info}/WHEEL +0 -0
- {tinyssg-1.2.0.dist-info → tinyssg-1.3.0.dist-info}/top_level.txt +0 -0
tinyssg/__init__.py
CHANGED
@@ -159,17 +159,17 @@ class TinySSGUtility:
|
|
159
159
|
return {k: v for k, v in data.items() if not k.startswith('__')}
|
160
160
|
|
161
161
|
@classmethod
|
162
|
-
def get_fullpath(cls,
|
162
|
+
def get_fullpath(cls, pathkey: str = '') -> str:
|
163
163
|
"""
|
164
164
|
Get the full path from the relative path
|
165
165
|
"""
|
166
|
-
if isinstance(args['curdir'], str) and len(args['curdir']) > 0:
|
167
|
-
basedir = args['curdir']
|
166
|
+
if isinstance(TinySSG.args['curdir'], str) and len(TinySSG.args['curdir']) > 0:
|
167
|
+
basedir = TinySSG.args['curdir']
|
168
168
|
else:
|
169
169
|
basedir = os.getcwd()
|
170
170
|
|
171
|
-
if isinstance(args[pathkey], str) and len(args[pathkey]) > 0:
|
172
|
-
result = os.path.join(basedir, args[pathkey])
|
171
|
+
if isinstance(TinySSG.args[pathkey], str) and len(TinySSG.args[pathkey]) > 0:
|
172
|
+
result = os.path.join(basedir, TinySSG.args[pathkey])
|
173
173
|
else:
|
174
174
|
result = basedir
|
175
175
|
|
@@ -184,11 +184,11 @@ class TinySSGUtility:
|
|
184
184
|
shutil.rmtree(output_full_path)
|
185
185
|
|
186
186
|
@classmethod
|
187
|
-
def clear_start(cls
|
187
|
+
def clear_start(cls) -> None:
|
188
188
|
"""
|
189
189
|
Delete the output directory
|
190
190
|
"""
|
191
|
-
output_full_path = cls.get_fullpath(
|
191
|
+
output_full_path = cls.get_fullpath('output')
|
192
192
|
cls.clear_output(output_full_path)
|
193
193
|
|
194
194
|
@classmethod
|
@@ -196,22 +196,17 @@ class TinySSGUtility:
|
|
196
196
|
"""
|
197
197
|
Output log message (Console Execution Only)
|
198
198
|
"""
|
199
|
-
|
200
|
-
|
201
|
-
env = get_ipython().__class__.__name__
|
202
|
-
if env == 'ZMQInteractiveShell':
|
203
|
-
return
|
204
|
-
except: # noqa: E722
|
205
|
-
pass
|
199
|
+
if TinySSG.args['nolog']:
|
200
|
+
return
|
206
201
|
|
207
|
-
print(message)
|
202
|
+
print(message, flush=True)
|
208
203
|
|
209
204
|
@classmethod
|
210
205
|
def error_print(cls, message: str) -> None:
|
211
206
|
"""
|
212
207
|
Output error message
|
213
208
|
"""
|
214
|
-
print(message)
|
209
|
+
print(message, flush=True)
|
215
210
|
|
216
211
|
|
217
212
|
class TinySSGGenerator:
|
@@ -265,12 +260,12 @@ class TinySSGGenerator:
|
|
265
260
|
return convert_filename == convert_input_file
|
266
261
|
|
267
262
|
@classmethod
|
268
|
-
def search_route(cls
|
263
|
+
def search_route(cls) -> dict:
|
269
264
|
"""
|
270
265
|
Search for Page classes in the specified directory
|
271
266
|
"""
|
272
|
-
static_path = args['static']
|
273
|
-
input_file = args['input']
|
267
|
+
static_path = TinySSG.args['static']
|
268
|
+
input_file = TinySSG.args['input']
|
274
269
|
|
275
270
|
try:
|
276
271
|
prev_dont_write_bytecode = sys.dont_write_bytecode
|
@@ -278,7 +273,7 @@ class TinySSGGenerator:
|
|
278
273
|
|
279
274
|
routes = {}
|
280
275
|
|
281
|
-
full_pages_path = TinySSGUtility.get_fullpath(
|
276
|
+
full_pages_path = TinySSGUtility.get_fullpath('page')
|
282
277
|
page_counter = 0
|
283
278
|
|
284
279
|
for root, dirs, files in os.walk(full_pages_path):
|
@@ -384,11 +379,11 @@ class TinySSGGenerator:
|
|
384
379
|
return result
|
385
380
|
|
386
381
|
@classmethod
|
387
|
-
def generate_routes(cls
|
382
|
+
def generate_routes(cls) -> dict:
|
388
383
|
"""
|
389
384
|
Generate HTML content dictionary from Page classes
|
390
385
|
"""
|
391
|
-
route = cls.search_route(
|
386
|
+
route = cls.search_route()
|
392
387
|
return cls.traverse_route(route)
|
393
388
|
|
394
389
|
@classmethod
|
@@ -407,31 +402,37 @@ class TinySSGGenerator:
|
|
407
402
|
f.write(value)
|
408
403
|
|
409
404
|
@classmethod
|
410
|
-
def generator_start(cls
|
405
|
+
def generator_start(cls) -> None:
|
411
406
|
"""
|
412
407
|
Generate HTML files from Page classes
|
413
408
|
"""
|
414
|
-
|
409
|
+
TinySSGUtility.log_print('Page generation start...')
|
410
|
+
start_time = time.perf_counter()
|
411
|
+
|
412
|
+
input_full_path = TinySSGUtility.get_fullpath('page')
|
415
413
|
|
416
414
|
if not os.path.isdir(input_full_path):
|
417
415
|
raise TinySSGException(f"The specified page directory does not exist. ({input_full_path})")
|
418
416
|
|
419
|
-
page_data = cls.generate_routes(
|
420
|
-
output_full_path = TinySSGUtility.get_fullpath(
|
417
|
+
page_data = cls.generate_routes()
|
418
|
+
output_full_path = TinySSGUtility.get_fullpath('output')
|
421
419
|
|
422
420
|
if not os.path.exists(output_full_path):
|
423
421
|
os.makedirs(output_full_path)
|
424
422
|
|
425
423
|
cls.output_file(page_data, output_full_path)
|
426
424
|
|
427
|
-
static_full_path = TinySSGUtility.get_fullpath(
|
428
|
-
output_static_full_path = os.path.join(output_full_path, args['static'])
|
425
|
+
static_full_path = TinySSGUtility.get_fullpath('static')
|
426
|
+
output_static_full_path = os.path.join(output_full_path, TinySSG.args['static'])
|
429
427
|
|
430
428
|
if os.path.isdir(static_full_path):
|
431
429
|
if not os.path.exists(output_static_full_path):
|
432
430
|
os.makedirs(output_static_full_path)
|
433
431
|
shutil.copytree(static_full_path, output_static_full_path, dirs_exist_ok=True)
|
434
432
|
|
433
|
+
end_time = time.perf_counter()
|
434
|
+
TinySSGUtility.log_print('Page generation time: {:.2f} sec'.format((end_time-start_time)/60))
|
435
|
+
|
435
436
|
|
436
437
|
class TinySSGDebugHTTPServer(HTTPServer):
|
437
438
|
"""
|
@@ -588,15 +589,19 @@ class TinySSGDebug:
|
|
588
589
|
TinySSGUtility.error_print(process.stderr.read() if process.stderr else '')
|
589
590
|
|
590
591
|
@classmethod
|
591
|
-
def server_start(cls
|
592
|
+
def server_start(cls) -> None:
|
592
593
|
"""
|
593
594
|
Run the debug server
|
594
595
|
"""
|
595
|
-
reload = args['mode'] == 'servreload'
|
596
|
-
|
597
|
-
|
598
|
-
|
599
|
-
|
596
|
+
reload = TinySSG.args['mode'] == 'servreload'
|
597
|
+
TinySSGUtility.log_print('Page generation start...')
|
598
|
+
start_time = time.perf_counter()
|
599
|
+
route = TinySSGGenerator.generate_routes()
|
600
|
+
end_time = time.perf_counter()
|
601
|
+
TinySSGUtility.log_print('Page generation time: {:.2f} sec'.format((end_time-start_time)/60))
|
602
|
+
server_address = ('', TinySSG.args['port'])
|
603
|
+
httpd = TinySSGDebugHTTPServer(server_address, TinySSGDebugHTTPHandler, TinySSG.args, route, reload)
|
604
|
+
TinySSGUtility.error_print(f"Starting server on http://localhost:{TinySSG.args['port']}/{TinySSG.args['output']}/")
|
600
605
|
httpd.serve_forever()
|
601
606
|
|
602
607
|
|
@@ -605,7 +610,7 @@ class TinySSGLauncher:
|
|
605
610
|
Watchdog and Server Launcher
|
606
611
|
"""
|
607
612
|
@classmethod
|
608
|
-
def check_for_changes(cls, mod_time: float,
|
613
|
+
def check_for_changes(cls, mod_time: float, pathlits: list) -> bool:
|
609
614
|
"""
|
610
615
|
Check for changes in the specified directories
|
611
616
|
"""
|
@@ -623,7 +628,7 @@ class TinySSGLauncher:
|
|
623
628
|
new_mod_time = max(path_times)
|
624
629
|
|
625
630
|
if new_mod_time > mod_time:
|
626
|
-
mod_time = new_mod_time + args['wait']
|
631
|
+
mod_time = new_mod_time + TinySSG.args['wait']
|
627
632
|
return True, mod_time
|
628
633
|
except Exception as e:
|
629
634
|
TinySSGUtility.log_print(f"update check warning: {e}")
|
@@ -631,21 +636,21 @@ class TinySSGLauncher:
|
|
631
636
|
return False, mod_time
|
632
637
|
|
633
638
|
@classmethod
|
634
|
-
def launch_server(cls,
|
639
|
+
def launch_server(cls, reload: bool) -> None:
|
635
640
|
"""
|
636
641
|
Launch the server
|
637
642
|
"""
|
638
643
|
servcommand = 'serv' if not reload else 'servreload'
|
639
644
|
|
640
|
-
newargv = args.copy()
|
645
|
+
newargv = TinySSG.args.copy()
|
641
646
|
newargv['mode'] = servcommand
|
642
647
|
|
643
648
|
command = [sys.executable, '-m', 'tinyssg', '--config', f"{json.dumps(newargv)}", 'config']
|
644
649
|
|
645
650
|
process = subprocess.Popen(
|
646
651
|
command,
|
647
|
-
stdout=None if not args['nolog'] else subprocess.PIPE,
|
648
|
-
stderr=None if not args['nolog'] else subprocess.PIPE,
|
652
|
+
stdout=None if not TinySSG.args['nolog'] else subprocess.PIPE,
|
653
|
+
stderr=None if not TinySSG.args['nolog'] else subprocess.PIPE,
|
649
654
|
text=True,
|
650
655
|
encoding='utf-8'
|
651
656
|
)
|
@@ -660,11 +665,11 @@ class TinySSGLauncher:
|
|
660
665
|
return None
|
661
666
|
|
662
667
|
@classmethod
|
663
|
-
def open_browser(cls
|
668
|
+
def open_browser(cls) -> bool:
|
664
669
|
"""
|
665
670
|
Open the browser or Display Jupyter Iframe
|
666
671
|
"""
|
667
|
-
url = f"http://localhost:{args['port']}/{args['output']}/"
|
672
|
+
url = f"http://localhost:{TinySSG.args['port']}/{TinySSG.args['output']}/"
|
668
673
|
|
669
674
|
is_jupyter = False
|
670
675
|
|
@@ -678,22 +683,24 @@ class TinySSGLauncher:
|
|
678
683
|
|
679
684
|
if is_jupyter:
|
680
685
|
from IPython import display
|
681
|
-
display.display(display.IFrame(url, width=args['jwidth'], height=args['jheight']))
|
686
|
+
display.display(display.IFrame(url, width=TinySSG.args['jwidth'], height=TinySSG.args['jheight']))
|
682
687
|
else:
|
683
688
|
webbrowser.open(url)
|
684
689
|
|
690
|
+
return is_jupyter
|
691
|
+
|
685
692
|
@classmethod
|
686
|
-
def launcher_start(cls
|
693
|
+
def launcher_start(cls) -> None:
|
687
694
|
"""
|
688
695
|
Launch the debug server and file change detection
|
689
696
|
"""
|
690
|
-
if isinstance(args['curdir'], str) and len(args['curdir']) > 0:
|
691
|
-
os.chdir(args['curdir'])
|
697
|
+
if isinstance(TinySSG.args['curdir'], str) and len(TinySSG.args['curdir']) > 0:
|
698
|
+
os.chdir(TinySSG.args['curdir'])
|
692
699
|
|
693
700
|
cur_dir = os.getcwd()
|
694
|
-
page_dir = os.path.join(cur_dir, args['page'])
|
695
|
-
static_dir = os.path.join(cur_dir, args['static'])
|
696
|
-
lib_dir = os.path.join(cur_dir, args['lib'])
|
701
|
+
page_dir = os.path.join(cur_dir, TinySSG.args['page'])
|
702
|
+
static_dir = os.path.join(cur_dir, TinySSG.args['static'])
|
703
|
+
lib_dir = os.path.join(cur_dir, TinySSG.args['lib'])
|
697
704
|
mod_time = 0.0
|
698
705
|
should_reload = False
|
699
706
|
|
@@ -708,16 +715,18 @@ class TinySSGLauncher:
|
|
708
715
|
if os.path.isdir(lib_dir):
|
709
716
|
check_dirs.append(lib_dir)
|
710
717
|
|
711
|
-
if not args['noreload']:
|
712
|
-
_, mod_time = cls.check_for_changes(0.0,
|
718
|
+
if not TinySSG.args['noreload']:
|
719
|
+
_, mod_time = cls.check_for_changes(0.0, check_dirs)
|
713
720
|
|
714
|
-
process = cls.launch_server(
|
721
|
+
process = cls.launch_server(False)
|
715
722
|
|
716
723
|
if process is None:
|
717
724
|
return
|
718
725
|
|
719
|
-
if not args['noopen']:
|
720
|
-
cls.open_browser(
|
726
|
+
if not TinySSG.args['noopen']:
|
727
|
+
is_jupyter = cls.open_browser()
|
728
|
+
if is_jupyter:
|
729
|
+
TinySSG.args['nolog'] = True
|
721
730
|
|
722
731
|
while True:
|
723
732
|
try:
|
@@ -726,13 +735,13 @@ class TinySSGLauncher:
|
|
726
735
|
TinySSGUtility.log_print('Server stopped.')
|
727
736
|
TinySSGDebug.server_stop_output(process)
|
728
737
|
break
|
729
|
-
if not args['noreload']:
|
730
|
-
should_reload, mod_time = cls.check_for_changes(mod_time,
|
738
|
+
if not TinySSG.args['noreload']:
|
739
|
+
should_reload, mod_time = cls.check_for_changes(mod_time, check_dirs)
|
731
740
|
if should_reload:
|
732
741
|
TinySSGUtility.log_print('File changed. Reloading...')
|
733
742
|
TinySSGDebug.stop_server(process)
|
734
743
|
time.sleep(1)
|
735
|
-
process = cls.launch_server(
|
744
|
+
process = cls.launch_server(True)
|
736
745
|
except KeyboardInterrupt:
|
737
746
|
TinySSGDebug.stop_server(process)
|
738
747
|
TinySSGUtility.error_print('Server stopped.')
|
@@ -751,19 +760,21 @@ class TinySSG:
|
|
751
760
|
"""
|
752
761
|
exitcode = 0
|
753
762
|
|
763
|
+
cls.args = args
|
764
|
+
|
754
765
|
try:
|
755
766
|
if args['mode'] == 'gen':
|
756
767
|
if args['input'] == '':
|
757
|
-
TinySSGUtility.clear_start(
|
758
|
-
TinySSGGenerator.generator_start(
|
768
|
+
TinySSGUtility.clear_start()
|
769
|
+
TinySSGGenerator.generator_start()
|
759
770
|
TinySSGUtility.log_print('HTML files generated.')
|
760
771
|
elif args['mode'] == 'dev':
|
761
|
-
TinySSGLauncher.launcher_start(
|
772
|
+
TinySSGLauncher.launcher_start()
|
762
773
|
elif args['mode'] == 'cls':
|
763
|
-
TinySSGUtility.clear_start(
|
774
|
+
TinySSGUtility.clear_start()
|
764
775
|
TinySSGUtility.log_print('Output directory cleared.')
|
765
776
|
elif args['mode'] == 'serv' or args['mode'] == 'servreload':
|
766
|
-
TinySSGDebug.server_start(
|
777
|
+
TinySSGDebug.server_start()
|
767
778
|
elif args['mode'] == 'config':
|
768
779
|
config = json.loads(args['config'])
|
769
780
|
default_args = cls.get_default_arg_dict()
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.2
|
2
2
|
Name: tinyssg
|
3
|
-
Version: 1.
|
3
|
+
Version: 1.3.0
|
4
4
|
Summary: A simple static site generator
|
5
5
|
Author: Uniras
|
6
6
|
Author-email: tkappeng@gmail.com
|
@@ -60,13 +60,13 @@ Create a Python file in the `pages` directory and create a class that extends th
|
|
60
60
|
from tinyssg import TinySSGPage
|
61
61
|
|
62
62
|
class IndexPage(TinySSGPage):.
|
63
|
-
def query(self)
|
63
|
+
def query(self) -> any:
|
64
64
|
return {
|
65
65
|
'title': 'Index', 'content': 'Hello, World!
|
66
66
|
'content': 'Hello, World!'
|
67
67
|
}
|
68
68
|
|
69
|
-
def template(self):
|
69
|
+
def template(self) -> str:
|
70
70
|
return self.indent("""
|
71
71
|
<!DOCTYPE html>
|
72
72
|
<html>
|
@@ -106,7 +106,7 @@ Each page must be defined individually, but since this is a simple Python class,
|
|
106
106
|
python -m tinyssg dev
|
107
107
|
```
|
108
108
|
|
109
|
-
The local server for development will be started.You can see the generated HTML by accessing
|
109
|
+
The local server for development will be started.You can see the generated HTML by accessing `http://localhost:8000`.
|
110
110
|
|
111
111
|
If you change files in the `pages`, `libs`, or `static` directories, the server will automatically restart to reflect the changes.
|
112
112
|
|
@@ -121,7 +121,6 @@ HTML files will be generated in the `dist` directory.
|
|
121
121
|
### options (excerpt)
|
122
122
|
|
123
123
|
```text
|
124
|
-
|
125
124
|
usage: python -m tinyssg [--page PAGE] [--static STATIC] [--lib LIB] [--input INPUT] [--output OUTPUT] [--port PORT] [--wait WAIT] [--nolog] [--noreloadnoreload] [--noopen] [--curdir CURDIR] [mode]
|
126
125
|
|
127
126
|
MODE:
|
@@ -167,12 +166,12 @@ from tinyssg import TinySSGPage
|
|
167
166
|
from lib.jinja2_page import Jinja2Page
|
168
167
|
|
169
168
|
class IndexPage(Jinja2Page):
|
170
|
-
def query(self):
|
169
|
+
def query(self) -> any:
|
171
170
|
return {
|
172
171
|
'title': 'Index', 'content': 'Hello, World!'
|
173
172
|
}
|
174
173
|
|
175
|
-
def template(self):
|
174
|
+
def template(self) -> str:
|
176
175
|
return self.indent("""
|
177
176
|
<!DOCTYPE html>
|
178
177
|
<html>
|
@@ -210,12 +209,12 @@ from tinyssg import TinySSGPage
|
|
210
209
|
from lib.markdown_page import MarkdownPage
|
211
210
|
|
212
211
|
class IndexPage(MarkdownPage):
|
213
|
-
def query(self):
|
212
|
+
def query(self) -> any:
|
214
213
|
return {
|
215
214
|
'title': 'Index', 'content': 'Hello, World!'
|
216
215
|
}
|
217
216
|
|
218
|
-
def template(self):
|
217
|
+
def template(self) -> str:
|
219
218
|
return self.indent("""
|
220
219
|
# {{ title }}
|
221
220
|
|
@@ -0,0 +1,6 @@
|
|
1
|
+
tinyssg/__init__.py,sha256=chZ0V-pOqPvEW88DLyHhwuj4AqTdOWWNEJD5p0H7Y18,31189
|
2
|
+
tinyssg/__main__.py,sha256=E8PEZ-wWYae76H_iWbY1Xu9VYGb6sfsWMN-hzqTMoBc,83
|
3
|
+
tinyssg-1.3.0.dist-info/METADATA,sha256=ed7CDTme-MnCLWgzpY7RawYWfs3JL2hH2HzvUCOaBf0,8100
|
4
|
+
tinyssg-1.3.0.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
|
5
|
+
tinyssg-1.3.0.dist-info/top_level.txt,sha256=8u1XtPYCatbklb6u3NbJbFUbwA8nDKZ6cY3FScGwJDQ,8
|
6
|
+
tinyssg-1.3.0.dist-info/RECORD,,
|
tinyssg-1.2.0.dist-info/RECORD
DELETED
@@ -1,6 +0,0 @@
|
|
1
|
-
tinyssg/__init__.py,sha256=5dn_SPH78JJStnQCxz_7YMflRHQRFusF-hJAdGWQ8X4,30677
|
2
|
-
tinyssg/__main__.py,sha256=E8PEZ-wWYae76H_iWbY1Xu9VYGb6sfsWMN-hzqTMoBc,83
|
3
|
-
tinyssg-1.2.0.dist-info/METADATA,sha256=3nFvOkOZmcjeYVja9crVQ6fhFPhxyw4CXllMyzRYHKU,8063
|
4
|
-
tinyssg-1.2.0.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
|
5
|
-
tinyssg-1.2.0.dist-info/top_level.txt,sha256=8u1XtPYCatbklb6u3NbJbFUbwA8nDKZ6cY3FScGwJDQ,8
|
6
|
-
tinyssg-1.2.0.dist-info/RECORD,,
|
File without changes
|
File without changes
|