Fossil SCM
added POST.payload to json_getenv() list. Re-organized /json/branch/list CLI/HTTP arg handling to behave sanely in CLI mode. Minor typo fix in main.c.
Commit
4a9b51649d6499d33a5fa26fef31d068025d399d
Parent
267739dd20e2ea4…
2 files changed
+66
-29
+1
-1
+66
-29
| --- src/json.c | ||
| +++ src/json.c | ||
| @@ -277,40 +277,50 @@ | ||
| 277 | 277 | return cson_value_new_string( json_rc_cstr(code), 11 ); |
| 278 | 278 | } |
| 279 | 279 | |
| 280 | 280 | |
| 281 | 281 | /* |
| 282 | -** Gets a POST/GET/COOKIE/ENV value. The returned memory is owned by the | |
| 283 | -** g.json object (one of its sub-objects). Returns NULL if no match is | |
| 284 | -** found. | |
| 282 | +** Gets a POST/POST.payload/GET/COOKIE/ENV value. The returned memory | |
| 283 | +** is owned by the g.json object (one of its sub-objects). Returns | |
| 284 | +** NULL if no match is found. | |
| 285 | 285 | ** |
| 286 | 286 | ** ENV means the system environment (getenv()). |
| 287 | 287 | ** |
| 288 | -** Precedence: GET, COOKIE, POST, ENV. COOKIE _should_ be after POST | |
| 289 | -** but currently is not for internal order-of-init reasons. Since | |
| 290 | -** fossil only uses one cookie, this is not a real/high-priority | |
| 291 | -** problem. | |
| 288 | +** Precedence: POST.payload, GET, COOKIE, POST, ENV. | |
| 289 | +** | |
| 290 | +** The precedence SHOULD be: GET, POST.payload, POST, COOKIE, ENV, but | |
| 291 | +** the amalgamation of the GET/POST vars makes it difficult for me to | |
| 292 | +** do that. Since fossil only uses one cookie, cookie precedence isn't | |
| 293 | +** a real/high-priority problem. | |
| 292 | 294 | */ |
| 293 | 295 | cson_value * json_getenv( char const * zKey ){ |
| 294 | 296 | cson_value * rc; |
| 297 | + rc = g.json.reqPayload.o | |
| 298 | + ? cson_object_get( g.json.reqPayload.o, zKey ) | |
| 299 | + : NULL; | |
| 300 | + if(rc){ | |
| 301 | + return rc; | |
| 302 | + } | |
| 295 | 303 | rc = cson_object_get( g.json.param.o, zKey ); |
| 296 | 304 | if( rc ){ |
| 297 | 305 | return rc; |
| 298 | - }else{ | |
| 299 | - rc = cson_object_get( g.json.post.o, zKey ); | |
| 300 | - if(rc){ | |
| 301 | - return rc; | |
| 302 | - }else{ | |
| 303 | - char const * cv = PD(zKey,NULL); | |
| 304 | - if(!cv){ | |
| 305 | - cv = getenv(zKey); | |
| 306 | - } | |
| 307 | - if(cv){/*transform it to JSON for later use.*/ | |
| 308 | - rc = cson_value_new_string(cv,strlen(cv)); | |
| 309 | - cson_object_set( g.json.param.o, zKey, rc ); | |
| 310 | - return rc; | |
| 311 | - } | |
| 306 | + } | |
| 307 | + rc = cson_object_get( g.json.post.o, zKey ); | |
| 308 | + if(rc){ | |
| 309 | + return rc; | |
| 310 | + }else{ | |
| 311 | + char const * cv = PD(zKey,NULL); | |
| 312 | + if(!cv){ | |
| 313 | + cv = getenv(zKey); | |
| 314 | + } | |
| 315 | + if(cv){/*transform it to JSON for later use.*/ | |
| 316 | + /* TODO: use sscanf() to figure out if it's an int, | |
| 317 | + and transform it to JSON int if it is. | |
| 318 | + */ | |
| 319 | + rc = cson_value_new_string(cv,strlen(cv)); | |
| 320 | + json_setenv( zKey, rc ); | |
| 321 | + return rc; | |
| 312 | 322 | } |
| 313 | 323 | } |
| 314 | 324 | return NULL; |
| 315 | 325 | } |
| 316 | 326 | |
| @@ -1563,26 +1573,50 @@ | ||
| 1563 | 1573 | ** Impl for /json/branch/list |
| 1564 | 1574 | ** |
| 1565 | 1575 | ** TODO: change how the "range" of branches is specified. |
| 1566 | 1576 | ** Take a string arg in the form ("open","all","closed") |
| 1567 | 1577 | ** and decide based off of that. |
| 1578 | +** | |
| 1579 | +** | |
| 1580 | +** CLI mode options: | |
| 1581 | +** | |
| 1582 | +** --range X | -r X, where X is one of (open,closed,all) | |
| 1583 | +** (only the first letter is significant, default=open). | |
| 1584 | +** -a (same as --range a) | |
| 1585 | +** -c (same as --range c) | |
| 1586 | +** | |
| 1587 | +** HTTP mode options: | |
| 1588 | +** | |
| 1589 | +** "range" GET/POST.payload parameter. FIXME: currently we also use | |
| 1590 | +** POST, but really want to restrict this to POST.payload. | |
| 1568 | 1591 | */ |
| 1569 | 1592 | static cson_value * json_branch_list(unsigned int depth){ |
| 1570 | 1593 | cson_value * payV = cson_value_new_object(); |
| 1571 | 1594 | cson_object * pay = cson_value_get_object(payV); |
| 1572 | 1595 | cson_value * listV = cson_value_new_array(); |
| 1573 | 1596 | cson_array * list = cson_value_get_array(listV); |
| 1574 | 1597 | char const * range = NULL; |
| 1575 | - int showAll = json_getenv_int("all",0); | |
| 1576 | - int showClosed = showAll ? 0 : json_getenv_int("closed",0); | |
| 1577 | 1598 | int which = 0; |
| 1578 | 1599 | Stmt q; |
| 1579 | - range = json_getenv_cstr("range"); | |
| 1600 | + if(!g.isHTTP){ | |
| 1601 | + range = find_option("range","r",1); | |
| 1602 | + if(!range||!*range){ | |
| 1603 | + range = find_option("all","a",0); | |
| 1604 | + if(range && *range){ | |
| 1605 | + range = "a"; | |
| 1606 | + }else{ | |
| 1607 | + range = find_option("closed","c",0); | |
| 1608 | + if(range&&*range){ | |
| 1609 | + range = "c"; | |
| 1610 | + } | |
| 1611 | + } | |
| 1612 | + } | |
| 1613 | + }else{ | |
| 1614 | + range = json_getenv_cstr("range"); | |
| 1615 | + } | |
| 1580 | 1616 | if(!range || !*range){ |
| 1581 | - range = showAll | |
| 1582 | - ? "all" | |
| 1583 | - : (showClosed?"closed":"open"); | |
| 1617 | + range = "o"; | |
| 1584 | 1618 | } |
| 1585 | 1619 | assert( (NULL != range) && *range ); |
| 1586 | 1620 | switch(*range){ |
| 1587 | 1621 | case 'c': |
| 1588 | 1622 | range = "closed"; |
| @@ -1603,11 +1637,14 @@ | ||
| 1603 | 1637 | while((SQLITE_ROW==db_step(&q))){ |
| 1604 | 1638 | cson_value * v = cson_sqlite3_column_to_value(q.pStmt,0); |
| 1605 | 1639 | if(v){ |
| 1606 | 1640 | cson_array_append(list,v); |
| 1607 | 1641 | }else{ |
| 1608 | - json_warn(FSL_JSON_W_COL_TO_JSON_FAILED,NULL); | |
| 1642 | + char * msg = mprintf("Column-to-json failed @ %s:%d", | |
| 1643 | + __FILE__,__LINE__); | |
| 1644 | + json_warn(FSL_JSON_W_COL_TO_JSON_FAILED,msg); | |
| 1645 | + free(msg); | |
| 1609 | 1646 | } |
| 1610 | 1647 | } |
| 1611 | 1648 | return payV; |
| 1612 | 1649 | } |
| 1613 | 1650 | |
| @@ -1687,11 +1724,11 @@ | ||
| 1687 | 1724 | ** /json/timeline/ci |
| 1688 | 1725 | ** |
| 1689 | 1726 | ** Far from complete. |
| 1690 | 1727 | */ |
| 1691 | 1728 | static cson_value * json_timeline_ci(unsigned int depth){ |
| 1692 | - static const int defaultLimit = 10; | |
| 1729 | + static const int defaultLimit = 20; | |
| 1693 | 1730 | cson_value * payV = NULL; |
| 1694 | 1731 | cson_object * pay = NULL; |
| 1695 | 1732 | cson_value * tmp = NULL; |
| 1696 | 1733 | cson_value * listV = NULL; |
| 1697 | 1734 | cson_array * list = NULL; |
| 1698 | 1735 |
| --- src/json.c | |
| +++ src/json.c | |
| @@ -277,40 +277,50 @@ | |
| 277 | return cson_value_new_string( json_rc_cstr(code), 11 ); |
| 278 | } |
| 279 | |
| 280 | |
| 281 | /* |
| 282 | ** Gets a POST/GET/COOKIE/ENV value. The returned memory is owned by the |
| 283 | ** g.json object (one of its sub-objects). Returns NULL if no match is |
| 284 | ** found. |
| 285 | ** |
| 286 | ** ENV means the system environment (getenv()). |
| 287 | ** |
| 288 | ** Precedence: GET, COOKIE, POST, ENV. COOKIE _should_ be after POST |
| 289 | ** but currently is not for internal order-of-init reasons. Since |
| 290 | ** fossil only uses one cookie, this is not a real/high-priority |
| 291 | ** problem. |
| 292 | */ |
| 293 | cson_value * json_getenv( char const * zKey ){ |
| 294 | cson_value * rc; |
| 295 | rc = cson_object_get( g.json.param.o, zKey ); |
| 296 | if( rc ){ |
| 297 | return rc; |
| 298 | }else{ |
| 299 | rc = cson_object_get( g.json.post.o, zKey ); |
| 300 | if(rc){ |
| 301 | return rc; |
| 302 | }else{ |
| 303 | char const * cv = PD(zKey,NULL); |
| 304 | if(!cv){ |
| 305 | cv = getenv(zKey); |
| 306 | } |
| 307 | if(cv){/*transform it to JSON for later use.*/ |
| 308 | rc = cson_value_new_string(cv,strlen(cv)); |
| 309 | cson_object_set( g.json.param.o, zKey, rc ); |
| 310 | return rc; |
| 311 | } |
| 312 | } |
| 313 | } |
| 314 | return NULL; |
| 315 | } |
| 316 | |
| @@ -1563,26 +1573,50 @@ | |
| 1563 | ** Impl for /json/branch/list |
| 1564 | ** |
| 1565 | ** TODO: change how the "range" of branches is specified. |
| 1566 | ** Take a string arg in the form ("open","all","closed") |
| 1567 | ** and decide based off of that. |
| 1568 | */ |
| 1569 | static cson_value * json_branch_list(unsigned int depth){ |
| 1570 | cson_value * payV = cson_value_new_object(); |
| 1571 | cson_object * pay = cson_value_get_object(payV); |
| 1572 | cson_value * listV = cson_value_new_array(); |
| 1573 | cson_array * list = cson_value_get_array(listV); |
| 1574 | char const * range = NULL; |
| 1575 | int showAll = json_getenv_int("all",0); |
| 1576 | int showClosed = showAll ? 0 : json_getenv_int("closed",0); |
| 1577 | int which = 0; |
| 1578 | Stmt q; |
| 1579 | range = json_getenv_cstr("range"); |
| 1580 | if(!range || !*range){ |
| 1581 | range = showAll |
| 1582 | ? "all" |
| 1583 | : (showClosed?"closed":"open"); |
| 1584 | } |
| 1585 | assert( (NULL != range) && *range ); |
| 1586 | switch(*range){ |
| 1587 | case 'c': |
| 1588 | range = "closed"; |
| @@ -1603,11 +1637,14 @@ | |
| 1603 | while((SQLITE_ROW==db_step(&q))){ |
| 1604 | cson_value * v = cson_sqlite3_column_to_value(q.pStmt,0); |
| 1605 | if(v){ |
| 1606 | cson_array_append(list,v); |
| 1607 | }else{ |
| 1608 | json_warn(FSL_JSON_W_COL_TO_JSON_FAILED,NULL); |
| 1609 | } |
| 1610 | } |
| 1611 | return payV; |
| 1612 | } |
| 1613 | |
| @@ -1687,11 +1724,11 @@ | |
| 1687 | ** /json/timeline/ci |
| 1688 | ** |
| 1689 | ** Far from complete. |
| 1690 | */ |
| 1691 | static cson_value * json_timeline_ci(unsigned int depth){ |
| 1692 | static const int defaultLimit = 10; |
| 1693 | cson_value * payV = NULL; |
| 1694 | cson_object * pay = NULL; |
| 1695 | cson_value * tmp = NULL; |
| 1696 | cson_value * listV = NULL; |
| 1697 | cson_array * list = NULL; |
| 1698 |
| --- src/json.c | |
| +++ src/json.c | |
| @@ -277,40 +277,50 @@ | |
| 277 | return cson_value_new_string( json_rc_cstr(code), 11 ); |
| 278 | } |
| 279 | |
| 280 | |
| 281 | /* |
| 282 | ** Gets a POST/POST.payload/GET/COOKIE/ENV value. The returned memory |
| 283 | ** is owned by the g.json object (one of its sub-objects). Returns |
| 284 | ** NULL if no match is found. |
| 285 | ** |
| 286 | ** ENV means the system environment (getenv()). |
| 287 | ** |
| 288 | ** Precedence: POST.payload, GET, COOKIE, POST, ENV. |
| 289 | ** |
| 290 | ** The precedence SHOULD be: GET, POST.payload, POST, COOKIE, ENV, but |
| 291 | ** the amalgamation of the GET/POST vars makes it difficult for me to |
| 292 | ** do that. Since fossil only uses one cookie, cookie precedence isn't |
| 293 | ** a real/high-priority problem. |
| 294 | */ |
| 295 | cson_value * json_getenv( char const * zKey ){ |
| 296 | cson_value * rc; |
| 297 | rc = g.json.reqPayload.o |
| 298 | ? cson_object_get( g.json.reqPayload.o, zKey ) |
| 299 | : NULL; |
| 300 | if(rc){ |
| 301 | return rc; |
| 302 | } |
| 303 | rc = cson_object_get( g.json.param.o, zKey ); |
| 304 | if( rc ){ |
| 305 | return rc; |
| 306 | } |
| 307 | rc = cson_object_get( g.json.post.o, zKey ); |
| 308 | if(rc){ |
| 309 | return rc; |
| 310 | }else{ |
| 311 | char const * cv = PD(zKey,NULL); |
| 312 | if(!cv){ |
| 313 | cv = getenv(zKey); |
| 314 | } |
| 315 | if(cv){/*transform it to JSON for later use.*/ |
| 316 | /* TODO: use sscanf() to figure out if it's an int, |
| 317 | and transform it to JSON int if it is. |
| 318 | */ |
| 319 | rc = cson_value_new_string(cv,strlen(cv)); |
| 320 | json_setenv( zKey, rc ); |
| 321 | return rc; |
| 322 | } |
| 323 | } |
| 324 | return NULL; |
| 325 | } |
| 326 | |
| @@ -1563,26 +1573,50 @@ | |
| 1573 | ** Impl for /json/branch/list |
| 1574 | ** |
| 1575 | ** TODO: change how the "range" of branches is specified. |
| 1576 | ** Take a string arg in the form ("open","all","closed") |
| 1577 | ** and decide based off of that. |
| 1578 | ** |
| 1579 | ** |
| 1580 | ** CLI mode options: |
| 1581 | ** |
| 1582 | ** --range X | -r X, where X is one of (open,closed,all) |
| 1583 | ** (only the first letter is significant, default=open). |
| 1584 | ** -a (same as --range a) |
| 1585 | ** -c (same as --range c) |
| 1586 | ** |
| 1587 | ** HTTP mode options: |
| 1588 | ** |
| 1589 | ** "range" GET/POST.payload parameter. FIXME: currently we also use |
| 1590 | ** POST, but really want to restrict this to POST.payload. |
| 1591 | */ |
| 1592 | static cson_value * json_branch_list(unsigned int depth){ |
| 1593 | cson_value * payV = cson_value_new_object(); |
| 1594 | cson_object * pay = cson_value_get_object(payV); |
| 1595 | cson_value * listV = cson_value_new_array(); |
| 1596 | cson_array * list = cson_value_get_array(listV); |
| 1597 | char const * range = NULL; |
| 1598 | int which = 0; |
| 1599 | Stmt q; |
| 1600 | if(!g.isHTTP){ |
| 1601 | range = find_option("range","r",1); |
| 1602 | if(!range||!*range){ |
| 1603 | range = find_option("all","a",0); |
| 1604 | if(range && *range){ |
| 1605 | range = "a"; |
| 1606 | }else{ |
| 1607 | range = find_option("closed","c",0); |
| 1608 | if(range&&*range){ |
| 1609 | range = "c"; |
| 1610 | } |
| 1611 | } |
| 1612 | } |
| 1613 | }else{ |
| 1614 | range = json_getenv_cstr("range"); |
| 1615 | } |
| 1616 | if(!range || !*range){ |
| 1617 | range = "o"; |
| 1618 | } |
| 1619 | assert( (NULL != range) && *range ); |
| 1620 | switch(*range){ |
| 1621 | case 'c': |
| 1622 | range = "closed"; |
| @@ -1603,11 +1637,14 @@ | |
| 1637 | while((SQLITE_ROW==db_step(&q))){ |
| 1638 | cson_value * v = cson_sqlite3_column_to_value(q.pStmt,0); |
| 1639 | if(v){ |
| 1640 | cson_array_append(list,v); |
| 1641 | }else{ |
| 1642 | char * msg = mprintf("Column-to-json failed @ %s:%d", |
| 1643 | __FILE__,__LINE__); |
| 1644 | json_warn(FSL_JSON_W_COL_TO_JSON_FAILED,msg); |
| 1645 | free(msg); |
| 1646 | } |
| 1647 | } |
| 1648 | return payV; |
| 1649 | } |
| 1650 | |
| @@ -1687,11 +1724,11 @@ | |
| 1724 | ** /json/timeline/ci |
| 1725 | ** |
| 1726 | ** Far from complete. |
| 1727 | */ |
| 1728 | static cson_value * json_timeline_ci(unsigned int depth){ |
| 1729 | static const int defaultLimit = 20; |
| 1730 | cson_value * payV = NULL; |
| 1731 | cson_object * pay = NULL; |
| 1732 | cson_value * tmp = NULL; |
| 1733 | cson_value * listV = NULL; |
| 1734 | cson_array * list = NULL; |
| 1735 |
+1
-1
| --- src/main.c | ||
| +++ src/main.c | ||
| @@ -200,11 +200,11 @@ | ||
| 200 | 200 | } cmd; |
| 201 | 201 | struct { /* JSON POST data. */ |
| 202 | 202 | cson_value * v; |
| 203 | 203 | cson_object * o; |
| 204 | 204 | } post; |
| 205 | - struct { /* GET/COOKIE params in JSON form. */ | |
| 205 | + struct { /* GET/COOKIE params in JSON mode. */ | |
| 206 | 206 | cson_value * v; |
| 207 | 207 | cson_object * o; |
| 208 | 208 | } param; |
| 209 | 209 | struct { |
| 210 | 210 | cson_value * v; |
| 211 | 211 |
| --- src/main.c | |
| +++ src/main.c | |
| @@ -200,11 +200,11 @@ | |
| 200 | } cmd; |
| 201 | struct { /* JSON POST data. */ |
| 202 | cson_value * v; |
| 203 | cson_object * o; |
| 204 | } post; |
| 205 | struct { /* GET/COOKIE params in JSON form. */ |
| 206 | cson_value * v; |
| 207 | cson_object * o; |
| 208 | } param; |
| 209 | struct { |
| 210 | cson_value * v; |
| 211 |
| --- src/main.c | |
| +++ src/main.c | |
| @@ -200,11 +200,11 @@ | |
| 200 | } cmd; |
| 201 | struct { /* JSON POST data. */ |
| 202 | cson_value * v; |
| 203 | cson_object * o; |
| 204 | } post; |
| 205 | struct { /* GET/COOKIE params in JSON mode. */ |
| 206 | cson_value * v; |
| 207 | cson_object * o; |
| 208 | } param; |
| 209 | struct { |
| 210 | cson_value * v; |
| 211 |