#include #include #include #include #include #include using namespace std; // The uglyness that is global variables :-) static char *version; static PGconn *conn; // Forward declaration static bool ProcessFile(char *fullname, char *filename); int main(int argc, char *argv[]) { // Check the syntax if (argc < 6) { cout << "Usage: " << argv[0] << " []\n\n"; exit(1); } version = argv[2]; struct dirent *de; DIR *d = opendir(argv[1]); if (!d) { cerr << "Couldn't open directory " << argv[1] << "!" << endl; exit(1); } // Open the db connection char connstr[1024]; sprintf(connstr, "host=%s dbname=%s user=%s", argv[3], argv[4], argv[5]); if (argc == 5) { strcat(connstr, " password="); strcat(connstr, argv[6]); } conn = PQconnectdb(connstr); if (PQstatus(conn) != CONNECTION_OK) { cerr << "Failed to connect to database: " << PQerrorMessage(conn) << endl; exit(1); } if (PQresultStatus(PQexec(conn, "BEGIN TRANSACTION")) != PGRES_COMMAND_OK) { cerr << "Failed to start transaction: " << PQerrorMessage(conn) << endl; exit(1); } char qry[128]; sprintf(qry,"DELETE FROM docs WHERE version='%s'",version); if (PQresultStatus(PQexec(conn, qry)) != PGRES_COMMAND_OK) { cerr << "Failed to delete old documentation: " << PQerrorMessage(conn) << endl; exit(1); } if (PQresultStatus( PQprepare(conn, "docins", "INSERT INTO docs (file, version, title, content) VALUES ($1, $2, $3, $4)", 4, NULL) ) != PGRES_COMMAND_OK) { cerr << "Failed to prepare insert statement: " << PQerrorMessage(conn) << endl; exit(1); } while ((de = readdir(d)) != NULL) { char fn[1024]; struct stat st; if (!strcmp(de->d_name,".") || !strcmp(de->d_name,"..")) continue; sprintf(fn, "%s/%s", argv[1], de->d_name); if (stat(fn, &st) < 0) { cerr << "Couldn't stat file " << fn << "!" << endl; exit(1); } if (S_ISDIR(st.st_mode)) { cerr << "Found subdirectory: " << fn << endl << "NOT SUPPORTED!" << endl; exit(1); } else { cout << "Processing file: " << de->d_name << endl; if (!ProcessFile(fn, de->d_name)) exit(1); } } closedir(d); if (PQresultStatus(PQexec(conn, "COMMIT")) != PGRES_COMMAND_OK) { cerr << "Failed to commit transaction: " << PQerrorMessage(conn) << endl; exit(1); } PQfinish(conn); return 0; } static bool ProcessFile(char *fullname, char *filename) { // Open the file ifstream inFile(fullname); if (!inFile) { cerr << "Couldn't open " << fullname << " for input!" << endl; return false; } // Read, and try to tidy up the HTML a bit. This is a hack from hell, but if DocBook // didn't write such nastily formatted HTML... int inBody = 0, inPre = 0; char str1[8192], str2[256000], content[256000], title[255], temp[2]; memset(str1,0,sizeof(str1)); memset(content,0,sizeof(content)); memset(title,0,sizeof(title)); memset(temp,0,sizeof(temp)); while (!inFile.eof()) { char *str1pt = str1; inFile.getline(str1, 8192, '\n'); if ((inBody == 1) && (strstr(str1, ">") != 0)) { inBody = 2; if (str1[0] == '>') str1pt++; /* Skip past this starter */ } else { if (strstr(str1, ""); // Execute our prepared query PGresult *qryRes; char *paramVals[4] = { filename, version, title, content }; int paramLengths[4] = { strlen(filename), strlen(version), strlen(title), strlen(content) }; qryRes = PQexecPrepared(conn, "docins", 4, paramVals, paramLengths, NULL, 0); if (PQresultStatus(qryRes) != PGRES_COMMAND_OK) { cerr << "Query failed: " << PQerrorMessage(conn) << endl; exit(1); } PQclear(qryRes); return true; }