自定义Jekyll插件(液体过滤器?)将脚本标签呈现为文本,而不是JavaScript [英] Custom Jekyll Plugin (Liquid Filter?) rendering script tags as text, not as JavaScript

查看:67
本文介绍了自定义Jekyll插件(液体过滤器?)将脚本标签呈现为文本,而不是JavaScript的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试使用Jekyll为朋友构建网站.

I'm experimenting with building a site using Jekyll for a friend.

我正在尝试将前端内容从/_events/2020-02-25-an-event.md/_events/2020-02-26-another-event.md之类的文件转换为可以轻松地嵌入到各种内容构建体的主体中的东西,并生成访问者所查看的那些页面,包括符合 schema.org事件标准的<script type="application/ld+json">...</script>标签.

I'm trying to transform front matter from files like /_events/2020-02-25-an-event.md and /_events/2020-02-26-another-event.md into something that can be easily embedded into the body of various building blocks of content and result in those pages, as viewed by a visitor, including <script type="application/ld+json">...</script> tags conforming to schema.org event standards.

类似于/_events/2020-02-25-an-event.md的文件如下所示:

A file like /_events/2020-02-25-an-event.md looks like this:

---
layout: event
title: An event
published: true
startdatetime: 2020-02-28
venue: Best Club Ever
---

events集合的成员旨在呈现为单个可见的URL,并且应在其呈现的输出中隐藏以下JavaScript代码段:

Members of the events collection are meant to render as individual viewable URLs and should have a snippet of JavaScript hiding in their rendered output like this:

<script type="application/ld+json">
    [
        {
            "@context" : "http://schema.org",
            "@type" : "Event",
            "name" : "An event",
            "startDate" : "2020-02-28",
            "location" : "Best Club Ever blah blah ... have address stuff to work out, still"
        }
    ]
</script>

我通过编写/_plugins/event_schema.rb来完成该工作:

I got that working by writing /_plugins/event_schema.rb as follows:

require 'liquid'

module EventSchemaFilters

  def do_not_use_me_directly_single_json_curly(input_object)
    %Q(
        {
            "@context" : "http://schema.org",
            "@type" : "Event",
            "name" : "#{input_object['title']}",
            "startDate" : "#{input_object['startdatetime']}",
            "location" : "#{input_object['venue']}"
        }
    )
  end

  def event_single_schema_script(input_object)
    %Q(
        <script type="application/ld+json">
        [
            #{do_not_use_me_directly_single_json_curly(input_object)}
        ]
        </script>
    )
  end

  def event_multiple_schema_script(input_object_array)
    %Q(
        <script type="application/ld+json">
        [
            #{input_object_array.map(&method(:do_not_use_me_directly_single_json_curly)).join(',')}
        ]
        </script>
    )
  end

  def event_multiple_schema_script(input_object_array)
    %Q(
        <script type="application/ld+json">
        [
            #{input_object_array.map(&method(:do_not_use_me_directly_single_json_curly)).join(',')}
        ]
        </script>
    )
  end

  end

Liquid::Template.register_filter(EventSchemaFilters)

然后写/_layouts/event.html (查找页面"布局,查找默认"布局)为:

---
layout: page
---

{{ page | event_single_schema_script }}

不幸的是,如果我这样编写/index.md,虽然我得到了一些即将发生的事件,但它会被<code> ... </code>标记包围并显示在主页正文中:

Unfortunately, if I write /index.md like this, while I get a nice little array of upcoming events, it renders surrounded by <code>...</code> tags and shows up in the body of the home page:

---
title: Home Page
layout: default
---

# {{ page.title }}

{{ site.events | event_multiple_schema_script }}

希望此脚本成为DOM JavaScript的一部分,而不是页面文本的一部分:

The desire is to have this script be part of the DOM's JavaScript ... not part of the text on the page:

<script type="application/ld+json">
    [
        {
            "@context" : "http://schema.org",
            "@type" : "Event",
            "name" : "An event",
            "startDate" : "2020-02-28",
            "location" : "Best Club Ever blah blah ... have address stuff to work out, still"
        }
        ,
        {
            "@context" : "http://schema.org",
            "@type" : "Event",
            "name" : "Another event",
            "startDate" : "2020-02-27",
            "location" : "Less Good Club blah blah ... have address stuff to work out, still"
        }
    ]
</script>

{{ site.events | event_multiple_schema_script }}用作/_includes/event_all_schema_script.html的内容并尝试{% include event_all_schema_script.html %}根本没有帮助-相同的问题.

Moving {{ site.events | event_multiple_schema_script }} to be the contents of /_includes/event_all_schema_script.html and trying {% include event_all_schema_script.html %} didn't help at all -- same problem.

