可以重用数据库连接吗?

时间:2013-01-04 11:10:40

标签: c++ sql postgresql

我正在尝试创建一个可以访问PostgreSQL数据库的程序。问题是我一直在

  

警告:已有正在进行的交易

消息和程序很快就会退出。我是否需要在需要时关闭并重新打开连接,还是可以解决问题并在整个程序中重复使用相同的连接?

    int i = 0;
    std::string spassw = "";
    std::string suname = "";

    theconn = NULL;

    // Make a connection to the database
    theconn = PQconnectdb("user=postgres password=changeme dbname=database hostaddr=127.0.0.1    port=5432");

    // Check to see that the backend connection was successfully made
    if ( PQstatus(theconn) != CONNECTION_OK )   {

        std::cout << "Connection to database failed.\nPress any key to continue.\n";
        PQfinish(theconn);
        getchar();
        exit(1);
     }

    PGresult *res  = PQexec(theconn, "BEGIN");

    if (PQresultStatus(res) != PGRES_COMMAND_OK)    {

        printf("BEGIN command failed");
        PQclear(res);
        PQfinish(theconn);
        std::cout << "Goodbye.\n";
        getchar();
        exit(1);
    }

    // Clear result
    PQclear(res);

    res = PQexec(theconn, "DECLARE emprec CURSOR FOR select * from dbtable");

    if (PQresultStatus(res) != PGRES_COMMAND_OK)    {

        printf("DECLARE CURSOR failed\n");
        PQclear(res);
        PQfinish(theconn);
        std::cout << "Goodbye.\n";
        getchar();
        exit(1);
     }

    PQclear(res);
    res = PQexec(theconn, "FETCH ALL in emprec");

    if (PQresultStatus(res) != PGRES_TUPLES_OK) {

        printf("FETCH ALL failed");
        PQclear(res);
        PQfinish(theconn);
        std::cout << "Goodbye.\n";
        getchar();
        exit(1);
    }

    for ( i = 0; i < PQntuples(res); i++ )    {

        std::string suname = PQgetvalue( res, i, 0 );
        std::string spassw = PQgetvalue( res, i, 1 );

        if( pname == suname && pword == spassw )    {

        res = PQexec( theconn, "COMMIT");
        PQclear(res);

        res = PQexec(theconn, "CLOSE emprec" );
        PQclear(res);

        // End the transaction
        res = PQexec(theconn, "END");

        // Clear result
        PQclear(res);
        return true;
        }

    }

    res = PQexec( theconn, "COMMIT");
        PQclear(res);

    res = PQexec(theconn, "CLOSE emprec");
    PQclear(res);

    // End the transaction
    res = PQexec(theconn, "END");

    // Clear result
    PQclear(res);


    return false;
}

2 个答案:

答案 0 :(得分:4)

这里有一个提示:您可以在整个应用程序执行过程中使用单个连接,但需要注意事务。您收到的警告是由于正在进行的交易,因此请确保您正确地提交和关闭交易。我不能给你一个关于你的c ++代码的建议,因为我不是一个c ++程序员,但看起来你的问题不是语言特定的,而是概念性的。如果不这样做,我道歉。

答案 1 :(得分:0)

由于代码有一个BEGIN来启动一个事务,它应该有一个(只有一个)匹配COMMITEND,但不能同时匹配。{/ p>

原因是END实际上是COMMIT的同义词。以下是manual对此的说法:

  

此命令是PostgreSQL扩展,相当于COMMIT。

鉴于你的代码当前是如何通过关闭游标来组织的,出现了:

   res = PQexec( theconn, "COMMIT");
        PQclear(res);

应该被删除。