HTML 服务:最佳实践
使用集合让一切井井有条
根据您的偏好保存内容并对其进行分类。
使用 HTML 服务创建用户界面时,遵循的模式和实践与进行其他类型的 Web 开发时基本相同。不过,有些方面是 Apps 脚本环境所特有的,或者值得重点介绍。下面我们将介绍一些在开发自己的 HTML 服务界面时应牢记的最佳实践。
分离 HTML、CSS 和 JavaScript
将所有 HTML、CSS 和 JavaScript 代码都放在一个文件中,可能会导致项目难以阅读和开发。虽然 Apps 脚本要求将客户端代码放置在 .html 文件中,但您仍然可以将 CSS 和客户端 JavaScript 分别放置在不同的文件中,然后使用自定义函数将它们包含在主 HTML 页面中。
以下示例在 Code.gs 文件中定义了一个自定义服务器端 include()
函数,用于将 Stylesheet.html 和 JavaScript.html 文件内容导入到 Page.html 文件中。使用打印 scriptlet 调用时,此函数会将指定的文件内容导入到当前文件中。请注意,包含的文件包含 <style>
和 <script>
标记,因为它们是 HTML 代码段,而不是纯 .css 或 .js 文件。
Code.gs
function doGet(request) {
return HtmlService.createTemplateFromFile('Page')
.evaluate();
}
function include(filename) {
return HtmlService.createHtmlOutputFromFile(filename)
.getContent();
}
Page.html
<!DOCTYPE html>
<html>
<head>
<base target="_top">
<?!= include('Stylesheet'); ?>
</head>
<body>
<h1>Welcome</h1>
<p>Please enjoy this helpful script.</p>
<?!= include('JavaScript'); ?>
</body>
</html>
Stylesheet.html
<style>
p {
color: green;
}
</style>
JavaScript.html
<script>
window.addEventListener('load', function() {
console.log('Page is loaded');
});
</script>
异步加载数据,而不是在模板中加载
模板化 HTML 可用于快速构建简单界面,但应限制其使用,以确保界面具有自适应性。模板中的代码在网页加载时执行一次,并且在处理完成之前不会向客户端发送任何内容。在 scriptlet 代码中执行长时间运行的任务可能会导致界面显得缓慢。
使用 scriptlet 标记可快速完成一次性任务,例如包含其他内容或设置静态值。所有其他数据都应使用 google.script.run
调用加载。以这种异步方式进行编码难度更大,但可让界面加载速度更快,并有机会向用户显示微调框或其他加载消息。
不要 - 加载到模板中
<p>List of things:</p>
<? var things = getLotsOfThings(); ?>
<ul>
<? for (var i = 0; i < things.length; i++) { ?>
<li><?= things[i] ?></li>
<? } ?>
</ul>
正确做法 - 异步加载
<p>List of things:</p>
<ul id="things">
<li>Loading...</li>
</ul>
<script
src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js">
</script>
<script>
// The code in this function runs when the page is loaded.
$(function() {
google.script.run.withSuccessHandler(showThings)
.getLotsOfThings();
});
function showThings(things) {
var list = $('#things');
list.empty();
for (var i = 0; i < things.length; i++) {
list.append('<li>' + things[i] + '</li>');
}
}
</script>
使用 HTTPS 加载资源
如果您的网页采用较新的 IFRAME
沙盒模式,那么包含未使用 HTTPS 提供的 JavaScript 或 CSS 文件会导致出现如下错误。
混合内容:网页“https://...”是通过 HTTPS 加载的,但请求了不安全的脚本“http://...”。此请求已被屏蔽;内容必须通过 HTTPS 提供。
大多数热门库都支持 HTTP 和 HTTPS,因此切换通常只需在网址中插入一个额外的“s”。
使用 HTML5 文档类型声明
如果您的网页是使用较新的 IFRAME
沙盒模式提供的,请务必在 HTML 文件顶部添加以下代码段。
<!DOCTYPE html>
此文档类型声明会告知浏览器,您设计的网页适用于现代浏览器,因此浏览器不应使用怪异模式呈现您的网页。即使您不打算利用现代 HTML5 元素或 JavaScript API,此操作也有助于确保网页正确显示。
最后加载 JavaScript
许多 Web 开发者建议在网页底部加载 JavaScript 代码,以提高响应速度,对于 HTML 服务而言,这一点尤为重要。将 <script>
代码移至网页末尾,可让 HTML 内容在 JavaScript 处理之前呈现,从而让您向用户显示微调框或其他消息。
利用 jQuery
jQuery 是一种热门的 JavaScript 库,可简化 Web 开发中的许多常见任务。
如未另行说明,那么本页面中的内容已根据知识共享署名 4.0 许可获得了许可,并且代码示例已根据 Apache 2.0 许可获得了许可。有关详情,请参阅 Google 开发者网站政策。Java 是 Oracle 和/或其关联公司的注册商标。
最后更新时间 (UTC):2025-08-31。
[null,null,["最后更新时间 (UTC):2025-08-31。"],[[["\u003cp\u003eSeparate your HTML, CSS, and JavaScript into different files for better organization and readability, using a custom server-side function to include them in the main HTML.\u003c/p\u003e\n"],["\u003cp\u003eLoad data asynchronously using \u003ccode\u003egoogle.script.run\u003c/code\u003e to keep the UI responsive and avoid delays caused by long-running tasks in templates.\u003c/p\u003e\n"],["\u003cp\u003eEnsure all resources are loaded over HTTPS to prevent mixed content errors, especially in sandbox mode.\u003c/p\u003e\n"],["\u003cp\u003eUtilize the HTML5 document type declaration (\u003ccode\u003e<!DOCTYPE html>\u003c/code\u003e) to ensure your page is rendered correctly in modern browsers.\u003c/p\u003e\n"],["\u003cp\u003eLoad JavaScript code at the end of your page to prioritize HTML content rendering and improve perceived performance.\u003c/p\u003e\n"]]],[],null,["# HTML Service: Best Practices\n\nCreating user interfaces with the HTML service follows many of the same patterns\nand practices as other types of web development. However, there are some aspects\nthat are unique to the Apps Script environment or are otherwise worth\nhighlighting. Below we'll cover some best practices you should keep in mind when\ndeveloping your own HTML-service UIs.\n\nSeparate HTML, CSS, and JavaScript\n----------------------------------\n\nKeeping all the HTML, CSS, and JavaScript code in one file can make your project\ndifficult to read and develop. While Apps Script does require client-side code\nto be placed in .html files, you can still separate your CSS and client-side\nJavaScript into different files and then include them in the main HTML page\nwith a custom function.\n\nThe example below defines a custom server-side `include()` function in the\nCode.gs file to import the Stylesheet.html and JavaScript.html file content\ninto the Page.html file. When called using\n[printing scriptlets](/apps-script/guides/html/templates#printing_scriptlets),\nthis function imports the specified file content into the current file. Notice\nthat the included files contain `\u003cstyle\u003e` and `\u003cscript\u003e` tags because\nthey're HTML snippets and not pure .css or .js files. \n\n### Code.gs\n\n```html\nfunction doGet(request) {\n return HtmlService.createTemplateFromFile('Page')\n .evaluate();\n}\n\nfunction include(filename) {\n return HtmlService.createHtmlOutputFromFile(filename)\n .getContent();\n}\n```\n\n### Page.html\n\n```html\n\u003c!DOCTYPE html\u003e\n\u003chtml\u003e\n \u003chead\u003e\n \u003cbase target=\"_top\"\u003e\n \u003c?!= include('Stylesheet'); ?\u003e\n \u003c/head\u003e\n \u003cbody\u003e\n \u003ch1\u003eWelcome\u003c/h1\u003e\n \u003cp\u003ePlease enjoy this helpful script.\u003c/p\u003e\n \u003c?!= include('JavaScript'); ?\u003e\n \u003c/body\u003e\n\u003c/html\u003e\n```\n\n### Stylesheet.html\n\n```html\n\u003cstyle\u003e\np {\n color: green;\n}\n\u003c/style\u003e\n```\n\n### JavaScript.html\n\n```html\n\u003cscript\u003e\nwindow.addEventListener('load', function() {\n console.log('Page is loaded');\n});\n\u003c/script\u003e\n```\n\nLoad data asynchronously, not in templates\n------------------------------------------\n\n[Templated HTML](/apps-script/guides/html/templates) can be used to quickly\nbuild simple interfaces, but its use should be limited to ensure your UI is\nresponsive. The code in templates is executed once when the page is loaded, and\nno content is sent to the client until the processing is complete. Having\nlong-running tasks in your scriptlet code can cause your UI to appear slow.\n\nUse scriptlet tags for quick, one-time tasks such as including other content\nor setting static values. All other data should be loaded using\n[`google.script.run`](/apps-script/guides/html/communication) calls.\nCoding in this asynchronous manner is more difficult but allows the UI to load\nmore quickly and gives it the opportunity to present a spinner or other\nloading message to the user.\n\nDon't --- load in templates \n\n```html\n\u003cp\u003eList of things:\u003c/p\u003e\n\u003c? var things = getLotsOfThings(); ?\u003e\n\u003cul\u003e\n \u003c? for (var i = 0; i \u003c things.length; i++) { ?\u003e\n \u003cli\u003e\u003c?= things[i] ?\u003e\u003c/li\u003e\n \u003c? } ?\u003e\n\u003c/ul\u003e\n```\n\nDo --- load asynchronously \n\n```html\n\u003cp\u003eList of things:\u003c/p\u003e\n\u003cul id=\"things\"\u003e\n \u003cli\u003eLoading...\u003c/li\u003e\n\u003c/ul\u003e\n\n\u003cscript\nsrc=\"//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js\"\u003e\n\u003c/script\u003e\n\u003cscript\u003e\n// The code in this function runs when the page is loaded.\n$(function() {\n google.script.run.withSuccessHandler(showThings)\n .getLotsOfThings();\n});\n\nfunction showThings(things) {\n var list = $('#things');\n list.empty();\n for (var i = 0; i \u003c things.length; i++) {\n list.append('\u003cli\u003e' + things[i] + '\u003c/li\u003e');\n }\n}\n\u003c/script\u003e\n```\n\nLoad resources using HTTPS\n--------------------------\n\nIf your page is served using the newer `IFRAME`\n[sandbox mode](/apps-script/guides/html/restrictions#sandbox_mode), including\nJavaScript or CSS files not served using HTTPS will result in errors like the\none below.\n\u003e Mixed Content: The page at 'https://...' was loaded over HTTPS, but\n\u003e requested an insecure script 'http://...'. This request has been blocked;\n\u003e the content must be served over HTTPS.\n\nMost popular libraries support both HTTP and HTTPS, so switching is usually\njust a matter of inserting an addition 's' into the URL.\n\nUse the HTML5 document type declaration\n---------------------------------------\n\nIf your page is served using the newer `IFRAME`\n[sandbox mode](/apps-script/guides/html/restrictions#sandbox_mode), make sure\nto include the following snippet of code at the top of your HTML file. \n\n \u003c!DOCTYPE html\u003e\n\nThis document type declations tells the browser that you designed the page for\nmodern browsers, and that it shouldn't render your page using\n[quirks mode](http://en.wikipedia.org/wiki/Quirks_mode). Even if you don't plan\nto take advantage of modern HTML5 elements or JavaScript APIs, this will help\nensure your page is displayed correctly.\n\nLoad JavaScript last\n--------------------\n\nMany web developers recommend loading JavaScript code at the bottom of the page\nto increase responsiveness, and this is even more important with the HTML\nservice. Moving your `\u003cscript\u003e` tags to the end of your page will let HTML\ncontent render before the JavaScript is processed, allowing you to present a\nspinner or other message to the user.\n\nTake advantage of jQuery\n------------------------\n\n[jQuery](http://jquery.com/) is a popular JavaScript library that simplifies\nmany common tasks in web development."]]