pretext 2.33.2__tar.gz → 2.33.2.dev20251211064632__tar.gz

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.
Files changed (64) hide show
  1. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/PKG-INFO +3 -3
  2. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/__init__.py +1 -1
  3. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/codechat.py +1 -3
  4. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/project/__init__.py +32 -25
  5. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/resources/core.zip +0 -0
  6. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/resources/pelican.zip +0 -0
  7. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/resources/resource_hash_table.json +9 -9
  8. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/resources/rs_cache.zip +0 -0
  9. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/resources/templates.zip +0 -0
  10. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/utils.py +6 -30
  11. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pyproject.toml +3 -3
  12. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/LICENSE +0 -0
  13. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/README.md +0 -0
  14. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/__main__.py +0 -0
  15. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/cli.py +0 -0
  16. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/constants.py +0 -0
  17. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/core/__init__.py +0 -0
  18. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/core/braille_format.py +0 -0
  19. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/core/pretext.py +0 -0
  20. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/logger.py +0 -0
  21. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Alignment.jinja2s +0 -0
  22. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Arrays.jinja2s +0 -0
  23. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Bibliography.jinja2s +0 -0
  24. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Boxes.jinja2s +0 -0
  25. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Breaking.jinja2s +0 -0
  26. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Crossref.jinja2s +0 -0
  27. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Floats.jinja2s +0 -0
  28. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/FontSelection.jinja2s +0 -0
  29. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Footnotes.jinja2s +0 -0
  30. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Index.jinja2s +0 -0
  31. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Lists.jinja2s +0 -0
  32. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Pictures.jinja2s +0 -0
  33. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Quotations.jinja2s +0 -0
  34. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Sectioning.jinja2s +0 -0
  35. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Sentences.jinja2s +0 -0
  36. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Space.jinja2s +0 -0
  37. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Tabbing.jinja2s +0 -0
  38. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Themes/__init__.py +0 -0
  39. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Themes/default/__init__.py +0 -0
  40. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Themes/default/default-layout.jinja2 +0 -0
  41. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Themes/default/document-layout.jinja2 +0 -0
  42. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Thms.jinja2s +0 -0
  43. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/Verbatim.jinja2s +0 -0
  44. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/__init__.py +0 -0
  45. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/babel.jinja2s +0 -0
  46. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/graphicx.jinja2s +0 -0
  47. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/hyperref.jinja2s +0 -0
  48. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/lipsum.jinja2s +0 -0
  49. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/longtable.jinja2s +0 -0
  50. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/math.jinja2s +0 -0
  51. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/misc.jinja2s +0 -0
  52. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/natbib.jinja2s +0 -0
  53. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/p.jinja2s +0 -0
  54. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/subfig.jinja2s +0 -0
  55. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/textcomp.jinja2s +0 -0
  56. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/tikzcd.jinja2 +0 -0
  57. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/tikzpicture.jinja2 +0 -0
  58. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/url.jinja2s +0 -0
  59. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/plastex/wrapfig.jinja2s +0 -0
  60. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/project/generate.py +0 -0
  61. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/project/xml.py +0 -0
  62. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/resources/__init__.py +0 -0
  63. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/server.py +0 -0
  64. {pretext-2.33.2 → pretext-2.33.2.dev20251211064632}/pretext/types.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: pretext
3
- Version: 2.33.2
3
+ Version: 2.33.2.dev20251211064632
4
4
  Summary: A package to author, build, and deploy PreTeXt projects.
5
5
  Home-page: https://pretextbook.org
6
6
  License: GPL-3.0-or-later
@@ -24,12 +24,12 @@ Requires-Dist: click-log (>=0.4,<0.5)
24
24
  Requires-Dist: coloraide (>=4,<5)
25
25
  Requires-Dist: ghp-import (>=2,<3)
26
26
  Requires-Dist: jinja2 (>=3,<4)
27
- Requires-Dist: lxml (>=6,<7)
27
+ Requires-Dist: lxml (>=5.3,<6.0)
28
28
  Requires-Dist: pdfCropMargins (>=1.0.9,<1.1.0)
29
29
  Requires-Dist: pelican[markdown] (>=4.10,<5.0) ; extra == "homepage" or extra == "all"
30
30
  Requires-Dist: plastex (>=3,<4)
31
31
  Requires-Dist: playwright (>=1,<2)
