Search code examples
c++linuxapachewebunixodbc

Linux Apache CGI can't open lib when visiting the website


I'm using unixODBC and Apache CGI to build a database website on Linux. The following problems occurred when I tested the query of the database.

Connect Error
[01000] [unixODBC][Driver Manager]Can't open lib '/usr/local/lib/psqlodbcw.so' : file not found (0)

The above information appears on another computer on which I tried to access the website using Windows.

http://serverIP/cgi-bin/website.cgi?first=1

Strangely, when I run this CGI file directly on the Linux server, it executes normally. That is, successfully connect to the database and query the output results. The successful connection of isql also proves that it can connect to the database.

Equivalent to the following

root@VM-4-11-ubuntu:~# /var/www/cgi-bin/website.cgi
Content-type:text/html

<html>
  <head>
    <title>test button</title>
  </head>
  <body>
    <p>Connected!</p>
    <p>SELECT * FROM people WHERE id = 1;<p>
    <p>id = 1 name = Tom</p>
  </body>
</html>
// -----
root@VM-4-11-ubuntu:~# curl http://localhost/cgi-bin/website.cgi
<html>
  <head>
    <title>test button</title>
  </head>
  <body>
    <p>Connect Error</p>
    <p>[01000] [unixODBC][Driver Manager]Can't open lib '/usr/local/lib/psqlodbcw.so' : file not found (0)</p>
  </body>
</html>

The following is the code to output the error message

// In DataBase's constructor
// ...
  V_OD_erg = SQLConnect(V_OD_hdbc, dataSource, SQL_NTS,
                        usrName, SQL_NTS, password, SQL_NTS);
  if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO)) {
    noErr = false;
    printf("<p>Connect Error</p>\n");
    showDBCErr(V_OD_erg);
  }
// ...
void DataBase::showDBCErr(SQLRETURN retCode) {
  HandleDiagnosticRecord(V_OD_hdbc, SQL_HANDLE_DBC, retCode);
}
// ...
void DataBase::HandleDiagnosticRecord(SQLHANDLE hHandle, SQLSMALLINT hType,
                                      RETCODE RetCode) {
  SQLSMALLINT iRec = 0;
  SQLINTEGER iError;
  SQLCHAR wszMessage[1000];
  SQLCHAR wszState[SQL_SQLSTATE_SIZE + 1];

  if (RetCode == SQL_INVALID_HANDLE) {
    printf("<p>Invalid handle!</p>");
    return;
  }

  while (SQLGetDiagRec(hType, hHandle, ++iRec, wszState, &iError, wszMessage,
                       (SQLSMALLINT)(sizeof(wszMessage) / sizeof(SQLCHAR)),
                       (SQLSMALLINT*)NULL) == SQL_SUCCESS) {
    // Hide data truncated..
    if (strcmp((const char*)wszState, "01004")) {
      printf("<p>[%5.5s] %s (%d)</p>", wszState, wszMessage, iError);
    }
  }
}

// in /usr/local/etc/odbcinst.ini
[ODBC]
Trace=Yes
TraceFile=~/unixODBCLog/odbctrace.log

[GaussMPP]
Driver64=/usr/local/lib/psqlodbcw.so
setup=/usr/local/lib/psqlodbcw.so

// in ~/.bashrc
# ...
export LD_LIBRARY_PATH=/usr/local/lib/:$LD_LIBRARY_PATH
export ODBCSYSINI=/usr/local/etc
export ODBCINI=/usr/local/etc/odbc.ini
root@VM-4-11-ubuntu:~# odbcinst -j
unixODBC 2.3.7pre
DRIVERS............: /usr/local/etc/odbcinst.ini
SYSTEM DATA SOURCES: /usr/local/etc/odbc.ini
FILE DATA SOURCES..: /usr/local/etc/ODBCDataSources
USER DATA SOURCES..: /usr/local/etc/odbc.ini
SQLULEN Size.......: 8
SQLLEN Size........: 8
SQLSETPOSIROW Size.: 8

I have no idea how to solve this problem. I can provide more information if necessary.


Solution

  • Okay, guys, I've solved this problem. Like Some programmer dude said, "Generally don't use the root user for any kind of development, that can give you the false impression that things works ". When I use tar as ubuntu (not root), system shows the same error "file not found". Then I realize that the ODBC library installed as root may not be available to ordinary users. So I reinstall as ubuntu. It works!

    Thanks, @Some programmer dude, @Alan Birtles, @Stephen Ostermiller