Fossil SCM

Use drop-down menus to select the user on the /reports pages.

drh 2015-05-18 22:05 UTC andygoth-user-reports
Commit 675274612dc320046b8887070218ba9fc9238f65
2 files changed +16 -22 +37
+16 -22
--- src/statrep.c
+++ src/statrep.c
@@ -577,31 +577,19 @@
577577
char **azYear = 0; /* Year dropdown menu */
578578
int rowCount = 0;
579579
int total = 0;
580580
581581
stats_report_init_view();
582
- db_prepare(&q,
583
- "SELECT DISTINCT substr(date(mtime),1,4) AS y"
584
- " FROM v_reports"
585
- " WHERE ifnull(coalesce(euser,user,'')=%Q,1)"
586
- " GROUP BY y ORDER BY y DESC", zUserName);
587
- while( SQLITE_ROW == db_step(&q) ){
588
- azYear = fossil_realloc(azYear, sizeof(char*)*(n+2));
589
- azYear[n] = fossil_strdup(db_column_text(&q,0));
590
- azYear[n+1] = azYear[n];
591
- if( !isValidYear && fossil_strcmp(zYear,azYear[n])==0 ) isValidYear = 1;
592
- n += 2;
593
- }
594
- db_finalize(&q);
595
- if( !isValidYear ){
596
- if( n ){
597
- zYear = azYear[0];
598
- }else{
599
- zYear = db_text("1970","SELECT substr(date('now'),1,4);");
600
- }
601
- }
602
- style_submenu_multichoice("y", n/2, (const char**)azYear, 0);
582
+ style_submenu_sql("y", "Year:",
583
+ "WITH RECURSIVE a(b) AS ("
584
+ " SELECT substr(date('now'),1,4) UNION ALL"
585
+ " SELECT b-1 FROM a"
586
+ " WHERE b>0+(SELECT substr(date(min(mtime)),1,4) FROM event)"
587
+ ") SELECT b, b FROM a ORDER BY b DESC");
588
+ if( zYear==0 || strlen(zYear)!=4 ){
589
+ zYear = db_text("1970","SELECT substr(date('now'),1,4);");
590
+ }
603591
cgi_printf("<br/>");
604592
db_prepare(&q,
605593
"SELECT DISTINCT strftime('%%W',mtime) AS wk, "
606594
" count(*) AS n "
607595
" FROM v_reports "
@@ -753,11 +741,17 @@
753741
style_submenu_multichoice("view", nView/2, azView, 0);
754742
if( eType!=RPT_BYFILE ){
755743
style_submenu_multichoice("type", ArraySize(azType)/2, azType, 0);
756744
}
757745
if( eType!=RPT_BYUSER ){
758
- style_submenu_entry("u", "User:", 12, 0);
746
+ style_submenu_sql("u","User:",
747
+ "SELECT '', 'All Users' UNION ALL "
748
+ "SELECT x, x FROM ("
749
+ " SELECT DISTINCT trim(coalesce(euser,user)) AS x FROM event %s"
750
+ " ORDER BY 1 COLLATE nocase) WHERE x!=''",
751
+ eType==RPT_BYFILE ? "WHERE type='ci'" : ""
752
+ );
759753
}
760754
}
761755
style_submenu_element("Stats", "Stats", "%R/stat");
762756
url_reset(&url);
763757
style_header("Activity Reports");
764758
--- src/statrep.c
+++ src/statrep.c
@@ -577,31 +577,19 @@
577 char **azYear = 0; /* Year dropdown menu */
578 int rowCount = 0;
579 int total = 0;
580
581 stats_report_init_view();
582 db_prepare(&q,
583 "SELECT DISTINCT substr(date(mtime),1,4) AS y"
584 " FROM v_reports"
585 " WHERE ifnull(coalesce(euser,user,'')=%Q,1)"
586 " GROUP BY y ORDER BY y DESC", zUserName);
587 while( SQLITE_ROW == db_step(&q) ){
588 azYear = fossil_realloc(azYear, sizeof(char*)*(n+2));
589 azYear[n] = fossil_strdup(db_column_text(&q,0));
590 azYear[n+1] = azYear[n];
591 if( !isValidYear && fossil_strcmp(zYear,azYear[n])==0 ) isValidYear = 1;
592 n += 2;
593 }
594 db_finalize(&q);
595 if( !isValidYear ){
596 if( n ){
597 zYear = azYear[0];
598 }else{
599 zYear = db_text("1970","SELECT substr(date('now'),1,4);");
600 }
601 }
602 style_submenu_multichoice("y", n/2, (const char**)azYear, 0);
603 cgi_printf("<br/>");
604 db_prepare(&q,
605 "SELECT DISTINCT strftime('%%W',mtime) AS wk, "
606 " count(*) AS n "
607 " FROM v_reports "
@@ -753,11 +741,17 @@
753 style_submenu_multichoice("view", nView/2, azView, 0);
754 if( eType!=RPT_BYFILE ){
755 style_submenu_multichoice("type", ArraySize(azType)/2, azType, 0);
756 }
757 if( eType!=RPT_BYUSER ){
758 style_submenu_entry("u", "User:", 12, 0);
 
 
 
 
 
 
759 }
760 }
761 style_submenu_element("Stats", "Stats", "%R/stat");
762 url_reset(&url);
763 style_header("Activity Reports");
764
--- src/statrep.c
+++ src/statrep.c
@@ -577,31 +577,19 @@
577 char **azYear = 0; /* Year dropdown menu */
578 int rowCount = 0;
579 int total = 0;
580
581 stats_report_init_view();
582 style_submenu_sql("y", "Year:",
583 "WITH RECURSIVE a(b) AS ("
584 " SELECT substr(date('now'),1,4) UNION ALL"
585 " SELECT b-1 FROM a"
586 " WHERE b>0+(SELECT substr(date(min(mtime)),1,4) FROM event)"
587 ") SELECT b, b FROM a ORDER BY b DESC");
588 if( zYear==0 || strlen(zYear)!=4 ){
589 zYear = db_text("1970","SELECT substr(date('now'),1,4);");
590 }
 
 
 
 
 
 
 
 
 
 
 
 
591 cgi_printf("<br/>");
592 db_prepare(&q,
593 "SELECT DISTINCT strftime('%%W',mtime) AS wk, "
594 " count(*) AS n "
595 " FROM v_reports "
@@ -753,11 +741,17 @@
741 style_submenu_multichoice("view", nView/2, azView, 0);
742 if( eType!=RPT_BYFILE ){
743 style_submenu_multichoice("type", ArraySize(azType)/2, azType, 0);
744 }
745 if( eType!=RPT_BYUSER ){
746 style_submenu_sql("u","User:",
747 "SELECT '', 'All Users' UNION ALL "
748 "SELECT x, x FROM ("
749 " SELECT DISTINCT trim(coalesce(euser,user)) AS x FROM event %s"
750 " ORDER BY 1 COLLATE nocase) WHERE x!=''",
751 eType==RPT_BYFILE ? "WHERE type='ci'" : ""
752 );
753 }
754 }
755 style_submenu_element("Stats", "Stats", "%R/stat");
756 url_reset(&url);
757 style_header("Activity Reports");
758
+37
--- src/style.c
+++ src/style.c
@@ -285,11 +285,45 @@
285285
aSubmenuCtrl[nSubmenuCtrl].azChoice = azChoice;
286286
aSubmenuCtrl[nSubmenuCtrl].isDisabled = isDisabled;
287287
aSubmenuCtrl[nSubmenuCtrl].eType = FF_MULTI;
288288
nSubmenuCtrl++;
289289
}
290
+void style_submenu_sql(
291
+ const char *zName, /* Query parameter name */
292
+ const char *zLabel, /* Label on the control */
293
+ const char *zFormat, /* Format string for SQL command for choices */
294
+ ... /* Arguments to the format string */
295
+){
296
+ Stmt q;
297
+ int n = 0;
298
+ int nAlloc = 0;
299
+ char **az = 0;
300
+ va_list ap;
290301
302
+ va_start(ap, zFormat);
303
+ db_vprepare(&q, 0, zFormat, ap);
304
+ va_end(ap);
305
+ while( SQLITE_ROW==db_step(&q) ){
306
+ if( n+2>=nAlloc ){
307
+ nAlloc += nAlloc + 20;
308
+ az = fossil_realloc(az, sizeof(char*)*nAlloc);
309
+ }
310
+ az[n++] = fossil_strdup(db_column_text(&q,0));
311
+ az[n++] = fossil_strdup(db_column_text(&q,1));
312
+ }
313
+ db_finalize(&q);
314
+ if( n>0 ){
315
+ aSubmenuCtrl[nSubmenuCtrl].zName = zName;
316
+ aSubmenuCtrl[nSubmenuCtrl].zLabel = zLabel;
317
+ aSubmenuCtrl[nSubmenuCtrl].iSize = n/2;
318
+ aSubmenuCtrl[nSubmenuCtrl].azChoice = (const char**)az;
319
+ aSubmenuCtrl[nSubmenuCtrl].isDisabled = 0;
320
+ aSubmenuCtrl[nSubmenuCtrl].eType = FF_MULTI;
321
+ nSubmenuCtrl++;
322
+ }
323
+}
324
+
291325
292326
/*
293327
** Compare two submenu items for sorting purposes
294328
*/
295329
static int submenuCompare(const void *a, const void *b){
@@ -514,10 +548,13 @@
514548
break;
515549
}
516550
case FF_MULTI: {
517551
int j;
518552
const char *zVal = P(zQPN);
553
+ if( aSubmenuCtrl[i].zLabel ){
554
+ cgi_printf("&nbsp;%h", aSubmenuCtrl[i].zLabel);
555
+ }
519556
cgi_printf(
520557
"<select class='submenuctrl' size='1' name='%s'%s "
521558
"onchange='gebi(\"f01\").submit();'>\n",
522559
zQPN, zDisabled
523560
);
524561
--- src/style.c
+++ src/style.c
@@ -285,11 +285,45 @@
285 aSubmenuCtrl[nSubmenuCtrl].azChoice = azChoice;
286 aSubmenuCtrl[nSubmenuCtrl].isDisabled = isDisabled;
287 aSubmenuCtrl[nSubmenuCtrl].eType = FF_MULTI;
288 nSubmenuCtrl++;
289 }
 
 
 
 
 
 
 
 
 
 
 
