Annotation of rpm2html/sql.c, revision 1.35
1.1 veillard 1: /*
2: * sql.c: front-end for MySQL database
3: */
4:
1.2 veillard 5: #include "config.h"
6:
7: #include <stdio.h>
8: #include <stdlib.h>
9: #include <sys/types.h>
10: #include <sys/stat.h>
11: #ifdef HAVE_FCNTL_H
12: #include <fcntl.h>
13: #endif
1.1 veillard 14: #include <stdio.h>
15: #include <stdlib.h>
1.2 veillard 16: #include <string.h>
1.28 daniel 17: #include <time.h>
1.2 veillard 18: #ifdef HAVE_UNISTD_H
19: #include <unistd.h>
20: #endif
21: /********
22: #include <rpm/rpmlib.h>
23: ********/
24:
1.1 veillard 25: #include <mysql/mysql.h>
1.16 veillard 26: #include <mysql/errmsg.h>
1.2 veillard 27: #include "rpm2html.h"
1.26 veillard 28: #include "rpmdata.h"
1.2 veillard 29: /********
30: #include "rpmdata.h"
31: ********/
1.1 veillard 32: #include "sql.h"
1.28 daniel 33: #include "html.h"
1.1 veillard 34:
1.31 veillard 35: #define SQL_DEBUG_TIMING
36:
1.26 veillard 37: #define SQL_MAX_DISTRIBS 500
38:
1.1 veillard 39: /************************************************************************
40: * *
41: * Generic inititialisation/close of the DB *
42: * *
43: ************************************************************************/
44:
45: static MYSQL *sql = NULL;
1.16 veillard 46: static const char *myhost, *mybase, *myuser, *mypasswd;
1.1 veillard 47:
1.11 veillard 48: int init_sql(const char *host, const char *base, const char *user, const char *passwd) {
1.16 veillard 49: int attempts = 0;
50:
51: /*
52: * Close the previous connection if any
53: */
54: if (sql != NULL) {
55: close_sql();
56: if (myhost != NULL) free((char *) myhost);
57: myhost = NULL;
58: if (mybase != NULL) free((char *) mybase);
59: mybase = NULL;
60: if (myuser != NULL) free((char *) myuser);
61: myuser = NULL;
62: if (mypasswd != NULL) free((char *) mypasswd);
63: mypasswd = NULL;
64: }
65:
1.11 veillard 66: if (host == NULL)
67: host = getenv("MySQL_HOST");
68: if (host == NULL)
69: host = "localhost";
70: if (base == NULL)
71: base = getenv("MySQL_BASE");
1.1 veillard 72: if (base == NULL)
73: base = "rpmfind";
74: if (passwd == NULL)
75: passwd = getenv("MySQL_PASS");
76: if (user == NULL)
77: user = getenv("MySQL_USER");
78: if (user == NULL)
79: user = getenv("USER");
80: if (user == NULL)
81: user = getenv("USERNAME");
82: if (user == NULL)
83: user = getenv("LOGNAME");
84: sql = mysql_init(NULL);
85: if (mysql_errno(sql)) {
86: fprintf(stderr, "mysql_init failed: %s\n", mysql_error(sql));
87: return(-1);
88: }
1.16 veillard 89: for (attempts = 0; ;attempts ++) {
90: mysql_real_connect(sql, host, user, passwd, base, 0, NULL, 0);
91: if (mysql_errno(sql)) {
1.26 veillard 92: if ((attempts == 0) && (passwd == NULL)) {
93: fprintf(stderr, "No passwd defined, use MySQL_PASS env\n");
94: }
1.16 veillard 95: if (attempts >= 20) {
96: fprintf(stderr,
97: "mysql: connect as %s to %s on host %s failed: %s\n",
98: user, base, host, mysql_error(sql));
1.24 daniel 99: return(-1);
100: } else {
101: fprintf(stderr,
102: "mysql: retrying connect as %s to %s on host %s failed: %s\n",
103: user, base, host, mysql_error(sql));
1.16 veillard 104: }
105: } else {
106: break;
107: }
108: sleep(15);
1.1 veillard 109: }
1.16 veillard 110: myhost = strdup(host);
111: mybase = strdup(base);
112: myuser = strdup(user);
113: mypasswd = strdup(passwd);
1.2 veillard 114: sql_check_tables();
1.1 veillard 115: return(0);
116: }
117:
118: int close_sql(void) {
119: mysql_close(sql);
120: if (mysql_errno(sql)) {
121: fprintf(stderr, "mysql_close failed: %s\n", mysql_error(sql));
122: return(-1);
123: }
1.16 veillard 124: sql = NULL;
1.1 veillard 125: return(0);
126: }
127:
1.16 veillard 128: int restart_sql(void) {
129: int attempts = 0;
130:
131: /*
132: * Close the previous connection if any
133: */
134: if (sql != NULL) {
135: close_sql();
136: sql = NULL;
137: }
138:
139: sql = mysql_init(NULL);
140: if (mysql_errno(sql)) {
141: fprintf(stderr, "mysql_init failed: %s\n", mysql_error(sql));
142: return(-1);
143: }
144: for (attempts = 0; ;attempts ++) {
145: mysql_real_connect(sql, myhost, myuser, mypasswd, mybase, 0, NULL, 0);
146: if (mysql_errno(sql)) {
147: if (attempts >= 20) {
148: fprintf(stderr,
149: "mysql: reconnect as %s to %s on host %s failed: %s\n",
150: myuser, mybase, myhost, mysql_error(sql));
151: return(-1);
152: }
153: } else {
154: break;
155: }
156: sleep(15);
157: }
158: sql_check_tables();
159: return(0);
160: }
161:
162: /*
163: * Handle disconnects by doing a reconnect and a retry.
164: */
165: int do_sql_query(const char *query, int len) {
166: int res;
167:
168: if (sql == NULL) {
169: res = restart_sql();
170: if (res != 0)
171: return(res);
172: }
173: res = mysql_real_query(sql, query, len);
1.19 daniel 174: if ((res == CR_SERVER_GONE_ERROR) || (res == CR_SERVER_LOST)) {
1.16 veillard 175: res = restart_sql();
176: if (res != 0)
177: return(res);
178: res = mysql_real_query(sql, query, len);
179: }
180: return(res);
181: }
182:
1.1 veillard 183: /************************************************************************
184: * *
185: * Generic functions to access the tables *
186: * *
187: ************************************************************************/
188:
1.6 veillard 189: #define MAX_QUERY 8000
190: #define SMALL_QUERY 500
1.1 veillard 191:
192: int sql_update_id(const char *table, int id,
193: const char *field, const char *value) {
194: MYSQL_RES *result;
1.6 veillard 195: char query[MAX_QUERY];
1.1 veillard 196: int nb_fields = 0;
1.6 veillard 197: int left = MAX_QUERY - 1;
198: int len;
199: char *end;
1.1 veillard 200:
201: if ((table == NULL) ||
202: (field == NULL) || (value == NULL))
203: return(-1);
204:
1.6 veillard 205: len = snprintf(query, left, "UPDATE %s SET %s='", table, field);
206: if (len < 0) {
207: fprintf(stderr, "sql_update_id : %s(%d).%s overflow\n",
208: table, id, field);
209: return(-1);
210: }
211: end = &query[len];
212: left -= len;
213: len = strlen(value);
214: if (len * 2 >= left) {
215: fprintf(stderr, "sql_update_id : %s(%d).%s overflow\n",
216: table, id, field);
217: return(-1);
218: }
219: len = mysql_escape_string(end, value, len);
220: left -= len;
221: if (left <= 0) {
222: fprintf(stderr, "sql_update_id : %s(%d).%s overflow\n",
223: table, id, field);
224: return(-1);
225: }
226: end += len;
227: len = snprintf(end, left, "' WHERE ID=%d", id);
228: if (len < 0) {
229: fprintf(stderr, "sql_update_id : %s(%d).%s overflow\n",
230: table, id, field);
231: return(-1);
232: }
233: end += len;
234: query[MAX_QUERY - 1] = 0;
235:
1.16 veillard 236: if (do_sql_query(query, (unsigned int) (end - query))) {
1.1 veillard 237: printf("sql_update_id: UPDATE %s %d failed: %s\n",
238: table, id, mysql_error(sql));
239: return(-1);
240: }
241: result = mysql_store_result(sql);
242: if (result != NULL) {
243: nb_fields = mysql_num_fields(result);
244: mysql_free_result(result);
245: } else {
246: nb_fields = 1;
247: }
248: if(mysql_errno(sql)) {
249: fprintf(stderr, "sql_update_id UPDATE error: %s\n",
250: mysql_error(sql));
251: return(-1);
252: }
253: return(nb_fields);
254: }
255:
256: int sql_blind_insert(const char *table, const char *key,
257: const char *value, int id) {
258: MYSQL_RES *result;
1.6 veillard 259: char query[MAX_QUERY];
260: int left = MAX_QUERY - 1;
261: int len;
262: char *end;
1.8 veillard 263: int insert = -1;
1.1 veillard 264:
1.2 veillard 265: if ((table == NULL) ||
1.1 veillard 266: (key == NULL) || (value == NULL))
267: return(-1);
268:
269: /*
270: * Search first for the ID if it already exists
271: */
1.2 veillard 272: if (id > 0) {
1.6 veillard 273: len = snprintf(query, left, "INSERT INTO %s (ID, %s) VALUES (%d, '",
274: table, key, id);
275: if (len < 0) {
276: fprintf(stderr, "sql_blind_insert : %s(%d).%s overflow\n",
277: table, id, key);
278: return(-1);
279: }
280: end = &query[len];
281: left -= len;
282: len = strlen(value);
283: if (len * 2 >= left) {
284: fprintf(stderr, "sql_blind_insert : %s(%d).%s overflow\n",
285: table, id, key);
286: return(-1);
287: }
288: len = mysql_escape_string(end, value, len);
289: left -= len;
290: if (left <= 0) {
291: fprintf(stderr, "sql_blind_insert : %s(%d).%s overflow\n",
292: table, id, key);
293: return(-1);
294: }
295: end += len;
296: len = snprintf(end, left, "')");
297: if (len < 0) {
298: fprintf(stderr, "sql_blind_insert : %s(%d).%s overflow\n",
299: table, id, key);
300: return(-1);
301: }
302: end += len;
303: query[MAX_QUERY - 1] = 0;
304:
1.2 veillard 305: } else {
1.6 veillard 306: len = snprintf(query, left, "INSERT INTO %s (%s) VALUES ('",
307: table, key);
308: if (len < 0) {
309: fprintf(stderr, "sql_blind_insert : %s.%s overflow\n",
310: table, key);
311: return(-1);
312: }
313: end = &query[len];
314: left -= len;
315: len = strlen(value);
316: if (len * 2 >= left) {
317: fprintf(stderr, "sql_blind_insert : %s.%s overflow\n",
318: table, key);
319: return(-1);
320: }
321: len = mysql_escape_string(end, value, len);
322: left -= len;
323: if (left <= 0) {
324: fprintf(stderr, "sql_blind_insert : %s.%s overflow\n",
325: table, key);
326: return(-1);
327: }
328: end += len;
329: len = snprintf(end, left, "')");
330: if (len < 0) {
331: fprintf(stderr, "sql_blind_insert : %s.%s overflow\n",
332: table, key);
333: return(-1);
334: }
335: end += len;
336: query[MAX_QUERY - 1] = 0;
337:
1.2 veillard 338: }
1.6 veillard 339: query[MAX_QUERY - 1] = 0;
1.16 veillard 340: if (do_sql_query(query, (unsigned int) (end - query))) {
1.6 veillard 341: #ifdef SQL_DEBUG
342: fprintf(stderr, "sql_blind_insert Error: %s\n", mysql_error(sql));
343: #endif
1.1 veillard 344: return(-1);
345: }
346: result = mysql_store_result(sql);
1.8 veillard 347: insert = mysql_insert_id(sql);
1.1 veillard 348: if (result) {
349: mysql_free_result(result);
1.8 veillard 350: return(insert);
1.1 veillard 351: }
352: if(mysql_errno(sql)) {
353: fprintf(stderr, "sql_blind_insert Error: %s\n", mysql_error(sql));
354: return(-1);
355: }
1.8 veillard 356: return(insert);
1.1 veillard 357: }
358:
359: int sql_update(const char *table, const char *name,
360: const char *field, const char *value) {
361: MYSQL_RES *result;
362: MYSQL_ROW row;
1.6 veillard 363: char query[MAX_QUERY];
1.1 veillard 364: int id;
365: int nb_fields = 0;
1.6 veillard 366: int left = MAX_QUERY - 1;
367: int len;
368: char *end;
1.1 veillard 369:
370: if ((name == NULL) || (table == NULL) ||
371: (field == NULL) || (value == NULL))
372: return(-1);
373:
374: /*
375: * Search first for the ID if it already exists
376: */
1.6 veillard 377: snprintf(query, MAX_QUERY - 1, "SELECT ID FROM %s WHERE Name='%s'", table, name);
378: query[MAX_QUERY - 1] = 0;
1.1 veillard 379: if (mysql_query(sql,query)) {
380: printf("sql_update: SELECT failed\n");
381: return(-1);
382: }
383:
384: result = mysql_use_result(sql);
385: if (result) {
386: while((row = mysql_fetch_row(result)))
387: {
388: if (row[0] == NULL) {
389: printf("sql_update: select ID for %s returns NULL !\n", name);
390: return(-1);
391: }
392: if (sscanf(row[0], "%d", &id) != 1) {
393: printf("sql_update: ID non numeric %s\n", row[0]);
394: return(-1);
395: }
1.6 veillard 396:
397: left = MAX_QUERY - 1;
398: len = snprintf(query, left, "UPDATE %s SET %s='", table, field);
399: if (len < 0) {
400: fprintf(stderr, "sql_update : %s(%d).%s overflow\n",
401: table, id, field);
402: return(-1);
403: }
404: end = &query[len];
405: left -= len;
406: len = strlen(value);
407: if (len * 2 >= left) {
408: fprintf(stderr, "sql_update : %s(%d).%s overflow\n",
409: table, id, field);
410: return(-1);
411: }
412: len = mysql_escape_string(end, value, len);
413: left -= len;
414: if (left <= 0) {
415: fprintf(stderr, "sql_update : %s(%d).%s overflow\n",
416: table, id, field);
417: return(-1);
418: }
419: end += len;
420: len = snprintf(end, left, "' WHERE ID=%d", id);
421: if (len < 0) {
422: fprintf(stderr, "sql_update : %s(%d).%s overflow\n",
423: table, id, field);
424: return(-1);
425: }
426: end += len;
427: query[MAX_QUERY - 1] = 0;
428:
1.1 veillard 429: mysql_free_result(result);
1.16 veillard 430: if (do_sql_query(query, (unsigned int) (end - query))) {
1.2 veillard 431: printf("sql_update: UPDATE failed: %s\n", mysql_error(sql));
1.1 veillard 432: return(-1);
433: }
434: result = mysql_store_result(sql);
435: if (result != NULL) {
436: nb_fields = mysql_num_fields(result);
437: mysql_free_result(result);
438: } else {
1.2 veillard 439: return(1);
1.1 veillard 440: }
441: /* Do not loop ... only the first */
442: return(nb_fields);
443: }
444: mysql_free_result(result);
1.2 veillard 445: if (nb_fields == 0) {
446: /*
447: * Propagate an insert
448: */
1.6 veillard 449: snprintf(query, MAX_QUERY - 1,
1.2 veillard 450: "INSERT INTO %s (Name,%s) VALUES ('%s','%s')",
451: table, field, name, value);
1.6 veillard 452: query[MAX_QUERY - 1] = 0;
1.2 veillard 453: mysql_free_result(result);
454: if (mysql_query(sql, query)) {
455: printf("sql_update: INSERT failed: %s\n", mysql_error(sql));
456: return(-1);
457: }
458: result = mysql_store_result(sql);
459: if (result != NULL) {
460: nb_fields = mysql_num_fields(result);
461: mysql_free_result(result);
462: } else {
463: return(1);
464: }
465: }
1.1 veillard 466: }
467: if(mysql_errno(sql)) {
468: fprintf(stderr, "sql_update Error: %s\n", mysql_error(sql));
469: return(-1);
470: }
471: return(nb_fields);
472: }
473:
1.6 veillard 474: int sql_get_key(const char *table, const char *name, const char *value) {
1.1 veillard 475: int id;
476: MYSQL_RES *result;
477: MYSQL_ROW row;
1.6 veillard 478: char query[SMALL_QUERY];
1.1 veillard 479:
480: if ((table == NULL) || (name == NULL))
481: return(-1);
482:
483: /*
484: * Search first for the ID if it already exists
485: */
1.6 veillard 486: snprintf(query, SMALL_QUERY - 1, "SELECT ID FROM %s WHERE %s='%s'",
487: table, name, value);
488: query[SMALL_QUERY - 1] = 0;
1.1 veillard 489: if (mysql_query(sql,query)) {
490: printf("sql_create: SELECT %s failed %s\n", name, mysql_error(sql));
491: return(-1);
492: }
493:
494: result = mysql_use_result(sql);
495: if (result) {
496: while((row = mysql_fetch_row(result)))
497: {
498: /*
499: * Lookup the first ID and return it
500: */
501: if (row[0] == NULL) {
502: mysql_free_result(result);
503: printf("sql_create: select returns NULL !\n");
504: return(-1);
505: }
506: if (sscanf(row[0], "%d", &id) != 1) {
507: mysql_free_result(result);
508: printf("sql_create: ID non numeric %s\n", row[0]);
509: return(-1);
510: }
511: mysql_free_result(result);
512: return(id);
513: }
514: mysql_free_result(result);
515: }
516: if(mysql_errno(sql)) {
517: fprintf(stderr, "Error: %s\n", mysql_error(sql));
518: return(-1);
519: }
520:
521: /*
522: * Do a creation
523: */
524:
1.6 veillard 525: snprintf(query, SMALL_QUERY - 1, "INSERT INTO %s (%s) VALUES ('%s')",
526: table, name, value);
527: query[SMALL_QUERY - 1] = 0;
1.1 veillard 528: if (mysql_query(sql,query)) {
1.2 veillard 529: printf("sql_get_key: INSERT %s failed %s\n", name, mysql_error(sql));
1.1 veillard 530: return(-1);
531: }
532: id = mysql_insert_id(sql);
533: result = mysql_store_result(sql);
534: if (result != NULL)
535: mysql_free_result(result);
536: return(id);
537: }
538:
539: int sql_read_key(const char *table, const char *name) {
540: int id;
541: MYSQL_RES *result;
542: MYSQL_ROW row;
1.6 veillard 543: char query[SMALL_QUERY];
1.1 veillard 544:
545: if ((table == NULL) || (name == NULL))
546: return(-1);
547:
548: /*
549: * Search for the ID it has to exist
550: */
1.6 veillard 551: snprintf(query, SMALL_QUERY - 1, "SELECT ID FROM %s WHERE Name='%s'", table, name);
552: query[SMALL_QUERY - 1] = 0;
1.2 veillard 553: if (mysql_query(sql,query)) {
554: printf("sql_create: SELECT %s failed %s\n", name, mysql_error(sql));
555: return(-1);
556: }
557:
558: result = mysql_use_result(sql);
559: if (result) {
560: while((row = mysql_fetch_row(result)))
561: {
562: /*
563: * Lookup the first ID and return it
564: */
565: if (row[0] == NULL) {
566: mysql_free_result(result);
567: printf("sql_create: select returns NULL !\n");
568: return(-1);
569: }
570: if (sscanf(row[0], "%d", &id) != 1) {
571: mysql_free_result(result);
572: printf("sql_create: ID non numeric %s\n", row[0]);
573: return(-1);
574: }
575: mysql_free_result(result);
576: return(id);
577: }
578: mysql_free_result(result);
579: }
580: if(mysql_errno(sql)) {
581: fprintf(stderr, "Error: %s\n", mysql_error(sql));
582: return(-1);
583: }
584: return(-1);
585: }
586:
587: int sql_read_info_key(const char *table, const char *name, const char *value) {
588: int id;
589: MYSQL_RES *result;
590: MYSQL_ROW row;
1.6 veillard 591: char query[SMALL_QUERY];
1.2 veillard 592:
593: if ((table == NULL) || (name == NULL) || (value == NULL))
594: return(-1);
595:
596: /*
597: * Search for the ID it has to exist
598: */
1.6 veillard 599: snprintf(query, SMALL_QUERY - 1, "SELECT ID FROM %s WHERE %s='%s'", table, name, value);
600: query[SMALL_QUERY - 1] = 0;
1.1 veillard 601: if (mysql_query(sql,query)) {
602: printf("sql_create: SELECT %s failed %s\n", name, mysql_error(sql));
603: return(-1);
604: }
605:
606: result = mysql_use_result(sql);
607: if (result) {
608: while((row = mysql_fetch_row(result)))
609: {
610: /*
611: * Lookup the first ID and return it
612: */
613: if (row[0] == NULL) {
614: mysql_free_result(result);
615: printf("sql_create: select returns NULL !\n");
616: return(-1);
617: }
618: if (sscanf(row[0], "%d", &id) != 1) {
619: mysql_free_result(result);
620: printf("sql_create: ID non numeric %s\n", row[0]);
621: return(-1);
622: }
623: mysql_free_result(result);
624: return(id);
625: }
626: mysql_free_result(result);
627: }
628: if(mysql_errno(sql)) {
629: fprintf(stderr, "Error: %s\n", mysql_error(sql));
630: return(-1);
631: }
632: return(-1);
633: }
634:
635: /************************************************************************
636: * *
637: * Tables handling *
638: * *
639: ************************************************************************/
640:
1.2 veillard 641: int sql_rebuild_config(void) {
642: const char *query =
643: "CREATE TABLE Config ( \n\
644: ID int(11) NOT NULL auto_increment, \n\
645: Name varchar(50) NOT NULL, \n\
646: Value varchar(255), \n\
647: PRIMARY KEY (ID), \n\
648: KEY Name (Name(10)) \n\
649: )";
650:
651: if (mysql_query(sql,query)) {
652: printf("sql_rebuild_config: CREATE TABLE Config failed %s\n",
653: mysql_error(sql));
654: return(-1);
655: }
656: return(0);
657: }
658:
1.1 veillard 659: int sql_rebuild_vendors(void) {
660: const char *query =
661: "CREATE TABLE Vendors ( \n\
662: ID int(11) NOT NULL auto_increment, \n\
663: Name varchar(255) NOT NULL, \n\
664: URL varchar(255), \n\
665: Key1 text, \n\
666: Key2 text, \n\
667: Key3 text, \n\
668: Description text, \n\
669: PRIMARY KEY (ID), \n\
670: KEY Name (Name(10)) \n\
671: )";
672:
673: if (mysql_query(sql,query)) {
1.2 veillard 674: printf("sql_rebuild_vendors: CREATE TABLE Vendors failed %s\n",
1.1 veillard 675: mysql_error(sql));
676: return(-1);
677: }
678: return(0);
679: }
680:
681: int sql_rebuild_mirrors(void) {
682: const char *query =
683: "CREATE TABLE Mirrors ( \n\
684: ID int(11), \n\
685: URL varchar(255) NOT NULL, \n\
686: Country int(11), \n\
687: UNIQUE(URL) \n\
688: )";
689:
690: if (mysql_query(sql,query)) {
1.2 veillard 691: printf("sql_rebuild_mirrors: CREATE TABLE Mirrors failed %s\n",
692: mysql_error(sql));
693: return(-1);
694: }
695: return(0);
696: }
697:
698: int sql_rebuild_metadata(void) {
699: const char *query =
700: "CREATE TABLE Metadata ( \n\
701: URL varchar(255) NOT NULL, \n\
702: Maintainer int(11), \n\
703: Country int(11), \n\
704: UNIQUE(URL) \n\
705: )";
706:
707: if (mysql_query(sql,query)) {
708: printf("sql_rebuild_metadata: CREATE TABLE Metadata failed %s\n",
1.1 veillard 709: mysql_error(sql));
710: return(-1);
711: }
712: return(0);
713: }
714:
715: int sql_rebuild_distribs(void) {
716: const char *query =
717: "CREATE TABLE Distribs ( \n\
718: ID int(11) NOT NULL auto_increment, \n\
719: Name varchar(255) NOT NULL, \n\
720: Vendor int(11), \n\
1.2 veillard 721: Directory varchar(255), \n\
1.1 veillard 722: Path varchar(100) NOT NULL, \n\
723: URL varchar(255), \n\
724: URLSrc varchar(255), \n\
1.9 veillard 725: Html varchar(8), \n\
726: Color varchar(10), \n\
1.1 veillard 727: Key1 text, \n\
728: Key2 text, \n\
729: Description text, \n\
730: PRIMARY KEY (ID), \n\
731: KEY Name (Name(10)) \n\
732: )";
733:
734: if (mysql_query(sql,query)) {
1.2 veillard 735: printf("sql_rebuild_distribs: CREATE TABLE Distribs failed %s\n",
736: mysql_error(sql));
737: return(-1);
738: }
739: return(0);
740: }
741:
742: int sql_rebuild_packages(void) {
743: const char *query =
744: "CREATE TABLE Packages ( \n\
745: ID int(11) NOT NULL auto_increment, \n\
746: filename varchar(255) NOT NULL, \n\
747: Name varchar(50) NOT NULL, \n\
748: Version varchar(50) NOT NULL, \n\
749: Release varchar(50) NOT NULL, \n\
1.6 veillard 750: Arch varchar(15) NOT NULL, \n\
1.2 veillard 751: Dist int(11), \n\
752: URL varchar(255), \n\
753: URLSrc varchar(255), \n\
754: Vendor int(11), \n\
755: Packager int(11), \n\
756: Category varchar(255), \n\
757: Summary varchar(255), \n\
758: Description text, \n\
759: Copyright varchar(255), \n\
1.25 veillard 760: Date int(11), \n\
1.33 veillard 761: Os varchar(12), \n\
1.2 veillard 762: PRIMARY KEY (ID), \n\
1.7 veillard 763: KEY filename (filename(80)), \n\
764: KEY Name (Name(15)) \n\
1.2 veillard 765: )";
766:
767: if (mysql_query(sql,query)) {
768: printf("sql_rebuild_packages: CREATE TABLE Packages failed %s\n",
769: mysql_error(sql));
770: return(-1);
771: }
772: return(0);
773: }
774:
775: int sql_rebuild_files(void) {
776: const char *query =
777: "CREATE TABLE Files ( \n\
1.6 veillard 778: ID int(11) NOT NULL, \n\
1.7 veillard 779: Path varchar(35) NOT NULL, \n\
780: UNIQUE KEY id (ID,Path(35)), \n\
1.6 veillard 781: INDEX (ID), \n\
782: INDEX (Path) \n\
1.2 veillard 783: )";
784:
785: if (mysql_query(sql,query)) {
786: printf("sql_rebuild_files: CREATE TABLE Files failed %s\n",
1.1 veillard 787: mysql_error(sql));
788: return(-1);
789: }
790: return(0);
791: }
792:
1.8 veillard 793: int sql_rebuild_provides(void) {
794: const char *query =
795: "CREATE TABLE Provides ( \n\
796: ID int(11) NOT NULL, \n\
797: Resource varchar(35) NOT NULL, \n\
798: UNIQUE KEY id (ID,Resource(35)), \n\
799: INDEX (ID), \n\
800: INDEX (Resource) \n\
801: )";
802:
803: if (mysql_query(sql,query)) {
1.21 daniel 804: printf("sql_rebuild_provides: CREATE TABLE Provides failed %s\n",
1.8 veillard 805: mysql_error(sql));
806: return(-1);
807: }
808: return(0);
809: }
810:
811: int sql_rebuild_requires(void) {
812: const char *query =
813: "CREATE TABLE Requires ( \n\
814: ID int(11) NOT NULL, \n\
815: Resource varchar(35) NOT NULL, \n\
816: Rel char(2), \n\
817: Value varchar(20), \n\
818: UNIQUE KEY id (ID,Resource(35)), \n\
819: INDEX (ID), \n\
820: INDEX (Resource) \n\
821: )";
822:
823: if (mysql_query(sql,query)) {
1.21 daniel 824: printf("sql_rebuild_requires: CREATE TABLE Requires failed %s\n",
825: mysql_error(sql));
826: return(-1);
827: }
828: return(0);
829: }
830:
831: int sql_rebuild_queries(void) {
832: const char *query =
833: "CREATE TABLE Queries ( \n\
834: ID int(11) NOT NULL auto_increment,\n\
835: Value varchar(50) NOT NULL, \n\
836: Count int(11) NOT NULL, \n\
837: Results int(11) NOT NULL, \n\
838: UNIQUE KEY id (ID,Value(35)), \n\
839: INDEX (ID), \n\
840: INDEX (Value) \n\
841: )";
842:
843: if (mysql_query(sql,query)) {
844: printf("sql_rebuild_queries: CREATE TABLE Queries failed %s\n",
1.8 veillard 845: mysql_error(sql));
846: return(-1);
847: }
848: return(0);
849: }
850:
1.1 veillard 851:
852: int sql_check_tables(void) {
853: const char *query = "SHOW TABLES";
854: MYSQL_RES *result;
855: MYSQL_ROW row;
1.2 veillard 856: int config = 0;
1.1 veillard 857: int distribs = 0;
1.8 veillard 858: int requires = 0;
859: int provides = 0;
1.1 veillard 860: int vendors = 0;
861: int mirrors = 0;
1.2 veillard 862: int metadata = 0;
863: int packages = 0;
864: int files = 0;
1.21 daniel 865: int queries = 0;
1.2 veillard 866:
1.1 veillard 867: int rebuilt = 0;
868:
869: if (mysql_query(sql,query)) {
1.2 veillard 870: printf("sql_check_tables: SHOW TABLES failed %s\n",
1.1 veillard 871: mysql_error(sql));
872: return(-1);
873: }
874:
875: result = mysql_use_result(sql);
876: if (result) {
877: while((row = mysql_fetch_row(result)))
878: {
879: if (row[0] == NULL) {
880: mysql_free_result(result);
881: printf("sql_check_tables: SHOW TABLES returns NULL !\n");
882: return(-1);
883: }
1.2 veillard 884: if (!strcmp(row[0], "Config"))
885: config = 1;
1.1 veillard 886: if (!strcmp(row[0], "Distribs"))
887: distribs = 1;
888: if (!strcmp(row[0], "Vendors"))
889: vendors = 1;
890: if (!strcmp(row[0], "Mirrors"))
891: mirrors = 1;
1.2 veillard 892: if (!strcmp(row[0], "Metadata"))
893: metadata = 1;
894: if (!strcmp(row[0], "Packages"))
895: packages = 1;
896: if (!strcmp(row[0], "Files"))
897: files = 1;
1.8 veillard 898: if (!strcmp(row[0], "Requires"))
899: requires = 1;
900: if (!strcmp(row[0], "Provides"))
901: provides = 1;
1.21 daniel 902: if (!strcmp(row[0], "Queries"))
903: queries = 1;
1.1 veillard 904: }
905: mysql_free_result(result);
906: }
907: if(mysql_errno(sql)) {
908: fprintf(stderr, "Error: %s\n", mysql_error(sql));
909: return(-1);
910: }
911:
1.2 veillard 912: if (!config) {
913: fprintf(stderr, "Table Config disapeared: rebuilding it\n");
914: if (!sql_rebuild_config())
915: rebuilt++;
916: }
1.1 veillard 917: if (!vendors) {
918: fprintf(stderr, "Table Vendors disapeared: rebuilding it\n");
919: if (!sql_rebuild_vendors())
920: rebuilt++;
921: }
922: if (!distribs) {
923: fprintf(stderr, "Table Distribs disapeared: rebuilding it\n");
924: if (!sql_rebuild_distribs())
925: rebuilt++;
926: }
927: if (!mirrors) {
928: fprintf(stderr, "Table Mirrors disapeared: rebuilding it\n");
929: if (!sql_rebuild_mirrors())
930: rebuilt++;
931: }
1.2 veillard 932: if (!metadata) {
933: fprintf(stderr, "Table Metadata disapeared: rebuilding it\n");
934: if (!sql_rebuild_metadata())
935: rebuilt++;
936: }
937: if (!packages) {
938: fprintf(stderr, "Table Packages disapeared: rebuilding it\n");
939: if (!sql_rebuild_packages())
940: rebuilt++;
941: }
942: if (!files) {
943: fprintf(stderr, "Table Files disapeared: rebuilding it\n");
944: if (!sql_rebuild_files())
945: rebuilt++;
946: }
1.8 veillard 947: if (!requires) {
948: fprintf(stderr, "Table Requires disapeared: rebuilding it\n");
949: if (!sql_rebuild_requires())
950: rebuilt++;
951: }
952: if (!provides) {
953: fprintf(stderr, "Table Provides disapeared: rebuilding it\n");
954: if (!sql_rebuild_provides())
1.21 daniel 955: rebuilt++;
956: }
957: if (!queries) {
958: fprintf(stderr, "Table Queries disapeared: rebuilding it\n");
959: if (!sql_rebuild_queries())
1.8 veillard 960: rebuilt++;
961: }
1.1 veillard 962: return(rebuilt);
963: }
964:
965: /************************************************************************
966: * *
967: * Specific rpm2html functions *
968: * *
969: ************************************************************************/
970:
1.5 veillard 971: int sql_add_dist_mirror(int distrib, const char *URL, int country) {
1.1 veillard 972: if (URL == NULL)
973: return(-1);
974: if (distrib < 0)
975: return(-1);
976: return(sql_blind_insert("Mirrors", "URL", URL, distrib));
977: }
978:
1.5 veillard 979: int sql_add_mirror(const char *Name, const char *URL, int country) {
1.1 veillard 980: int distrib;
981:
982: if ((Name == NULL) || (URL == NULL))
983: return(-1);
984: distrib = sql_read_key("Distribs", Name);
985: if (distrib < 0)
986: return(distrib);
987: return(sql_blind_insert("Mirrors", "URL", URL, distrib));
988: }
989:
1.6 veillard 990: int sql_add_file(const char *filename, int package) {
991: if ((filename == NULL) || (package <= 0))
992: return(-1);
1.7 veillard 993: if (strlen(filename) > 35)
994: return(0);
1.6 veillard 995:
996: return(sql_blind_insert("Files", "Path", filename, package));
997: }
998:
1.8 veillard 999: int sql_add_provides(int package, const char *resource) {
1000: if ((resource == NULL) || (package <= 0))
1001: return(-1);
1002: if (strlen(resource) > 35)
1003: return(0);
1004:
1005: return(sql_blind_insert("Provides", "Resource", resource, package));
1006: }
1007:
1.14 veillard 1008: int sql_add_requires(int package, const char *resource, rpm_dep_flag rel,
1.8 veillard 1009: const char *value) {
1010: int record;
1011: if ((resource == NULL) || (package <= 0))
1012: return(-1);
1013: if (strlen(resource) > 35)
1014: return(0);
1015:
1016: record = sql_blind_insert("Requires", "Resource", resource, package);
1.14 veillard 1017: if ((rel != RPM2HTML_REQ_NONE) && (value != NULL) &&
1018: (strlen(value) <= 50)) {
1.8 veillard 1019: char query[SMALL_QUERY];
1.14 veillard 1020:
1021: switch (rel) {
1022: case RPM2HTML_REQ_LT:
1023: snprintf(query, SMALL_QUERY - 1,
1024: "UPDATE Requires SET Rel='<',Value='%s' WHERE ID=%d",
1025: value, record);
1.15 daniel 1026: break;
1.14 veillard 1027: case RPM2HTML_REQ_LEQ:
1028: snprintf(query, SMALL_QUERY - 1,
1029: "UPDATE Requires SET Rel='<=',Value='%s' WHERE ID=%d",
1030: value, record);
1.15 daniel 1031: break;
1.14 veillard 1032: case RPM2HTML_REQ_GT:
1033: snprintf(query, SMALL_QUERY - 1,
1034: "UPDATE Requires SET Rel='>',Value='%s' WHERE ID=%d",
1035: value, record);
1.15 daniel 1036: break;
1.14 veillard 1037: case RPM2HTML_REQ_GEQ:
1038: snprintf(query, SMALL_QUERY - 1,
1039: "UPDATE Requires SET Rel='>=',Value='%s' WHERE ID=%d",
1040: value, record);
1.15 daniel 1041: break;
1.14 veillard 1042: case RPM2HTML_REQ_EQU:
1043: snprintf(query, SMALL_QUERY - 1,
1044: "UPDATE Requires SET Rel='=',Value='%s' WHERE ID=%d",
1045: value, record);
1.15 daniel 1046: break;
1.14 veillard 1047: case RPM2HTML_REQ_NONE:
1048: query[0] = 0;
1049: }
1.8 veillard 1050: query[SMALL_QUERY - 1] = 0;
1051: if (mysql_query(sql,query)) {
1052: printf("sql_create: UPDATE Requires %d failed %s\n",
1053: record, mysql_error(sql));
1054: return(record);
1055: }
1056: }
1057: return(record);
1058: }
1059:
1.34 veillard 1060: int sql_add_vendor(const char *Name, const char *URL, const char *Description) {
1061: int id;
1062:
1063: if (Name == NULL)
1064: return(-1);
1065:
1066: id = sql_get_key("Vendors", "Name", Name);
1067: if (id <= 0) {
1068: id = sql_blind_insert("Vendors", "Name", Name, 0);
1069: if (id <= 0)
1070: return(id);
1071: }
1072: if (URL != NULL)
1073: sql_update_id("Vendors", id, "URL", URL);
1074: if (Description != NULL)
1075: sql_update_id("Vendors", id,
1076: "Description", Description);
1077:
1078: return(id);
1079: }
1080:
1081:
1.5 veillard 1082: int sql_add_package(const char *filename,
1.2 veillard 1083: const char *Name, const char *Version, const char *Release,
1.6 veillard 1084: const char *Arch,
1085: int dist, const char *URL, const char *URLSrc, int vendor,
1.2 veillard 1086: const char *Packager, const char *Category, const char *Summary,
1.33 veillard 1087: const char *Description, const char *Copyright, int Date,
1088: const char *Os) {
1.2 veillard 1089: int id;
1090: int nb_fields = 0;
1.35 ! veillard 1091: char installed_filename[500];
1.2 veillard 1092:
1.35 ! veillard 1093: if (filename == NULL) {
! 1094: sprintf(installed_filename, "localbase/%s-%s-%s.%s.rpm",
! 1095: Name,Version,Release,Arch);
! 1096: filename = installed_filename;
! 1097: }
1.6 veillard 1098:
1099: if (dist < 0)
1.2 veillard 1100: return(-1);
1.6 veillard 1101: if ((Name == NULL) || (Version == NULL) || (Release == NULL) ||
1102: (Arch == NULL))
1103: return(-1);
1104:
1105: id = sql_get_key("Packages", "filename", filename);
1.2 veillard 1106: if (id <= 0)
1107: return(-1);
1108: nb_fields = 1;
1.8 veillard 1109:
1110: if (rpm2htmlVerbose > 1)
1111: printf("Adding %s ID %d\n", filename, id);
1112:
1.2 veillard 1113: if (Name != NULL)
1.6 veillard 1114: nb_fields += sql_update_id("Packages", id, "Name", Name);
1.2 veillard 1115: if (Version != NULL)
1116: nb_fields += sql_update_id("Packages", id, "Version", Version);
1117: if (Release != NULL)
1118: nb_fields += sql_update_id("Packages", id, "Release", Release);
1.6 veillard 1119: if (Release != NULL)
1120: nb_fields += sql_update_id("Packages", id, "Arch", Arch);
1.2 veillard 1121: if (Category != NULL)
1122: nb_fields += sql_update_id("Packages", id, "Category", Category);
1123: if (URL != NULL)
1124: nb_fields += sql_update_id("Packages", id, "URL", URL);
1125: if (URLSrc != NULL)
1126: nb_fields += sql_update_id("Packages", id, "URLSrc", URLSrc);
1.17 veillard 1127: if (dist >= 0) {
1128: char str[30];
1129: snprintf(str, 30, "%d", dist);
1130: str[29] = 0;
1131: nb_fields += sql_update_id("Packages", id, "Dist", str);
1132: }
1.2 veillard 1133: if (Summary != NULL)
1134: nb_fields += sql_update_id("Packages", id, "Summary", Summary);
1135: if (Description != NULL)
1136: nb_fields += sql_update_id("Packages", id,
1137: "Description", Description);
1138: if (Copyright != NULL)
1139: nb_fields += sql_update_id("Packages", id, "Copyright", Copyright);
1.25 veillard 1140: if (Date != 0) {
1141: char str[30];
1142: snprintf(str, 30, "%d", Date);
1143: str[29] = 0;
1144: nb_fields += sql_update_id("Packages", id, "Date", str);
1145: }
1.35 ! veillard 1146: if (vendor > 0) {
! 1147: char str[30];
! 1148: snprintf(str, 30, "%d", vendor);
! 1149: str[29] = 0;
! 1150: nb_fields += sql_update_id("Packages", id, "Vendor", str);
! 1151: }
1.33 veillard 1152: if (Os != NULL)
1153: nb_fields += sql_update_id("Packages", id, "Os", Os);
1.34 veillard 1154: if (Packager != NULL) {
1155: char str[30];
1.35 ! veillard 1156: int packager = sql_add_vendor(Packager, NULL, NULL);
1.34 veillard 1157:
1.35 ! veillard 1158: if (packager > 0) {
! 1159: snprintf(str, 30, "%d", packager);
1.34 veillard 1160: str[29] = 0;
1.35 ! veillard 1161: nb_fields += sql_update_id("Packages", id, "Packager", str);
1.34 veillard 1162: }
1163: }
1.2 veillard 1164:
1.6 veillard 1165: return(id);
1.17 veillard 1166: }
1167:
1168: int sql_get_distrib_by_name(const char *Name) {
1169: int ret;
1170:
1171: if (Name == NULL)
1172: return(-1);
1173: ret = sql_read_key("Distribs", Name);
1174:
1.18 daniel 1175: #ifdef SQL_DEBUG
1.17 veillard 1176: fprintf(stderr, "sql_get_distrib_by_name(%s) => %d\n", Name, ret);
1.18 daniel 1177: #endif
1.17 veillard 1178:
1179: return(ret);
1180: }
1181:
1182: int sql_get_distrib_by_directory(const char *Directory) {
1183: int ret;
1184:
1185: if (Directory == NULL)
1186: return(-1);
1187:
1188: ret = sql_get_key("Distribs", "Directory", Directory);
1189:
1.18 daniel 1190: #ifdef SQL_DEBUG
1.17 veillard 1191: fprintf(stderr, "sql_get_distrib_by_directory(%s) => %d\n", Directory, ret);
1.18 daniel 1192: #endif
1.17 veillard 1193:
1194: return(ret);
1.2 veillard 1195: }
1196:
1.5 veillard 1197: int sql_add_distrib(const char *Name, const char *Vendor,
1.2 veillard 1198: const char *Directory, const char *Path, const char *URL,
1.9 veillard 1199: const char *URLSrc, const char *Description,
1200: const char *Html, const char *Color) {
1.1 veillard 1201: int id, vendor;
1202: int nb_fields = 0;
1203: char VendorStr[15];
1204:
1205: if (Name == NULL)
1206: return(-1);
1207:
1.6 veillard 1208: id = sql_get_key("Distribs", "Name", Name);
1.1 veillard 1209: nb_fields = 1;
1210: if (Vendor != NULL) {
1.6 veillard 1211: vendor = sql_get_key("Vendors", "Name", Vendor);
1.1 veillard 1212: sprintf(VendorStr, "%d", vendor);
1213: nb_fields += sql_update_id("Distribs", id, "Vendor", VendorStr);
1214: }
1.2 veillard 1215: if (Directory != NULL)
1216: nb_fields += sql_update_id("Distribs", id, "Directory", Directory);
1.1 veillard 1217: if (Path != NULL)
1218: nb_fields += sql_update_id("Distribs", id, "Path", Path);
1219: if (URL != NULL)
1220: nb_fields += sql_update_id("Distribs", id, "URL", URL);
1221: if (URLSrc != NULL)
1222: nb_fields += sql_update_id("Distribs", id, "URLSrc", URLSrc);
1.9 veillard 1223: if (Html != NULL)
1224: nb_fields += sql_update_id("Distribs", id, "Html", Html);
1225: if (Color != NULL)
1226: nb_fields += sql_update_id("Distribs", id, "Color", Color);
1.1 veillard 1227: if (Description != NULL)
1228: nb_fields += sql_update_id("Distribs", id,
1229: "Description", Description);
1230:
1231: return(nb_fields);
1232: }
1233:
1.5 veillard 1234: void sql_add_config_info(const char *name, const char *value) {
1.2 veillard 1235: sql_update("Config", name, "Value", value);
1236: }
1237:
1.5 veillard 1238: void sql_add_metadata_base(const char *URL) {
1.2 veillard 1239: sql_blind_insert("Metadata", "URL", URL, -1);
1240: }
1241:
1.6 veillard 1242: /************************************************************************
1243: * *
1.8 veillard 1244: * Cleanup functions *
1245: * *
1246: ************************************************************************/
1247:
1248: int sql_remove_package(int id) {
1249: char query[SMALL_QUERY];
1250:
1251: if (id <= 0)
1252: return(-1);
1253:
1254: /*
1255: * remove the ID from the package list
1256: */
1257: snprintf(query, SMALL_QUERY - 1, "DELETE FROM Packages WHERE ID=%d", id);
1258: query[SMALL_QUERY - 1] = 0;
1259: if (mysql_query(sql,query)) {
1260: printf("sql_create: DELETE package %d failed %s\n", id, mysql_error(sql));
1261: return(-1);
1262: }
1263: if(mysql_errno(sql)) {
1264: fprintf(stderr, "Error: %s\n", mysql_error(sql));
1265: return(-1);
1266: }
1267:
1268: /*
1269: * remove the associated files from the Files list
1270: */
1271: snprintf(query, SMALL_QUERY - 1, "DELETE FROM Files WHERE ID=%d", id);
1272: query[SMALL_QUERY - 1] = 0;
1273: if (mysql_query(sql,query)) {
1274: printf("sql_create: DELETE Files %d failed %s\n", id, mysql_error(sql));
1275: return(-1);
1276: }
1277: if(mysql_errno(sql)) {
1278: fprintf(stderr, "Error: %s\n", mysql_error(sql));
1279: return(-1);
1280: }
1281:
1282: /*
1283: * remove the associated Provides entries
1284: */
1285: snprintf(query, SMALL_QUERY - 1, "DELETE FROM Provides WHERE ID=%d", id);
1286: query[SMALL_QUERY - 1] = 0;
1287: if (mysql_query(sql,query)) {
1288: printf("sql_create: DELETE Provides %d failed %s\n", id, mysql_error(sql));
1289: return(-1);
1290: }
1291: if(mysql_errno(sql)) {
1292: fprintf(stderr, "Error: %s\n", mysql_error(sql));
1293: return(-1);
1294: }
1295:
1296: /*
1297: * remove the associated Requires entries
1298: */
1299: snprintf(query, SMALL_QUERY - 1, "DELETE FROM Requires WHERE ID=%d", id);
1300: query[SMALL_QUERY - 1] = 0;
1301: if (mysql_query(sql,query)) {
1302: printf("sql_create: DELETE Requires %d failed %s\n", id, mysql_error(sql));
1303: return(-1);
1304: }
1305: if(mysql_errno(sql)) {
1306: fprintf(stderr, "Error: %s\n", mysql_error(sql));
1307: return(-1);
1308: }
1309:
1310: return(-1);
1311: }
1312:
1313: int sql_check_packages(void) {
1314: MYSQL_RES *result;
1315: MYSQL_ROW row;
1.20 daniel 1316: char *query = "SELECT filename,ID FROM Packages";
1.8 veillard 1317: struct stat buf;
1318: int id;
1.22 daniel 1319: int ids[2500]; /* Do not remove more than 2500 package per run */
1.8 veillard 1320: int index;
1321: int total = 0;
1322:
1323: if (rpm2htmlVerbose)
1324: printf("Database cleanup\n");
1325: index = 0;
1326: /*
1327: * Search first for the ID if it already exists
1328: */
1329: if (mysql_query(sql,query)) {
1330: printf("sql_check_packages: SELECT from Packages failed: %s\n",
1331: mysql_error(sql));
1332: return(-1);
1333: }
1334:
1335: result = mysql_use_result(sql);
1336: if (result) {
1337: while((row = mysql_fetch_row(result)))
1338: {
1339: if ((row[0] == NULL) || (row[1] == NULL)) {
1340: printf("sql_check_packages: Path or ID is NULL !\n");
1341: continue;
1342: }
1.35 ! veillard 1343: if (!strncmp(row[0], "localbase", 9))
! 1344: continue;
! 1345:
1.8 veillard 1346: if ((stat(row[0], &buf) < 0) || (buf.st_size < 50)) {
1347: /*
1348: * Need to remove the package from the database.
1349: */
1350: if (sscanf(row[1], "%d", &id) != 1) {
1351: printf("sql_check_packages: ID non numeric %s\n", row[1]);
1352: continue;
1353: }
1354: ids[index++] = id;
1.20 daniel 1355: if (rpm2htmlVerbose)
1.8 veillard 1356: printf("Removing %s ID %d\n", row[0], id);
1.22 daniel 1357: if (index >= 2500)
1.8 veillard 1358: break;
1359: }
1360: }
1361: mysql_free_result(result);
1362: }
1363: if(mysql_errno(sql)) {
1364: fprintf(stderr, "sql_update Error: %s\n", mysql_error(sql));
1365: return(-1);
1366: }
1367:
1368: /*
1369: * Do the cleanup.
1370: */
1.20 daniel 1371: if (rpm2htmlVerbose)
1372: printf("Database cleanup : removing %d entries...\n", index);
1.8 veillard 1373: for (id = 0;id < index;id++) {
1374: sql_remove_package(ids[id]);
1375: }
1376:
1.34 veillard 1377: printf("Database cleanup : removed %d entries\n", index);
1.8 veillard 1378: return(total);
1379: }
1380:
1381: /************************************************************************
1.26 veillard 1382: * *
1383: * Package lists extraction *
1384: * *
1385: ************************************************************************/
1386: int sqlDirListInitialized = 0;
1387: rpmDirPtr sqlDirList[SQL_MAX_DISTRIBS];
1.35 ! veillard 1388: int sqlVendorListInitialized = 0;
! 1389: int sqlVendorListLen;
! 1390: char **sqlVendorList;
! 1391:
! 1392: char *
! 1393: sqlRpmAnalyzeVendorRow(MYSQL_ROW row) {
! 1394: const char *id;
! 1395: const char *name;
! 1396: char **tmp;
! 1397: int vendor;
! 1398:
! 1399: if (row == NULL)
! 1400: return(NULL);
! 1401: id = row[0];
! 1402: name = row[1];
! 1403: if ((id == NULL) || (name == NULL))
! 1404: return(NULL);
! 1405:
! 1406: if (sscanf(id, "%d", &vendor) != 1)
! 1407: return(NULL);
! 1408: if ((vendor <= 0) || (vendor > 100000)) {
! 1409: fprintf(stderr, "Dist number out of range %d\n", vendor);
! 1410: return(NULL);
! 1411: }
! 1412: if (vendor >= sqlVendorListLen) {
! 1413: int i = sqlVendorListLen;
! 1414: sqlVendorListLen = vendor + 100;
! 1415: tmp = (char **) debugRealloc(sqlVendorList,
! 1416: (sqlVendorListLen) * sizeof(char *));
! 1417: if (sqlVendorList == NULL) {
! 1418: fprintf(stderr, "sqlInitSqlVendorList Error: out of memory\n");
! 1419: return(NULL);
! 1420: }
! 1421: sqlVendorList = tmp;
! 1422: memset(&sqlVendorList[i], 0, sizeof(char *) * (sqlVendorListLen - i));
! 1423: }
! 1424:
! 1425: sqlVendorList[vendor] = debugStrdup(name);
! 1426: return(sqlVendorList[vendor]);
! 1427: }
! 1428:
! 1429: void
! 1430: sqlInitSqlVendorList(void) {
! 1431: MYSQL_RES *result;
! 1432: MYSQL_ROW row;
! 1433: char *query;
! 1434: int i;
! 1435:
! 1436: if (sqlVendorListInitialized != 0)
! 1437: return;
! 1438:
! 1439: if (rpm2htmlVerbose)
! 1440: printf("sqlInitSqlVendorList query\n");
! 1441:
! 1442: /*
! 1443: * Allocate the array
! 1444: */
! 1445: sqlVendorListLen = 100;
! 1446: sqlVendorList = (char **) debugMalloc((sqlVendorListLen) * sizeof(char *));
! 1447: if (sqlVendorList == NULL) {
! 1448: fprintf(stderr, "sqlInitSqlVendorList Error: out of memory\n");
! 1449: return;
! 1450: }
! 1451:
! 1452: /*
! 1453: * query the database for the values
! 1454: */
! 1455: query = "select ID,Name from Vendors";
! 1456:
! 1457: if (mysql_query(sql,query)) {
! 1458: printf("sqlInitSqlVendorList: SELECT from Packages failed: %s\n",
! 1459: mysql_error(sql));
! 1460: return;
! 1461: }
! 1462:
! 1463: i = 0;
! 1464: result = mysql_use_result(sql);
! 1465: if (result) {
! 1466: while((row = mysql_fetch_row(result)))
! 1467: {
! 1468: if (sqlRpmAnalyzeVendorRow(row) != NULL)
! 1469: i++;
! 1470: }
! 1471: mysql_free_result(result);
! 1472: }
! 1473: if(mysql_errno(sql)) {
! 1474: fprintf(stderr, "sqlInitSqlVendorList Error: %s\n", mysql_error(sql));
! 1475: return;
! 1476: }
! 1477:
! 1478:
! 1479: if (rpm2htmlVerbose)
! 1480: printf("sqlInitSqlVendorList done: %d entries\n", i);
! 1481: sqlVendorListInitialized++;
! 1482: return;
! 1483: }
1.26 veillard 1484:
1485: rpmDirPtr
1486: sqlRpmAnalyzeDirRow(MYSQL_ROW row) {
1487: rpmDirPtr ret;
1488: const char *id;
1489: const char *name;
1490: const char *vendor;
1491: const char *directory;
1492: const char *path;
1493: const char *url;
1494: const char *urlSrc;
1495: const char *html;
1496: const char *color;
1497: int dist;
1498:
1499: if (row == NULL)
1500: return(NULL);
1501: id = row[0];
1502: name = row[1];
1503: vendor = row[2];
1504: directory = row[3];
1505: path = row[4];
1506: url = row[5];
1507: urlSrc = row[6];
1508: html = row[7];
1509: color = row[8];
1510: if ((id == NULL) || (name == NULL) ||
1511: (directory == NULL) || (path == NULL) || (url == NULL))
1512: return(NULL);
1513:
1514: if (sscanf(id, "%d", &dist) != 1)
1515: return(NULL);
1516: if ((dist <= 0) || (dist > SQL_MAX_DISTRIBS)) {
1517: fprintf(stderr, "Dist number out of range %d\n", dist);
1518: return(NULL);
1519: }
1520:
1521:
1522: ret = (rpmDirPtr) debugMalloc(sizeof(rpmDir));
1523: if (ret == NULL)
1524: return(NULL);
1525: memset(ret, 0, sizeof(rpmDir));
1526: /* Generic stuff */
1.28 daniel 1527: if (rpm2html_dir != NULL)
1.26 veillard 1528: ret->dir = debugStrdup(rpm2html_dir);
1.28 daniel 1529: if (rpm2html_host != NULL)
1.26 veillard 1530: ret->host = debugStrdup(rpm2html_host);
1.28 daniel 1531: if (rpm2html_maint != NULL)
1.26 veillard 1532: ret->maint = debugStrdup(rpm2html_maint);
1.28 daniel 1533: if (rpm2html_mail != NULL)
1.26 veillard 1534: ret->mail = debugStrdup(rpm2html_mail);
1.28 daniel 1535: if (rpm2html_url != NULL)
1.26 veillard 1536: ret->url = debugStrdup(rpm2html_url);
1537: /* specific stuff */
1538: ret->no = dist;
1539: ret->rpmdir = debugStrdup(directory);
1540: ret->subdir = debugStrdup(path);
1541: ret->name = debugStrdup(name);
1542: ret->ftp = debugStrdup(url);
1543: if (color != NULL)
1544: ret->color = debugStrdup(color);
1.28 daniel 1545: else
1546: ret->color = debugStrdup("#ffffff");
1.26 veillard 1547: if (urlSrc != NULL)
1548: ret->ftpsrc = debugStrdup(urlSrc);
1549: return(ret);
1550: }
1551:
1552: void
1553: sqlInitSqlDirList(void) {
1.28 daniel 1554: char host[200];
1.26 veillard 1555: rpmDirPtr cur;
1556: MYSQL_RES *result;
1557: MYSQL_ROW row;
1558: char *query;
1559: int i;
1560:
1561: if (sqlDirListInitialized != 0)
1562: return;
1563:
1.28 daniel 1564: gethostname(host, sizeof(host));
1565: currentTime = time(NULL);
1566: rpm2html_rpm2html_thishost = &host[0];
1567: readConfigSql();
1568: if (rpm2html_host == NULL) {
1569: rpm2html_host = strdup(rpm2html_rpm2html_thishost);
1570: }
1.26 veillard 1571: for (i = 0; i < SQL_MAX_DISTRIBS;i++)
1572: sqlDirList[i] = NULL;
1573:
1574: if (rpm2htmlVerbose)
1575: printf("sqlInitSqlDirList query\n");
1576:
1.29 veillard 1577: query = "select ID,Name,Vendor,Directory,Path,URL,URLSrc,Html,Color from Distribs";
1.26 veillard 1578:
1579: if (mysql_query(sql,query)) {
1580: printf("sqlInitSqlDirList: SELECT from Packages failed: %s\n",
1581: mysql_error(sql));
1582: return;
1583: }
1584:
1585: i = 0;
1586: result = mysql_use_result(sql);
1587: if (result) {
1588: while((row = mysql_fetch_row(result)))
1589: {
1590: cur = sqlRpmAnalyzeDirRow(row);
1591: if (cur != NULL) {
1592: sqlDirList[cur->no] = cur;
1593: i++;
1594: }
1595: }
1596: mysql_free_result(result);
1597: }
1598: if(mysql_errno(sql)) {
1599: fprintf(stderr, "sqlInitSqlDirList Error: %s\n", mysql_error(sql));
1600: return;
1601: }
1602:
1603: if (rpm2htmlVerbose)
1604: printf("sqlInitSqlDirList done: %d entries\n", i);
1605: sqlDirListInitialized++;
1606: return;
1607: }
1608:
1609: rpmDataPtr
1610: sqlRpmAnalyzeRow(MYSQL_ROW row) {
1611: rpmDataPtr ret;
1612: const char *id;
1613: const char *name;
1614: const char *version;
1615: const char *release;
1616: const char *arch;
1617: const char *date;
1618: const char *summary;
1619: const char *filename;
1620: const char *distrib;
1.30 daniel 1621: const char *group;
1.33 veillard 1622: const char *os;
1.35 ! veillard 1623: const char *packager;
1.26 veillard 1624: int dist;
1625:
1626: if (row == NULL)
1627: return(NULL);
1628: id = row[0];
1629: name = row[1];
1630: version = row[2];
1631: release = row[3];
1632: arch = row[4];
1633: date = row[5];
1634: summary = row[6];
1635: filename = row[7];
1636: distrib = row[8];
1.30 daniel 1637: group = row[9];
1.33 veillard 1638: os = row[10];
1.35 ! veillard 1639: packager = row[11];
1.26 veillard 1640: if ((id == NULL) || (name == NULL) || (version == NULL) ||
1641: (release == NULL) || (arch == NULL) || (date == NULL) ||
1642: (summary == NULL) || (filename == NULL) || (distrib == NULL))
1643: return(NULL);
1644:
1645: ret = (rpmDataPtr) debugMalloc(sizeof(rpmData));
1646: if (ret == NULL)
1647: return(NULL);
1648: memset(ret, 0, sizeof(rpmData));
1649: ret->name = debugStrdup(name);
1650: ret->version = debugStrdup(version);
1651: ret->release = debugStrdup(release);
1652: ret->arch = debugStrdup(arch);
1653: ret->summary = debugStrdup(summary);
1654: ret->name = debugStrdup(name);
1655: ret->filename = debugStrdup(filename);
1.33 veillard 1656: if (os == NULL)
1657: ret->os = debugStrdup("Linux");
1658: else
1659: ret->os = debugStrdup(os);
1.30 daniel 1660: if (group != NULL)
1661: ret->group = debugStrdup(group);
1.26 veillard 1662: sscanf(date, "%d", (int *) &(ret->date));
1.35 ! veillard 1663: if (packager != NULL) {
! 1664: int tmp = 0;
! 1665: sscanf(packager, "%d", (int *) &tmp);
! 1666: if ((tmp > 0) && (tmp < sqlVendorListLen)) {
! 1667: if (sqlVendorList[tmp] != NULL)
! 1668: ret->vendor = debugStrdup(sqlVendorList[tmp]);
! 1669: }
! 1670: }
! 1671: if (ret->vendor == NULL)
! 1672: ret->vendor = debugStrdup("Unknown");
! 1673: if (ret->distribution == NULL)
! 1674: ret->distribution = debugStrdup("Unknown");
1.26 veillard 1675: sscanf(distrib, "%d", &dist);
1676: ret->dir = sqlDirList[dist];
1.28 daniel 1677: if ((ret->dir != NULL) && (ret->dir->rpmdir != NULL)) {
1678: int len = strlen(ret->dir->rpmdir);
1679: if (!strncmp(ret->filename, ret->dir->rpmdir, len)) {
1680: char *start, *end;
1681: start = &(ret->filename[len]);
1682: while (*start == '/') start++;
1683: end = &start[strlen(start) - 1];
1684: while ((end >= start) && (*end != '/')) end--;
1685: if (end > start) {
1686: char *tmp;
1687: tmp = debugMalloc((end - start) + 1);
1688: if (tmp != NULL) {
1689: strncpy(tmp, start, end - start);
1690: tmp[end - start] = 0;
1691: ret->subdir = tmp;
1692: }
1693: }
1694: }
1695: }
1.26 veillard 1696: return(ret);
1697: }
1698:
1699: rpmDataPtr
1700: sqlRpmByDate(void) {
1701: rpmDataPtr list = NULL;
1702: rpmDataPtr cur, last = NULL;
1703: MYSQL_RES *result;
1704: MYSQL_ROW row;
1705: char *query;
1706:
1707: sqlInitSqlDirList();
1.35 ! veillard 1708: sqlInitSqlVendorList();
1.26 veillard 1709: if (rpm2htmlVerbose)
1710: printf("sqlRpmByDate query\n");
1711:
1.35 ! veillard 1712: query = "select ID,Name,Version,Release,Arch,Date,Summary,filename,Dist,Category,Os,Packager,Vendor from Packages where Date IS NOT NULL and Date < UNIX_TIMESTAMP() + 300000 order by Date desc limit 1000";
1.26 veillard 1713:
1714: /*
1715: * Search first for the ID if it already exists
1716: */
1717: if (mysql_query(sql,query)) {
1718: printf("sqlRpmByDate: SELECT from Packages failed: %s\n",
1719: mysql_error(sql));
1720: return(NULL);
1721: }
1722:
1723: result = mysql_use_result(sql);
1724: if (result) {
1725: while((row = mysql_fetch_row(result)))
1726: {
1727: cur = sqlRpmAnalyzeRow(row);
1728: if (cur != NULL) {
1729: if (last == NULL)
1730: list = cur;
1731: else
1732: last->next = cur;
1733: last = cur;
1734: }
1735: }
1736: mysql_free_result(result);
1737: }
1738: if(mysql_errno(sql)) {
1739: fprintf(stderr, "sqlRpmByDate Error: %s\n", mysql_error(sql));
1740: return(NULL);
1741: }
1742:
1743: if (rpm2htmlVerbose)
1744: printf("sqlRpmByDate done\n");
1745: return(list);
1746: }
1747:
1.29 veillard 1748: rpmDataPtr
1749: sqlRpmAll(void) {
1750: rpmDataPtr list = NULL;
1751: rpmDataPtr cur, last = NULL;
1752: MYSQL_RES *result;
1753: MYSQL_ROW row;
1754: char *query;
1755:
1756: sqlInitSqlDirList();
1.35 ! veillard 1757: sqlInitSqlVendorList();
1.29 veillard 1758: if (rpm2htmlVerbose)
1759: printf("sqlRpmAll query\n");
1760:
1.35 ! veillard 1761: query = "select ID,Name,Version,Release,Arch,Date,Summary,filename,Dist,Category,Os,Packager,Vendor from Packages";
1.29 veillard 1762:
1763: /*
1764: * Search first for the ID if it already exists
1765: */
1766: if (mysql_query(sql,query)) {
1767: printf("sqlRpmByDate: SELECT from Packages failed: %s\n",
1768: mysql_error(sql));
1769: return(NULL);
1770: }
1771:
1772: result = mysql_use_result(sql);
1773: if (result) {
1774: while((row = mysql_fetch_row(result)))
1775: {
1776: cur = sqlRpmAnalyzeRow(row);
1777: if (cur != NULL) {
1778: if (last == NULL)
1779: list = cur;
1780: else
1781: last->next = cur;
1782: last = cur;
1.32 daniel 1783:
1784: rpmAddSoftware(cur);
1.29 veillard 1785: }
1786: }
1787: mysql_free_result(result);
1788: }
1789: if(mysql_errno(sql)) {
1790: fprintf(stderr, "sqlRpmByDate Error: %s\n", mysql_error(sql));
1791: return(NULL);
1792: }
1793:
1794: if (rpm2htmlVerbose)
1795: printf("sqlRpmAll done\n");
1796: return(list);
1797: }
1798:
1.26 veillard 1799: /************************************************************************
1.8 veillard 1800: * *
1.6 veillard 1801: * Export functions *
1802: * *
1803: ************************************************************************/
1804:
1805: void sql_show_config(void) {
1806: MYSQL_RES *result;
1807: MYSQL_ROW row;
1.8 veillard 1808: int id, i;
1809: int index = 0;
1810: int ids[500];
1811: char query[SMALL_QUERY];
1.6 veillard 1812:
1813:
1.8 veillard 1814: printf(";\n; Configuration file for rpm2html\n");
1815: printf("; http://rpmfind.net/linux/rpm2html/\n;\n\n");
1816: mysql_query(sql,"SELECT Name,Value FROM Config");
1.6 veillard 1817: result = mysql_use_result(sql);
1818:
1819: while((row = mysql_fetch_row(result)))
1820: {
1.8 veillard 1821: if (row[0] == NULL) {
1822: printf("\n");
1823: } else {
1824: if (!strcmp(row[0], "maint"))
1825: printf("; maintainer of the local rpm mirror\n");
1826: else if (!strcmp(row[0], "mail"))
1827: printf("; mail for the maintainer\n");
1828: else if (!strcmp(row[0], "dir"))
1829: printf("; Directory to store the HTML pages produced\n");
1830: else if (!strcmp(row[0], "url"))
1831: printf("; The relative URL for front pages\n");
1832: else if (!strcmp(row[0], "header"))
1833: printf("; Extra link in the navigation bar\n");
1834: else if (!strcmp(row[0], "html"))
1835: printf("; Export the local packages in HTML format\n");
1836: else if (!strcmp(row[0], "tree"))
1837: printf("; Build the tree for the distributions\n");
1838: else if (!strcmp(row[0], "rdf"))
1839: printf("; Export the local packages in RDF format\n");
1840: else if (!strcmp(row[0], "rdf_dir"))
1841: printf("; Directory to store the RDf tree\n");
1842: else if (!strcmp(row[0], "rdf_resources"))
1843: printf("; Compile a list of resources in RDF format\n");
1844: else if (!strcmp(row[0], "rdf_resources_dir"))
1845: printf("; Directory to store the RDf resources tree\n");
1846:
1.6 veillard 1847: if (row[1] == NULL)
1.8 veillard 1848: printf("%s\n\n", row[0]);
1.6 veillard 1849: else
1.8 veillard 1850: printf("%s=%s\n\n", row[0], row[1]);
1851: }
1852: }
1853: mysql_free_result(result);
1854: if(mysql_errno(sql)) {
1855: fprintf(stderr, "Error: %s\n", mysql_error(sql));
1856: }
1857:
1858: /*
1859: * Dump the Metadata
1860: */
1861: printf(";\n; The metadata mirrors list\n;\n\n[metadata]\n");
1862: mysql_query(sql,"SELECT URL FROM Metadata");
1863: result = mysql_use_result(sql);
1864:
1865: while((row = mysql_fetch_row(result)))
1866: {
1867: if (row[0] != NULL) {
1868: printf("mirror=%s\n", row[0]);
1.6 veillard 1869: }
1870: }
1.8 veillard 1871: mysql_free_result(result);
1.6 veillard 1872: if(mysql_errno(sql)) {
1873: fprintf(stderr, "Error: %s\n", mysql_error(sql));
1874: }
1875:
1.8 veillard 1876: /*
1877: * Dump the distributions informations
1878: * 1/ collect the list of IDs for the distribs
1879: */
1880: printf("\n\n;\n; The distribution list\n;\n\n");
1881: mysql_query(sql,"SELECT ID FROM Distribs");
1882: result = mysql_use_result(sql);
1883:
1884: while((row = mysql_fetch_row(result)))
1885: {
1886: if (row[0] != NULL) {
1887: if (sscanf(row[0], "%d", &id) == 1) {
1888: ids[index++] = id;
1889: }
1890: }
1891: }
1892: mysql_free_result(result);
1893:
1894: /*
1895: * Dump each distribution separately.
1896: */
1897: for (i = 0;i < index;i++) {
1898:
1899: snprintf(query, SMALL_QUERY - 1,
1.10 veillard 1900: "SELECT Directory,Name,Vendor,Path,URL,URLSrc,Description,Html,Color \
1.8 veillard 1901: FROM Distribs WHERE ID=%d", ids[i]);
1902: query[SMALL_QUERY - 1] = 0;
1903: if (mysql_query(sql,query)) {
1904: printf("sql_show_config: SELECT Distrib %d failed: %s\n",
1905: ids[i], mysql_error(sql));
1906: continue;
1907: }
1908:
1909: result = mysql_use_result(sql);
1910: if (result) {
1911: while((row = mysql_fetch_row(result)))
1912: {
1913: if (row[0] == NULL)
1914: break;
1915: printf("[%s]\n", row[0]);
1916: if (row[1] != NULL)
1917: printf("name=%s\n", row[1]);
1918: if (row[3] != NULL)
1919: printf("subdir=%s\n", row[3]);
1920: if (row[4] != NULL)
1921: printf("ftp=%s\n", row[4]);
1922: if (row[5] != NULL)
1923: printf("ftpsrc=%s\n", row[5]);
1.10 veillard 1924: if (row[7] != NULL)
1925: printf("html=%s\n", row[7]);
1926: if (row[8] != NULL)
1927: printf("color=%s\n", row[8]);
1.8 veillard 1928: }
1929: }
1930: mysql_free_result(result);
1.12 veillard 1931:
1932: /*
1933: * Extract the mirrors for this distribution.
1934: */
1935: snprintf(query, SMALL_QUERY - 1,
1936: "SELECT URL FROM Mirrors WHERE ID=%d", ids[i]);
1937: query[SMALL_QUERY - 1] = 0;
1938: if (mysql_query(sql,query)) {
1939: printf("sql_show_config: SELECT Mirrors %d failed: %s\n",
1940: ids[i], mysql_error(sql));
1941: printf("\n\n");
1942: continue;
1943: }
1944: result = mysql_use_result(sql);
1945: if (result) {
1946: while((row = mysql_fetch_row(result)))
1947: {
1948: if (row[0] == NULL)
1949: continue;
1950: printf("mirror=%s\n", row[0]);
1951: }
1952: }
1953: mysql_free_result(result);
1954:
1.8 veillard 1955: printf("\n\n");
1956: }
1957:
1958: printf(";\n; End of the configuration file for rpm2html\n;\n");
1.6 veillard 1959: }
1960:
1961: void sql_show_metadata(void) {
1962: MYSQL_RES *result;
1963: MYSQL_ROW row;
1964:
1965:
1966: mysql_query(sql,"SELECT URL FROM Metadata");
1967: result = mysql_use_result(sql);
1968:
1969: while((row = mysql_fetch_row(result)))
1970: {
1971: if (row[0] == NULL)
1972: printf("NULL !\n");
1973: else {
1974: printf("%s\n", row[0]);
1975: }
1976: }
1977: if(mysql_errno(sql)) {
1978: fprintf(stderr, "Error: %s\n", mysql_error(sql));
1979: }
1980:
1981: }
1982:
1983: void sql_show_mirrors(void) {
1984: MYSQL_RES *result;
1985: MYSQL_ROW row;
1986:
1987:
1988: mysql_query(sql,"SELECT URL FROM Mirrors");
1989: result = mysql_use_result(sql);
1990:
1991: while((row = mysql_fetch_row(result)))
1992: {
1993: if (row[0] == NULL)
1994: printf("NULL !\n");
1995: else {
1996: printf("%s\n", row[0]);
1997: }
1998: }
1999: if(mysql_errno(sql)) {
2000: fprintf(stderr, "Error: %s\n", mysql_error(sql));
2001: }
2002: }
2003:
1.5 veillard 2004: void sql_show_vendors(void) {
1.1 veillard 2005: MYSQL_RES *result;
2006: MYSQL_ROW row;
2007:
2008:
2009: mysql_query(sql,"SELECT Name, URL FROM Vendors");
2010: result = mysql_use_result(sql);
2011:
2012: while((row = mysql_fetch_row(result)))
2013: {
2014: if (row[0] == NULL)
2015: printf("NULL !\n");
2016: else {
2017: if (row[1] == NULL)
2018: printf("%s : no url\n", row[0]);
2019: else
2020: printf("%s : %s\n", row[0], row[1]);
2021: }
2022: }
2023: if(mysql_errno(sql)) {
2024: fprintf(stderr, "Error: %s\n", mysql_error(sql));
2025: }
2026:
2027: }
2028:
1.5 veillard 2029: void sql_show_distribs(void) {
1.1 veillard 2030: MYSQL_RES *result;
2031: MYSQL_ROW row;
2032:
2033:
2034: mysql_query(sql,"SELECT Name, Path, URL FROM Distribs");
2035: result = mysql_use_result(sql);
2036:
2037: while((row = mysql_fetch_row(result)))
2038: {
2039: if (row[0] == NULL)
2040: printf("NULL !\n");
2041: else {
2042: if (row[1] == NULL)
2043: printf("%s : no Path\n", row[0]);
2044: else {
2045: if (row[2] == NULL)
2046: printf("%s : %s : no url\n", row[0], row[1]);
2047: else
2048: printf("%s : %s : %s\n", row[0], row[1], row[2]);
2049: }
2050: }
2051: }
2052: if(mysql_errno(sql)) {
2053: fprintf(stderr, "Error: %s\n", mysql_error(sql));
2054: }
2055:
2056: }
2057:
1.5 veillard 2058: int sql_show_table_stats(const char *table, const char *key) {
1.6 veillard 2059: char query[MAX_QUERY];
1.2 veillard 2060: MYSQL_RES *result;
2061: MYSQL_ROW row;
2062: int res;
2063:
2064: /*
2065: * Search first for the ID if it already exists
2066: */
1.6 veillard 2067: snprintf(query, MAX_QUERY - 1, "SELECT COUNT(%s) FROM %s", key, table);
2068: query[MAX_QUERY - 1] = 0;
1.2 veillard 2069: if (mysql_query(sql,query)) {
1.5 veillard 2070: printf("sql_show_table_stats: SELECT COUNT failed: %s\n",
1.2 veillard 2071: mysql_error(sql));
2072: return(-1);
2073: }
2074:
2075: result = mysql_use_result(sql);
2076: if (result) {
2077: while((row = mysql_fetch_row(result)))
2078: {
2079: /*
2080: * Lookup the value and return it
2081: */
2082: if (row[0] == NULL) {
2083: mysql_free_result(result);
1.5 veillard 2084: printf("sql_show_table_stats: select count returns NULL !\n");
1.2 veillard 2085: return(-1);
2086: }
2087: if (sscanf(row[0], "%d", &res) != 1) {
2088: mysql_free_result(result);
1.5 veillard 2089: printf("sql_show_table_stats: value non numeric %s\n", row[0]);
1.2 veillard 2090: return(-1);
2091: }
2092: mysql_free_result(result);
2093: if (res <= 0)
2094: printf(" %s is empty\n", table);
2095: else
2096: printf(" %s contains %d records\n", table, res);
2097: return(res);
2098: }
2099: mysql_free_result(result);
2100: }
2101: if(mysql_errno(sql)) {
1.5 veillard 2102: fprintf(stderr, "sql_show_stats error: %s\n", mysql_error(sql));
1.2 veillard 2103: }
2104: return(-1);
2105: }
2106:
1.5 veillard 2107: int sql_show_stats(void) {
1.2 veillard 2108: const char *query = "SHOW TABLES";
2109: MYSQL_RES *result;
2110: MYSQL_ROW row;
2111:
2112: int tables = 0;
2113: int records = 0;
2114:
2115: if (mysql_query(sql,query)) {
2116: printf("sql_check_tables: SHOW TABLES failed %s\n",
2117: mysql_error(sql));
2118: return(-1);
2119: }
2120:
2121: result = mysql_use_result(sql);
2122: if (result) {
2123: while((row = mysql_fetch_row(result)))
2124: {
2125: if (row[0] == NULL) {
2126: mysql_free_result(result);
2127: printf("sql_check_tables: SHOW TABLES returns NULL !\n");
2128: return(-1);
2129: }
2130: tables++;
2131: }
2132: mysql_free_result(result);
2133: }
2134: if(mysql_errno(sql)) {
1.5 veillard 2135: fprintf(stderr, "sql_show_stats error: %s\n", mysql_error(sql));
1.2 veillard 2136: }
2137: printf("%d tables in use\n", tables);
1.5 veillard 2138: records += sql_show_table_stats("Config", "Name");
2139: records += sql_show_table_stats("Distribs", "Name");
2140: records += sql_show_table_stats("Vendors", "Name");
2141: records += sql_show_table_stats("Mirrors", "URL");
2142: records += sql_show_table_stats("Metadata", "URL");
2143: records += sql_show_table_stats("Packages", "Name");
1.8 veillard 2144: records += sql_show_table_stats("Requires", "Resource");
2145: records += sql_show_table_stats("Provides", "Resource");
1.5 veillard 2146: records += sql_show_table_stats("Files", "Path");
1.2 veillard 2147: printf("Total: %d records\n", records);
2148: return(records);
2149: }
2150:
1.26 veillard 2151: void sql_show_latests(void) {
2152: rpmDataPtr list;
2153:
2154: list = sqlRpmByDate();
2155: if (list == NULL) {
2156: fprintf(stderr, "no package in database\n");
2157: return;
2158: }
1.28 daniel 2159: dumpRpmByDate(list, 0);
1.29 veillard 2160: }
2161:
2162: void sql_show_all(void) {
2163: rpmDataPtr list;
1.31 veillard 2164: #ifdef SQL_DEBUG_TIMING
2165: time_t cur, last;
1.29 veillard 2166:
1.31 veillard 2167: last = time(NULL);
2168: #endif
1.29 veillard 2169: list = sqlRpmAll();
2170: if (list == NULL) {
2171: fprintf(stderr, "no package in database\n");
2172: return;
2173: }
1.31 veillard 2174: #ifdef SQL_DEBUG_TIMING
2175: cur = time(NULL);
2176: fprintf(stderr, "sqlRpmAll took %d seconds\n", (int)(cur - last));
2177: last = cur;
2178: #endif
2179:
2180: rpmNameSort(&list, 0);
2181: dumpRpmByName(rpmSoftwareList, 0);
2182:
2183: #ifdef SQL_DEBUG_TIMING
2184: cur = time(NULL);
2185: fprintf(stderr, "dumpRpmByName took %d seconds\n", (int)(cur - last));
2186: last = cur;
2187: #endif
2188:
2189: rpmGroupSort(&list, 0);
1.32 daniel 2190: dumpRpmByGroups(rpmSoftwareList, 0);
1.31 veillard 2191:
2192: #ifdef SQL_DEBUG_TIMING
2193: cur = time(NULL);
2194: fprintf(stderr, "dumpRpmByGroups took %d seconds\n", (int)(cur - last));
2195: last = cur;
2196: #endif
1.35 ! veillard 2197:
! 2198: rpmVendorSort(&list, 0);
! 2199: dumpRpmByVendors(list, 0);
! 2200:
! 2201: #ifdef SQL_DEBUG_TIMING
! 2202: cur = time(NULL);
! 2203: fprintf(stderr, "dumpRpmByVendors took %d seconds\n", (int)(cur - last));
! 2204: last = cur;
! 2205: #endif
! 2206:
1.26 veillard 2207: }
2208:
1.2 veillard 2209: /************************************************************************
2210: * *
2211: * rpm2html configuration functions *
2212: * *
2213: ************************************************************************/
2214:
2215: int readConfigSql(void) {
1.6 veillard 2216: char query[MAX_QUERY];
1.3 veillard 2217: MYSQL_RES *result;
2218: MYSQL_ROW row;
1.4 veillard 2219: int dir = 0;
1.3 veillard 2220:
1.2 veillard 2221: /*
1.3 veillard 2222: * General configuration informations
1.2 veillard 2223: */
1.6 veillard 2224: snprintf(query, MAX_QUERY - 1, "SELECT Name,Value FROM Config");
2225: query[MAX_QUERY - 1] = 0;
1.3 veillard 2226: if (mysql_query(sql,query)) {
2227: printf("sql_check_tables: SELECT Config failed %s\n",
2228: mysql_error(sql));
2229: return(-1);
2230: }
2231:
2232: result = mysql_use_result(sql);
2233: if (result) {
2234: while((row = mysql_fetch_row(result)))
2235: {
2236: if ((row[0] == NULL) || (row[1] == NULL)) {
2237: fprintf(stderr, "readConfigSql : found NULL value\n");
2238: continue;
2239: }
1.4 veillard 2240: if (!strcmp(row[0], "dir"))
2241: dir = 1;
1.3 veillard 2242: addConfigEntry(RPM2HTML_NAME, row[0], row[1]);
2243: }
2244: mysql_free_result(result);
2245: }
2246: if(mysql_errno(sql)) {
1.5 veillard 2247: fprintf(stderr, "sql_show_stats error: %s\n", mysql_error(sql));
1.4 veillard 2248: }
2249: if (dir == 0) {
2250: fprintf(stderr, "readConfigSql : no directory\n");
2251: return(-1);
1.3 veillard 2252: }
2253:
2254: /*
2255: * The metadata mirror list.
2256: */
1.6 veillard 2257: snprintf(query, MAX_QUERY - 1, "SELECT URL FROM Metadata");
2258: query[MAX_QUERY - 1] = 0;
1.3 veillard 2259: if (mysql_query(sql,query)) {
2260: printf("sql_check_tables: SELECT Metadata failed %s\n",
2261: mysql_error(sql));
2262: return(-1);
2263: }
2264:
2265: result = mysql_use_result(sql);
2266: if (result) {
2267: while((row = mysql_fetch_row(result)))
2268: {
2269: if (row[0] == NULL) {
2270: fprintf(stderr, "readConfigSql : found NULL metadata\n");
2271: continue;
2272: }
2273: addConfigEntry("metadata", "mirror", row[0]);
2274: }
2275: mysql_free_result(result);
2276: }
2277: if(mysql_errno(sql)) {
1.5 veillard 2278: fprintf(stderr, "sql_show_stats error: %s\n", mysql_error(sql));
1.3 veillard 2279: }
2280:
2281: /*
2282: * The distribution lists
2283: */
1.6 veillard 2284: snprintf(query, MAX_QUERY - 1, "SELECT Directory,Name,URL,URLSrc,Path FROM Distribs");
2285: query[MAX_QUERY - 1] = 0;
1.3 veillard 2286: if (mysql_query(sql,query)) {
2287: printf("sql_check_tables: SELECT Distribs failed %s\n",
2288: mysql_error(sql));
2289: return(-1);
2290: }
2291:
2292: result = mysql_use_result(sql);
2293: if (result) {
2294: while((row = mysql_fetch_row(result)))
2295: {
2296: if (row[0] == NULL) {
2297: fprintf(stderr, "readConfigSql : found NULL distro\n");
2298: continue;
2299: }
2300:
2301: if (row[1] != NULL)
2302: addConfigEntry(row[0], "name", row[1]);
2303: if (row[2] != NULL)
2304: addConfigEntry(row[0], "ftp", row[2]);
2305: if (row[3] != NULL)
2306: addConfigEntry(row[0], "ftp", row[3]);
2307: if (row[4] != NULL)
2308: addConfigEntry(row[0], "subdir", row[4]);
2309: }
2310: mysql_free_result(result);
2311: }
2312: if(mysql_errno(sql)) {
1.5 veillard 2313: fprintf(stderr, "sql_show_stats error: %s\n", mysql_error(sql));
1.3 veillard 2314: }
2315:
2316: /*
2317: * The Mirrors
2318: */
1.6 veillard 2319: snprintf(query, MAX_QUERY - 1, "SELECT Distribs.Directory,Mirrors.URL FROM Distribs,Mirrors WHERE Distribs.ID = Mirrors.ID");
2320: query[MAX_QUERY - 1] = 0;
1.3 veillard 2321: if (mysql_query(sql,query)) {
2322: printf("sql_check_tables: SELECT Distribs failed %s\n",
2323: mysql_error(sql));
2324: return(-1);
2325: }
2326:
2327: result = mysql_use_result(sql);
2328: if (result) {
2329: while((row = mysql_fetch_row(result)))
2330: {
2331: if ((row[0] == NULL) || (row[1] == NULL)) {
2332: fprintf(stderr, "readConfigSql : found NULL mirror\n");
2333: continue;
2334: }
2335:
2336: addConfigEntry(row[0], "mirror", row[1]);
2337: }
2338: mysql_free_result(result);
2339: }
2340: if(mysql_errno(sql)) {
1.5 veillard 2341: fprintf(stderr, "sql_show_stats error: %s\n", mysql_error(sql));
1.3 veillard 2342: }
2343:
1.5 veillard 2344: /*
2345: * TODO: add the language(s) stuff
2346: */
1.3 veillard 2347: return(0);
1.2 veillard 2348: }
2349:
2350: void sqlConfigEntry(const char *rpmdir, const char *name, const char *value) {
2351: int distrib;
2352:
2353: if (rpm2htmlVerbose > 1)
2354: printf("sqlConfigEntry(\"%s\", \"%s\", \"%s\")\n", rpmdir, name, value);
2355:
2356: /*
2357: * case of global option for rpm2html.
2358: */
2359: if (!strcasecmp(rpmdir, RPM2HTML_NAME)) {
1.5 veillard 2360: sql_add_config_info(name, value);
1.2 veillard 2361: return;
2362: }
2363:
2364: /*
2365: * Options for the metadata mirrors.
2366: */
2367: if (!strcasecmp(rpmdir, "metadata")) {
2368: if (!strcasecmp(name, "mirror")) {
1.5 veillard 2369: sql_add_metadata_base(value);
1.2 veillard 2370: } else {
2371: printf("Config file : %s entry for [metadata] ignored\n", name);
2372: }
2373: return;
2374: }
2375:
2376: /*
2377: * option for a directory.
2378: */
2379: if (!strcasecmp(name, "name")) {
1.9 veillard 2380: sql_add_distrib(value, NULL, rpmdir, NULL, NULL, NULL, NULL,
2381: NULL, NULL);
1.2 veillard 2382: } else if (!strcasecmp(name, "subdir")) {
2383: distrib = sql_read_info_key("Distribs", "Directory", rpmdir);
2384: if (distrib > 0)
2385: sql_update_id("Distribs", distrib, "Path", value);
2386: } else if (!strcasecmp(name, "url")) {
2387: distrib = sql_read_info_key("Distribs", "Directory", rpmdir);
2388: if (distrib > 0)
2389: sql_update_id("Distribs", distrib, "URL", value);
2390: } else if (!strcasecmp(name, "ftp")) {
2391: distrib = sql_read_info_key("Distribs", "Directory", rpmdir);
2392: if (distrib > 0)
2393: sql_update_id("Distribs", distrib, "URL", value);
2394: } else if (!strcasecmp(name, "ftpsrc")) {
2395: distrib = sql_read_info_key("Distribs", "Directory", rpmdir);
2396: if (distrib > 0)
2397: sql_update_id("Distribs", distrib, "URLSrc", value);
1.9 veillard 2398: } else if (!strcasecmp(name, "html")) {
2399: distrib = sql_read_info_key("Distribs", "Directory", rpmdir);
2400: if (distrib > 0)
2401: sql_update_id("Distribs", distrib, "Html", value);
2402: } else if (!strcasecmp(name, "color")) {
2403: distrib = sql_read_info_key("Distribs", "Directory", rpmdir);
2404: if (distrib > 0)
2405: sql_update_id("Distribs", distrib, "Color", value);
1.2 veillard 2406: } else if (!strcasecmp(name, "mirror")) {
2407: distrib = sql_read_info_key("Distribs", "Directory", rpmdir);
2408: if (distrib > 0)
1.5 veillard 2409: sql_add_dist_mirror(distrib, value, 0);
1.2 veillard 2410: } else {
2411: printf("Config file : %s entry for [%s] ignored\n", name, rpmdir);
2412: }
2413: }
1.1 veillard 2414:
Webmaster