chore(ts): fix types in renderer (#16)

This commit is contained in:
Xin Du (Clark) 2020-08-12 11:00:47 +01:00 committed by GitHub
parent d6ae2c73d9
commit b82d75d883
9 changed files with 44 additions and 14 deletions

View File

@ -5,7 +5,7 @@ type Plugin = string | { mode?: 'all' | 'client' | 'server', src: string, ssr?:
interface AppOptions {
css: string[]
head: MetaInfo
head: MetaInfo | (() => MetaInfo)
ErrorPage: null | string
extendPlugins: null | ((plugins: Plugin[]) => Plugin[])
features: {

View File

@ -108,7 +108,7 @@ interface CommonConfiguration {
ignore: Array<string | IgnoreInstance>
// TODO: remove in Nuxt 3
mode: Mode
modern?: boolean
modern?: boolean | 'client' | 'server'
modules: NuxtModule[]
privateRuntimeConfig: Record<string, any> | ((env: NodeJS.ProcessEnv) => Record<string, any>)
publicRuntimeConfig: Record<string, any> | ((env: NodeJS.ProcessEnv) => Record<string, any>)

View File

@ -27,7 +27,7 @@ type CspPolicyName = 'child-src' | 'connect-src' | 'default-src' | 'font-src' |
interface RenderOptions {
bundleRenderer: {
shouldPrefetch: () => boolean
shouldPrefetch: (fileWithoutQuery: string, asType: string) => boolean
shouldPreload: (fileWithoutQuery: string, asType: string) => boolean
runInNewContext?: boolean
}
@ -63,6 +63,7 @@ interface RenderOptions {
preloadFiles: PreloadFile[]
) => string[])
}
injectScripts?: boolean
resourceHints: boolean
ssr?: boolean
ssrLog?: boolean | 'collapsed'

View File

@ -21,6 +21,8 @@ import createTimingMiddleware from './middleware/timing'
interface Manifest {
assetsMapping: Record<string, string[]>
publicPath: string
initial: Array<string>
async: Array<string>
}
export default class Server {
@ -37,6 +39,7 @@ export default class Server {
renderer: VueRenderer
resources: {
clientManifest?: Manifest
loadingHTML?: string
modernManifest?: Manifest
serverManifest?: Manifest
ssrTemplate?: TemplateExecutor

View File

@ -65,7 +65,7 @@ export const isModernBrowser = (ua: string) => {
)
}
export const isModernRequest = (req: NuxtRequest, modernMode = false) => {
export const isModernRequest = (req: NuxtRequest, modernMode: boolean | string = false) => {
if (modernMode === false) {
return false
}

View File

@ -2,19 +2,37 @@ import path from 'path'
import fs from 'fs-extra'
import consola from 'consola'
import template from 'lodash/template'
import { TARGETS, isModernRequest, waitFor } from 'src/utils'
import { Target, TARGETS, isModernRequest, waitFor } from 'src/utils'
import ServerContext from 'src/server/context'
import SPARenderer from './renderers/spa'
import SSRRenderer from './renderers/ssr'
import ModernRenderer from './renderers/modern'
declare module 'fs-extra' {
export function exists(path: string): Promise<boolean>;
}
export interface RenderContext {
target?: Target
spa?: boolean
modern?: boolean
req?: any
res?: any
runtimeConfig?: {
private: ServerContext['options']['privateRuntimeConfig'],
public: ServerContext['options']['publicRuntimeConfig']
}
url?: string
}
export default class VueRenderer {
__closed?: boolean
_state?: 'created' | 'loading' | 'ready' | 'error'
_error?: null
_readyPromise?: Promise<any>
distPath: string
options: ServerContext['options']
serverContext: ServerContext
renderer: {
ssr: any
@ -252,7 +270,7 @@ export default class VueRenderer {
return renderer.render(renderContext)
}
async renderRoute (url, renderContext = {}, _retried = 0) {
async renderRoute (url, renderContext : RenderContext = {}, _retried = 0) {
/* istanbul ignore if */
if (!this.isReady) {
// Fall-back to loading-screen if enabled

View File

@ -1,4 +1,5 @@
import ServerContext from 'nuxt/server/context'
import ServerContext from 'src/server/context'
import { RenderContext } from '../renderer'
export default class BaseRenderer {
serverContext: ServerContext
@ -18,7 +19,7 @@ export default class BaseRenderer {
return templateFn(opts)
}
render (renderContext) {
render (_renderContext: RenderContext) {
throw new Error('`render()` needs to be implemented')
}
}

View File

@ -37,7 +37,7 @@ export default class SPARenderer extends BaseRenderer {
const modernMode = this.options.modern
const modern = (modernMode && this.options.target === TARGETS.static) || isModernRequest(req, modernMode)
const cacheKey = `${modern ? 'modern:' : 'legacy:'}${url}`
let meta = this.cache.get(cacheKey)
let meta : Record<string, any> = this.cache.get(cacheKey)
if (meta) {
// Return a copy of the content, so that future
@ -127,7 +127,7 @@ export default class SPARenderer extends BaseRenderer {
.map(file => ({ ...file, modern }))
meta.resourceHints += meta.preloadFiles
.map(({ file, extension, fileWithoutQuery, asType, modern }) => {
.map(({ file, extension, asType, modern }) => {
let extra = ''
if (asType === 'font') {
extra = ` type="font/${extension}"${cors ? '' : ' crossorigin'}`

View File

@ -11,6 +11,8 @@ import ServerContext from 'src/server/context'
import BaseRenderer from './base'
export default class SSRRenderer extends BaseRenderer {
vueRenderer: typeof import('@vue/server-renderer')
constructor (serverContext: ServerContext) {
super(serverContext)
this.createRenderer()
@ -170,9 +172,14 @@ export default class SSRRenderer extends BaseRenderer {
}
const { csp } = this.options.render
// Only add the hash if 'unsafe-inline' rule isn't present to avoid conflicts (#5387)
const containsUnsafeInlineScriptSrc = csp.policies && csp.policies['script-src'] && csp.policies['script-src'].includes('\'unsafe-inline\'')
const shouldHashCspScriptSrc = csp && (csp.unsafeInlineCompatibility || !containsUnsafeInlineScriptSrc)
let shouldHashCspScriptSrc = false
if (typeof csp === 'object') {
const { policies, unsafeInlineCompatibility } = csp
shouldHashCspScriptSrc = unsafeInlineCompatibility ||
// Only add the hash if 'unsafe-inline' rule isn't present to avoid conflicts (#5387)
!(policies && policies['script-src'] && policies['script-src'].includes('\'unsafe-inline\''))
}
const inlineScripts = []
if (renderContext.staticAssetsBase) {
@ -228,7 +235,7 @@ export default class SSRRenderer extends BaseRenderer {
// Calculate CSP hashes
const cspScriptSrcHashes = []
if (csp) {
if (typeof csp === 'object') {
if (shouldHashCspScriptSrc) {
for (const script of inlineScripts) {
const hash = crypto.createHash(csp.hashAlgorithm)