Skip to content
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

serde transparently #466

Open
uyha opened this issue Jan 17, 2024 · 3 comments
Open

serde transparently #466

uyha opened this issue Jan 17, 2024 · 3 comments
Assignees
Labels
enhancement New feature or request

Comments

@uyha
Copy link
Contributor

uyha commented Jan 17, 2024

After #255, type checking for deserialization is declared at the type level, not at deserialization invocation anymore, this leads to having no way to do type checking at a snippet like this (I actually have problem with msgpack, but I use JSON since it's more popular):

from serde.json import from_json, to_json


int_json = to_json(1)
string_json = to_json("1")

print(f"{int_json=} {string_json=}")
print(f"{from_json(str, int_json)=} {from_json(int, string_json)=}")

One solution I'd like to propose is to have a transparent attribute, similar to what the Rust crate serde has (transparent) which allows creating wrapper around a type without requiring using the target format's container type. So we'd have something like

from serde import serde, Strict
from serde.json import from_json, to_json

@serde(transparent=True, type_check=Strict)
class StrictString:
    value: str

int_json = to_json(1)
string_json = to_json("1")

from_json(str, string_json) # returns a normal str
from_json(StrictString, string_json) # returns a StrictString with value being "1"
from_json(StrictString, int_json) # raises SerdeError
@yukinarit
Copy link
Owner

Hi @uyha
Thanks for a proposal with good example! Yeah, It's nice to have transparent feature.

Right now, I am working on a pretty big change #237 right now (branch). I can take a look at this after that. Or If you're interested in contributing to pyserde, I am happy to assist you.

@yukinarit yukinarit added the enhancement New feature or request label Jan 18, 2024
@yukinarit
Copy link
Owner

Awesome!

I think the implementation will be similar to flatten feature.
you can find code serializing and serializing flatten here

  • Serialize:

    pyserde/serde/se.py

    Lines 815 to 820 in 03c0c1f

    if arg.flatten:
    flattened = []
    for f in sefields(arg.type, self.serialize_class_var):
    f.parent = arg # type: ignore
    flattened.append(self.render(f))
    return ", ".join(flattened)
  • Deserialize:

    pyserde/serde/de.py

    Lines 819 to 827 in 03c0c1f

    else:
    # Because the field is flattened
    # e.g. "data" will be used as variable name.
    assert arg.datavar
    if arg.iterbased:
    var = f"{arg.datavar}[{arg.index}:]"
    else:
    var = arg.datavar

It's good to know how to see the generated code by

python -m serde.insepct {source} {class}

e.g. To see generated code for flatten example.

python -m serde.inspect examples/flatten.py Foo
 

@uyha-kwz uyha-kwz removed their assignment Jan 18, 2024
@uyha
Copy link
Contributor Author

uyha commented Jan 18, 2024

sorry, I was using my work account to comment, so I removed that, I'll still keep working on a PR though.

# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

3 participants