简体   繁体   English

如何通过云功能将 Nuxt SSR 应用部署到 firebase?

[英]How to deploy Nuxt SSR app to firebase through cloud functions?

I followed this medium post as a guide to host my nuxt app on firebase hosting.我按照这篇中等帖子作为指南,在 firebase 主机上托管我的 nuxt 应用程序。

The deploy goes through, however, when I then visit the url I get a Cannot GET / error message.部署完成,但是,当我访问url时,我收到Cannot GET /错误消息。 If I check the function logs I see that the function completes with a 404 error.如果我检查 function 日志,我会看到 function 完成时出现 404 错误。

This is my functions/index.js这是我的函数/index.js

const functions = require('firebase-functions')
const admin = require("firebase-admin")
const { Nuxt } = require('nuxt-start')
const nuxtConfig = require('./nuxt.config.js')

admin.initializeApp()

const config = {
  ...nuxtConfig,
  dev: false,
  debug: true,
  buildDir: "nuxt",
  publicPath: "public",
}

const nuxt = new Nuxt(config)

exports.ssrapp = functions.https.onRequest(async (req, res) => {
  await nuxt.ready()
  nuxt.render(req, res)
})

And this is the firebase configuration这是firebase配置

{
  "functions": {
    "source": "functions",
    "predeploy": [
      "npm --prefix src run build && rm -rf functions/nuxt && cp -r src/nuxt/ functions/nuxt/ && cp src/nuxt.config.js functions/"
    ]
  },
  "hosting": {
    "predeploy": [
      "rm -rf public/* && mkdir -p public/_nuxt && cp -a src/nuxt/dist/client/. public/_nuxt && cp -a src/static/. public/ && cp -a public_base/. public/"
    ],
    "public": "public",
    "ignore": [
      "firebase.json",
      "**/.*",
      "**/node_modules/**"
    ],
    "rewrites": [
      {
        "source": "**",
        "function": "ssrapp"
      }
    ]
  }
}

The project structure is this项目结构是这样的

/
 /src
 /functions
 /public
 /public_base

When I run firebase deploy I do see the content of /src being copied to /functions/nuxt.当我运行firebase deploy时,我确实看到 /src 的内容被复制到 /functions/nuxt。 For the sake of testing I also have my /functions/package.json file include all the dependencies that I have in my /src/package.json file.为了测试,我还有我的/functions/package.json文件包括我在/src/package.json文件中的所有依赖项。

How can I get this app up and running?我怎样才能启动并运行这个应用程序? If you need any more details, let me know.如果您需要更多详细信息,请告诉我。

Update #1更新#1

I tried serving hosting and functions using the command firebase serve --only functions,hosting -p 5004 .我尝试使用命令firebase serve --only functions,hosting -p 5004服务托管和功能。

Running the server like so gave me some more insights.像这样运行服务器给了我更多的见解。 Specifically I got this warning message at load time that then resulted in actual error message when loading the page.具体来说,我在加载时收到此警告消息,然后在加载页面时导致实际错误消息。

WARN  Module @firebase/app not found. Silently ignoring module as programatic usage detected

I didn't install this package in the functions directory as I did not have it in my src directory either.我没有在函数目录中安装这个 package,因为我的 src 目录中也没有它。 However, after installing it inside /functions and restarting the dev server, that warning message was gone and with it also the error I was getting on page load.但是,在 /functions 中安装它并重新启动开发服务器后,该警告消息消失了,并且我在页面加载时遇到了错误。

I also spotted a couple of warnings that had to do with vue, vue-server-renderer and vue-template-compiler not running the same version.我还发现了一些与 vue、vue-server-renderer 和 vue-template-compiler 未运行相同版本有关的警告。

Now everything seems to be working fine!现在一切似乎都运行良好!

Your config and structure look right.您的配置和结构看起来正确。

I also did this about a year ago with my app and I ran into the same problem.大约一年前,我也用我的应用程序这样做了,我遇到了同样的问题。 It has to do with the function code itself.它与 function 代码本身有关。 I also tried using nuxt.render(req, res) ( Docs ) but it never worked for me so I ended up using nuxt.renderRoute(route) ( Docs ) instead.我也尝试过使用nuxt.render(req, res)Docs ),但它从来没有为我工作过,所以我最终改用了nuxt.renderRoute(route)Docs )。 This worked perfectly fine.这工作得很好。

You could change your code to something like this:您可以将代码更改为以下内容:

const { Nuxt } = require('nuxt')

...

exports.ssrapp = functions.https.onRequest(async (req, res) => {
  await nuxt.ready()

  const result = await nuxt.renderRoute(req.path) // Returns { html, error, redirected }
  res.send(result.html) // Sends html as response
})

This worked for me.这对我有用。 You should consider catching any errors though.不过,您应该考虑捕获任何错误。 I hope this solves your problem.我希望这能解决你的问题。

This is only a work-around, if anyone knows why nuxt.render isn't working, I would be interested to know.这只是一种解决方法,如果有人知道为什么nuxt.render不起作用,我很想知道。 I wasted many hours because of this with my app...因为这个,我在我的应用程序上浪费了很多时间......

I tried serving hosting and functions locally using the command firebase serve --only functions,hosting -p 5004 .我尝试使用命令firebase serve --only functions,hosting -p 5004在本地提供托管和功能。

By doing this I was able to spot a bunch of warnings and errors such as通过这样做,我能够发现一堆警告和错误,例如

FATAL 

Vue packages version mismatch:

- vue@2.5.21
- vue-server-renderer@2.6.11

This may cause things to work incorrectly. Make sure to use the same version for both.

WARN  Module @firebase/app not found. Silently ignoring module as programatic usage detected

I then made sure that those vue packages were indeed running the same version.然后我确保那些 vue 包确实在运行相同的版本。 Then I also added the @firebase/app package in /functions/package.json (that however, is not present in /src/package.json .然后我还在 /functions/package.json 中添加了@firebase/app /functions/package.json (但是,在/src/package.json中不存在。

I run the local server again and everything worked.我再次运行本地服务器,一切正常。 I then deployed to firebase and everything was working as expected.然后我部署到 firebase,一切都按预期工作。

the following works for me (using nuxt-start instead):以下对我有用(使用 nuxt-start 代替):

const functions = require("firebase-functions");
const { Nuxt } = require("nuxt-start");

const config = {
  dev: false
};

const nuxt = new Nuxt(config);

let isReady = false;

async function handleRequest(req, res) {
  if (!isReady) {
    try {
      isReady = await nuxt.ready();
    } catch (error) {
      process.exit(1);
    }
  }
  await nuxt.render(req, res);
}

exports.nuxtssr = functions.https.onRequest(handleRequest);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM