Fossil SCM
added /json/user/list.
Commit
59ef1667acec8536f54277a89e8ec5a939f0221f
Parent
0475e63d44d86de…
1 file changed
+68
-10
+68
-10
| --- src/json.c | ||
| +++ src/json.c | ||
| @@ -1570,25 +1570,45 @@ | ||
| 1570 | 1570 | {"wik", json_timeline_wiki, 0}, |
| 1571 | 1571 | {"wiki", json_timeline_wiki, 0}, |
| 1572 | 1572 | /* Last entry MUST have a NULL name. */ |
| 1573 | 1573 | {NULL,NULL,0} |
| 1574 | 1574 | }; |
| 1575 | + | |
| 1576 | +static cson_value * json_user_list(); | |
| 1577 | +#if 0 | |
| 1578 | +static cson_value * json_user_detail(); | |
| 1579 | +static cson_value * json_user_create(); | |
| 1580 | +static cson_value * json_user_edit(); | |
| 1581 | +#endif | |
| 1582 | + | |
| 1583 | +/* | |
| 1584 | +** Mapping of /json/user/XXX commands/paths to callbacks. | |
| 1585 | +*/ | |
| 1586 | +static const JsonPageDef JsonPageDefs_User[] = { | |
| 1587 | +{"list", json_user_list, 0}, | |
| 1588 | +{"detail", json_page_nyi, 0}, | |
| 1589 | +{"create", json_page_nyi, 1}, | |
| 1590 | +{"edit", json_page_nyi, 1}, | |
| 1591 | +/* Last entry MUST have a NULL name. */ | |
| 1592 | +{NULL,NULL,0} | |
| 1593 | +}; | |
| 1594 | + | |
| 1575 | 1595 | |
| 1576 | 1596 | /* |
| 1577 | 1597 | ** A page/command dispatch helper for fossil_json_f() implementations. |
| 1578 | -** depth should be the depth parameter passed to the fossil_json_f(). | |
| 1579 | 1598 | ** pages must be an array of JsonPageDef commands which we can |
| 1580 | -** dispatch. The final item in the array MUST have a NULL name | |
| 1599 | +** dispatch. The final item in the array MUST have a NULL name | |
| 1581 | 1600 | ** element. |
| 1582 | 1601 | ** |
| 1583 | -** This function takes json_comand_arg(1+g.json.dispatchDepth) and | |
| 1584 | -** searches pages for a matching name. If found then that page's | |
| 1585 | -** func() is called to fetch the payload, which is returned to the | |
| 1586 | -** caller. | |
| 1602 | +** This function takes the command specified in | |
| 1603 | +** json_comand_arg(1+g.json.dispatchDepth) and searches pages for a | |
| 1604 | +** matching name. If found then that page's func() is called to fetch | |
| 1605 | +** the payload, which is returned to the caller. | |
| 1587 | 1606 | ** |
| 1588 | 1607 | ** On error, g.json.resultCode is set to one of the FossilJsonCodes |
| 1589 | -** values. | |
| 1608 | +** values and NULL is returned. If non-NULL is returned, ownership is | |
| 1609 | +** transfered to the caller. | |
| 1590 | 1610 | */ |
| 1591 | 1611 | static cson_value * json_page_dispatch_helper(JsonPageDef const * pages){ |
| 1592 | 1612 | JsonPageDef const * def; |
| 1593 | 1613 | char const * cmd = json_command_arg(1+g.json.dispatchDepth); |
| 1594 | 1614 | assert( NULL != pages ); |
| @@ -1606,12 +1626,19 @@ | ||
| 1606 | 1626 | return (*def->func)(); |
| 1607 | 1627 | } |
| 1608 | 1628 | } |
| 1609 | 1629 | |
| 1610 | 1630 | /* |
| 1611 | -** Implements the /json/wiki family of pages/commands. Far from | |
| 1612 | -** complete. | |
| 1631 | +** Implements the /json/user family of pages/commands. | |
| 1632 | +** | |
| 1633 | +*/ | |
| 1634 | +static cson_value * json_page_user(){ | |
| 1635 | + return json_page_dispatch_helper(&JsonPageDefs_User[0]); | |
| 1636 | +} | |
| 1637 | + | |
| 1638 | +/* | |
| 1639 | +** Implements the /json/wiki family of pages/commands. | |
| 1613 | 1640 | ** |
| 1614 | 1641 | */ |
| 1615 | 1642 | static cson_value * json_page_wiki(){ |
| 1616 | 1643 | return json_page_dispatch_helper(&JsonPageDefs_Wiki[0]); |
| 1617 | 1644 | } |
| @@ -2422,10 +2449,41 @@ | ||
| 2422 | 2449 | g.json.resultCode = FSL_JSON_E_RESOURCE_NOT_FOUND; |
| 2423 | 2450 | } |
| 2424 | 2451 | db_finalize(&q); |
| 2425 | 2452 | return payload; |
| 2426 | 2453 | } |
| 2454 | + | |
| 2455 | +static cson_value * json_user_list(){ | |
| 2456 | + cson_value * payV = NULL; | |
| 2457 | + cson_array * pay = NULL; | |
| 2458 | + Stmt q; | |
| 2459 | + if(! g.perm.Admin ){ | |
| 2460 | + g.json.resultCode = FSL_JSON_E_DENIED; | |
| 2461 | + return NULL; | |
| 2462 | + } | |
| 2463 | + payV = cson_value_new_array(); | |
| 2464 | + pay = cson_value_get_array(payV); | |
| 2465 | + db_prepare(&q,"SELECT uid AS uid," | |
| 2466 | + " login AS name," | |
| 2467 | + " cap AS capabilities," | |
| 2468 | + " info AS info," | |
| 2469 | + " mtime AS mtime" | |
| 2470 | + " FROM user ORDER BY login"); | |
| 2471 | + | |
| 2472 | + while( (SQLITE_ROW==db_step(&q)) ){ | |
| 2473 | + cson_value * row = cson_sqlite3_row_to_object(q.pStmt); | |
| 2474 | + if(!row){ | |
| 2475 | + json_warn( FSL_JSON_W_ROW_TO_JSON_FAILED, | |
| 2476 | + "Could not convert at least one user result row to JSON." ); | |
| 2477 | + continue; | |
| 2478 | + } | |
| 2479 | + cson_array_append(pay, row); | |
| 2480 | + } | |
| 2481 | + db_finalize(&q); | |
| 2482 | + return payV; | |
| 2483 | +} | |
| 2484 | + | |
| 2427 | 2485 | |
| 2428 | 2486 | /* |
| 2429 | 2487 | ** Mapping of names to JSON pages/commands. Each name is a subpath of |
| 2430 | 2488 | ** /json (in CGI mode) or a subcommand of the json command in CLI mode |
| 2431 | 2489 | */ |
| @@ -2440,11 +2498,11 @@ | ||
| 2440 | 2498 | {"logout",json_page_logout,1}, |
| 2441 | 2499 | {"stat",json_page_stat,0}, |
| 2442 | 2500 | {"tag", json_page_nyi,0}, |
| 2443 | 2501 | {"ticket", json_page_nyi,0}, |
| 2444 | 2502 | {"timeline", json_page_timeline,0}, |
| 2445 | -{"user", json_page_nyi,0}, | |
| 2503 | +{"user",json_page_user,0}, | |
| 2446 | 2504 | {"version",json_page_version,0}, |
| 2447 | 2505 | {"whoami",json_page_whoami,1/*FIXME: work in CLI mode*/}, |
| 2448 | 2506 | {"wiki",json_page_wiki,0}, |
| 2449 | 2507 | /* Last entry MUST have a NULL name. */ |
| 2450 | 2508 | {NULL,NULL,0} |
| 2451 | 2509 |
| --- src/json.c | |
| +++ src/json.c | |
| @@ -1570,25 +1570,45 @@ | |
| 1570 | {"wik", json_timeline_wiki, 0}, |
| 1571 | {"wiki", json_timeline_wiki, 0}, |
| 1572 | /* Last entry MUST have a NULL name. */ |
| 1573 | {NULL,NULL,0} |
| 1574 | }; |
| 1575 | |
| 1576 | /* |
| 1577 | ** A page/command dispatch helper for fossil_json_f() implementations. |
| 1578 | ** depth should be the depth parameter passed to the fossil_json_f(). |
| 1579 | ** pages must be an array of JsonPageDef commands which we can |
| 1580 | ** dispatch. The final item in the array MUST have a NULL name |
| 1581 | ** element. |
| 1582 | ** |
| 1583 | ** This function takes json_comand_arg(1+g.json.dispatchDepth) and |
| 1584 | ** searches pages for a matching name. If found then that page's |
| 1585 | ** func() is called to fetch the payload, which is returned to the |
| 1586 | ** caller. |
| 1587 | ** |
| 1588 | ** On error, g.json.resultCode is set to one of the FossilJsonCodes |
| 1589 | ** values. |
| 1590 | */ |
| 1591 | static cson_value * json_page_dispatch_helper(JsonPageDef const * pages){ |
| 1592 | JsonPageDef const * def; |
| 1593 | char const * cmd = json_command_arg(1+g.json.dispatchDepth); |
| 1594 | assert( NULL != pages ); |
| @@ -1606,12 +1626,19 @@ | |
| 1606 | return (*def->func)(); |
| 1607 | } |
| 1608 | } |
| 1609 | |
| 1610 | /* |
| 1611 | ** Implements the /json/wiki family of pages/commands. Far from |
| 1612 | ** complete. |
| 1613 | ** |
| 1614 | */ |
| 1615 | static cson_value * json_page_wiki(){ |
| 1616 | return json_page_dispatch_helper(&JsonPageDefs_Wiki[0]); |
| 1617 | } |
| @@ -2422,10 +2449,41 @@ | |
| 2422 | g.json.resultCode = FSL_JSON_E_RESOURCE_NOT_FOUND; |
| 2423 | } |
| 2424 | db_finalize(&q); |
| 2425 | return payload; |
| 2426 | } |
| 2427 | |
| 2428 | /* |
| 2429 | ** Mapping of names to JSON pages/commands. Each name is a subpath of |
| 2430 | ** /json (in CGI mode) or a subcommand of the json command in CLI mode |
| 2431 | */ |
| @@ -2440,11 +2498,11 @@ | |
| 2440 | {"logout",json_page_logout,1}, |
| 2441 | {"stat",json_page_stat,0}, |
| 2442 | {"tag", json_page_nyi,0}, |
| 2443 | {"ticket", json_page_nyi,0}, |
| 2444 | {"timeline", json_page_timeline,0}, |
| 2445 | {"user", json_page_nyi,0}, |
| 2446 | {"version",json_page_version,0}, |
| 2447 | {"whoami",json_page_whoami,1/*FIXME: work in CLI mode*/}, |
| 2448 | {"wiki",json_page_wiki,0}, |
| 2449 | /* Last entry MUST have a NULL name. */ |
| 2450 | {NULL,NULL,0} |
| 2451 |
| --- src/json.c | |
| +++ src/json.c | |
| @@ -1570,25 +1570,45 @@ | |
| 1570 | {"wik", json_timeline_wiki, 0}, |
| 1571 | {"wiki", json_timeline_wiki, 0}, |
| 1572 | /* Last entry MUST have a NULL name. */ |
| 1573 | {NULL,NULL,0} |
| 1574 | }; |
| 1575 | |
| 1576 | static cson_value * json_user_list(); |
| 1577 | #if 0 |
| 1578 | static cson_value * json_user_detail(); |
| 1579 | static cson_value * json_user_create(); |
| 1580 | static cson_value * json_user_edit(); |
| 1581 | #endif |
| 1582 | |
| 1583 | /* |
| 1584 | ** Mapping of /json/user/XXX commands/paths to callbacks. |
| 1585 | */ |
| 1586 | static const JsonPageDef JsonPageDefs_User[] = { |
| 1587 | {"list", json_user_list, 0}, |
| 1588 | {"detail", json_page_nyi, 0}, |
| 1589 | {"create", json_page_nyi, 1}, |
| 1590 | {"edit", json_page_nyi, 1}, |
| 1591 | /* Last entry MUST have a NULL name. */ |
| 1592 | {NULL,NULL,0} |
| 1593 | }; |
| 1594 | |
| 1595 | |
| 1596 | /* |
| 1597 | ** A page/command dispatch helper for fossil_json_f() implementations. |
| 1598 | ** pages must be an array of JsonPageDef commands which we can |
| 1599 | ** dispatch. The final item in the array MUST have a NULL name |
| 1600 | ** element. |
| 1601 | ** |
| 1602 | ** This function takes the command specified in |
| 1603 | ** json_comand_arg(1+g.json.dispatchDepth) and searches pages for a |
| 1604 | ** matching name. If found then that page's func() is called to fetch |
| 1605 | ** the payload, which is returned to the caller. |
| 1606 | ** |
| 1607 | ** On error, g.json.resultCode is set to one of the FossilJsonCodes |
| 1608 | ** values and NULL is returned. If non-NULL is returned, ownership is |
| 1609 | ** transfered to the caller. |
| 1610 | */ |
| 1611 | static cson_value * json_page_dispatch_helper(JsonPageDef const * pages){ |
| 1612 | JsonPageDef const * def; |
| 1613 | char const * cmd = json_command_arg(1+g.json.dispatchDepth); |
| 1614 | assert( NULL != pages ); |
| @@ -1606,12 +1626,19 @@ | |
| 1626 | return (*def->func)(); |
| 1627 | } |
| 1628 | } |
| 1629 | |
| 1630 | /* |
| 1631 | ** Implements the /json/user family of pages/commands. |
| 1632 | ** |
| 1633 | */ |
| 1634 | static cson_value * json_page_user(){ |
| 1635 | return json_page_dispatch_helper(&JsonPageDefs_User[0]); |
| 1636 | } |
| 1637 | |
| 1638 | /* |
| 1639 | ** Implements the /json/wiki family of pages/commands. |
| 1640 | ** |
| 1641 | */ |
| 1642 | static cson_value * json_page_wiki(){ |
| 1643 | return json_page_dispatch_helper(&JsonPageDefs_Wiki[0]); |
| 1644 | } |
| @@ -2422,10 +2449,41 @@ | |
| 2449 | g.json.resultCode = FSL_JSON_E_RESOURCE_NOT_FOUND; |
| 2450 | } |
| 2451 | db_finalize(&q); |
| 2452 | return payload; |
| 2453 | } |
| 2454 | |
| 2455 | static cson_value * json_user_list(){ |
| 2456 | cson_value * payV = NULL; |
| 2457 | cson_array * pay = NULL; |
| 2458 | Stmt q; |
| 2459 | if(! g.perm.Admin ){ |
| 2460 | g.json.resultCode = FSL_JSON_E_DENIED; |
| 2461 | return NULL; |
| 2462 | } |
| 2463 | payV = cson_value_new_array(); |
| 2464 | pay = cson_value_get_array(payV); |
| 2465 | db_prepare(&q,"SELECT uid AS uid," |
| 2466 | " login AS name," |
| 2467 | " cap AS capabilities," |
| 2468 | " info AS info," |
| 2469 | " mtime AS mtime" |
| 2470 | " FROM user ORDER BY login"); |
| 2471 | |
| 2472 | while( (SQLITE_ROW==db_step(&q)) ){ |
| 2473 | cson_value * row = cson_sqlite3_row_to_object(q.pStmt); |
| 2474 | if(!row){ |
| 2475 | json_warn( FSL_JSON_W_ROW_TO_JSON_FAILED, |
| 2476 | "Could not convert at least one user result row to JSON." ); |
| 2477 | continue; |
| 2478 | } |
| 2479 | cson_array_append(pay, row); |
| 2480 | } |
| 2481 | db_finalize(&q); |
| 2482 | return payV; |
| 2483 | } |
| 2484 | |
| 2485 | |
| 2486 | /* |
| 2487 | ** Mapping of names to JSON pages/commands. Each name is a subpath of |
| 2488 | ** /json (in CGI mode) or a subcommand of the json command in CLI mode |
| 2489 | */ |
| @@ -2440,11 +2498,11 @@ | |
| 2498 | {"logout",json_page_logout,1}, |
| 2499 | {"stat",json_page_stat,0}, |
| 2500 | {"tag", json_page_nyi,0}, |
| 2501 | {"ticket", json_page_nyi,0}, |
| 2502 | {"timeline", json_page_timeline,0}, |
| 2503 | {"user",json_page_user,0}, |
| 2504 | {"version",json_page_version,0}, |
| 2505 | {"whoami",json_page_whoami,1/*FIXME: work in CLI mode*/}, |
| 2506 | {"wiki",json_page_wiki,0}, |
| 2507 | /* Last entry MUST have a NULL name. */ |
| 2508 | {NULL,NULL,0} |
| 2509 |