Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(functions): use notifyError() instead of throwing #6773

Merged
merged 2 commits into from
Mar 14, 2025

Conversation

thatfiredev
Copy link
Member

@thatfiredev thatfiredev commented Mar 14, 2025

Throwing inside the PublisherStream causes a Runtime exception that can't be caught in the call site.
Instead, we should use notifyError() so that the error can be caught in the Subscriber#onError() function.

I tried to catch the exception using both of the code snippets below, but none of them worked. (they both work with the changes in this PR):

functions.getHttpsCallable("nonExistentFunction")
    .stream().asFlow()
    .catch {
        // Handle error for a 404 function
    }
    .collect {
        // ...
    }
try {
    functions.getHttpsCallable("nonExistentFunction")
        .stream().asFlow()
        .collect {
            // ...
        }
} catch(e: Exception) {
    // Handle error for a 404 function
}

Runtime exception thrown:

FATAL EXCEPTION: OkHttp Dispatcher
    Process: com.google.samples.quickstart.functions, PID: 13321
    com.google.firebase.functions.FirebaseFunctionsException: Value <html><head> of type java.lang.String cannot be converted to JSONObject Unexpected Response:
                                                                             
    <html><head>
    <meta http-equiv="content-type" content="text/html;charset=utf-8">
    <title>404 Page not found</title>
    </head>
        <body text=#000000 bgcolor=#ffffff>
            <h1>Error: Page not found</h1>
            <h2>The requested URL was not found on this server.</h2>
            <h2></h2>
        </body></html>
                                                                              
    at com.google.firebase.functions.PublisherStream.validateResponse(PublisherStream.kt:316)
    at com.google.firebase.functions.PublisherStream.access$validateResponse(PublisherStream.kt:41)
    at com.google.firebase.functions.PublisherStream$startStreaming$1$4.onResponse(PublisherStream.kt:161)
    at okhttp3.RealCall$AsyncCall.execute(RealCall.java:203)
    at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1156)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:651)
    at java.lang.Thread.run(Thread.java:1119)

Copy link
Contributor

github-actions bot commented Mar 14, 2025

📝 PRs merging into main branch

Our main branch should always be in a releasable state. If you are working on a larger change, or if you don't want this change to see the light of the day just yet, consider using a feature branch first, and only merge into the main branch when the code complete and ready to be released.

@google-oss-bot
Copy link
Contributor

1 Warning
⚠️ Did you forget to add a changelog entry? (Add the 'no-changelog' label to the PR to silence this warning.)

Generated by 🚫 Danger

@google-oss-bot
Copy link
Contributor

google-oss-bot commented Mar 14, 2025

Copy link
Contributor

github-actions bot commented Mar 14, 2025

Test Results

14 files  ±0  14 suites  ±0   13s ⏱️ -1s
23 tests ±0  23 ✅ ±0  0 💤 ±0  0 ❌ ±0 
46 runs  ±0  46 ✅ ±0  0 💤 ±0  0 ❌ ±0 

Results for commit 6b62413. ± Comparison against base commit b9be9f1.

♻️ This comment has been updated with latest results.

@google-oss-bot
Copy link
Contributor

google-oss-bot commented Mar 14, 2025

Size Report 1

Affected Products

  • firebase-functions

    TypeBase (b9be9f1)Merge (f63fbbc)Diff
    aar80.4 kB80.5 kB+10 B (+0.0%)
    apk (release)5.46 MB5.46 MB+36 B (+0.0%)

Test Logs

  1. https://storage.googleapis.com/firebase-sdk-metric-reports/ain2POUgsf.html

@rlazo rlazo merged commit 0554f0d into main Mar 14, 2025
31 of 33 checks passed
@rlazo rlazo deleted the rpf/functions-fix-publisher-errors branch March 14, 2025 21:10
emilypgoogle pushed a commit that referenced this pull request Mar 17, 2025
Throwing inside the `PublisherStream` causes a Runtime exception that
can't be caught in the call site.
Instead, we should use `notifyError()` so that the error can be caught
in the `Subscriber#onError()` function.

