简体   繁体   English

如何转义 node.js 中的 EJS 模板代码以在客户端进行评估?

[英]How do I escape EJS template code in node.js to be evaluated on the client side?

I use node.js/ejs on the server side and backbone.js on the client side.我在服务器端使用 node.js/ejs,在客户端使用backbone.js。 Both server side and client side use the same templating style.服务器端和客户端都使用相同的模板样式。 So the problem is, if I put template code meant for the client inside a template it still get's parsed on the server side.所以问题是,如果我将用于客户端的模板代码放在模板中,它仍然会在服务器端解析。

If found out that something like this works:如果发现这样的事情有效:

<%- "<%= done ? 'done' : '' %\>" %>

However, IMHO this uglifies the code in a way which makes the whole point of using templates useless.但是,恕我直言,这使代码变得丑陋,这使得使用模板的整个意义变得毫无用处。

How would you approach this?你会如何处理这个问题?

Is there a way to define blocks of code inside EJS-templates which do not get parsed like a {literal}-tag used in other templating languages?有没有办法在 EJS 模板中定义代码块,这些代码块不会像其他模板语言中使用的 {literal} 标签那样被解析?

Update: For now I use backbone's _.templateSettings to use different delimiters on the client side.更新:现在我使用主干的 _.templateSettings 在客户端使用不同的分隔符。

Update: Here's a similar solution in a JSP context: Underscore.js Templates Within JSP更新:这是 JSP 上下文中的类似解决方案: Underscore.js Templates Within JSP

The way I have dealt with this is to override the opening and closing tags on node so that the 2 instances of ejs are lookgin for different tags.我处理这个问题的方法是覆盖节点上的开始和结束标签,以便 ejs 的 2 个实例寻找不同的标签。

On node you can pass in options在节点上,您可以传入选项

{open:'<%',close:'%>'}

In my case I use <% and <@ for my two versions.就我而言,我使用 <% 和 <@ 作为我的两个版本。 Then in node ejs template I have something like this (where name is from backbone and everyauth obviously from node):然后在节点 ejs 模板中,我有这样的东西(其中名称来自主干,而everyauth 显然来自节点):

<% if(everyauth.loggedIn) %><h1><@= name @></h1><% } %>

I use backbone.layout.manager on both the client and server side, because I want my templates to be exactly the same.我在客户端和服务器端都使用了backbone.layout.manager ,因为我希望我的模板完全一样。

The way I solved the template delimiter issue was to render the page on the server side, then inject the raw backbone templates.我解决模板分隔符问题的方法是在服务器端渲染页面,然后注入原始主干模板。

With new ejs you can add a custom delimiter at client side :使用新的 ejs,您可以在客户端添加自定义分隔符:

https://github.com/mde/ejs#custom-delimiters https://github.com/mde/ejs#custom-delimiters

eg :例如:

Custom delimiters can be applied on a per-template basis, or globally:自定义分隔符可以在每个模板的基础上应用,也可以全局应用:

var ejs = require('ejs'),
    users = ['geddy', 'neil', 'alex'];

// Just one template
ejs.render('<?= users.join(" | "); ?>', {users: users}, {delimiter: '?'});
// => 'geddy | neil | alex'

// Or globally
ejs.delimiter = '$';
ejs.render('<$= users.join(" | "); $>', {users: users});
// => 'geddy | neil | alex'

I assume the question could be read as following because it was this thread Google provide me at first link:我认为这个问题可以理解如下,因为这是谷歌在第一个链接上为我提供的这个线程:

“How I can escape EJS template code delimiter tag only for limited items?” “我如何才能仅针对有限的项目转义 EJS 模板代码分隔符标签?”

tl;dr: tl;博士:

Use <%# %> to break the original parsing code (eg <<%# %>%= done ? 'done' : '' %<%# %>> will done the following unparsed code <%= done ? 'done' : '' %> )使用<%# %>来打破原来的解析代码(例如<<%# %>%= done ? 'done' : '' %<%# %>>将完成以下未解析的代码<%= done ? 'done' : '' %> )

Long explanation长解释

Imagine a case I decide to change % by ?想象一下我决定改变% by 的情况? using { delimiter: '?' }使用{ delimiter: '?' } { delimiter: '?' } option (that could be the case here, because we want not to use the same has Backbone.js). { delimiter: '?' }选项(这可能是这里的情况,因为我们要不要使用相同的具有Backbone.js的)。

