Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Google Cloud Functions: Return valid JSON

I´m trying to call a Google Cloud Function from my Flutter App using the cloud_functions package.

This is my Cloud Function:

export const helloWorld = functions.region('europe-west1').https.onRequest((request, response) => {
response.status(200).json({
    message: "Hello World!"
  });
});

And this is my flutter method that calls this function:

try {
  final dynamic resp =
      await CloudFunctions.instance.call(
    functionName: "helloWorld"
  );
  print(resp);

} on CloudFunctionsException catch (e) {
  ...
} catch (e) {
  ...
} finally {
  ...
}

As you can see it´s the most simply form of a request without any params.

My problem: Each call to the Cloud Function results in a CloudFunctionsException. Reason: "Response is not valid JSON object.".

Maybe somebody has an idea what´s going wrong here? If I call the cloud function via Postman or a browser, a valid JSON Object is returned and no exception is thrown.

Thanks in advance, Michael

like image 368
Michael Avatar asked Jan 05 '19 22:01

Michael


People also ask

How do I return JSON in cloud function?

Cloud Functions has Flask available under the hood, so you can use it's jsonify function to return a JSON response. This will return a flask. Response object with the application/json Content-Type and your data serialized to JSON. Python has a standard library to deal with json (json.

Can a JSON value be a function?

The JSONVALUE function parses data in JavaScript Object Notation (JSON) format that is accessed at the specified path, and it extracts a scalar value that has the specified ID.

How do I Unnest JSON?

There are three parts to this: flatten the original JSON array and select the values you want from it. create new JSON objects based on the resulting row values. combine the JSON objects into a single object.


3 Answers

If you want to use the Flutter SDK to invoke a callable function, you need to actually define a callable function. Right now, you're declaring an HTTP function, which is not the same. Please read the documentation for callable functions to learn how to declare and implement a callable.

Instead of this:

functions.https.onRequest(...)

It will look like this:

functions.https.onCall(...)

Then, you return a JavaScript object to convert to JSON, rather than using a response object.

like image 159
Doug Stevenson Avatar answered Oct 22 '22 08:10

Doug Stevenson


I could find the bug: As soon as you define another region that the default one, the flutter package cloud_functions seems not to be able to find the function anymore:

Works:

export const helloWorld = functions.https.onCall((data, context) => {
    return {
        message: "Hello World"
    }
});

Doesn´t work:

export const helloWorld = functions.region('europe-west1').https.onCall((data, context) => {
    return {
        message: "Hello World"
    }
});
like image 31
Michael Avatar answered Oct 22 '22 08:10

Michael


I was having the same problem, and what worked for me was:

(Adding to @Michael 's answer)

When declaring and calling the cloud function, it's important to specify the region in both cases.

My mistake was that I was only setting the region code on the function declaration.

More here: https://firebase.google.com/docs/functions/locations#client-side_location_selection_for_callable_functions.

For Flutter you should specify the region in the region parameter of the singleton CloudFunctions:

CloudFunctions(app: FirebaseApp.instance, region: "europe-west1")
like image 2
Marco Nascimento Avatar answered Oct 22 '22 08:10

Marco Nascimento