will/crystal-pg

No method overload with Array(Time)

jwoertink opened this issue · 5 comments

When reading out with __temp_104.read(Array(Time)) I get this error:

instantiating 'PG::ResultSet#read(Array(Time).class)'
in lib/pg/src/pg/result_set.cr:93: instantiating 'read_array(Array(Time).class)'

    read_array(Array(T)) do
    ^~~~~~~~~~

in lib/pg/src/pg/result_set.cr:112: instantiating 'PG::Decoders:Module#decode_array(IO+, Int32, Array(Time).class)'

      Decoders.decode_array(conn.soc, col_bytesize, T)
               ^~~~~~~~~~~~

in lib/pg/src/pg/decoders/array_decoder.cr:60: instantiating 'decode_array_element(IO+, Array(Time).class, Array(NamedTuple(dim: Int32, lbound: Int32)))'

      decode_array_element(io, t, dim_info)
      ^~~~~~~~~~~~~~~~~~~~

in lib/pg/src/pg/decoders/array_decoder.cr:66: no overload matches 'PG::Decoders.decode_array_element' with types IO+, Time.class, Array(NamedTuple(dim: Int32, lbound: Int32))
Overloads are:
 - PG::Decoders.decode_array_element(io, t : Array(T).class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Bool.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Bool | ::Nil.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Char.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Char | ::Nil.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Int16.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Int16 | ::Nil.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Int32.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Int32 | ::Nil.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : String.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : String | ::Nil.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Int64.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Int64 | ::Nil.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Float32.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Float32 | ::Nil.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Float64.class, dim_info)
 - PG::Decoders.decode_array_element(io, t : Float64 | ::Nil.class, dim_info)

      Array(T).new(size) { decode_array_element(io, T, rest) }
                           ^~~~~~~~~~~~~~~~~~~~

From looking at that list, I'm gonna assume Array(UUID) would also have the same issue. Not sure if those are difficult to add, but just wanted to give a heads up just in case.

will commented

Would you be willing to submit a patch for these types and tests? It should be doable.

the shoddy psql example program helps figure out the binary formats

~/c/crystal-pg (master)> crystal examples/shoddy_psql.cr
# select array[now(),now()]
 array
---------------------------------------------------------------------------------------------------------------------------------------------------------------
 Bytes[0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 4, 160, 0, 0, 0, 2, 0, 0, 0, 1, 0, 0, 0, 8, 0, 2, 48, 220, 87, 219, 76, 143, 0, 0, 0, 8, 0, 2, 48, 220, 87, 219, 76, 143]
(1 row)

# ⏎

as well as the hexdump in crystal (that I added to help build these binary types and the wire protocol :) ) https://crystal-lang.org/api/0.29.0/IO/Hexdump.html

Then the regular decoders are at
https://github.com/will/crystal-pg/blob/master/src/pg/decoder.cr
https://github.com/will/crystal-pg/blob/master/spec/pg/decoder_spec.cr
to see how most of the binary decoding is done

and the array versions are at
https://github.com/will/crystal-pg/blob/master/src/pg/decoders/array_decoder.cr
https://github.com/will/crystal-pg/blob/master/spec/pg/decoders/array_decoder_spec.cr

I can take a look. It may be above my skill, but worth a shot! Thanks for the help.

I can do this. It should be pretty easy now that I know how arrays are decoded. I'll probably do it on top of #173

boom! 💥 That's amazing! Great work @asterite thanks so much for tackling that.