32
- Requires-Dist: prefig[text] (>=0.4.6,<0.5.0) ; extra == "prefigure" or extra == "all"
32
+ Requires-Dist: prefig[text] (>=0.4.2,<0.5.0) ; extra == "prefigure" or extra == "all"
33
33
  Requires-Dist: psutil (>=7,<8)
34
34
  Requires-Dist: pyMuPDF (>=1.24,<2.0)
35
35
  Requires-Dist: pydantic-xml (==2.14.3)
@@ -19,7 +19,7 @@ from single_version import get_version
19
19
  VERSION = get_version("pretext", Path(__file__).parent.parent)
20
20
 
21
21
 
22
- CORE_COMMIT = "1c97959297d51749717f9b34ce5da131c960b92d"
22
+ CORE_COMMIT = '1c97959297d51749717f9b34ce5da131c960b92d'
23
23
 
24
24
 
25
25
  def activate() -> None:
@@ -88,9 +88,7 @@ def map_path_to_xml_id(
88
88
  # Load the XML, performing xincludes using this loader.
89
89
  huge_parser = ET.XMLParser(huge_tree=True)
90
90
  src_tree = ET.parse(_xml, parser=huge_parser)
91
- # Previously, we used the following line instead of .xinclude(), but that no longer seems to work in 6.0 lxml.
92
- # lxml.ElementInclude.include(src_tree, loader=my_loader)
93
- src_tree.xinclude()
91
+ lxml.ElementInclude.include(src_tree, loader=my_loader)
94
92
 
95
93
  # Walk though every element with an xml ID. Note: the type stubs don't have the ``iterfind`` method, hence the ignore in the next line.
96
94
  for elem in src_tree.iterfind(f".//*[@{xml_id_attrib}]"): # type: ignore
@@ -128,8 +128,6 @@ class Target(pxml.BaseXmlModel, tag="target", search_mode=SearchMode.UNORDERED):
128
128
  #
129
129
  # A path to the root source for this target, relative to the project's `source` path.
130
130
  source: Path = pxml.attr(default=Path("main.ptx"))
131
- # Cache of assembled source element.
132
- _source_element: t.Optional[ET._Element] = None
133
131
  # A path to the publication file for this target, relative to the project's `publication` path. This is mostly validated by `post_validate`.
134
132
  publication: Path = pxml.attr(default=None)
135
133
  latex_engine: LatexEngine = pxml.attr(
@@ -370,9 +368,29 @@ class Target(pxml.BaseXmlModel, tag="target", search_mode=SearchMode.UNORDERED):
370
368
  if server.name not in self_server_names:
371
369
  self.server.append(server)
372
370
 
373
- # NB as of 2025-04-08, we are no longer setting the output directory automatically for
374
- # Runestone targets. This must be managed by the project.ptx file or by a client script.
375
- # Check history here for how that was done.
371
+ # For the Runestone format, determine the `<document-id>`, which specifies the `output_dir`.
372
+ if self.format == Format.HTML and self.platform == Platform.RUNESTONE:
373
+ # We expect `d_list == ["document-id contents here"]`.
374
+ d_list = self.source_element().xpath("/pretext/docinfo/document-id/text()")
375
+ if isinstance(d_list, list):
376
+ if len(d_list) != 1:
377
+ raise ValueError(
378
+ "Only one `document-id` tag is allowed in a PreTeXt document."
379
+ )
380
+ # NB as of 2025-04-08, we are no longer setting the output directory automatically for
381
+ # Runestone targets. This must be managed by the project.ptx file or by a client script.
382
+ # The commented code below is how we used to do this.
383
+
384
+ # d = d_list[0]
385
+ # assert isinstance(d, str)
386
+ # # Use the correct number of `../` to undo the project's `output-dir`, so the output from the build is located in the correct directory of `published/document-id`.
387
+ # self.output_dir = Path(
388
+ # f"{'../'*len(self._project.output_dir.parents)}published/{d}"
389
+ # )
390
+ else:
391
+ raise ValueError(
392
+ "The `document-id` tag must be defined for the Runestone format."
393
+ )
376
394
 
377
395
  def source_abspath(self) -> Path:
378
396
  return self._project.source_abspath() / self.source
@@ -390,21 +408,14 @@ class Target(pxml.BaseXmlModel, tag="target", search_mode=SearchMode.UNORDERED):
390
408
  def source_element(self) -> ET._Element:
391
409
  """
392
410
  Returns the root element for the assembled source, after processing with the "version-only" assembly.
393
- Caches the result for future calls.
394
411
  """
395
- if self._source_element is None:
396
- log.debug(
397
- f"Parsing source element for target {self.name}",
398
- )
399
- self._source_element = core.assembly_internal(
400
- xml=self.source_abspath(),
401
- pub_file=self.publication_abspath().as_posix(),
402
- stringparams=self.stringparams.copy(),
403
- method="version",
404
- ).getroot()
405
- else:
406
- log.debug(f"Using cached source_element for target {self.name}")
407
- return self._source_element
412
+ assembled = core.assembly_internal(
413
+ xml=self.source_abspath(),
414
+ pub_file=self.publication_abspath().as_posix(),
415
+ stringparams=self.stringparams.copy(),
416
+ method="version",
417
+ )
418
+ return assembled.getroot()
408
419
 
409
420
  def publication_abspath(self) -> Path:
410
421
  return self._project.publication_abspath() / self.publication
@@ -671,16 +682,12 @@ class Target(pxml.BaseXmlModel, tag="target", search_mode=SearchMode.UNORDERED):
671
682
  self.stringparams["cli.version"] = VERSION[: VERSION.rfind(".")]
672
683
 
673
684
  # Check for xml syntax errors and quit if xml invalid:
674
- try:
675
- # Access the source_element to trigger assembly if it hasn't been done yet.
676
- self.source_element()
677
- except Exception as e:
678
- log.error(f"Error assembling source file: {e}")
685
+ if not utils.xml_syntax_is_valid(self.source_abspath()):
679
686
  raise RuntimeError("XML syntax for source file is invalid")
680
687
  if not utils.xml_syntax_is_valid(self.publication_abspath(), "publication"):
681
688
  raise RuntimeError("XML syntax for publication file is invalid")
682
689
  # Validate xml against schema; continue with warning if invalid:
683
- utils.xml_validates_against_schema(self.source_element())
690
+ utils.xml_source_validates_against_schema(self.source_abspath())
684
691
 
685
692
  # Clean output upon request
686
693
  if clean:
@@ -513,14 +513,14 @@
513
513
  "installPandoc.sh": "3d4ee0fe164575e7f17dda651c12570f12fed3e042ca4739edd5bbfcaaec5c24",
514
514
  "installSage.sh": "e9682f35f46c2faf5c062b679fd2e17d9767098022b5f10164b8c4e5439544a9"
515
515
  },
516
- "2.33.2": {
517
- "project.ptx": "08f992b2f4b2420bf9c3002deb8b4a2be8d6fc90ce770eb5bf47437859db10f7",
518
- "codechat_config.yaml": "78634ed0c6f14bd1df9aaf7b29c73ff0f5cae126898179381549b6d7b00cb8b5",
519
- ".gitignore": "d62ea9ea215f605c430ffcedeb33b81e808490a94c6d30cabbbefdf3a4de1ae8",
520
- "devcontainer.json": "94ea6ba7e57b238543d39b2997142d52792fefaf543064184485f2a851f75348",
521
- "pretext-cli.yml": "2d6fc8ad7efbf30ce061feb5c387a89d9e9cae3663e17ece9842d50a1bf14fa2",
522
- "pretext-deploy.yml": "fe66cd20fb2bfb52b1cf01228a99a203829691dd173b7995c317180fdfcf3f09",
523
- "installPandoc.sh": "a18b850870b5e2d744c99300c0643f12a81eba3e27dfd985927554af2062c967",
524
- "installSage.sh": "8020b532e1101c77c5681c0dfaff308a36c60e95db6b0f652bf230f7de216cb8"
516
+ "2.33.2.dev20251211064632": {
517
+ "project.ptx": "2ab72c22ee7e4c2fa44428c41b26f991ef457ac543886029473e400413b7dcfd",
518
+ "codechat_config.yaml": "2f22e90dbf76a7918556f7f0ba43dc7b503b02c15c246757b4a53e093c69d04e",
519
+ ".gitignore": "c34611fa875e15a57a1aeddaad5a403933ac179e83333f78cbf6dfb00900624f",
520
+ "devcontainer.json": "6674ef076ce8df47d288c59a366b59e0a01039c2195eb7aba99ca9eb7b751c34",
521
+ "pretext-cli.yml": "cbffb8d0663cefc11832ebcff190bdfea67ec7caf99faa00276b47aa188e684f",
522
+ "pretext-deploy.yml": "d9bfed1750deaf694651e4113f1b3c5215153b429460bd08b6b3c683857529fc",
523
+ "installPandoc.sh": "28e29981435545a4cea0ad2fc0df8603ad51a32181b12e40c253396cc02a655f",
524
+ "installSage.sh": "2504f9fad7cb557b4f5a653f48868f53a6fa1abf66ce43a3c052cc76129c3c52"
525
525
  }
526
526
  }
@@ -12,7 +12,6 @@ import shutil
12
12
  import socketserver
13
13
  import socket
14
14
  import subprocess
15
- import time as time
16
15
  import logging
17
16
  import logging.handlers
18
17
  import psutil
@@ -204,13 +203,17 @@ def xml_syntax_is_valid(xmlfile: Path, root_tag: str = "pretext") -> bool:
204
203
  return True
205
204
 
206
205
 
207
- def xml_validates_against_schema(etree: _Element) -> bool:
206
+ def xml_source_validates_against_schema(xmlfile: Path) -> bool:
208
207
  # get path to RelaxNG schema file:
209
208
  schemarngfile = resources.resource_base_path() / "core" / "schema" / "pretext.rng"
210
209
 
211
210
  # Open schemafile for validation:
212
211
  relaxng = ET.RelaxNG(file=schemarngfile)
213
212
 
213
+ # Parse xml file:
214
+ source_xml = ET.parse(xmlfile)
215
+ source_xml.xinclude()
216
+
214
217
  # just for testing
215
218
  # ----------------
216
219
  # relaxng.validate(source_xml)
@@ -219,7 +222,7 @@ def xml_validates_against_schema(etree: _Element) -> bool:
219
222
 
220
223
  # validate against schema
221
224
  try:
222
- relaxng.assertValid(etree)
225
+ relaxng.assertValid(source_xml)
223
226
  log.info("PreTeXt source passed schema validation.")
224
227
  except ET.DocumentInvalid as err:
225
228
  log.debug(
@@ -1101,30 +1104,3 @@ def rs_methods(
1101
1104
  f"PTX-BUG: Format {format} not recognized for running ext_rs_methods. Something is wrong with the pretext script."
1102
1105
  )
1103
1106
  return None
1104
-
1105
-
1106
- class Stopwatch:
1107
- """A simple stopwatch class for measuring elapsed time."""
1108
-
1109
- """print_log set to false disables logging of elapsed time """
1110
-
1111
- def __init__(self, name: str = "", print_log: bool = True):
1112
- self.name = name
1113
- self.print_log = print_log
1114
- self.start_time = time.time()
1115
- self.last_log_time = self.start_time
1116
-
1117
- def reset(self) -> None:
1118
- """Reset the log timer to the current time."""
1119
- self.last_log_time = time.time()
1120
-
1121
- def log(self, timepoint_description: str = "") -> None:
1122
- """Print a log message with the elapsed time since the last log event."""
1123
- if self.print_log:
1124
- cur_time = time.time()
1125
- elapsed_time = cur_time - self.start_time
1126
- since_last_log_time = cur_time - self.last_log_time
1127
- self.reset()
1128
- log.debug(
1129
- f"** Timing report from {self.name}: {timepoint_description}, {since_last_log_time:.2f}s since last watch reset. {elapsed_time:.2f}s total elapsed time."
1130
- )
@@ -11,7 +11,7 @@
11
11
  # ----------------
12
12
  [tool.poetry]
13
13
  name = "pretext"
14
- version = "2.33.2"
14
+ version = "2.33.2.dev20251211064632"
15
15
  description = "A package to author, build, and deploy PreTeXt projects."
16
16
  readme = "README.md"
17
17
  homepage = "https://pretextbook.org"
@@ -27,7 +27,7 @@ include = ["pretext/core/pretext.py", "pretext/core/braille_format.py", "pretext
27
27
  # ------------
28
28
  [tool.poetry.dependencies]
29
29
  python = "^3.10"
30
- lxml = "^6"
30
+ lxml = "^5.3"
31
31
  requests = "^2"
32
32
  GitPython = "^3"
33
33
  click = "^8"
@@ -45,7 +45,7 @@ plastex = "^3"
45
45
  jinja2 = "^3"
46
46
  coloraide = "^4"
47
47
  pelican = { extras = ["markdown"], version = "^4.10", optional = true }
48
- prefig = { extras = ["text"], version = "^0.4.6", optional = true }
48
+ prefig = { extras = ["text"], version = "^0.4.2", optional = true }
49
49
  citeproc-py = "^0"
50
50
 
51
51