1

When i try to add user with BIG INT, psycopg2 throws Numberic Value out of range error. but still BIGINT is my data type in Column of my table and in local postgresql database.

Edit1: I have added the source code for chat_members model.

My table Schema code

    class Users(BASE):
    __tablename__ = "users"
    user_id = Column(BigInteger, primary_key=True)
    username = Column(UnicodeText)

    def __init__(self, user_id, username=None):
        self.user_id = user_id
        self.username = username

    def __repr__(self):
        return "<User {} ({})>".format(self.username, self.user_id)

class Chats(BASE):
    __tablename__ = "chats"
    chat_id = Column(String(14), primary_key=True)
    chat_name = Column(UnicodeText, nullable=False)

    def __init__(self, chat_id, chat_name):
        self.chat_id = str(chat_id)
        self.chat_name = chat_name

    def __repr__(self):
        return "<Chat {} ({})>".format(self.chat_name, self.chat_id)


class ChatMembers(BASE):
    __tablename__ = "chat_members"
    priv_chat_id = Column(Integer, primary_key=True)
    # NOTE: Use dual primary key instead of private primary key?
    chat = Column(
        String(14),
        ForeignKey("chats.chat_id", onupdate="CASCADE", ondelete="CASCADE"),
        nullable=False,
    )
    user = Column(
        BigInteger,
        ForeignKey("users.user_id", onupdate="CASCADE", ondelete="CASCADE"),
        nullable=False,
    )
    __table_args__ = (UniqueConstraint("chat", "user", name="_chat_members_uc"),)

    def __init__(self, chat, user):
        self.chat = chat
        self.user = user

    def __repr__(self):
        return "<Chat user {} ({}) in chat {} ({})>".format(
            self.user.username,
            self.user.user_id,
            self.chat.chat_name,
            self.chat.chat_id,
        )


Users.__table__.create(checkfirst=True)
Chats.__table__.create(checkfirst=True)
ChatMembers.__table__.create(checkfirst=True)

code which throws error:


 def update_user(user_id, username, chat_id=None, chat_name=None):
    with INSERTION_LOCK:
        user = SESSION.query(Users).get(user_id)
        if not user:
            user = Users(user_id, username)
            SESSION.add(user)
            SESSION.flush()
        else:
            user.username = username

        if not chat_id or not chat_name:
            SESSION.commit()
            return

        chat = SESSION.query(Chats).get(str(chat_id))
        if not chat:
            chat = Chats(str(chat_id), chat_name)
            SESSION.add(chat)
            SESSION.flush()

        else:
            chat.chat_name = chat_name

        member = (
            SESSION.query(ChatMembers)
            .filter(ChatMembers.chat == chat.chat_id, ChatMembers.user == user.user_id)
            .first()
        )
        if not member:
            chat_member = ChatMembers(chat.chat_id, user.user_id)
            SESSION.add(chat_member)

        SESSION.commit()

my init.py file:


def start() -> scoped_session:
    engine = create_engine(DB_URI, client_encoding="utf8")
    BASE.metadata.bind = engine
    BASE.metadata.create_all(engine)
    return scoped_session(sessionmaker(bind=engine, autoflush=False))


BASE = declarative_base()
SESSION = start()

Tracelog:

sqlalchemy.exc.DataError: (psycopg2.errors.NumericValueOutOfRange) integer out of range

[SQL: INSERT INTO chat_members (chat, "user") VALUES (%(chat)s, %(user)s) RETURNING chat_members.priv_chat_id]
[parameters: {'chat': '-1001779301880', 'user': 5030277858}]
(Background on this error at: https://sqlalche.me/e/14/9h9h)
  • What is the type of `chat` in `chat_members`? – rfkortekaas Mar 09 '22 at 08:12
  • chat data type is string in ChatMembers – Joker Hacker Mar 09 '22 at 10:52
  • 1) You do not show the model for `chat_members` 2) I would verify that the `user`(not a good name by the way) column is actually a `bigint` not an `int` as: `select 5030277858::int; ERROR: integer out of range` – Adrian Klaver Mar 09 '22 at 19:18
  • I have added the model, now can you look at it – Joker Hacker Mar 10 '22 at 10:29
  • If you do `from sqlalchemy import inspect` followed by `insp = inspect(engine)` and `info = [f"{x['name']}: {x['type']}" for x in insp.get_columns("chat_members")]` what does `info` contain? – Gord Thompson Mar 10 '22 at 13:38
  • Use `psql`(preferred) or some other client to verify that the `chat_members` table actually has `user` set to `bigint` in the database. While you are at it verify there is only one `chat_members` table in the database. In other words that you don't have it in multiple schema and the `INSERT` is picking up the wrong one because of the [search_path](https://www.postgresql.org/docs/current/ddl-schemas.html#DDL-SCHEMAS-PATH) – Adrian Klaver Mar 10 '22 at 16:12

0 Answers0