Skip to content

SNOW-801402: Writing dictionary as variant using sqlalchemy ormΒ #411

@alex-linx

Description

@alex-linx

Please answer these questions before submitting your issue. Thanks!

  1. What version of Python are you using?

    3.9

  2. What operating system and processor architecture are you using?

    macOS-13.3.1-arm64-arm-64bit

  3. What are the component versions in the environment (pip freeze)?

    Replace with the output of python -m pip freeze

  4. What did you do?

from datetime import datetime
from uuid import uuid4
import json

from sqlalchemy.orm import declarative_base, Session
from sqlalchemy import create_engine, Column, VARCHAR

from snowflake.sqlalchemy import URL, VARIANT


Base = declarative_base()

class MyTable(Base):
    __tablename__ = "my_table"

    id_: str = Column(
        "id_", VARCHAR(200), primary_key=True, default=lambda: str(uuid4())
    )
    json_data = Column("json_data", VARIANT, nullable=False)

Base.metadata.create_all(engine)

my_dict = {"hello": "world"}
my_item = MyTable(json_data=my_dict)

with Session(engine) as sess:
    sess.add(my_item)
    sess.commit()

When I run sess.commit() I get an error

ProgrammingError: (snowflake.connector.errors.ProgrammingError) 252004: Failed processing pyformat-parameters: 255001: Binding data in type (dict) is not supported.
[SQL: INSERT INTO my_table (id_, json_data) VALUES (%(id_)s, %(json_data)s)]
[parameters: {'id_': '26c72a93-d68d-4ff3-b40d-dbaa348309d6', 'json_data': {'hello': 'world'}}]
(Background on this error at: https://sqlalche.me/e/14/f405)

I also tried with my_item = MyTable(json_data=json.dumps(my_dict)), then I get a different error

ProgrammingError: (snowflake.connector.errors.ProgrammingError) 002023 (22000): SQL compilation error:
Expression type does not match column data type, expecting VARIANT but got VARCHAR(18) for column JSON_DATA
[SQL: INSERT INTO my_table (id_, json_data) VALUES (%(id_)s, %(json_data)s)]
[parameters: {'id_': '35008208-e84d-4e1d-b751-df8a8997666b', 'json_data': '{"hello": "world"}'}]
(Background on this error at: https://sqlalche.me/e/14/f405)

I also tried converting the dictionary to a string and wrapping it with "PARSE_JSON()".
None of it worked.

  1. What did you expect to see?

    I expect to be able to run

sess.add(my_item)
sess.commit()

And the dictionary to be written to snowflake as a json object with VARIANT type.

Is there any way to do that?

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementThe issue is a request for improvement or a new featurestatus-triage_doneInitial triage done, will be further handled by the driver team

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions