* @param {{body: string, css?: string|undefined, extensions: Array |undefined, head?: string|undefined, spec?: string|undefined, mode?: string|undefined}} config * @return {string}
(config)
| 220 | * @return {string} |
| 221 | */ |
| 222 | function composeDocument(config) { |
| 223 | const {body, css, extensions, head, mode, spec} = config; |
| 224 | |
| 225 | const m = mode || SERVE_MODE; |
| 226 | const cdn = m === 'cdn'; |
| 227 | const minified = m === 'minified'; |
| 228 | |
| 229 | const cssTag = css ? `<style amp-custom>${css}</style>` : ''; |
| 230 | |
| 231 | // Set link[rel=canonical], CSS boilerplate and runtime <script> depending |
| 232 | // on the AMP spec. |
| 233 | let canonical, boilerplate, runtime; |
| 234 | const amp = spec || 'amp'; |
| 235 | switch (amp) { |
| 236 | case 'amp': |
| 237 | canonical = '<link rel="canonical" href="http://nonblocking.io" />'; |
| 238 | boilerplate = |
| 239 | '<style amp-boilerplate>body{-webkit-animation:-amp-start 8s steps(1,end) 0s 1 normal both;-moz-animation:-amp-start 8s steps(1,end) 0s 1 normal both;-ms-animation:-amp-start 8s steps(1,end) 0s 1 normal both;animation:-amp-start 8s steps(1,end) 0s 1 normal both}@-webkit-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@-moz-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@-ms-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@-o-keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}@keyframes -amp-start{from{visibility:hidden}to{visibility:visible}}</style><noscript><style amp-boilerplate>body{-webkit-animation:none;-moz-animation:none;-ms-animation:none;animation:none}</style></noscript>'; |
| 240 | runtime = cdn |
| 241 | ? 'https://cdn.ampproject.org/v0.js' |
| 242 | : `/dist/${minified ? 'v0' : 'amp'}.js`; |
| 243 | break; |
| 244 | case 'amp4ads': |
| 245 | canonical = ''; |
| 246 | boilerplate = |
| 247 | '<style amp4ads-boilerplate>body{visibility:hidden}</style>'; |
| 248 | runtime = cdn |
| 249 | ? 'https://cdn.ampproject.org/amp4ads-v0.js' |
| 250 | : `/dist/${minified ? 'amp4ads-v0' : 'amp-inabox'}.js`; |
| 251 | break; |
| 252 | case 'amp4email': |
| 253 | canonical = ''; |
| 254 | boilerplate = |
| 255 | '<style amp4email-boilerplate>body{visibility:hidden}</style>'; |
| 256 | runtime = cdn |
| 257 | ? 'https://cdn.ampproject.org/v0.js' |
| 258 | : `/dist/${minified ? 'v0' : 'amp'}.js`; |
| 259 | break; |
| 260 | default: |
| 261 | throw new Error('Unrecognized AMP spec: ' + spec); |
| 262 | } |
| 263 | const runtimeScript = `<script async src="${runtime}"></script>`; |
| 264 | |
| 265 | // Generate extension <script> markup. |
| 266 | let extensionScripts = ''; |
| 267 | if (extensions) { |
| 268 | extensionScripts = extensions |
| 269 | .map((extension) => { |
| 270 | const tuple = extension.split(':'); |
| 271 | const name = tuple[0]; |
| 272 | const version = tuple[1] || '0.1'; |
| 273 | const src = cdn |
| 274 | ? `https://cdn.ampproject.org/v0/${name}-${version}.js` |
| 275 | : `/dist/v0/${name}-${version}.${minified ? '' : 'max.'}js`; |
| 276 | const type = CUSTOM_TEMPLATES.includes(name) |
| 277 | ? 'custom-template' |
| 278 | : 'custom-element'; |
| 279 | return `<script async ${type}="${name}" src="${src}"></script>`; |
no test coverage detected