Skip to content

Decoding error when saving nested object #157

New issue

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

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

Already on GitHub? # to your account

Closed
ribotinho opened this issue Jun 10, 2021 · 14 comments · Fixed by #158
Closed

Decoding error when saving nested object #157

ribotinho opened this issue Jun 10, 2021 · 14 comments · Fixed by #158
Labels
type:bug Impaired feature or lacking behavior that is likely assumed

Comments

@ribotinho
Copy link

ribotinho commented Jun 10, 2021

Hi all,

I am encountering an issue when saving a nested object.

I have a teacher object that has a name (string) and a language (custom object)

struct teacher : ParseObject {
    
    var objectId: String?
    var createdAt: Date?
    var updatedAt: Date?
    var ACL: ParseACL?
    
    var name : String
    var langauge : language
}
struct language : ParseObject{
    var objectId: String?
    var createdAt: Date?
    var updatedAt: Date?
    var ACL: ParseACL?
    
    var code : String
}

I have no problem creating and saving language objects, but when I try to save a Teacher object I am getting a decoding error:

ParseError(code: ParseSwift.ParseError.Code.unknownError, message: "decoding error: typeMismatch(Swift.Array, Swift.DecodingError.Context(codingPath: [], debugDescription: "Expected to decode Array but found a dictionary instead.", underlyingError: nil))")

I am running the parse server on a localhost. macOS Big Sur and SwiftUI.

I have also tried saving the example of Author and Book in the Swift Playgrounds example code but I am getting exactly the same output.

Any one would know how can I solve this? Or what I am missing?

Kind regards,
Pau

@cbaker6
Copy link
Contributor

cbaker6 commented Jun 10, 2021

Hi Pau, your nested object properties need to be "optional" because after it's saved it will come back as a Parse Pointer and will not contain the property code. Try:

struct language : ParseObject{
    var objectId: String?
    var createdAt: Date?
    var updatedAt: Date?
    var ACL: ParseACL?
    
    var code : String? //change to optional
}

Because of this, I recommend making all of your properties optional as you most likely have pointers to many of your Parse Objects in the future.

You can look at the playgrounds for examples: https://github.com/parse-community/Parse-Swift/blob/main/ParseSwift.playground/Pages/8%20-%20Pointers.xcplaygroundpage/Contents.swift

@cbaker6 cbaker6 added the type:question Support or code-level question label Jun 10, 2021
@cbaker6
Copy link
Contributor

cbaker6 commented Jun 10, 2021

Also, be sure to check through closed issues. This has been answered before here: #130 (comment)

@cbaker6 cbaker6 added the state:duplicate Duplicate of already reported issue label Jun 10, 2021
@ribotinho
Copy link
Author

Thanks for your prompt reply Corey!

I am afraid changing the property to optional is not solving the issue.

I've tried once again with the example code in the playgrounds you linked and I am getting the same exact error:

Fatal error: Error saving: ParseError(code: ParseSwift.ParseError.Code.unknownError, message: "decoding error: typeMismatch(Swift.Array, Swift.DecodingError.Context(codingPath: [], debugDescription: "Expected to decode Array but found a dictionary instead.", underlyingError: nil))")

@cbaker6
Copy link
Contributor

cbaker6 commented Jun 10, 2021

What version of the Swift SDK and the parse-server are you running? I just ran the latest version of the Swift SDK against the latest server and 4.5.0 and I'm not getting any errors.

Also, the test cases in the SDK will catch this if it is broken

@ribotinho
Copy link
Author

ribotinho commented Jun 10, 2021

I installed the SDK via Podfile this morning

  • ParseSwift (1.8.0)

And it looks like I am running 3.9. I'll upgrade to 4.5 and try this again

"parse-server": "^3.9.0"

EDIT:
Upgraded to 4.5.0 but no luck, the issue is still there. Teacher still can't be saved, but language does.

BTW, despite being able to save a language option, I am getting these:

