perf(comments): 评论加载提速 + 骨架屏 + 友链弹窗 pjax 修复 + toast 统一 Message.js
优化: - initArtalk 加节点级幂等守卫(mount.__atkInited,失败回滚), 消除 artalk.html/mypjax 多入口导致的 4× comments + 4× pv 重复请求 - fetch 包装层对无 body 的 GET/HEAD 去掉多余 content-type, 消掉 Artalk 对 GET /comments 的 CORS 预检(按完整 URL 缓存, 每篇文章都重付一次 RTT)。实测评论列表 +1150~1565ms → +626ms 修复: - 评论列表骨架屏改注入 .atk-list-body(原骨架在 #Comments 内, 被 Artalk.init 清空),list-loaded/故障/12s 兜底移除 - 友链申请弹窗抽成 modules/friendlink.js 进 page-only bundle (原内联脚本在 #pjax-container 外,pjax 后 flApplyOpenModal 未定义) - toast 统一走本地化 Message.js/Qmsg 适配层(保留 window.Toast/showToast 旧 API) 文档: - README / 架构总览 更新;新增 评论加载优化方案.md
This commit is contained in:
1 parent
9e972f2b61
commit
50a906e07c
14 files changed
+1018
-486
No files matched your search
@@ -229,6 +229,16 @@
|
||||
</div>
|
||||
<!-- JS -->
|
||||
<!-- <script src="/js/Artalk.js"></script> -->
|
||||
<!-- ── /api/v2/conf 内联快照 ─────────────────────────────────────────────
|
||||
构建期由 .cnb.yml 拉一次 /api/v2/conf 落到 data/artalk_conf.json,这里原样内联。
|
||||
artalk.js 对匿名 /conf 请求直接本地合成响应,省掉一次跨境 RTT ——
|
||||
Artalk 内部 conf 与评论列表是「严格串行」的,去掉这一跳首屏即少一整个往返。
|
||||
文件不存在时(本地预览 / 拉取失败)不输出,前端自动回退到远程请求。 -->
|
||||
{{ with site.Data.artalk_conf }}
|
||||
{{- $snapJson := . | jsonify }}
|
||||
{{- $snapJson = replace $snapJson "</" "<\\/" }}
|
||||
<script>window.__artalkConfSnapshot = {{ $snapJson | safeJS }};</script>
|
||||
{{ end }}
|
||||
<script>
|
||||
// Configuration for Artalk and AI Comment
|
||||
window.artalkConfig = {
|
||||
|
||||
@@ -53,6 +53,9 @@
|
||||
{{ $iconfont := resources.Get "js/libs/iconfont.js" }}
|
||||
{{ $uikit := resources.Get "js/libs/uikit.min.js" }}
|
||||
{{ $viewimage := resources.Get "js/libs/view-image.min.js" }}
|
||||
{{/* Message.js(Qmsg)+ Toast 适配层放在 utils 之前,保证任何 toast 调用点执行时组件已就绪 */}}
|
||||
{{ $message := resources.Get "js/libs/message.min.js" }}
|
||||
{{ $toast := resources.Get "js/modules/toast.js" }}
|
||||
{{ $utils := resources.Get "js/modules/utils.js" }}
|
||||
{{ $loader := resources.Get "js/modules/loader.js" }}
|
||||
{{ $cache := resources.Get "js/modules/cache.js" }}
|
||||
@@ -67,7 +70,7 @@
|
||||
{{ $lazyload := resources.Get "js/modules/lazyload.js" }}
|
||||
{{ $main := resources.Get "js/main.js" }}
|
||||
|
||||
{{ $coreScripts := slice $iconfont $uikit $viewimage $utils $loader $cache $search $floatingTools $nprogress $pjaxLib $mypjax $pangu $linkify $shortcodesJs $lazyload $main | resources.Concat "js/core.js" | resources.Minify | resources.Fingerprint }}
|
||||
{{ $coreScripts := slice $iconfont $uikit $viewimage $message $toast $utils $loader $cache $search $floatingTools $nprogress $pjaxLib $mypjax $pangu $linkify $shortcodesJs $lazyload $main | resources.Concat "js/core.js" | resources.Minify | resources.Fingerprint }}
|
||||
|
||||
<script defer src="{{ $coreScripts.RelPermalink }}"></script>
|
||||
|
||||
@@ -136,21 +139,24 @@
|
||||
|
||||
{{/* 文章详情页专用JS */}}
|
||||
{{ if .IsPage }}
|
||||
{{/* 友链申请弹窗放最前:artalk.js 渲染申请卡片时会调 window.flApplyOpenModal */}}
|
||||
{{ $friendlink := resources.Get "js/modules/friendlink.js" }}
|
||||
{{ $artalkModule := resources.Get "js/modules/artalk.js" }}
|
||||
{{ $paragraphComments := resources.Get "js/modules/paragraph-comments.js" }}
|
||||
{{ $reward := resources.Get "js/modules/reward.js" }}
|
||||
|
||||
{{ $pageScripts := slice $artalkModule $paragraphComments $reward | resources.Concat "js/page-only.js" | resources.Minify | resources.Fingerprint }}
|
||||
{{ $pageScripts := slice $friendlink $artalkModule $paragraphComments $reward | resources.Concat "js/page-only.js" | resources.Minify | resources.Fingerprint }}
|
||||
|
||||
<script defer src="{{ $pageScripts.RelPermalink }}"></script>
|
||||
<script>window._pageOnlyScriptUrl = '{{ $pageScripts.RelPermalink }}';</script>
|
||||
{{ else }}
|
||||
{{/* 非文章页面:仍然计算URL,但不加载,用于PJAX动态加载 */}}
|
||||
{{ $friendlink := resources.Get "js/modules/friendlink.js" }}
|
||||
{{ $artalkModule := resources.Get "js/modules/artalk.js" }}
|
||||
{{ $paragraphComments := resources.Get "js/modules/paragraph-comments.js" }}
|
||||
{{ $reward := resources.Get "js/modules/reward.js" }}
|
||||
|
||||
{{ $pageScripts := slice $artalkModule $paragraphComments $reward | resources.Concat "js/page-only.js" | resources.Minify | resources.Fingerprint }}
|
||||
{{ $pageScripts := slice $friendlink $artalkModule $paragraphComments $reward | resources.Concat "js/page-only.js" | resources.Minify | resources.Fingerprint }}
|
||||
|
||||
<script>window._pageOnlyScriptUrl = '{{ $pageScripts.RelPermalink }}';</script>
|
||||
{{ end }}
|
||||
@@ -169,31 +175,7 @@
|
||||
<script defer src="{{ $tiaozhuan.RelPermalink }}"></script>
|
||||
{{ end }}
|
||||
|
||||
{{/* ====== 5. 延迟加载的非关键JS ====== */}}
|
||||
{{ $toast := resources.Get "js/modules/toast.js" }}
|
||||
|
||||
{{ $deferredScripts := slice $toast | resources.Concat "js/deferred.js" | resources.Minify | resources.Fingerprint }}
|
||||
|
||||
<script>
|
||||
// 使用requestIdleCallback在浏览器空闲时加载
|
||||
if ('requestIdleCallback' in window) {
|
||||
requestIdleCallback(function() {
|
||||
var script = document.createElement('script');
|
||||
script.src = '{{ $deferredScripts.RelPermalink }}';
|
||||
script.defer = true;
|
||||
document.body.appendChild(script);
|
||||
});
|
||||
} else {
|
||||
setTimeout(function() {
|
||||
var script = document.createElement('script');
|
||||
script.src = '{{ $deferredScripts.RelPermalink }}';
|
||||
script.defer = true;
|
||||
document.body.appendChild(script);
|
||||
}, 1000);
|
||||
}
|
||||
</script>
|
||||
|
||||
{{/* ====== 6. 第三方脚本 ====== */}}
|
||||
{{/* ====== 5. 第三方脚本 ====== */}}
|
||||
<script async src="/js/bsz.js"></script>
|
||||
</body>
|
||||
|
||||
|
||||
@@ -42,7 +42,17 @@
|
||||
<link rel="icon" type="image/x-icon" href="/favicon.ico">
|
||||
<!-- Resource Hints -->
|
||||
<link rel="preconnect" href="https://cravatar.cn">
|
||||
{{ with site.Params.rssapi.base }}<link rel="preconnect" href="{{ . }}">{{ end }}
|
||||
{{- /* 评论 / RSS API:Artalk 与友链数据都发 CORS 跨域请求。
|
||||
preconnect 必须带 crossorigin —— 浏览器对「带凭据」和「匿名」两条连接分池,
|
||||
不带 crossorigin 预热的连接 CORS 请求无法复用,等于白预连(net::ERR 之外
|
||||
还要重付一次 DNS + TCP + TLS)。dns-prefetch 兜底不支持 preconnect 的浏览器。 */ -}}
|
||||
{{- $apiHosts := slice -}}
|
||||
{{- with site.Params.artalk.server }}{{ $apiHosts = $apiHosts | append (strings.TrimSuffix "/" .) }}{{ end -}}
|
||||
{{- with site.Params.rssapi.base }}{{ $apiHosts = $apiHosts | append (strings.TrimSuffix "/" .) }}{{ end -}}
|
||||
{{- range ($apiHosts | uniq) }}
|
||||
<link rel="preconnect" href="{{ . }}" crossorigin>
|
||||
<link rel="dns-prefetch" href="{{ . }}">
|
||||
{{- end }}
|
||||
{{ with site.Params.rssapi.base }}<script>window.rssApiBase = "{{ . }}";</script>{{ end }}
|
||||
<link rel="dns-prefetch" href="https://bsz.dusays.com:9001">
|
||||
<!-- Analytics -->
|
||||
|
||||
Reference in new issue
Block a user