Closed travisstaloch closed 5 years ago
If your field is private, you must put the YAML dumping/loading code in the package that defines the type. That's the whole point of the field being private.
More generally speaking, serialization is and has always been the enemy of information hiding. A serialization library needs access to private data, when all other purposes you use a package for should really be forbidden to do it. NimYAML's solution is to generate serialization code via generics, template instantiation and macros in the package where you call dump
, and that needs to be the package that has access to the private information.
At least, that's the concept. Actually, I'm not sure if it works, so just try and define a helper function in point.nim
that calls dump, and then call that in test_point.nim
and report your findings :).
I see what you mean. I discovered that nim's json package has the same behavior, not allowing dumping/loading objects with private fields. I was hoping to be able to (de)serialize some 3rd party objects without having to write much code. I guess its not too much hassle to include the package and define these dumping/loading procs. I'll likely make a macro for this.
This works. Thanks for your suggestion and thoughts.
# point.nim
import yaml/serialization, streams
type
Point* = object
x:int
y*:int
proc dumpPoint*(p: Point): string =
dump(p)
proc loadPoint*(s: string): Point =
let ss = newStringStream(s)
load(ss, result)
#test_point.nim
let
p = Point(y:2)
s = dumpPoint(p)
y = "%YAML 1.2\nx: 0\ny: 2\n"
p = loadPoint(y)
You have to provide values for each field to load. If either x or y is missing:
Unhandled exception: While constructing Point: Missing field: "y" [YamlConstructionError] [FAILED] load point
If you have a third-party library, you potentially could use include
instead of import
which makes the declarations part of your package (e.g. original file is foo
, your file is enhancedFoo
and has include foo
; all your other files must depend on enhancedFoo
instead of foo
). However, that won't work as soon as other third-party code imports the original package.
Is there any way to dump objects with non-exported (private) fields?
Here is a minimal example and error message:
I am on nim 0.20 using k0zmo's devel branch
I would like to be able to dump the object, skipping the private fields.