2020-02-12 21:31:22 +00:00
|
|
|
import * as plugins from './smartssr.plugins';
|
|
|
|
import * as paths from './smartssr.paths';
|
|
|
|
|
|
|
|
import { serializeFunction } from './smartssr.function.serialize';
|
|
|
|
|
2020-08-06 15:13:38 +00:00
|
|
|
export interface ISmartSSROptions {
|
|
|
|
debug: boolean;
|
|
|
|
}
|
|
|
|
|
2020-02-12 21:31:22 +00:00
|
|
|
/**
|
|
|
|
*
|
|
|
|
*/
|
|
|
|
export class SmartSSR {
|
2020-08-06 15:13:38 +00:00
|
|
|
public options: ISmartSSROptions;
|
|
|
|
|
|
|
|
constructor(optionsArg?: ISmartSSROptions) {
|
|
|
|
this.options = {
|
2020-08-06 15:17:01 +00:00
|
|
|
...{
|
|
|
|
debug: false,
|
2020-08-06 15:13:38 +00:00
|
|
|
},
|
2020-08-06 15:17:01 +00:00
|
|
|
...optionsArg,
|
2020-08-06 15:13:38 +00:00
|
|
|
};
|
|
|
|
}
|
|
|
|
|
2020-02-12 21:31:22 +00:00
|
|
|
public async renderPage(urlArg: string) {
|
2020-03-01 13:50:28 +00:00
|
|
|
const overallTimeMeasurement = new plugins.smarttime.HrtMeasurement();
|
|
|
|
overallTimeMeasurement.start();
|
2020-02-12 21:31:22 +00:00
|
|
|
const resultDeferred = plugins.smartpromise.defer<string>();
|
2021-08-16 08:30:46 +00:00
|
|
|
const browser = new plugins.smartpuppeteer.IncognitoBrowser();
|
2020-03-01 13:50:28 +00:00
|
|
|
const renderTimeMeasurement = new plugins.smarttime.HrtMeasurement();
|
2021-08-16 14:26:13 +00:00
|
|
|
let renderedPageString: string;
|
2020-08-06 15:30:54 +00:00
|
|
|
let screenshotBuffer: Buffer;
|
2021-08-16 14:26:13 +00:00
|
|
|
await browser.start();
|
|
|
|
try {
|
|
|
|
const context = await browser.getNewIncognitoContext();
|
|
|
|
const page = await context.newPage();
|
|
|
|
|
|
|
|
// lets protect against left open tabs
|
|
|
|
plugins.smartdelay.delayFor(30000).then(async () => {
|
2021-08-16 15:47:20 +00:00
|
|
|
try {
|
|
|
|
await browser.stop();
|
|
|
|
} catch {}
|
2021-08-16 14:26:13 +00:00
|
|
|
});
|
2020-08-06 15:30:54 +00:00
|
|
|
|
2021-08-16 14:26:13 +00:00
|
|
|
page.on('console', (msg) => {
|
|
|
|
console.log(`${urlArg}: ${msg.text()}`);
|
2020-08-06 15:30:54 +00:00
|
|
|
});
|
|
|
|
|
2021-08-16 14:26:13 +00:00
|
|
|
renderTimeMeasurement.start();
|
|
|
|
await page.goto(urlArg, {
|
|
|
|
waitUntil: 'networkidle2',
|
|
|
|
timeout: 30000,
|
|
|
|
});
|
2020-08-06 15:30:54 +00:00
|
|
|
|
2021-08-16 14:26:13 +00:00
|
|
|
if (this.options.debug) {
|
|
|
|
screenshotBuffer = await page.screenshot({
|
|
|
|
encoding: 'binary',
|
2021-08-17 10:54:19 +00:00
|
|
|
}) as Buffer;
|
2021-08-16 14:26:13 +00:00
|
|
|
}
|
2020-03-01 13:50:28 +00:00
|
|
|
|
2021-08-16 14:26:13 +00:00
|
|
|
await page.$eval('body', serializeFunction);
|
|
|
|
const pageContent = await page.content();
|
|
|
|
renderedPageString = pageContent;
|
|
|
|
resultDeferred.resolve(renderedPageString);
|
|
|
|
renderTimeMeasurement.stop();
|
|
|
|
|
|
|
|
// lets clean up async
|
|
|
|
await page.close();
|
|
|
|
await context.close();
|
|
|
|
} catch (e) {
|
|
|
|
console.log(e);
|
|
|
|
}
|
2021-08-16 08:30:46 +00:00
|
|
|
await browser.stop();
|
2020-03-01 13:50:28 +00:00
|
|
|
|
|
|
|
overallTimeMeasurement.stop();
|
2020-08-06 15:17:01 +00:00
|
|
|
console.log(
|
|
|
|
`Overall it took ${overallTimeMeasurement.milliSeconds} milliseconds to render ${urlArg}`
|
|
|
|
);
|
|
|
|
console.log(
|
|
|
|
`The rendering alone took ${renderTimeMeasurement.milliSeconds} milliseconds for ${urlArg}`
|
|
|
|
);
|
2020-08-06 15:30:54 +00:00
|
|
|
|
|
|
|
// debug
|
|
|
|
if (this.options.debug) {
|
|
|
|
plugins.smartfile.memory.toFsSync(
|
|
|
|
renderedPageString,
|
|
|
|
plugins.path.join(paths.noGitDir, 'test.html')
|
|
|
|
);
|
|
|
|
const fs = await import('fs');
|
|
|
|
fs.writeFileSync(plugins.path.join(paths.noGitDir, 'test.png'), screenshotBuffer);
|
|
|
|
}
|
|
|
|
|
2021-08-16 14:26:13 +00:00
|
|
|
return resultDeferred.promise;
|
2020-02-12 21:31:22 +00:00
|
|
|
}
|
|
|
|
}
|