Contentful with AWS Amplify and Next.js: TypeError: Expected parameter accessToken - next.js

I have a Next.js app hosted on AWS Amplify. I have a static page with a named export getStaticProps where I use contentful, like this:
const client = contentful.createClient({
space: process.env.CONTENTFUL_SPACE,
accessToken: process.env.CONTENTFUL_API_KEY,
})
However, I am getting this error:
TypeError: Expected parameter accessToken
at Module.createClient (/var/task/node_modules/contentful/dist/contentful.node.js:10095:11)
even though I added the CONTENTFUL_SPACE and CONTENTFUL_API_KEY environment variables in the AWS Amplify dashboard.
I don't get this issue when using Vercel. Does anyone know why I am getting this error on AWS Amplify even though I added the environment variables in the Amplify dashboard?

Here is how I solved this error:
In my next.config.js, I added:
module.exports = {
env: {
CONTENTFUL_SPACE: process.env.CONTENTFUL_SPACE,
CONTENTFUL_API_KEY: process.env.CONTENTFUL_API_KEY,
}
}
The reason this was necessary and the reason the environment variables weren’t accessible in getStaticProps on AWS Amplify is because Environment variables are not carried through to Lambda functions which is where getStaticProps runs.

Related

Why is NEXT_PUBLIC_VERCEL_URL is undefined on prod env NextJS+ useSWR

I want to deploy a small project on vercel. I am using useSWR to fetch data.
const { data, error } = useSWR(process.env.NEXT_PUBLIC_VERCEL_URL + '/api/series', fetcher, {
suspense: true,
});
The value for VERCEL_URL on local is:
NEXT_PUBLIC_VERCEL_URL="http://localhost:3000"
It works as expected on local with npm run dev.
Deployed to vercel and works fine on development branch.
with value as.
NEXT_PUBLIC_VERCEL_URL=https://myapp-development-myname.vercel.app
I get the response and in network tab it works.
Production environment
I have changed the VERCEL_URL to my apps website name.
There is a client side error as shown here.
The value is:
NEXT_PUBLIC_VERCEL_URL=https://abc.myappproduction.com
Also the network tab shows the url is undefined.
Why does it get undefined value? Am I missing something?

Vercel NextJS App Environement Variables Not Working [duplicate]

This question already has an answer here:
How to properly set environment variables in Next.js app deployed to Vercel?
(1 answer)
Closed 1 year ago.
Coming from Ruby on Rails, I found it really hard to grasp the concept of environment variables on NextJS, specifically on Vercell platform. I followed the NextJS documentation that recommends the Vercell documentation to set up the environment variables in their project settings even for development environments. So I did and pull them with vercel env pull .env.local. But when I run the development server, the process.env variables are always undefined. Found plenty of SO questions about this with no luck so far.
Example code that I use:
export function getEncodedClientIdAndSecret(): string {
const clientId = process.env.CLIENT_ID;
const clientSecret = process.env.CLIENT_SECRET;
if (!clientId || !clientSecret) {
throw new Error('Missing client ID or client secret');
}
const encodedString = Buffer.from(`${clientId}:${clientSecret}`).toString('base64');
return `Basic ${encodedString}`;
}
.env.local file:
# Created by Vercel CLI
REDIRECT_URI=localhost:3000/api/callback
BASE_URL=localhost:3000
FIREBASE_DATABASE_URL=projectid.firebaseio.com
FIREBASE_CLIENT_EMAIL=dfsdfo#projectid.iam.gserviceaccount.com
FIREBASE_PRIVATE_KEY_B64=longenccryptedprivatekey
FIREBASE_PROJECT_ID=projectid
CLIENT_SECRET=secreiclient
CLIENT_ID=clientid
I'm not a fan of JavaScript. This is really confusing.
After some time, I run into this question again.
But this time, the NEXT_PUBLIC_ prefix from the documentation works smoothly. I don't know why it didn't at that time when I tried that solution.
This is the working version of .env file:
NEXT_PUBLIC_REDIRECT_URI=<Callback URI from Spotify>
NEXT_PUBLIC_BASE_URL=<Base URL of the project>
NEXT_PUBLIC_CLIENT_ID=<Spotify app client ID>
CLIENT_SECRET=<Spotify app client secret key>
FIREBASE_PROJECT_ID=<Firebase project ID>
FIREBASE_PRIVATE_KEY_B64=<Base64-encoded string of Firebase private key>
FIREBASE_CLIENT_EMAIL=<Firebase client email>
FIREBASE_DATABASE_URL=<Firebase database URL>
WARMUP_KEY=<Secret to trigger Firebase database warmup>
This is the PR that I was working on.

Firebase Nuxt Does Not Recognize 'location' Object When Trying to Run The Whole App With Firebase Emulator

