Angular 9 SSR - где установить глобальное ['окно'] (с использованием домино)?

После обновления до Angular 9 я получаю сообщение об ошибке ReferenceError: window is not defined при запуске yarn serve:ssr.

В наших приложениях Angular мы используем трюк с Domino для имитации окна для SSR (например, https://github.com/Angular-RU/angular-universal-starter/blob/master/server.ts#L21).

Итак, после ng update я добавил эти строки после импорта в server.ts:


const distFolder = join(process.cwd(), 'dist/browser');
const indexHtml = existsSync(join(distFolder, 'index.original.html')) ? 'index.original.html' : 'index';

// Emulate browser APIs
const domino = require('domino');
const fs = require('fs');
const templateA = fs.readFileSync(join(distFolder, indexHtml)).toString();

const win = domino.createWindow(templateA);
win.Object = Object;
win.Math = Math;
global['window'] = win;
global['document'] = win.document;

Однако похоже, что установка global['window'] либо слишком поздно, либо никогда.

У вас есть идеи, где установить global['window'], чтобы компоненты и библиотеки angular могли получить к нему доступ в SSR?


person Lukáš Březina    schedule 10.02.2020    source источник
comment
Вы нашли какое-нибудь рабочее место? У меня такая же проблема = /   -  person Tito    schedule 06.05.2020


Ответы (3)


Решено благодаря этому комментарию https://github.com/angular/universal/issues/1678#issuecomment-627031128

Ключ в том, чтобы линия

import { AppServerModule } from './src/main.server';

после определения global['window']

Остерегайтесь автоформаторов в вашем редакторе, которые обычно автоматически помещают строки импорта поверх файла :)

person Lukáš Březina    schedule 13.05.2020

Я помещаю его ниже импорта и выше метода app ()


import { ngExpressEngine } from '@nguniversal/express-engine';
import * as express from 'express';
import { join } from 'path';

import { AppServerModule } from './src/main.server';
import { APP_BASE_HREF } from '@angular/common';
import { existsSync, readFileSync } from 'fs';
import * as domino from 'domino';
import * as core from 'express-serve-static-core';


const template = join('browser', 'index.html');
const win = domino.createWindow(template);

global['window'] = win;
global['document'] = win.document;

// The Express app is exported so that it can be used by serverless Functions.
export function app(): core.Express {
person Ales    schedule 13.02.2020
comment
Это не работает - по-прежнему ReferenceError: window is not defined через dist/server/main.js - person Lukáš Březina; 20.02.2020
comment
Какое-нибудь решение этой проблемы? - person Rajasekar; 08.07.2021

Я делаю две задачи, чтобы исправить это.

первый - в angular.json установите "optimisation": false для сборки сервера, это помогает найти модуль 3d paty, который вызывает ошибку

второй - я продвигаюсь вверх по домино на своем server.ts

person anton    schedule 19.03.2020