Vue s-s-r serverPrefetch 使用 this.$s-s-rContext.res.redirect 重定向服务器

Posted

技术标签:

【中文标题】Vue s-s-r serverPrefetch 使用 this.$s-s-rContext.res.redirect 重定向服务器【英文标题】:Vue s-s-r serverPrefetch server redirect with this.$s-s-rContext.res.redirect 【发布时间】:2020-01-02 22:00:32 【问题描述】:

是否可以在 VUE s-s-r 中从组件执行重定向,而不会在服务器控制台上收到错误:[ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client

代码如下:

serverPrefetch() 
    // need the data from this.fetchPage service to decide on the redirect
    return this.fetchPage().then(function (response) 
        // do some checks here

        // THIS IS THE NODE EXPRESS REDIRECT
        this.$s-s-rContext.res.redirect('/');
        this.$s-s-rContext.res.end(); // with or without, same error
    .bind(this));
,
beforeMount() 
    this.fetchPage();

注意:如果我尝试使用this.$router.replace('/')(或任何其他方法),我会收到错误:[Vue warn]: Error in callback for watcher $route: ReferenceError: document is not defined

在我的项目中,我在客户端进行了重定向,但我想知道这是否也可以从服务器完成。

【问题讨论】:

通常重定向是在中间件或页面中完成的,而不是 serverPrefetch 方法。在什么条件下你试图重定向? @user3254198,我需要从一个 api 调用(fetchPage 有多个 api 调用)中获取一些数据,告诉我重定向(例如,状态 301 / 302),但仅限于此页。现在该项目是在s-s-r.vuejs.org 文档之后实施的。在 nodejs 我没有明确的路线,只有 app.get('*', renderApp) 尝试在 nodejs 服务器的 renderApp 函数中进行重定向。您不应该在组件内部发出网络请求,只有页面组件才应该发出网络请求,否则会给您带来问题并使您的应用程序变慢。 【参考方案1】:

TL;DR:

使用 url: '/redirect-route' 拒绝 serverPrefetch

找到如下解决方案:如果你将 vue-s-s-r 项目实现为https://github.com/vuejs/vue-hackernews-2.0 repo,则在 server/index.js 中有一个 handleError 函数,其中包含重定向:

if (err.url) 
        res.redirect(err.url);
    

而您在组件中需要做的就是:

serverPrefetch() 
    return this.fetchPage().then(res => 
        if(res === 'MY_REDIRECT_CONDITION') 
            // !!! THE ACTUAL REDIRECT TRIGGER !!!
            return Promise.reject(url: '/');
        

    );
,

【讨论】:

以上是关于Vue s-s-r serverPrefetch 使用 this.$s-s-rContext.res.redirect 重定向服务器的主要内容,如果未能解决你的问题,请参考以下文章

在 Vue 中使用 s-s-r 时在哪里调用“Vue.use(plugin)”

如何在 laravel 应用程序中为单个 vue 组件实现 s-s-r?

使用 s-s-r 时无法在 vue3 中使用异步组件

延迟加载的 vue-router 组件不适用于 s-s-r

Vue.js 3 s-s-r - 客户端水合期间缺少模板或渲染功能

如何在 Vue 3 s-s-r 应用程序的路由器中使用 vuex 商店?