1
1
#! /usr/bin/env python3
2
2
# -*- coding: utf-8 -*-
3
+ import nh3
3
4
import os .path
4
- import string
5
5
import argparse
6
+ import html
7
+ import string
6
8
import subprocess
7
9
import re
8
10
import tempfile
@@ -35,13 +37,12 @@ def convert(problem: str, options: argparse.Namespace) -> bool:
35
37
statement_common .foreach_image (statement_path ,
36
38
lambda img_name : copy_image (problem , img_name ))
37
39
38
- command = ["pandoc" , statement_path , "-t" , "html" , "-f" , "markdown-raw_html" , "- -mathjax" ]
40
+ command = ["pandoc" , statement_path , "-t" , "html" , "--mathjax" ]
39
41
statement_html = subprocess .run (command , capture_output = True , text = True ,
40
42
shell = False , check = True ).stdout
41
43
42
44
43
45
templatepaths = [os .path .join (os .path .dirname (__file__ ), 'templates/markdown_html' ),
44
- os .path .join (os .path .dirname (__file__ ), '../templates/markdown_html' ),
45
46
'/usr/lib/problemtools/templates/markdown_html' ]
46
47
templatepath = next ((p for p in templatepaths
47
48
if os .path .isdir (p ) and os .path .isfile (os .path .join (p , "default-layout.html" ))),
@@ -50,30 +51,51 @@ def convert(problem: str, options: argparse.Namespace) -> bool:
50
51
if templatepath is None :
51
52
raise Exception ('Could not find directory with markdown templates' )
52
53
53
- problem_name = statement_common .get_problem_name (problem , options .language )
54
+ problem_name = statement_common .get_yaml_problem_name (problem , options .language )
54
55
55
- html_template = _substitute_template (templatepath , "default-layout.html" ,
56
+ if problem_name :
57
+ problem_name = html .escape (problem_name )
58
+
59
+ statement_html = _substitute_template (templatepath , "default-layout.html" ,
56
60
statement_html = statement_html ,
57
61
language = options .language ,
58
62
title = problem_name or "Missing problem name" ,
59
- problemid = problembase )
63
+ problemid = problembase ) # No need to escape problem shortname, the spec has tight restrictions directory names
60
64
61
65
samples = statement_common .format_samples (problem , to_pdf = False )
62
66
63
67
# Insert samples at {{nextsample}} and {{remainingsamples}}
64
- html_template , remaining_samples = statement_common .inject_samples (html_template , samples , "" )
68
+ statement_html , remaining_samples = statement_common .inject_samples (statement_html , samples , "" )
65
69
66
70
# Insert the remaining samples at the bottom
67
- if FOOTNOTES_STRING in html_template :
68
- pos = html_template .find (FOOTNOTES_STRING )
71
+ if FOOTNOTES_STRING in statement_html :
72
+ pos = statement_html .find (FOOTNOTES_STRING )
69
73
else :
70
- pos = html_template .find ("</body>" )
71
- html_template = html_template [:pos ] + "" .join (remaining_samples ) + html_template [pos :]
72
-
73
- html_template = replace_hr_in_footnotes (html_template )
74
+ pos = statement_html .find ("</body>" )
75
+ statement_html = statement_html [:pos ] + "" .join (remaining_samples ) + statement_html [pos :]
76
+
77
+ statement_html = replace_hr_in_footnotes (statement_html )
78
+ html_body = statement_html [statement_html .find ("<body>" ):]
79
+ statement_html = statement_html [:statement_html .find ("<body>" )]
80
+
81
+ allowed_classes = ("sample" , "problemheader" , "problembody" , "sampleinteractionwrite" , "sampleinteractionread" ,)
82
+ def attribute_filter (tag , attribute , value ):
83
+ if attribute == "class" and value in allowed_classes :
84
+ return value
85
+ if tag == "img" and attribute == "src" :
86
+ return value
87
+ return None
88
+
89
+ html_body = nh3 .clean (html_body ,
90
+ link_rel = "noopener nofollow noreferrer" ,
91
+ attribute_filter = attribute_filter ,
92
+ tags = nh3 .ALLOWED_TAGS | {"img" },
93
+ attributes = {"table" : {"class" }, "div" : {"class" }, "img" : {"src" }},
94
+ )
95
+ statement_html += html_body
74
96
75
97
with open (destfile , "w" , encoding = "utf-8" , errors = "xmlcharrefreplace" ) as output_file :
76
- output_file .write (html_template )
98
+ output_file .write (statement_html )
77
99
78
100
if options .css :
79
101
with open ("problem.css" , "w" ) as output_file :
0 commit comments