2017-10-19 8 views
0

J'écris une petite application NodeJS/Express. Je mis en place carlin comme moteur de modèle:pug.compile() ne peut pas trouver les fichiers modèles (res.render() peut)

const app = express(); 

app.set('view engine', 'pug'); 
app.set('views', __dirname + "/public/views"); 
app.use(express.static(__dirname + '/public/static')); 

Cela fonctionne bien lorsque vous appelez un res.render() à envoyer des réponses HTML:

app.get('/', function getIndex(req, res){ 
    res.render('index.pug'); 
}); 

Mais lorsque je tente de rendre les petits composants et les recueillir dans une chaîne ou un tableau en réponse à un appel AJAX, je n'arrive pas à le faire fonctionner.

const pug = require('pug'); 
const compile = pug.compileFile('option.pug'); 

Cela aboutit toujours à Error: ENOENT: no such file or directory, open 'option.pug'. J'ai essayé de changer le chemin vers la perspective du routeur (donc quelque chose comme ../../public/views/option.pug) mais cela n'aide pas non plus.

Je ne sais pas pourquoi les chemins sont interprétés différemment.

Comment faire référence à ce modèle lors de l'utilisation de pug.compileFile?

Répondre

2

À partir du code source Carlin, le chemin passé est défini comme le filename dans les options:

https://github.com/pugjs/pug/blob/926f7c720112cac76cfedb003e25e9f43d3a1767/packages/pug/lib/index.js#L354

Il est ensuite passé à handleTemplateCache pour lire le fichier:

https://github.com/pugjs/pug/blob/926f7c720112cac76cfedb003e25e9f43d3a1767/packages/pug/lib/index.js#L215

Donc finalement le chemin est simplement passé à fs.readFileSync, qui traite les chemins relatifs comme étant relatifs au répertoire de travail actuel, process.cwd().

Vous pouvez générer le chemin approprié en utilisant quelque chose comme ceci:

const file = app.get('views') + '/option.pug'; 

Il serait préférable d'utiliser path.join plutôt que concaténation de chaînes pour les chemins de construction, https://nodejs.org/api/path.html#path_path_join_paths

const path = require('path'); 
const file = path.join(app.get('views'), 'option.pug'); 

Si vous n'êtes pas vouloir (ou ne peut pas) utiliser app.get('views') vous pouvez simplement construire le chemin absolu par d'autres moyens, tels que l'utilisation __dirname directement.

Notez également que vous pouvez passer un rappel à res.render qui sera passé le HTML rendu au lieu de l'écrire à la réponse. Cela peut vous permettre d'éviter d'appeler le modèle directement en premier lieu.

+0

Désolé pour la réponse tardive. Cela fonctionne, même si j'ai évité le problème en faisant abstraction de cette partie de mon application. –