refactor: addResource compiler method
This commit is contained in:
+54
-32
@@ -5,7 +5,7 @@ import { createReadStream } from 'fs'
|
||||
import { Readable } from 'stream'
|
||||
import { spawn } from 'child_process'
|
||||
import { Logger } from './logger'
|
||||
import { readFileAsync, writeFileAsync, pathExistsAsync, dequote, isWindows } from './util'
|
||||
import { readFileAsync, writeFileAsync, pathExistsAsync, dequote, isWindows, bound } from './util'
|
||||
import { NexeOptions, nexeVersion } from './options'
|
||||
import { NexeTarget } from './target'
|
||||
import download = require('download')
|
||||
@@ -34,19 +34,16 @@ export class NexeCompiler {
|
||||
public log = new Logger(this.options.loglevel)
|
||||
public src: string
|
||||
public files: NexeFile[] = []
|
||||
public shims: string[] = []
|
||||
public input: string
|
||||
public bundledInput?: string
|
||||
public output: string | null
|
||||
public targets: NexeTarget[]
|
||||
public target: NexeTarget
|
||||
public resources: { bundle: string; index: { [key: string]: number[] } } = {
|
||||
public resources: { bundle: Buffer; index: { [key: string]: number[] } } = {
|
||||
index: {},
|
||||
bundle: ''
|
||||
bundle: Buffer.from('')
|
||||
}
|
||||
public readFileAsync: (file: string) => Promise<NexeFile>
|
||||
public writeFileAsync: (file: string, contents: Buffer | string) => Promise<void>
|
||||
public replaceInFileAsync: (file: string, replacer: any, replaceValue: string) => Promise<void>
|
||||
public setFileContentsAsync: (file: string, contents: string | Buffer) => Promise<void>
|
||||
private nodeSrcBinPath: string
|
||||
|
||||
constructor(public options: NexeOptions) {
|
||||
@@ -65,32 +62,50 @@ export class NexeCompiler {
|
||||
this.env.PYTHON = python
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
this.readFileAsync = async (file: string) => {
|
||||
let cachedFile = this.files.find(x => normalize(x.filename) === normalize(file))
|
||||
if (!cachedFile) {
|
||||
const absPath = join(this.src, file)
|
||||
cachedFile = {
|
||||
absPath,
|
||||
filename: file,
|
||||
contents: await readFileAsync(absPath, 'utf-8').catch(x => {
|
||||
if (x.code === 'ENOENT') return ''
|
||||
throw x
|
||||
})
|
||||
}
|
||||
this.files.push(cachedFile)
|
||||
@bound
|
||||
addResource(file: string, contents: Buffer) {
|
||||
const { resources } = this
|
||||
resources.index[file] = [resources.bundle.byteLength, contents.byteLength]
|
||||
resources.bundle = Buffer.concat([resources.bundle, contents])
|
||||
}
|
||||
|
||||
@bound
|
||||
async readFileAsync(file: string) {
|
||||
this.assertBuild()
|
||||
let cachedFile = this.files.find(x => normalize(x.filename) === normalize(file))
|
||||
if (!cachedFile) {
|
||||
const absPath = join(this.src, file)
|
||||
cachedFile = {
|
||||
absPath,
|
||||
filename: file,
|
||||
contents: await readFileAsync(absPath, 'utf-8').catch(x => {
|
||||
if (x.code === 'ENOENT') return ''
|
||||
throw x
|
||||
})
|
||||
}
|
||||
return cachedFile
|
||||
}
|
||||
this.writeFileAsync = (file, contents) => writeFileAsync(join(this.src, file), contents)
|
||||
this.replaceInFileAsync = async (file, replace: string | RegExp, value: string) => {
|
||||
const entry = await this.readFileAsync(file)
|
||||
entry.contents = entry.contents.replace(replace, value)
|
||||
}
|
||||
this.setFileContentsAsync = async (file: string, contents: string) => {
|
||||
const entry = await this.readFileAsync(file)
|
||||
entry.contents = contents
|
||||
this.files.push(cachedFile)
|
||||
}
|
||||
return cachedFile
|
||||
}
|
||||
|
||||
@bound
|
||||
writeFileAsync(file: string, contents: string | Buffer) {
|
||||
this.assertBuild()
|
||||
return writeFileAsync(join(this.src, file), contents)
|
||||
}
|
||||
|
||||
@bound
|
||||
async replaceInFileAsync(file: string, replace: string | RegExp, value: string) {
|
||||
const entry = await this.readFileAsync(file)
|
||||
entry.contents = entry.contents.replace(replace, value)
|
||||
}
|
||||
|
||||
@bound
|
||||
async setFileContentsAsync(file: string, contents: string) {
|
||||
const entry = await this.readFileAsync(file)
|
||||
entry.contents = contents
|
||||
}
|
||||
|
||||
quit() {
|
||||
@@ -99,6 +114,12 @@ export class NexeCompiler {
|
||||
return this.log.flush()
|
||||
}
|
||||
|
||||
assertBuild() {
|
||||
if (!this.options.build) {
|
||||
throw new Error('This feature is only available with `--build`')
|
||||
}
|
||||
}
|
||||
|
||||
public getNodeExecutableLocation(target?: NexeTarget) {
|
||||
if (target) {
|
||||
return join(this.options.temp, target.toString())
|
||||
@@ -217,12 +238,13 @@ export class NexeCompiler {
|
||||
artifact.push(chunk)
|
||||
})
|
||||
binary.on('close', () => {
|
||||
const content = this._serializeHeader(header) + this.input
|
||||
const content = this._serializeHeader(header) + this.shims.join(';') + ';' + this.input
|
||||
|
||||
artifact.push(content)
|
||||
artifact.push(this.resources.bundle)
|
||||
const lengths = Buffer.from(Array(16))
|
||||
lengths.writeDoubleLE(Buffer.byteLength(content), 0)
|
||||
lengths.writeDoubleLE(Buffer.byteLength(this.resources.bundle), 8)
|
||||
lengths.writeDoubleLE(this.resources.bundle.byteLength, 8)
|
||||
artifact.push(Buffer.concat([Buffer.from('<nexe~~sentinel>'), lengths]))
|
||||
artifact.push(null)
|
||||
})
|
||||
|
||||
+13
-6
@@ -148,10 +148,6 @@ function tryResolveMainFileName(cwd: string) {
|
||||
filename = basename(file).replace(extname(file), '')
|
||||
} catch (_) {}
|
||||
|
||||
if (filename === 'index' && basename(cwd)) {
|
||||
return basename(cwd)
|
||||
}
|
||||
|
||||
return filename ? filename : 'nexe_' + Date.now()
|
||||
}
|
||||
|
||||
@@ -162,12 +158,23 @@ function extractLogLevel(options: NexeOptions) {
|
||||
return 'info'
|
||||
}
|
||||
|
||||
function isName(name: string) {
|
||||
return name && name !== 'index'
|
||||
}
|
||||
|
||||
function extractName(options: NexeOptions) {
|
||||
let name = options.name
|
||||
if (!name && typeof options.input === 'string') {
|
||||
if (!isName(name) && typeof options.input === 'string') {
|
||||
name = basename(options.input).replace(extname(options.input), '')
|
||||
}
|
||||
name = name === 'index' ? tryResolveMainFileName(options.cwd) : name
|
||||
|
||||
if (!isName(name)) {
|
||||
name = tryResolveMainFileName(options.cwd)
|
||||
}
|
||||
|
||||
if (!isName(name) && basename(options.cwd)) {
|
||||
name = basename(options.cwd)
|
||||
}
|
||||
|
||||
return name.replace(/\.exe$/, '')
|
||||
}
|
||||
|
||||
@@ -18,15 +18,8 @@ export default async function resource(compiler: NexeCompiler, next: () => Promi
|
||||
count++
|
||||
step.log(`Including file: ${file}`)
|
||||
const contents = await readFileAsync(file)
|
||||
const commentSafeContents = contents.toString('base64')
|
||||
resources.index[file] = [
|
||||
Buffer.byteLength(resources.bundle),
|
||||
Buffer.byteLength(commentSafeContents)
|
||||
]
|
||||
resources.bundle += commentSafeContents
|
||||
compiler.addResource(file, contents)
|
||||
})
|
||||
step.log(
|
||||
`Included ${count} file(s). ${(Buffer.byteLength(resources.bundle) / 1e6).toFixed(3)} MB`
|
||||
)
|
||||
step.log(`Included ${count} file(s). ${(resources.bundle.byteLength / 1e6).toFixed(3)} MB`)
|
||||
return next()
|
||||
}
|
||||
|
||||
+17
@@ -26,6 +26,22 @@ function padRight(str: string, l: number) {
|
||||
return (str + ' '.repeat(l)).substr(0, l)
|
||||
}
|
||||
|
||||
const bound: MethodDecorator = function bound<T>(
|
||||
target: Object,
|
||||
propertyKey: string,
|
||||
descriptor: TypedPropertyDescriptor<T>
|
||||
) {
|
||||
const configurable = true
|
||||
return {
|
||||
configurable,
|
||||
get(this: T) {
|
||||
const value = (descriptor.value as any).bind(this)
|
||||
Object.defineProperty(this, propertyKey, { configurable, value, writable: true })
|
||||
return value
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function dequote(input: string) {
|
||||
input = input.trim()
|
||||
const singleQuote = input.startsWith("'") && input.endsWith("'")
|
||||
@@ -62,6 +78,7 @@ function isDirectoryAsync(path: string) {
|
||||
export {
|
||||
dequote,
|
||||
padRight,
|
||||
bound,
|
||||
isWindows,
|
||||
rimrafAsync,
|
||||
statAsync,
|
||||
|
||||
Reference in New Issue
Block a user