@@ -55,7 +55,7 @@ export default class TemplateRenderer {
55
55
this . inject = options . inject !== false
56
56
// if no template option is provided, the renderer is created
57
57
// as a utility object for rendering assets like preload links and scripts.
58
-
58
+
59
59
const { template } = options
60
60
this . parsedTemplate = template
61
61
? typeof template === 'string'
@@ -156,10 +156,14 @@ export default class TemplateRenderer {
156
156
157
157
renderPreloadLinks ( context : Object ) : string {
158
158
const files = this . getPreloadFiles ( context )
159
- const shouldPreload = this . options . shouldPreload
160
159
if ( files . length ) {
161
- return files . map ( ( { file, extension, fileWithoutQuery, asType } ) => {
162
- let extra = ''
160
+ const { getPreloadLinkAttrs, shouldPreload } = this . options
161
+ const hasAttrsFn = typeof getPreloadLinkAttrs === 'function'
162
+ return files . map ( ref => {
163
+ if ( hasAttrsFn ) {
164
+ ref = getPreloadLinkAttrs ( ref )
165
+ }
166
+ const { file, extension, fileWithoutQuery, asType, attrs } = ref
163
167
// by default, we only preload scripts or css
164
168
if ( ! shouldPreload && asType !== 'script' && asType !== 'style' ) {
165
169
return ''
@@ -168,6 +172,9 @@ export default class TemplateRenderer {
168
172
if ( shouldPreload && ! shouldPreload ( fileWithoutQuery , asType ) ) {
169
173
return ''
170
174
}
175
+
176
+ let extra = attrs || ''
177
+
171
178
if ( asType === 'font' ) {
172
179
extra = ` type="font/${ extension } " crossorigin`
173
180
}
@@ -185,20 +192,26 @@ export default class TemplateRenderer {
185
192
}
186
193
187
194
renderPrefetchLinks ( context : Object ) : string {
188
- const shouldPrefetch = this . options . shouldPrefetch
195
+ const { getPrefetchLinkAttrs , shouldPrefetch } = this . options
189
196
if ( this . prefetchFiles ) {
190
197
const usedAsyncFiles = this . getUsedAsyncFiles ( context )
191
198
const alreadyRendered = file => {
192
199
return usedAsyncFiles && usedAsyncFiles . some ( f => f . file === file )
193
200
}
194
- return this . prefetchFiles . map ( ( { file, fileWithoutQuery, asType } ) => {
201
+ const hasAttrsFn = typeof getPrefetchLinkAttrs === 'function'
202
+ return this . prefetchFiles . map ( ref => {
203
+ if ( hasAttrsFn ) {
204
+ ref = getPrefetchLinkAttrs ( ref )
205
+ }
206
+ const { file, fileWithoutQuery, asType } = ref
195
207
if ( shouldPrefetch && ! shouldPrefetch ( fileWithoutQuery , asType ) ) {
196
208
return ''
197
209
}
198
210
if ( alreadyRendered ( file ) ) {
199
211
return ''
200
212
}
201
- return `<link rel="prefetch" href="${ this . publicPath } ${ file } ">`
213
+ const { attrs= 'rel="prefetch"' } = ref
214
+ return `<link ${ attrs } href="${ this . publicPath } ${ file } ">`
202
215
} ) . join ( '' )
203
216
} else {
204
217
return ''
@@ -225,8 +238,14 @@ export default class TemplateRenderer {
225
238
const initial = this . preloadFiles . filter ( ( { file } ) => isJS ( file ) )
226
239
const async = ( this . getUsedAsyncFiles ( context ) || [ ] ) . filter ( ( { file } ) => isJS ( file ) )
227
240
const needed = [ initial [ 0 ] ] . concat ( async , initial . slice ( 1 ) )
228
- return needed . map ( ( { file } ) => {
229
- return `<script src="${ this . publicPath } ${ file } " defer></script>`
241
+ const { getScriptAttrs } = this . options
242
+ const hasAttrsFn = typeof getScriptAttrs === 'function'
243
+ return needed . map ( ( ref ) => {
244
+ if ( hasAttrsFn ) {
245
+ ref = getScriptAttrs ( ref )
246
+ }
247
+ const { file, attrs = 'defer' } = ref
248
+ return `<script src="${ this . publicPath } ${ file } " ${ attrs } ></script>`
230
249
} ) . join ( '' )
231
250
} else {
232
251
return ''
0 commit comments