attrs icon indicating copy to clipboard operation
attrs copied to clipboard

Evolve converts/validates again not changed fields

Open ponomar opened this issue 2 years ago • 1 comments

Here's the usecase:

def decrypt_secret(value):
    return ...

@attrs.frozen
class Settings:
    user: str
    pwd: str = attrs.field(converter=decrypt_secret)

sett = Settings(user="name", pwd=<encrypted_value>)
sett.pwd  # already decrypted value

attrs.evolve(sett, user="name2")

This will fail, because it tries to decrypt already decrypted value, although the field pwd not changed at all.

Probably it is a wrong behaviour to convert/validate not changed fields.

Didn't find how to avoid converting/validating in this case.

ponomar avatar Apr 13 '23 12:04 ponomar

With the current implementation that's sadly inevitable.

Evolve basically does:

kw = attrs.asdict()
kw["user"] = "name2"
Settings(**kw)

It would be cool if evolve would get a bit more sophisticated, but you example is a bit "heavy" for a converter. As the docs say, converters should be more on the light / idempotent side.

hynek avatar Apr 14 '23 04:04 hynek