from typing import Callable, cast, Optional, Tuple
from .abc import Buffer
+from . import errors as e
from ._compat import Protocol, TypeAlias
PackInt: TypeAlias = Callable[[int], bytes]
_struct_len = struct.Struct("!i")
pack_len = cast(Callable[[int], bytes], _struct_len.pack)
unpack_len = cast(UnpackLen, _struct_len.unpack_from)
+
+
+def pack_float4_bug_304(x: float) -> bytes:
+ raise e.InterfaceError(
+ "cannot dump Float4: Python affected by bug #304,"
+ " see https://github.com/psycopg/psycopg/issues/304"
+ )
+
+
+# If issue #304 is detected, raise an error instead of dumping wrong data.
+if struct.Struct("!f").pack(1.0) != bytes.fromhex("3f800000"):
+ pack_float4 = pack_float4_bug_304
assert result == 1
+@pytest.mark.parametrize("wrapper", "Int2 Int4 Int8 Oid Float4 Float8".split())
+@pytest.mark.parametrize("fmt_in", PyFormat)
+def test_dump_wrapper(conn, wrapper, fmt_in):
+ wrapper = getattr(psycopg.types.numeric, wrapper)
+ obj = wrapper(1)
+ cur = conn.execute(
+ f"select %(obj){fmt_in.value} = 1, %(obj){fmt_in.value}", {"obj": obj}
+ )
+ rec = cur.fetchone()
+ assert rec[0], rec[1]
+
+
@pytest.mark.parametrize("wrapper", "Int2 Int4 Int8 Oid Float4 Float8".split())
def test_dump_wrapper_oid(wrapper):
wrapper = getattr(psycopg.types.numeric, wrapper)