Great, that solves your problem.太好了,这解决了你的问题。 Imagine now later, for some reason, you use your templating system to generate an XML.现在想象一下,由于某种原因,您使用模板系统生成 XML。 This XML will start with <?xml version="1.0" encoding="UTF-8"?> .此 XML 将以<?xml version="1.0" encoding="UTF-8"?>开头。

You will facing the same issue again.您将再次面临同样的问题。 What do?做什么? You will change the delimiter again?你会再次更改分隔符吗? And after that, you will change again?而在那之后,你会再次改变吗? etc. No, for punctual escaping, what we should is just to be capable to say “Not parse this part of the document as EJS”.等等。不,为了准时转义,我们应该只是能够说“不要将文档的这部分解析为EJS”。

So a trick is to avoid EJS understand it's an EJS delimiter parser.所以一个技巧是避免 EJS 理解它是一个 EJS 分隔符解析器。 So avoid it (in our current case) parse <?所以避免它(在我们当前的情况下) parse <? (or <% in an original case). (或<%在原始情况下)。

So by simply adding <?# ?> to break the parsing, you will add nothing (the # item is for EJS comment) and you will avoid parser to understand <<?# ?>?xml version="1.0" encoding="UTF-8"?<?# ?>> .因此,通过简单地添加<?# ?>来中断解析,您将不添加任何内容( #项用于 EJS 注释)并且您将避免解析器理解<<?# ?>?xml version="1.0" encoding="UTF-8"?<?# ?>> The output will be <?xml version="1.0" encoding="UTF-8"?>输出将是<?xml version="1.0" encoding="UTF-8"?>

Conclusion结论

In a punctual necessity to avoid EJS parsing, you can just trick the parser to produce the output you need by using <%# %> as a delimiter tag breaker.准时必要性,以避免EJS解析,你可以欺骗解析器使用产生你所需要的输出<%# %>作为分隔符标签断路器。

For sure, probably in your case, you can just use the marked answer because you will use the EJS tag in a lot of cases.可以肯定的是,可能在您的情况下,您可以只使用标记的答案,因为您将在很多情况下使用 EJS 标记。

Well, the way that I currently approach this is to use require.js with the text plugin;好吧,我目前的方法是将require.js与文本插件一起使用; this allows me to include the templates using AJAX during development time and have them all compiled into an optimized/minified single file bundle during deploy time.这允许我在开发期间使用 AJAX 包含模板,并在部署期间将它们全部编译为优化/缩小的单个文件包。

Of course, if you don't use require.js for dependency management of the rest of your JS code this doesn't work nearly as well, but I can't stand to do javascript dev without require.js anymore now that I'm used to it anyway.当然,如果您不使用 require.js 来管理其余 JS 代码的依赖关系,这几乎不能正常工作,但是我现在无法忍受没有 require.js 的情况下进行 javascript 开发,因为我'反正我习惯了。

Alternately, there may be other similar technologies that you could use to solve the same problem.或者,可能还有其他类似的技术可用于解决相同的问题。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何在 Node.js 中呈现 EJS 模板文件? - How do I render an EJS template file in Node.js? 在Node.js中如何与客户端JavaScript通信? - In Node.js how do I communicate with client side JavaScript? 如何为生产关闭Node.js Express(ejs模板引擎)错误? - How do I turn off Node.js Express (ejs template engine) errors for production? 如何使用Node.js + Express3将变量注入EJS模板? - How do I inject a variable into an EJS template with Node.js + Express3? 如何在node.js EJS视图中转义HTML? - How to escape HTML in node.js EJS view? 我如何在node.js中将数组从服务器端传输到客户端? - How do I get to transfer an array from the server side to client side in node.js? 如何在客户端请求执行Node.js代码? - How to request a Node.js code execution on the client side? 如何使用browserify运行node.js客户端代码 - how to run node.js client side code with browserify 如何使用服务器端代码和客户端代码编写node.js Web应用程序? - How should I go about writing a node.js web application with both server and client side code? 如何使用来自 Node.js/Express/EJS 网站的一些 JS 脚本的 i18n JSON 翻译,这些脚本只能在客户端运行? - How to use i18n JSON translations from some JS scripts that are to be ran only client-side, from a Node.js / Express / EJS website?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM