K2InformaticsGmbH / erloci

Erlang Oracle native driver - DEPRECATED, see https://github.com/K2InformaticsGmbH/oranif instead
Apache License 2.0
37 stars 11 forks source link

Missing values of bound parameters on stmt reuse #23

Closed shamis closed 7 years ago

shamis commented 7 years ago

Following is an example of writing values and then reading the same back and checking for differences

Vars = [{<<":P_CON_ID">>, in,'SQLT_CHR'}, {<<":P_CON_ACID">>, in,'SQLT_CHR'}, {<<":P_CON_CONSOL">>, in,'SQLT_CHR'}, {<<":P_CON_DATEBLOCK">>, in,'SQLT_CHR'},{<<":P_CON_DATEEND">>, in,'SQLT_CHR'}, {<<":P_CON_DATESTART">>, in,'SQLT_CHR'}, {<<":P_CON_ESID">>, in,'SQLT_CHR'}, 
  {<<":P_CON_ESTID">>, in,'SQLT_CHR'},{<<":P_CON_ETID">>, in,'SQLT_CHR'}, {<<":P_CON_HDGROUP">>, in,'SQLT_CHR'}, {<<":P_CON_IGNORE_DUOBILL">>, in,'SQLT_CHR'}, {<<":P_CON_IWRS">>, in,'SQLT_CHR'},{<<":P_CON_MFGR">>, in,'SQLT_CHR'}, {<<":P_CON_MFLID">>, in,'SQLT_CHR'}, 
  {<<":P_CON_MINCHARGE">>, in,'SQLT_CHR'}, {<<":P_CON_MOROAMINGPROM">>, in,'SQLT_CHR'},{<<":P_CON_MTROAMINGPROM">>, in,'SQLT_CHR'}, {<<":P_CON_NAME">>, in,'SQLT_CHR'}, {<<":P_CON_PMID">>, in,'SQLT_CHR'}, {<<":P_CON_PRICE">>, in,'SQLT_CHR'},{<<":P_CON_PRICEHG">>, in,'SQLT_CHR'}, 
  {<<":P_CON_PRICEINT">>, in,'SQLT_CHR'}, {<<":P_CON_PRICEMOFN">>, in,'SQLT_CHR'}, {<<":P_CON_PROTOCOL">>, in,'SQLT_CHR'},{<<":P_CON_PSCALL">>, in,'SQLT_CHR'}, {<<":P_CON_RSID">>, in,'SQLT_CHR'}, {<<":P_CON_SHORTID">>, in,'SQLT_CHR'}, {<<":P_CON_TARID">>, in,'SQLT_CHR'},
  {<<":P_CON_THROUGPUT">>, in,'SQLT_CHR'}].

USql = <<"begin gpsh_tpac_con_put(:P_CON_ID,:P_CON_ACID,:P_CON_CONSOL,:P_CON_DATEBLOCK,:P_CON_DATEEND,:P_CON_DATESTART,:P_CON_ESID,:P_CON_ESTID,:P_CON_ETID,:P_CON_HDGROUP,:P_CON_IGNORE_DUOBILL,:P_CON_IWRS,:P_CON_MFGR,:P_CON_MFLID,:P_CON_MINCHARGE,:P_CON_MOROAMINGPROM,:P_CON_MTROAMINGPROM,:P_CON_NAME,:P_CON_PMID,:P_CON_PRICE,:P_CON_PRICEHG,:P_CON_PRICEINT,:P_CON_PRICEMOFN,:P_CON_PROTOCOL,:P_CON_PSCALL,:P_CON_RSID,:P_CON_SHORTID,:P_CON_TARID,:P_CON_THROUGPUT); end;">>.

RSql = <<"select * from GPSH_TPAC_CON_JSON where CKEY = :P_CON_ID">>.

f(OciPort).
f(Sess).
f(UpdStmt).
f(ConJsonStmt).
f(Diff).

OciPort = erloci:new([{env,[{"NLS_LANG","GERMAN_SWITZERLAND.AL32UTF8"}]}]).
Sess = OciPort:get_session(<<"(DESCRIPTION =(ENABLE=BROKEN)(ADDRESS_LIST=(ADDRESS=(PROTOCOL=TCP)(HOST=1.1.1.1)(PORT = 2222)))(CONNECT_DATA=(SERVER=DEDICATED)(SERVICE_NAME=XE)))">>, <<"a">>, <<"b">>).
UpdStmt = Sess:prep_sql(USql).
ok = UpdStmt:bind_vars(Vars).
ConJsonStmt = Sess:prep_sql(RSql).
ok = ConJsonStmt:bind_vars([{<<":P_CON_ID">>, in, 'SQLT_CHR'}]).
NValue = #{<<"CON_ACID">> => <<"546X0XM3HJ">>,
  <<"CON_CONSOL">> => <<"50254">>,
  <<"CON_DATEBLOCK">> => <<>>,
  <<"CON_DATEEND">> => <<>>,
  <<"CON_DATESTART">> => <<"2016-06-15T00:00:00Z">>,
  <<"CON_ESID">> => <<"A">>,
  <<"CON_ESTID">> => <<>>,
  <<"CON_ETID">> => <<"LAC">>,
  <<"CON_HDGROUP">> => <<"false">>,
  <<"CON_IGNORE_DUOBILL">> => <<"false">>,
  <<"CON_IWRS">> => <<>>,
  <<"CON_MFGR">> => <<>>,
  <<"CON_MFLID">> => <<>>,
  <<"CON_MINCHARGE">> => <<"200">>,
  <<"CON_MOROAMINGPROM">> => <<"false">>,
  <<"CON_MTROAMINGPROM">> => <<"false">>,
  <<"CON_NAME">> => <<"SMS Service">>,
  <<"CON_PMID">> => <<>>,
  <<"CON_PRICE">> => <<"8.00000000000000020000e-02">>,
  <<"CON_PRICEHG">> => <<"4.00000000000000010000e-02">>,
  <<"CON_PRICEINT">> => <<"8.00000000000000020000e-02">>,
  <<"CON_PRICEMOFN">> => <<>>,
  <<"CON_PROTOCOL">> => <<"UCP">>,
  <<"CON_PSCALL">> => <<"41754312835">>,
  <<"CON_RSID">> => <<"P0">>,
  <<"CON_SHORTID">> => <<>>,
  <<"CON_TARID">> => <<"h">>,
  <<"CON_THROUGHPUT">> => <<"1">>}.
Values =  [list_to_tuple([<<"ZK04ENGYDW">> | maps:values(NValue)])].
{executed, 1} = UpdStmt:exec_stmt(Values).
{cols, _} = ConJsonStmt:exec_stmt([{<<"ZK04ENGYDW">>}]).
{{rows, [[_,BinVal]]}, true}= ConJsonStmt:fetch_rows(1000).
DstVal =  maps:map(
      fun(_, I) when is_integer(I) -> integer_to_binary(I);
         (_, F) when is_float(F) -> float_to_binary(F);
         (_, null) -> <<>>;
         (_, A) when A == false; A == true -> atom_to_binary(A, utf8);
         (_, B) when is_binary(B) -> B
      end, maps:without([<<"AuditTime">>], imem_json:decode(BinVal, [return_maps]))).
lists:foldl(
        fun(K, M) ->
            L = maps:get(K, NValue, '$missing'),
            R = maps:get(K, DstVal , '$missing'),
            if L /= R ->
                   M#{K => #{local => L, remote => R}};
               true -> M
            end
        end, #{}, maps:keys(DstVal)).

Extected #{}. But this is not the case always