Repository: urql-graphql/urql (ts)

Issue:
When the server returns an error with an empty string message, `GraphQLError.message` becomes an object instead of a string
### Describe the bug

<img width="469" alt="react code" src="https://github.com/user-attachments/assets/ec5ae634-f06a-46e6-80f8-cb4d74c67740">

### If the server returns an non-empty string as `message`
<img width="242" alt="スクリーンショット 2024-08-05 14 47 03" src="https://github.com/user-attachments/assets/2a2870d1-208a-45a6-9664-a71db079b711">

Response
![スクリーンショット 2024-08-05 14 47 29](https://github.com/user-attachments/assets/c2c72a52-ea82-4c23-9114-8465089bad8e)

CombinedError
![スクリーンショット 2024-08-05 14 46 49](https://github.com/user-attachments/assets/68454c80-3da3-4a60-9e52-a884e0d52295)

### If the server returns an empty string as `message`
<img width="228" alt="server throws error" src="https://github.com/user-attachments/assets/745a88ed-d7c0-4bd1-9de8-a1acd4b7bc72">

Response
![スクリーンショット 2024-08-05 14 45 29](https://github.com/user-attachments/assets/814d17dd-8294-4e51-a1d1-b4e870822ea2)

CombinedError
![スクリーンショット 2024-08-05 14 45 05](https://github.com/user-attachments/assets/e6108158-83f6-49dc-9e93-a45733c901c2)

It is likely an issue with the condition within [rehydrateGraphQlError](https://github.com/urql-graphql/urql/blob/942eb161d11c7651f93e21f971a8122d6a97c0bb/packages/core/src/utils/error.ts#L19). When `error.message` is an empty string, `error.message` is falsy, leading to `return new GraphQLError(error as any)` even though `error` has the structure of a GraphQLError.



### Reproduction

https://github.com/koutaro-masaki/urql-issue-reproduction

### Urql version

urql v4.1.0

### Validations

- [X] I can confirm that this is a bug report, and not a feature request, RFC, question, or discussion, for which [GitHub Discussions](https://github.com/urql-graphql/urql/discussions) should be used
- [X] Read the [docs](https://formidable.com/open-source/urql/docs/).
- [X] Follow our [Code of Conduct](https://github.com/urql-graphql/urql/blob/main/CODE_OF_CONDUCT.md)

Pull request:
fix(core): Allow for empty error messages when rehydrating
Fixes #3649 

## Summary

Allow for empty error messages when rehydrating

Patch:
diff --git a/.changeset/good-walls-obey.md b/.changeset/good-walls-obey.md
new file mode 100644
index 00000000..b475ae8c
--- /dev/null
+++ b/.changeset/good-walls-obey.md
@@ -0,0 +1,5 @@
+---
+'@urql/core': patch
+---
+
+Allow empty error messages when re-hydrating GraphQL errors
diff --git a/packages/core/src/utils/error.ts b/packages/core/src/utils/error.ts
index 0d8bcc85..eeae84df 100644
--- a/packages/core/src/utils/error.ts
+++ b/packages/core/src/utils/error.ts
@@ -19,11 +19,11 @@ const generateErrorMessage = (
 const rehydrateGraphQlError = (error: any): GraphQLError => {
   if (
     error &&
-    error.message &&
+    typeof error.message === 'string' &&
     (error.extensions || error.name === 'GraphQLError')
   ) {
     return error;
-  } else if (typeof error === 'object' && error.message) {
+  } else if (typeof error === 'object' && typeof error.message === 'string') {
     return new GraphQLError(
       error.message,
       error.nodes,


Test patch:
diff --git a/packages/core/src/utils/error.test.ts b/packages/core/src/utils/error.test.ts
index 386d83bc..d035592f 100644
--- a/packages/core/src/utils/error.test.ts
+++ b/packages/core/src/utils/error.test.ts
@@ -60,6 +60,16 @@ describe('CombinedError', () => {
     expect(err.graphQLErrors).toEqual(graphQLErrors);
   });
 
+  it('accepts empty string errors for graphQLError', () => {
+    const graphQLErrors = [new Error('')];
+
+    const err = new CombinedError({ graphQLErrors });
+
+    expect(err.message).toBe('[GraphQL] ');
+
+    expect(err.graphQLErrors).toEqual(graphQLErrors);
+  });
+
   it('accepts a response that is attached to the resulting error', () => {
     const response = {};
     const err = new CombinedError({