微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

PostgreSQL游标重新打开GnuCOBOL中的错误

我试图在gnucobol上从Oracle迁移到Postgresql.我有一段使用游标的代码,需要多次打开游标.但是当我再次尝试打开游标时,我收到错误ERROR:游标“fetchtbl_c1”已经存在

IDENTIFICATION              DIVISION.
        PROGRAM-ID.                 FETCHTBL.

        DATA                        DIVISION.
        WORKING-STORAGE             SECTION.
        01  D-SOC-REC.
            05  D-SOC-NO-1          PIC  X(3).
            05  FILLER              PIC  X.
            05  D-SOC-NO-2          PIC  X(3).

        EXEC sql BEGIN DECLARE SECTION END-EXEC.
        01  USERNAME                PIC  X(30) VALUE SPACE.
        01  SOC-REC-VARS.
            05  SOC-NO-1            PIC X(3).
            05  SOC-NO-2            PIC X(3).
        EXEC sql END DECLARE SECTION END-EXEC.

        EXEC sql INCLUDE sqlCA END-EXEC.
        PROCEDURE                   DIVISION.
        MAIN-RTN.
            MOVE  SPACE             TO   USERNAME.
            EXEC sql
                CONNECT :USERNAME
            END-EXEC.
            IF  sqlCODE NOT = ZERO disPLAY "ERROR CONNECTING".

       *    DECLARE CURSOR
            EXEC sql
                DECLARE C1 CURSOR FOR
                SELECT SOC_NO_1,SOC_NO_2
                       FROM INSP
                       ORDER BY SOC_NO_1
            END-EXEC.
            EXEC sql
                OPEN C1
            END-EXEC.
            IF sqlCODE = ZERO disPLAY "OPEN SUCCESSFUL"
            ELSE disPLAY "OPEN Failed".

       *    FETCH
            EXEC sql
                FETCH C1 INTO :SOC-NO-1,:SOC-NO-2
            END-EXEC.
            IF sqlCODE = ZERO disPLAY "FETCH SUCCESSFUL"
            ELSE disPLAY "FETCH Failed".
            PERFORM UNTIL sqlCODE NOT = ZERO
               MOVE  SOC-NO-1      TO    D-SOC-NO-1
               MOVE  SOC-NO-2      TO    D-SOC-NO-2
               disPLAY D-SOC-REC
               EXEC sql
                   FETCH C1 INTO :SOC-NO-1,:SOC-NO-2
               END-EXEC
            END-PERFORM.

       *    CLOSE CURSOR
            EXEC sql
                CLOSE C1
            END-EXEC.
            IF sqlCODE = ZERO disPLAY "CLOSE SUCCESSFUL"
            ELSE disPLAY "CLOSE Failed".

       *    OPEN AGAIN
            EXEC sql
                OPEN C1
            END-EXEC.
            IF sqlCODE = ZERO disPLAY "REOPEN SUCCESSFUL"
            ELSE disPLAY "REOPEN Failed " sqlERRMC.
       *    COMMIT
            EXEC sql
                COMMIT WORK
            END-EXEC.

       *    disCONNECT
            EXEC sql
                disCONNECT ALL
            END-EXEC.

       *    END
            STOP RUN.

使用ocesql预编译代码并使用cobc -x编译

Postgres输出

OPEN SUCCESSFUL
FETCH SUCCESSFUL
003 001
005 001
CLOSE SUCCESSFUL
REOPEN Failed ERROR:  cursor "fetchtbl_c1" already exists

上面的代码在Oracle中运行得非常好(连接部分除外).

Oracle输出

OPEN SUCCESSFUL
FETCH SUCCESSFUL
003 001
CLOSE SUCCESSFUL
REOPEN SUCCESSFUL

我试过在互联网上搜索但没有任何运气.有谁可以帮我这个?
我正在使用Postgresql版本10.3和gnucobol版本2.2.0.

解决方法

ocesql预编译器似乎存在问题.我已经在函数OCDBSetResultStatus中修改了ocdb.c,以便在没有结果资源的情况下返回成功的代码(对于打开的游标情况会发生这种情况).

这可能不完全正确,但经过几个小时的测试后,我发现这个工作正常.

代码更改:

int
OCDBSetResultStatus(int id,struct sqlca_t *st){
    struct s_conn *p_conn;
    int retval;

    p_conn = look_up_conn_lists(id);
    if(p_conn == NULL){
      //return OCDB_RES_FATAL_ERROR;
        return RESULT_ERROR;
    }
    if(p_conn->resaddr == OCDB_RES_DEFAULT_ADDRESS){
        // 結果リソースが無いため成功で返す
        // Ankit: uncommented since there is no result resource,//        (true in case of open cursor)
        return OCDB_RES_COMMAND_OK;
        //return RESULT_ERROR;
    }

#ifdef PGsql_mode_ON
    retval = OCDB_PGSetResultStatus(p_conn->resaddr,st);
#endif
    return retval;
}

如果有人因为这种变化而面临任何问题,请告诉我.

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。

相关推荐