My firebase Nuxt app was recently converted to SSR from SPA mode. It was all working fine in SPA mode but when I tried to convert it, it generated a lot of errors. I tried to solve them one by one and I'm stuck with the error ReferenceError 'location' was not defined. I want to run my emulator because I want to test my other functions if it is running completely in SSR mode.
import firebaseTmp from "firebase/app";
import firebaseErrorsJa from "~/plugins/firebaseErrorsJa";
import "firebase/storage";
import "firebase/firestore";
import 'firebase/auth';
import 'firebase/functions';
const config = process.env.firebaseConfig;
if (!firebaseTmp.apps.length) {
firebaseTmp.initializeApp(config);
}
const db = firebaseTmp.firestore();
const functions = firebaseTmp.functions();
const firebase = firebaseTmp;
const firestore = firebaseTmp.firestore();
const storage = firebaseTmp.storage();
const auth = firebaseTmp.auth();
const firestoreTimestamp = firebaseTmp.firestore.Timestamp;
const serverTimestamp = firebaseTmp.firestore.FieldValue.serverTimestamp();
const firebaseErrors = firebaseErrorsJa;
if (location.hostname === "localhost") {
db.settings({
host: "localhost:8000",
ssl: false
});
functions.useEmulator("localhost", 5001);
auth.useEmulator('http://localhost:9099/');
}
export { db, firebase, firestore, auth, storage, firestoreTimestamp, serverTimestamp, functions, firebaseErrors }
I imported almost all libraries but still it does not work.
TAKE NOTE: This only happens when it is in SSR mode. Does this mean that location does not work in SSR mode?
I tried to take away the chunk of code that has 'location' in it. It works perfectly well locally but when I try to run my other functions, it generates CORS error. It accesses the link being used when we deploy our functions.
https://us-central1-talkfor-dev.cloudfunctions.net/v1-auth-updateUser
This is the link that was shown in the console
What I expected is that us-central1-talkfor-dev.cloudfunctions.net will be localhost:5000 since we are using the local development.
Do you have any Idea why is it like this?
Alex you understand that SSR mode is trying to render the website on the server. This can be your local running server instance, that means there is no window object for it to access location variable. Location is only accessible inside the browser. The SSR context is not in the browser, hence makes total sense.
Window.location here states.
Server vs Browser environments here states that
Because you are in a Node.js environment... You do not have access to the window or document objects... You can however use window or document by using the beforeMount or mounted hooks.
.
Why don't you try either of these,
use these beforeMount and mounted hooks like this.
beforeMount () {
window.alert('hello');
}
mounted () {
window.alert('hello');
}
using the process.client environment variable
if (process.client) {
// Do your stuff here
// I think this is what you are looking for.
}

Firebase Callable Function: Response for preflight in invalid

I have created a Firebase callable function, with a simple text return, but am receiving an error when I call the function, both on local and on my deployed app.
The callable function is a simple function to return some text for now:
exports.getSomeInfo = functions.https.onCall(async (data, context) => {
return 'some info';
});
In my app I load the function with:
const getSomeInfo = firebase.functions().httpsCallable('getSomeInfo');
And call it in the app with:
getSomeInfo();
This produces an error of:
Failed to load https://us-central1-[project-ID].cloudfunctions.net/getSomeInfo: Response for preflight is invalid (redirect)
This error occurs when calling the function on local using firebase serve and on the deployed app.
Viewing the logs in the Firebase Console shows no logs or errors.
Other issues mention this could be a CORS issue, or an incorrect Firebase config. I've ensured the Firebase config is correct. And tried a few of the CORS solutions, but continue to get the error above.
Using Firebase#5.5.2.
What else could be causing this error?
As indicated in the documentation, for an HTTPS Callable function you need to "return data that can be JSON encoded".
So if you do something like the following, it should work.
exports.getSomeInfo = functions.https.onCall((data, context) => {
return {result: 'some info'};
});
Update: removed the async
April 2020, I just learned the hard way that callable functions have their module name prepended...
In index.js:
const functions = require('firebase-functions')
// ...
exports.callable = require('./callable')
In callable.js:
const functions = require('firebase-functions');
// ... other stuff
exports.myCloudFunction = functions.https.onCall((data, context) => {
// ...
The way to call this "myCloudFunction" from a JS client is to use its name, prepended with its module name, like this
const fn = firebase.functions().httpsCallable("callable-myCloudFunction")
fn().then(result => { //...
This is documented nowhere, as far as I have found, and, as others have mentioned, almost any error that occurs prior to actually executing the cloud function ends up mislabeled as a CORS error.
After trying across 2 days a variety of refreshes/clean-ups and stuff with CORS, finally found it working after first deleting the function via Firebase console and then deploying the function.
In my case it seems the deployed version got corrupted somehow. It started yesterday when deploy for functions was getting stuck - it would hang and never exit - even though Firebase Status page said all is well. It lasted all day, and I finally let it go to see if it will work today. I thought it was my code, but the deploy is back to working today.
This happened to me a couple days ago. The problem was that when i ran firebase deploythe functions in my src directory were not being compiled. There were typescript errors which stopped it from compiling. You can see if it compiled by checking your lib folder and index.ts inside there I believe.

Use of Service account credentials when using Cloud Functions Shell

I've just migrated to Cloud Functions 1.0 and am trying out Cloud Functions shell/emulator to run functions locally (using instructions at https://firebase.google.com/docs/functions/local-emulator)
One of the functions is using code below to upload a file to cloud storage and then then generate url for it....but am getting following error:
SigningError: Cannot sign data without client_email.
const bucket = gcs.bucket(bucketName);
bucket.upload(localFilePath, {destination: destinationPath})
.then(data => {
const file = data[0];
return file.getSignedUrl({
action: 'read',
expires: '01-01-2099'
});
I can work around this locally by explicitly setting keyFileName as shown below but seems like this should not be necessary
const gcs = require('#google-cloud/storage')({keyFilename: 'service-account.json'});
The link above mentions that "Cloud Firestore and Realtime Database triggers already have sufficient credentials, and do not require additional setup" (I'm triggering this code from db write). I'm setting GOOGLE_APPLICATION_CREDENTIALS env variable in any case but doesn't look like it's picking it up.

Resources