/index.md中删除对{% include event_all_schema_script.html %}的调用,然后将其放入/_layouts/default.html中,而确实呈现了我想要的方式.但是现在它在每个页面上,包括https://example.com/events/2020-02-25-an-event/之类的页面,这不是我想要的.但这确实证明了我的问题是我写了一些我不能只是注入"某物……降价的东西……那将成为一个网页.

Removing the call to {% include event_all_schema_script.html %} from /index.md and putting it into /_layouts/default.html instead does render the way I want it to. But now it's on every page, including pages like https://example.com/events/2020-02-25-an-event/, which is not what I want. But it does demonstrate that my problem is that I wrote something I can't just "inject" into the markdown of a ... thing ... that's going to become a web page.

/index.md中也可以使用但不是我想要做的事情:

Things that also work in /index.md but aren't what I want to do:

  • 直接在其中手写<script>...</script>代码
  • {% include event_all_schema_script_hardcode.html %}放入其中,其中/_includes/event_all_schema_script_hardcode.html实际上只是从输出中复制粘贴的<script>...</script>文本,我向大家展示了.
    • 如果不是那么难找到(Jekyll文档不是很广泛; Google没用,因为静态网站生成器"一词很普遍),也许我可以编写代码,使在构建时构建这样的文件成为可能?但是,根据我目前的Jekyll/Ruby知识,这似乎是克服困难的一个很高的门槛.
    • Hand-writing <script>...</script> code straight into it
    • Putting {% include event_all_schema_script_hardcode.html %} into it, where /_includes/event_all_schema_script_hardcode.html is literally just <script>...</script> text copy-pasted from the output I showed all of you.
      • If only "generators for dummies" material weren't so hard to find (Jekyll documentation isn't very extensive; Google is useless because the phrase "static site generator" is to prevalent), maybe I could write code that would make building such a file at build-time possible? This seems like a pretty high bar to get over, though., with my current Jekyll/Ruby knowledge.

      顺便说一下,我愿意重新设计它.并没有过滤"诸如site.events之类的东西的想法.这与我进入"hello world"的程度一样.

      I'm open to re-architecting this, by the way. Not attached to the idea of "filtering" things like site.events, etc. This is just as far as I got in my "hello world."

      最终设计中我真正坚持的唯一原则:

      The only principles I'm really attached to in a final design:

      • 所有进入事件"日历的数据都应通过events集合中项目的首要事项完成(这样我就可以使用Forestry.io或Netlify CMS之类的CMS来玩得开心).
      • <script>...</script>块内容的计算应在独立的,可插入的组件"中进行.
        • 我不想在/_layouts/homepage.html内部做一个很大的Liquid循环,我不得不提醒网页设计师将其复制/粘贴到/_layouts/better_homepage.html.
        • 相反,我只想告诉一位网页设计师,嘿,如果要使页面的元数据包含事件的提要,只需将{% include event_all_schema_script.html %}放到其或其布局中的某个位置即可."
        • 我希望{% include event_all_schema_script.html %}或这里的其他等效人员帮助我,同时在页面/帖子/收藏-降价正文和布局中工作.
        • All data entry into the calendar of "events" should be done through the front matter of items in the events collection (so I can get a CMS like Forestry.io or Netlify CMS to play nice with it).
        • The computation of the contents of the <script>...</script> block should happen in an "independent, insertable component."
          • I don't want to do a big Liquid loop inside /_layouts/homepage.html that I have to remind a web designer to copy/paste into /_layouts/better_homepage.html.
          • Instead, I just want to be able to tell a web designer, "Hey, if you want to make a page's metadata include a feed of events, just drop {% include event_all_schema_script.html %} somewhere into it or its layout."
          • I want {% include event_all_schema_script.html %}, or whatever equivalent people here help me come up with, to work both in the body of pages/posts/collection-markdown and in layouts.
          • 同样,我不是网页设计师.我只是数据结构转换人员.我唯一的目标是生成漂亮的,无聊的" HTML代码段,这些代码段可供适当的Web设计人员按自己认为合适的方式进行重用和样式设置.

          是否有任何想法可以改善呈现HTML的这种尝试,使它既对布局又对Markdown友好?

          Any thoughts on how I can improve this attempt at rendering HTML so it will be both layout- and markdown-friendly?

          非常感谢.

          推荐答案

          我无法重现您的问题,但这当然是因为Kramdown可以理解任何带有四个空格缩进的行,或者更像是

          I can't reproduce your problem but it certainly comes from the fact that Kramdown understands any line with four spaces indentation or more like a standard code block.

          如果您不想处理降价文件的某些部分,则可以使用 nomarkdown扩展名像这样:

          If you don't want to process some parts of your markdown files, you can use nomarkdown extension like this :

          {::nomarkdown}  
               Any indented line or block
          {:/nomarkdown}
          

          另一种解决方法是将事件转换为html文件.

          Another workaround can be to switch to html files for your events.

          这篇关于自定义Jekyll插件(液体过滤器?)将脚本标签呈现为文本,而不是JavaScript的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