Angular 6 Server Side Rendering (SSR) set status code from Component

懵懂的女人 提交于 2021-02-07 10:37:19

问题


Is there any way to set status code like 404, 401, 500 as per requirement?

I am using Angular 6. There are lots of tutorials showing solutions but those are old and not working at all. All provides showing solutions regarding different server.ts file which is not related to new file showing on Angular site. I am able to render all pages server side. When it has some unexpected content in URL, I am change route to 404 page with skipping location change option.

While calling 404 component, I want to set statuscode = 404.

Server.ts

import 'zone.js/dist/zone-node';
import 'reflect-metadata';

import { enableProdMode } from '@angular/core';

import * as express from 'express';
import { join } from 'path';

// Faster server renders w/ Prod mode (dev mode never needed)
enableProdMode();

// Express server
const app = express();

const PORT = process.env.PORT || 4000;
const DIST_FOLDER = join(process.cwd(), 'dist');

// * NOTE :: leave this as require() since this file is built Dynamically from webpack
const { AppServerModuleNgFactory, LAZY_MODULE_MAP } = require('./dist/server/main');

// Express Engine
import { ngExpressEngine } from '@nguniversal/express-engine';
// Import module map for lazy loading
import { provideModuleMap } from '@nguniversal/module-map-ngfactory-loader';

app.engine('html', ngExpressEngine({
    bootstrap: AppServerModuleNgFactory,
    providers: [
        provideModuleMap(LAZY_MODULE_MAP)
    ]
}));

app.set('view engine', 'html');
app.set('views', join(DIST_FOLDER, 'browser'));

/* 404 status for 404Page route in both language */
app.get('/en/404Page', (req, res) => {
    res.status(404).render('index', { req });
});
app.get('/de/404Page', (req, res) => {
    res.status(404).render('index', { req });
});

// TODO: implement data requests securely
app.get('/api/*', (req, res) => {
    res.status(404).send('data requests are not supported');
});

// Server static files from /browser
app.get('*.*', express.static(join(DIST_FOLDER, 'browser')));

// All regular routes use the Universal engine
app.get('*', (req, res) => {
    res.render('index', { req });
});

// Start up the Node server
app.listen(PORT, () => {
    console.log(`Node server listening on http://localhost:${PORT}`);
});

static-page-http404.component.ts

import { Component, OnInit, Optional, Inject, PLATFORM_ID } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
import { RESPONSE } from '@nguniversal/express-engine/tokens';

@Component({
    selector: 'app-static-page-http404',
    templateUrl: './static-page-http404.component.html',
    styleUrls: [ './static-page-http404.component.scss' ]
})
export class StaticPageHttp404Component implements OnInit {

    constructor(
        private route: ActivatedRoute,
        @Optional() @Inject(RESPONSE) private response: any,
    ) {
    }

    ngOnInit() {

        if (this.response) {
            this.response.statusCode = 404;
            this.response.statusMessage = 'Not Found';
        }

    }

}

Can somebody help in this?


回答1:


I have managed to solve this by this code

app.engine('html', (_, options, callback) =>
  ngExpressEngine({
    bootstrap: AppServerModuleNgFactory,
    providers: [
      provideModuleMap(LAZY_MODULE_MAP),
      {
        provide: REQUEST,
        useValue: options.req,
      },
      {
        provide: RESPONSE,
        useValue: options.req.res,
      },
    ],
  })(_, options, callback)
)

And it's working :D

Thanks




回答2:


Try this maybe

import {RESPONSE} from '@nguniversal/express-engine/tokens';

// All regular routes use the Universal engine
app.get('*', (req, res) => {
  res.render('index', 
  { req, 
    res, 
    bootstrap: AppServerModuleNgFactory,

    providers: [
        provideModuleMap(LAZY_MODULE_MAP),
        {
          provide: RESPONSE,
          useValue: res
        }
    ]

    });
});



回答3:


For people arriving at this page for angular 8, for me this snippet worked.

https://stackoverflow.com/a/58639914/9187039




回答4:


I don't know why but...

Just change

res.render('index', { req });

to

res.render('index', { req, res });

It works for me. Without providers REQUEST and RESPONSE.

I tested it on Angular v.8.1



来源:https://stackoverflow.com/questions/52668630/angular-6-server-side-rendering-ssr-set-status-code-from-component

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!