تأجيل تحميل جافا سكريبت في القوالب والمكونات

Thanks to @david we have a very clean pattern for “eager” loading JavaScript in themes.

This means you just put *.js.es6 files into the javascripts directory and it works exactly like plugins do, this is glorious.

For example this is how you do an initializer now, which has 100% parity with plugins:

  • Create a file called /javascripts/discourse/initializers/my-init.js.es6
import { withPluginApi } from "discourse/lib/plugin-api";

function initialize(api) {
  // init via api here
}

export default {
  name: "discourse-otp",

  initialize() {
    withPluginApi("0.8.28", initialize);
  }
};

This is an enormously important feature cause we can now split up large complex themes into a lot of pieces, get linting, syntax highlighting and all the good stuff.

However, in some cases we may want to optionally ship a JS payload.

For example, say we are decorating posts, but only posts with very specific markdown. There is no point downloading a 100KB fancy library till we know we are going to use it.

I worked around this in my component following this fancy change:

With:

import loadScript from "discourse/lib/load-script";

function generateOtp($elem) {
  loadScript(settings.theme_uploads.jsotp).then(() => {
     // stuff goes here
  });
}

This meant

  1. I needed to add .js to theme authorized extensions
  2. I needed to add a bypass to the CSP for the particular asset in content security policy script src
  3. I needed to name the asset in my about.json

As a theme component writer, this is just too much friction cause you have no chance in the distribution game requiring this level of ninja.

I am thinking to make this usable there are 2 alternatives we can pick from

  1. We can teach the system to auto CSP the .js assets in active themes and by default allow themes to upload .js

  2. We can shift towards something like javascript_cache that non defer theme js uses.

I am kind of leaning on 1 cause adding .js to theme authorized extensions seems trivial and auto CSP should not be impossible.

@pmusaraj / @Johani / @Osama any thoughts here?

10 إعجابات

The ability to reference theme uploads in JS is a great addition! :100:

This makes a lot of sense to me because anything you can do in a .js file can already be done in files in the javascripts folder of the theme. So, I don’t see any harm in allowing themes to have .js uploads by default.

7 إعجابات

إحياء هذا الموضوع لأن الشيء الوحيد المتبقي هنا هو تعليم CSP للسماح بتحميلات js الخاصة بالقالب. تم السماح افتراضيًا لملفات js كتحميلات للقالب لفترة من الوقت الآن.

إذا لم يتم حظر تحميلات js الخاصة بالقالب بواسطة CSP، فلن تحتاج المكونات مثل Image Annotator - Allows you to annotate images in the previewer إلى تحميل تبعياتها على الصفحة الرئيسية (~170 كيلوبايت مضغوط). هذا المكون، على سبيل المثال، سيحتاج فقط إلى تحميل تلك التبعيات إذا تم فتح المنشئ. بالإضافة إلى ذلك، لا يحتاج أبدًا إلى تحميلها للمشاهدين المجهولين.

أيضًا، هذا التغيير “سيسمح” للقوالب بأن تحتوي على ملفات web worker التي يمكنها القيام ببعض العمليات الثقيلة خارج الخيط الرئيسي.

السماح في علامات الاقتباس أعلاه لأنك يمكن أن تحصل عليها كـ blobs، ولكن من الأفضل بكثير أن تكون في ملفات منفصلة بدلاً من العبث بـ javascript في سلسلة نصية.

4 إعجابات

لدي بعض الأخبار السارة هنا، إنها صعبة التنفيذ بعض الشيء ولكن في النهاية سندعم أصول JavaScript المحلية للحالات التي نريد فيها استخدام عمال الويب في مكونات السمات.

لا توجد طريقة أخرى نظيفة لتمرير هذا عبر CSP، وتقديم ملفات العامل من نفس النطاق يحل الثغرة الكبيرة هنا.

3 إعجابات

ملاحظة… تم شحن هذا الآن :confetti_ball:

5 إعجابات