# -*- test-case-name: twisted.web.test.test_script -*-
# Copyright (c) Twisted Matrix Laboratories.
# See LICENSE for details.
"""
I contain PythonScript, which is a very simple python script resource.
"""
import os
import traceback
from io import StringIO
from twisted import copyright
from twisted.python.compat import execfile, networkString
from twisted.python.filepath import _coerceToFilesystemEncoding
from twisted.web import http, resource, server, static, util
rpyNoResource = """
You forgot to assign to the variable "resource" in your script. For example:
"""
class AlreadyCached(Exception):
"""
This exception is raised when a path has already been cached.
"""
class CacheScanner:
def __init__(self, path, registry):
self.path = path
self.registry = registry
self.doCache = 0
def cache(self):
c = self.registry.getCachedPath(self.path)
if c is not None:
raise AlreadyCached(c)
self.recache()
def recache(self):
self.doCache = 1
noRsrc = resource._UnsafeErrorPage(500, "Whoops! Internal Error", rpyNoResource)
def ResourceScript(path, registry):
"""
I am a normal py file which must define a 'resource' global, which should
be an instance of (a subclass of) web.resource.Resource; it will be
renderred.
"""
cs = CacheScanner(path, registry)
glob = {
"__file__": _coerceToFilesystemEncoding("", path),
"resource": noRsrc,
"registry": registry,
"cache": cs.cache,
"recache": cs.recache,
}
try:
execfile(path, glob, glob)
except AlreadyCached as ac:
return ac.args[0]
rsrc = glob["resource"]
if cs.doCache and rsrc is not noRsrc:
registry.cachePath(path, rsrc)
return rsrc
def ResourceTemplate(path, registry):
from quixote import ptl_compile # type: ignore[import]
glob = {
"__file__": _coerceToFilesystemEncoding("", path),
"resource": resource._UnsafeErrorPage(
500, "Whoops! Internal Error", rpyNoResource
),
"registry": registry,
}
with open(path) as f: # Not closed by quixote as of 2.9.1
e = ptl_compile.compile_template(f, path)
code = compile(e, "