2021-06-10 17:11:34.842923+0200 test[4402:203186] [connection] nw_socket_handle_socket_event [C2.1:2] Socket SO_ERROR [61: Connection refused]
2021-06-10 17:11:34.843739+0200 test[4402:203186] [connection] nw_endpoint_handler_set_adaptive_read_handler [C2.2 127.0.0.1:1337 ready socket-flow (satisfied (Path is satisfied), viable, interface: lo0)] unregister notification for read_timeout failed
2021-06-10 17:11:34.843839+0200 test[4402:203186] [connection] nw_endpoint_handler_set_adaptive_write_handler [C2.2 127.0.0.1:1337 ready socket-flow (satisfied (Path is satisfied), viable, interface: lo0)] unregister notification for write_timeout failed
Successfully saved Optional("CA")

@cbaker6
Copy link
Contributor

cbaker6 commented Jun 10, 2021

Maybe you saved your Parse class properties with different types than your current type. If you use Parse Dashboard to delete your old class (assuming you only have dummy data in there) and then save your current type, it might fix your issue. The types for your properties need to match the types on your Parse server database (mongo or postgres)

The log output you sent seems related to your Xcode and network connection and don't seem to be related to the Swift SDK

@ribotinho
Copy link
Author

I am using MongoDB and this is just a test project so everything is dummy data.

This might sound stupid, but do I need to create each class in the database before trying to save instances there? I have not done so for language

@cbaker6
Copy link
Contributor

cbaker6 commented Jun 10, 2021

do I need to create each class in the database before trying to save instances there? I have not done so for language

Not necessarily, as long as you didn't set allowClientClassCreation == false on the server, you can create from the client, https://docs.parseplatform.org/ios/guide/#restricting-class-creation

You can see all of the server configuration options here: http://parseplatform.org/parse-server/api/master/ParseServerOptions.html

@ribotinho
Copy link
Author

Tried also deleting any previously saved data in the database but it's not that either. I guess I'll start from scratch tomorrow with a fresh install. Thanks for your help!

@ribotinho
Copy link
Author

Re-installed everything. Created a new Xcode project (with the playgrounds examples, book and author) and I am encountering the same exact behavior.

Server health is: ok
Saved Book ({"objectId":"BhbBuy4mRA","updatedAt":{"__type":"Date","iso":"2021-06-11T09:48:26.422Z"},"title":"hello","createdAt":{"__type":"Date","iso":"2021-06-11T09:48:26.422Z"}})
testParseMongo/ContentView.swift:57: Fatal error: Error saving: ParseError(code: ParseSwift.ParseError.Code.unknownError, message: "decoding error: typeMismatch(Swift.Array<Any>, Swift.DecodingError.Context(codingPath: [], debugDescription: \"Expected to decode Array<Any> but found a dictionary instead.\", underlyingError: nil))")
2021-06-11 11:48:26.444745+0200 testParseMongo[5980:148481] testParseMongo/ContentView.swift:57: Fatal error: Error saving: ParseError(code: ParseSwift.ParseError.Code.unknownError, message: "decoding error: typeMismatch(Swift.Array<Any>, Swift.DecodingError.Context(codingPath: [], debugDescription: \"Expected to decode Array<Any> but found a dictionary instead.\", underlyingError: nil))")

Any other ideas why this might be happening?

@cbaker6 cbaker6 added type:bug Impaired feature or lacking behavior that is likely assumed and removed state:duplicate Duplicate of already reported issue type:question Support or code-level question labels Jun 11, 2021
@cbaker6
Copy link
Contributor

cbaker6 commented Jun 11, 2021

This is a bug as it looks like the parse-server has issues supporting transactions for mongo (doesn't occur with postgres).

I'm working on a PR that will turn off transactions by default for internal operations in the Swift SDK such as saving child objects/pointers. The SDK began using transactions by default in Swift SDK 1.2.1, so I suspect 1.2.0 below work well with mongo

@cbaker6
Copy link
Contributor

cbaker6 commented Jun 11, 2021

@ribotinho thanks reporting and retesting.

Can you let us know if v1.8.1 solves the problem? When using the playgrounds, be sure to "Clean Build Folder" via Xcode

@ribotinho
Copy link
Author

@cbaker6 I confirm the issue is now fixed and I can successfully save the nested object. Thanks a ton once again for your help! :)

@cbaker6
Copy link
Contributor

cbaker6 commented Jun 13, 2021

Thanks for reporting! Let us know if you find any other bugs or suggested improvements.

# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
type:bug Impaired feature or lacking behavior that is likely assumed
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants