Unter Windows sollte FileSystemLoader
sowohl Pfade im Windows-Stil (mit \
) als auch im UNIX-Stil (mit /
) zulassen.
Unter Windows schlägt bei Verwendung FileSystemLoader
Folgendes fehl:
jinjaEnvironment.get_template('.\source\architecture\ARM\ARMv6-M-ARMv7-M\bo
ardTemplates\ARMv6-M-ARMv7-M.metadata')
mit
jinja2.exceptions.TemplateNotFound: .\source\architecture\ARM\ARMv6-M-ARMv7-M\bo
ardTemplates\ARMv6-M-ARMv7-M.metadata
während dieses jinjaEnvironment.get_template('.\source\architecture\ARM\ARMv6-M-ARMv7-M\bo
ardTemplates\ARMv6-M-ARMv7-M.metadata'.replace('\\', '/'))
einwandfrei funktioniert.
Traceback (most recent call last):
File "./scripts/generateBoard.py", line 186, in <module>
metadata = jinjaEnvironment.get_template(metadataFile).render(dictionary = d
ictionary)
File "C:\Python27\lib\site-packages\jinja2\environment.py", line 830, in get_t
emplate
return self._load_template(name, self.make_globals(globals))
File "C:\Python27\lib\site-packages\jinja2\environment.py", line 804, in _load
_template
template = self.loader.load(self, name, globals)
File "C:\Python27\lib\site-packages\jinja2\loaders.py", line 113, in load
source, filename, uptodate = self.get_source(environment, name)
File "C:\Python27\lib\site-packages\jinja2\loaders.py", line 168, in get_sourc
e
pieces = split_template_path(template)
File "C:\Python27\lib\site-packages\jinja2\loaders.py", line 31, in split_temp
late_path
raise TemplateNotFound(template)
jinja2.exceptions.TemplateNotFound: .\source\architecture\ARM\ARMv6-M-ARMv7-M\bo
ardTemplates\ARMv6-M-ARMv7-M.metadata
Jinja-Vorlagennamen sind keine Dateisystempfade (obwohl sie Dateisystempfaden zugeordnet sind, wenn nur ein FileSystemLoader verwendet wird). Sie verwenden immer Schrägstriche, damit dies wie beabsichtigt funktioniert.
Ich denke, diese Informationen sollten in der Dokumentation ausdrücklich in Fettschrift angegeben werden, wenn Sie nicht beabsichtigen, sie zu beheben. Es ist nicht so, dass ich absichtlich Backslashes verwendet habe - beim Generieren des Dateinamens mit einem anderen Python-Code (z. B. durch Durchsuchen der Ordner nach geeigneten Erweiterungen) hat die Zeichenfolge systemeigene Schrägstriche (also Backslashes unter Windows). In diesem Fall müssen Sie die Schrägstriche explizit ersetzen ...
Übrigens - ich benutze kein Windows, aber ich schreibe ein Skript, das auf allen Plattformen funktionieren sollte.
@FreddieChopin
Ist dieser fest? scheint mich 2019 noch zu beeinflussen.
Was ich tun muss, ist, alle \\
manuell durch $#$ /
$#$ zu ersetzen.
Ist dieser fest?
„Das ist kein Bug – das ist ein Feature!“ (;
Das ist wirklich seltsam! Könnte dies bitte geändert oder (in großen Buchstaben) in den Dokumenten erwähnt werden?
PR willkommen (für die Dokumente)
Ich habe mit einem angefangen, aber dann habe ich das hier gefunden: https://github.com/pallets/jinja/blob/master/jinja2/loaders.py#L43 -L61
A very basic example for a loader that looks up templates on the file
system could look like this::
from jinja2 import BaseLoader, TemplateNotFound
from os.path import join, exists, getmtime
class MyLoader(BaseLoader):
def __init__(self, path):
self.path = path
def get_source(self, environment, template):
path = join(self.path, template)
if not exists(path):
raise TemplateNotFound(template)
mtime = getmtime(path)
with file(path) as f:
source = f.read().decode('utf-8')
return source, path, lambda: mtime == getmtime(path)
Die Dokumentation sagt ausdrücklich, dass os.path.join verwendet werden sollte/könnte. Vielleicht ist ein Thema besser geeignet?
Das eigentliche Problem ist, dass das Python-Pfadmodul den Pfad standardmäßig mit „\“ unter Windows zurückgibt. Ich weiß, dass es irgendwie das richtige Verhalten ist, aber eingebaute Funktionen wie "open" akzeptieren sowohl Schrägstriche als auch umgekehrte Schrägstriche, sodass "manchmal funktioniert es, manchmal nicht" so etwas passiert. Wahrscheinlich brauchen wir eine Möglichkeit, Pfade unabhängig von Plattformen zu behandeln ... eine Art "Python-Konvention, um Pfade intern zu behandeln" ... Ich denke, das ist kein Problem von jinja2 (Dies ist ein Problem der historischen Konvention zwischen Unix und Windows und es scheint ewig zu dauern), aber einige "Hinweise" in einem Startdokument sind willkommen.
Das grundlegende Problem besteht darin, dass ein Vorlagen-"Pfad" nicht wirklich ein Betriebssystempfad ist, sondern nur "/"-Trennzeichen enthalten soll. Aber in loaders.get_source() denkt self.searchpath auch, dass das Pfadtrennzeichen immer "/" ist.
Die Vorlagenpfade sollten nicht in tatsächliche Betriebssystempfade geändert werden, da es anscheinend andere Stellen gibt, an denen diese kanonische Annahme verwendet wird.
Die Lösung besteht darin, sowohl die Vorlage als auch den Suchpfad so zu ändern, dass sie an der Stelle, an der Betriebssystempfade benötigt werden, tatsächliche Pfadtrennzeichen des Betriebssystems enthalten:
def get_source(self, environment, template):
_searchpaths = self.searchpath
if path.sep != '/':
template = template.replace('/', path.sep)
_searchpaths = [p.replace('/', path.sep) for p in self.searchpath]
pieces = os.path.split(template)
for searchpath in _searchpaths:
# Existing code continues here ...
Ich habe diesen Code kurz in Windows 10/Python 2.7 getestet und meinen Fehler „Vorlage nicht gefunden“ behoben.
Hilfreichster Kommentar
Ich denke, diese Informationen sollten in der Dokumentation ausdrücklich in Fettschrift angegeben werden, wenn Sie nicht beabsichtigen, sie zu beheben. Es ist nicht so, dass ich absichtlich Backslashes verwendet habe - beim Generieren des Dateinamens mit einem anderen Python-Code (z. B. durch Durchsuchen der Ordner nach geeigneten Erweiterungen) hat die Zeichenfolge systemeigene Schrägstriche (also Backslashes unter Windows). In diesem Fall müssen Sie die Schrägstriche explizit ersetzen ...
Übrigens - ich benutze kein Windows, aber ich schreibe ein Skript, das auf allen Plattformen funktionieren sollte.