290
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
291
292 /*
293 ** Compare two submenu items for sorting purposes
294 */
295 static int submenuCompare(const void *a, const void *b){
@@ -514,10 +548,13 @@
514 break;
515 }
516 case FF_MULTI: {
517 int j;
518 const char *zVal = P(zQPN);
 
 
 
519 cgi_printf(
520 "<select class='submenuctrl' size='1' name='%s'%s "
521 "onchange='gebi(\"f01\").submit();'>\n",
522 zQPN, zDisabled
523 );
524
--- src/style.c
+++ src/style.c
@@ -285,11 +285,45 @@
285 aSubmenuCtrl[nSubmenuCtrl].azChoice = azChoice;
286 aSubmenuCtrl[nSubmenuCtrl].isDisabled = isDisabled;
287 aSubmenuCtrl[nSubmenuCtrl].eType = FF_MULTI;
288 nSubmenuCtrl++;
289 }
290 void style_submenu_sql(
291 const char *zName, /* Query parameter name */
292 const char *zLabel, /* Label on the control */
293 const char *zFormat, /* Format string for SQL command for choices */
294 ... /* Arguments to the format string */
295 ){
296 Stmt q;
297 int n = 0;
298 int nAlloc = 0;
299 char **az = 0;
300 va_list ap;
301
302 va_start(ap, zFormat);
303 db_vprepare(&q, 0, zFormat, ap);
304 va_end(ap);
305 while( SQLITE_ROW==db_step(&q) ){
306 if( n+2>=nAlloc ){
307 nAlloc += nAlloc + 20;
308 az = fossil_realloc(az, sizeof(char*)*nAlloc);
309 }
310 az[n++] = fossil_strdup(db_column_text(&q,0));
311 az[n++] = fossil_strdup(db_column_text(&q,1));
312 }
313 db_finalize(&q);
314 if( n>0 ){
315 aSubmenuCtrl[nSubmenuCtrl].zName = zName;
316 aSubmenuCtrl[nSubmenuCtrl].zLabel = zLabel;
317 aSubmenuCtrl[nSubmenuCtrl].iSize = n/2;
318 aSubmenuCtrl[nSubmenuCtrl].azChoice = (const char**)az;
319 aSubmenuCtrl[nSubmenuCtrl].isDisabled = 0;
320 aSubmenuCtrl[nSubmenuCtrl].eType = FF_MULTI;
321 nSubmenuCtrl++;
322 }
323 }
324
325
326 /*
327 ** Compare two submenu items for sorting purposes
328 */
329 static int submenuCompare(const void *a, const void *b){
@@ -514,10 +548,13 @@
548 break;
549 }
550 case FF_MULTI: {
551 int j;
552 const char *zVal = P(zQPN);
553 if( aSubmenuCtrl[i].zLabel ){
554 cgi_printf("&nbsp;%h", aSubmenuCtrl[i].zLabel);
555 }
556 cgi_printf(
557 "<select class='submenuctrl' size='1' name='%s'%s "
558 "onchange='gebi(\"f01\").submit();'>\n",
559 zQPN, zDisabled
560 );
561

Keyboard Shortcuts

Open search /
Next entry (timeline) j
Previous entry (timeline) k
Open focused entry Enter
Show this help ?
Toggle theme Top nav button