1

I have a model with a PostGRES JSONField:

from django.contrib.postgres.fields import JSONField
# ... other imports ...

class Feature(models.Model):
    id = models.UUIDField(primary_key=True, default=uuid.uuid4, editable=False)
    # ... other fields ...
    meta = JSONField(default=dict)

And an importer command that either creates or updates features:

    my_meta = {
        'mykey': 'something',
    }
    feature = Feature.objects.filter(id=id).first()
    if feature is None:
        # The feature was not imported previously
        feature = Feature.objects.create(
            id=id,
            meta=my_meta,
        )
        print('CREATED FEATURE.META', feature.meta, feature.meta.__class__.__name__)
    else:
        # The feature was already imported above - update the existing feature with new metadata
        feature.meta = my_meta,
        feature.save()
        print('UPDATED FEATURE.META', feature.meta, feature.meta.__class__.__name__)

When running two different test cases, each creating one feature but testing the two branches of that 'if' statement, I get:

CREATED FEATURE.META {'mykey': 'something'} dict

UPDATED FEATURE.META ({'mykey': 'something'},) tuple

THE QUESTION

Why on earth is it decoding inside a tuple in that latter case?

NOTES

  • Yes, my default is a callable (common issue ppl have with JSONField)

  • No, I don't have django-jsonfield installed (which can cause weird incompatibilities with the native JSONField)

1 Answer 1

2

You've left a comma at the end of line, right here:

        feature.meta = my_meta,

This causes creation of a tuple with one member instead of assigning that member directly to meta. Remember that commas can work differently depending on the context.

Sign up to request clarification or add additional context in comments.

1 Comment

Oh my word. I went so deep on that completely obvious thing. Thanks @GwnBleidD, all solved. And this is why you always copy/paste code into SO instead of writing it out ;)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.