From 1bb777e5125d2c45c958fac84532a27bd4105381 Mon Sep 17 00:00:00 2001 From: John Donaldson Date: Thu, 15 Aug 2019 23:30:48 +0100 Subject: [PATCH 1/5] Adding support for Python libraries inside of puzzles and categories --- devel/devel-server.py | 2 +- devel/moth.py | 20 +++++++++++++++++++- example-puzzles/example/200/puzzle.py | 19 +++++++++++++++++++ example-puzzles/example/200/puzzlelib.py | 7 +++++++ example-puzzles/example/categorylib.py | 7 +++++++ 5 files changed, 53 insertions(+), 2 deletions(-) create mode 100755 example-puzzles/example/200/puzzle.py create mode 100644 example-puzzles/example/200/puzzlelib.py create mode 100644 example-puzzles/example/categorylib.py diff --git a/devel/devel-server.py b/devel/devel-server.py index 7f35e33..b405bd7 100755 --- a/devel/devel-server.py +++ b/devel/devel-server.py @@ -210,7 +210,7 @@ sessionStorage.setItem("id", "devel-server") self.end_headers() self.wfile.write(body.encode('utf-8')) endpoints.append((r"/", handle_index)) - endpoints.append((r"/{ignored}", handle_index)) + #endpoints.append((r"/{ignored}", handle_index)) def handle_theme_file(self): diff --git a/devel/moth.py b/devel/moth.py index 612d371..d3b3492 100644 --- a/devel/moth.py +++ b/devel/moth.py @@ -2,6 +2,7 @@ import argparse import contextlib +import copy import glob import hashlib import html @@ -11,6 +12,7 @@ import mistune import os import random import string +import sys import tempfile import shlex @@ -26,9 +28,24 @@ def djb2hash(str): def pushd(newdir): curdir = os.getcwd() os.chdir(newdir) + # Force a copy of the old path, instead of just a reference + old_path = list(sys.path) + old_modules = copy.copy(sys.modules) + sys.path.append(newdir) + print("New path: %s" % (sys.path,)) try: yield finally: + # Restore the old path + to_remove = [] + for module in sys.modules: + if module not in old_modules: + to_remove.append(module) + + for module in to_remove: + del(sys.modules[module]) + + sys.path = old_path os.chdir(curdir) @@ -316,7 +333,8 @@ class Category: with pushd(self.path): self.catmod.make(points, puzzle) else: - puzzle.read_directory(path) + with pushd(self.path): + puzzle.read_directory(path) return puzzle def __iter__(self): diff --git a/example-puzzles/example/200/puzzle.py b/example-puzzles/example/200/puzzle.py new file mode 100755 index 0000000..cfb9614 --- /dev/null +++ b/example-puzzles/example/200/puzzle.py @@ -0,0 +1,19 @@ +import io +import categorylib # Category-level libraries can be imported here + +def make(puzzle): + import puzzlelib # puzzle-level libraries can only be imported inside of the make function + puzzle.authors = ['donaldson'] + puzzle.summary = 'more crazy stuff you can do with puzzle generation using Python libraries' + + puzzle.body.write("## Crazy Things You Can Do With Puzzle Generation (part II)\n") + puzzle.body.write("\n") + puzzle.body.write("The source to this puzzle has some more advanced examples of stuff you can do in Python.\n") + puzzle.body.write("\n") + puzzle.body.write("1 == %s\n\n" % puzzlelib.getone(),) + puzzle.body.write("2 == %s\n\n" % categorylib.gettwo(),) + + puzzle.answers.append('tea') + answer = puzzle.make_answer() # Generates a random answer, appending it to puzzle.answers too + puzzle.log("Answers: {}".format(puzzle.answers)) + diff --git a/example-puzzles/example/200/puzzlelib.py b/example-puzzles/example/200/puzzlelib.py new file mode 100644 index 0000000..73ffeca --- /dev/null +++ b/example-puzzles/example/200/puzzlelib.py @@ -0,0 +1,7 @@ +"""This is an example of a puzzle-level library. + +This library can be imported by child puzzles using `import puzzlelib` +""" + +def getone(): + return 1 diff --git a/example-puzzles/example/categorylib.py b/example-puzzles/example/categorylib.py new file mode 100644 index 0000000..fb5a230 --- /dev/null +++ b/example-puzzles/example/categorylib.py @@ -0,0 +1,7 @@ +"""This is an example of a category-level library. + +This library can be imported by child puzzles using `import categorylib` +""" + +def gettwo(): + return 2 From a2ceea31762029e64ca0ea1a604787f21ef472bf Mon Sep 17 00:00:00 2001 From: John Donaldson Date: Thu, 15 Aug 2019 23:32:28 +0100 Subject: [PATCH 2/5] Fix how legacy puzzles with author (vs. authors) field are handled --- devel/moth.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/devel/moth.py b/devel/moth.py index d3b3492..fd53c6a 100644 --- a/devel/moth.py +++ b/devel/moth.py @@ -289,7 +289,7 @@ class Puzzle: files = [fn for fn,f in self.files.items() if f.visible] return { - 'authors': self.authors, + 'authors': self.get_authors(), 'hashes': self.hashes(), 'files': files, 'scripts': self.scripts, From ca88bffaf3b3521a7d875c2749dde2989f1d9267 Mon Sep 17 00:00:00 2001 From: John Donaldson Date: Thu, 15 Aug 2019 23:34:10 +0100 Subject: [PATCH 3/5] Removing leftover debugging output --- devel/moth.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/devel/moth.py b/devel/moth.py index fd53c6a..9ed0388 100644 --- a/devel/moth.py +++ b/devel/moth.py @@ -28,11 +28,12 @@ def djb2hash(str): def pushd(newdir): curdir = os.getcwd() os.chdir(newdir) + # Force a copy of the old path, instead of just a reference old_path = list(sys.path) old_modules = copy.copy(sys.modules) sys.path.append(newdir) - print("New path: %s" % (sys.path,)) + try: yield finally: From 150456167718df93bdd11bae6373b417ea9f96e3 Mon Sep 17 00:00:00 2001 From: John Donaldson Date: Thu, 15 Aug 2019 23:36:13 +0100 Subject: [PATCH 4/5] Hackishly pulling in upstream change --- devel/devel-server.py | 1 - 1 file changed, 1 deletion(-) diff --git a/devel/devel-server.py b/devel/devel-server.py index b405bd7..acde401 100755 --- a/devel/devel-server.py +++ b/devel/devel-server.py @@ -210,7 +210,6 @@ sessionStorage.setItem("id", "devel-server") self.end_headers() self.wfile.write(body.encode('utf-8')) endpoints.append((r"/", handle_index)) - #endpoints.append((r"/{ignored}", handle_index)) def handle_theme_file(self): From 18bae31912bf60f01b4d4a743607eea85669a0ea Mon Sep 17 00:00:00 2001 From: John Donaldson Date: Thu, 15 Aug 2019 23:41:08 +0100 Subject: [PATCH 5/5] Changing verbiage of puzzlelib example --- example-puzzles/example/200/puzzlelib.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/example-puzzles/example/200/puzzlelib.py b/example-puzzles/example/200/puzzlelib.py index 73ffeca..566be76 100644 --- a/example-puzzles/example/200/puzzlelib.py +++ b/example-puzzles/example/200/puzzlelib.py @@ -1,6 +1,6 @@ """This is an example of a puzzle-level library. -This library can be imported by child puzzles using `import puzzlelib` +This library can be imported by sibling puzzles using `import puzzlelib` """ def getone():