I tried to catch the exception using both of the code snippets below,
but none of them worked. (they both work with the changes in this PR):

```kotlin
functions.getHttpsCallable("nonExistentFunction")
    .stream().asFlow()
    .catch {
        // Handle error for a 404 function
    }
    .collect {
        // ...
    }
```

```kotlin
try {
    functions.getHttpsCallable("nonExistentFunction")
        .stream().asFlow()
        .collect {
            // ...
        }
} catch(e: Exception) {
    // Handle error for a 404 function
}
```

Runtime exception thrown:

```
FATAL EXCEPTION: OkHttp Dispatcher
    Process: com.google.samples.quickstart.functions, PID: 13321
    com.google.firebase.functions.FirebaseFunctionsException: Value <html><head> of type java.lang.String cannot be converted to JSONObject Unexpected Response:
                                                                             
    <html><head>
    <meta http-equiv="content-type" content="text/html;charset=utf-8">
    <title>404 Page not found</title>
    </head>
        <body text=#000000 bgcolor=#ffffff>
            <h1>Error: Page not found</h1>
            <h2>The requested URL was not found on this server.</h2>
            <h2></h2>
        </body></html>
                                                                              
    at com.google.firebase.functions.PublisherStream.validateResponse(PublisherStream.kt:316)
    at com.google.firebase.functions.PublisherStream.access$validateResponse(PublisherStream.kt:41)
    at com.google.firebase.functions.PublisherStream$startStreaming$1$4.onResponse(PublisherStream.kt:161)
    at okhttp3.RealCall$AsyncCall.execute(RealCall.java:203)
    at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1156)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:651)
    at java.lang.Thread.run(Thread.java:1119)
```
rlazo added a commit that referenced this pull request Mar 24, 2025
These improvements are both in the SDK itself, and in the code used for
the actual functions running in the cloud during integration testing:

A summary of the changes is:
- [Backend functions] Update the dependencies and node runtime version
- [Backend functions] Add logging in case the client does not support
streaming
- [SDK] Use a more robust handle of the media type
- [SDK] Fix issue introduced in #6773 that missed a return in case of
error
- [SDK] Other minor code fixes

b/404814020
gubatron pushed a commit to gubatron/firebase-android-sdk that referenced this pull request Mar 24, 2025
Throwing inside the `PublisherStream` causes a Runtime exception that
can't be caught in the call site.
Instead, we should use `notifyError()` so that the error can be caught
in the `Subscriber#onError()` function.

I tried to catch the exception using both of the code snippets below,
but none of them worked. (they both work with the changes in this PR):

```kotlin
functions.getHttpsCallable("nonExistentFunction")
    .stream().asFlow()
    .catch {
        // Handle error for a 404 function
    }
    .collect {
        // ...
    }
```

```kotlin
try {
    functions.getHttpsCallable("nonExistentFunction")
        .stream().asFlow()
        .collect {
            // ...
        }
} catch(e: Exception) {
    // Handle error for a 404 function
}
```

Runtime exception thrown:

```
FATAL EXCEPTION: OkHttp Dispatcher
    Process: com.google.samples.quickstart.functions, PID: 13321
    com.google.firebase.functions.FirebaseFunctionsException: Value <html><head> of type java.lang.String cannot be converted to JSONObject Unexpected Response:
                                                                             
    <html><head>
    <meta http-equiv="content-type" content="text/html;charset=utf-8">
    <title>404 Page not found</title>
    </head>
        <body text=#000000 bgcolor=#ffffff>
            <h1>Error: Page not found</h1>
            <h2>The requested URL was not found on this server.</h2>
            <h2></h2>
        </body></html>
                                                                              
    at com.google.firebase.functions.PublisherStream.validateResponse(PublisherStream.kt:316)
    at com.google.firebase.functions.PublisherStream.access$validateResponse(PublisherStream.kt:41)
    at com.google.firebase.functions.PublisherStream$startStreaming$1$4.onResponse(PublisherStream.kt:161)
    at okhttp3.RealCall$AsyncCall.execute(RealCall.java:203)
    at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1156)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:651)
    at java.lang.Thread.run(Thread.java:1119)
```
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants