diff --git a/README.md b/README.md index cd5306c..d06583c 100644 --- a/README.md +++ b/README.md @@ -15,7 +15,6 @@ We have some guides and general documentation in the [docs](docs/) directory. Am - [HTTP Router](docs/router.md) - [Template engine](docs/template.md) - [Script integrations](docs/util.md) -- [HTTP request API](docs/http.md) - [List of security fixes](docs/sec-fixes/) ## Dependencies diff --git a/docs/http.md b/docs/http.md deleted file mode 100644 index 0dcd150..0000000 --- a/docs/http.md +++ /dev/null @@ -1,43 +0,0 @@ -# HTTP - the proto, the API - -very work in progress file. - ---- - -## GET/POST parameters - -- `${get_data["param"]}` -- `${post_data["param"]}` - -Case-insensitive. If K/V pairs aren't used (but a string is provided, just without `=`) then -it can be accessed through `${get_data}` / `${post_data}` (array element 0). - -### Arrays - -HTTP does arrays through concatenating multiple parameters with the same name. In our case, values -are passed to a secondary array, and a reference to it is left for application use. - -``` -GET asdf/?a=1&a=2&a=3&b=1 -``` - -will result in: - -``` -declare -A get_data=([b]="1" [a]="[array]" ) -``` - -To get the value set out of an array, call `http_array `. For instance: - -``` -#!/bin/bash -if ! http_array a array; then - echo "Not an array" - return -fi - -for (( i=0; i<${#array[@]}; i++ )) { - echo "a[$i]=${array[i]}" -} -``` - diff --git a/docs/util.md b/docs/util.md index 94b5052..b11dc2c 100644 --- a/docs/util.md +++ b/docs/util.md @@ -4,8 +4,6 @@ HTTP.sh provides a number of useful APIs designed to make interfacing with HTTP Some of those (especially notORM) are also useful in a CLI environment, to help with migrations and other administrative tasks. -## Invocation - Utils integrate into HTTP.sh through calling the main script, with the utility name as the first parameter. So, for `meow.sh` the invocation would be `./http.sh meow`, or `./http.sh meow [params]` if the util takes any parameters. @@ -21,27 +19,6 @@ Of note: A list of utilities can be obtained by calling `./http.sh utils`. -## Creating your own - -Simply create a shell script in your namespace's util directory (that's usually `app/util/`), and -mark it as executable. It has to have `.sh` as an extension, but shebang currently doesn't matter. - -It's recommended that if your util takes any positional parameters, it should check for $1 being -set, and display a help message. An example of such script is listed below. - -``` -if [[ ! "$1" || "$1" == "help" ]]; then - echo "usage: $0 $HTTPSH_SCRIPTNAME - -Action can be one of: - meow - Mrrrrrrrp! - help - This message." - exit 1 -fi - -# script continues here... -``` - ## Built-in utils The following scripts are generic helpers shipped with HTTP.sh. We hope they'll come in handy. diff --git a/http.sh b/http.sh index 2e81d4c..02a220a 100755 --- a/http.sh +++ b/http.sh @@ -37,7 +37,7 @@ if [[ "$1" == "init" ]]; then # will get replaced with proper parameter parsing fi source config/master.sh - mkdir -p "${cfg[namespace]}/${cfg[root]}" "${cfg[namespace]}/workers/example" "${cfg[namespace]}/views" "${cfg[namespace]}/templates" "${cfg[namespace]}/util/" + mkdir -p "${cfg[namespace]}/${cfg[root]}" "${cfg[namespace]}/workers/example" "${cfg[namespace]}/views" "${cfg[namespace]}/templates" touch "${cfg[namespace]}/config.sh" "${cfg[namespace]}/workers/example/control" cp ".resources/config.sh" "${cfg[namespace]}/config.sh" cp ".resources/routes.sh" "${cfg[namespace]}/routes.sh" diff --git a/src/misc.sh b/src/misc.sh index 6d6b7ac..30caf1b 100755 --- a/src/misc.sh +++ b/src/misc.sh @@ -71,58 +71,3 @@ function url_decode() { function worker_add() { : } - -# internal function -# common GET/POST application/x-www-form-urlencoded parser -# -# _param_parse(input, destination_ref) -_param_parse() { - [[ ! "$1" || ! "$2" ]] && return 1 - local -n ref="$2" - - local i name value - - while read -d'&' i; do - name="${i%%=*}" - if [[ "$name" ]]; then - value="${i#*=}" - if [[ "${ref["$name"]}" ]]; then # array mode - if [[ ! "${http_array_refs["$name"]}" ]]; then - http_array_refs["$name"]=_param_$RANDOM - local -n arr="${http_array_refs["$name"]}" - - arr=("${ref["$name"]}") - ref["$name"]="[array]" - else - local -n arr="${http_array_refs["$name"]}" - fi - - arr+=("$(url_decode "$value")") - else - ref["$name"]="$(url_decode "$value")" - fi - fi - done <<< "$1" -} - - -# Safely receive a reference to a HTTP urlencoded array -# -# http_array(name, out_ref) -http_array() { - [[ ! "$1" || ! "$2" ]] && return 1 - if [[ ! "${http_array_refs[$1]}" ]]; then - declare -ga $2 - local -n ref=$2 - - if [[ "${post_data[$1]}" ]]; then - ref=("${post_data[$1]}") - elif [[ "${get_data[$1]}" ]]; then - ref=("${get_data[$1]}") - else - return 1 - fi - else - declare -gn $2=${http_array_refs[$1]} - fi -} diff --git a/src/server.sh b/src/server.sh index ebe16c9..4810a05 100755 --- a/src/server.sh +++ b/src/server.sh @@ -23,7 +23,6 @@ declare -A cookies # cookies! declare -A get_data # all GET params declare -A post_data # all POST params declare -A params # parsed router data -declare -A http_array_refs # references to GET/POST arrays r[status]=210 # Mommy always said that I was special r[req_headers]='' @@ -45,7 +44,16 @@ if [[ "${param,,}" =~ ^(get|post|patch|put|delete|meow) ]]; then # TODO: OPTIONS r[url]="$(sed -E 's/^ *//;s/HTTP\/[0-9]+\.[0-9]+//;s/ //g;s/\/*\r//g;s/\/\/*/\//g' <<< "$param")" unset IFS - _param_parse "${r[url]#*\?}&" get_data + if [[ "${r[url]}" == *'?'* ]]; then + while read -d'&' i; do + name="${i%%=*}" + if [[ "$name" ]]; then + value="${i#*=}" + get_data[$name]="$(url_decode "$value")" + fi + done <<< "${r[url]#*\?}&" + fi + else exit 1 # TODO: throw 400 here fi @@ -104,17 +112,11 @@ if [[ -n "${headers["host"]}" ]]; then r[host]="${headers["host"]}" r[host_portless]="${headers["host"]%%:*}" - cfg_temp="config/$(basename -- ${r[host]})" - - if [[ -f "$cfg_temp" ]]; then - source "$cfg_temp" - elif [[ "${r[host]}" != "${r[host_portless]}" ]]; then - cfg_temp_portless="config/$(basename -- ${r[host_portless]})" - [[ -f "$cfg_temp_portless" ]] && source "$cfg_temp_portless" - unset cfg_temp_portless + if [[ -f "config/$(basename -- ${r[host]})" ]]; then + source "config/$(basename -- ${r[host]})" + elif [[ -f "config/$(basename -- ${r[host_portless]})" ]]; then + source "config/$(basename -- ${r[host_portless]})" fi - - unset cfg_temp fi if [[ "${headers["connection"]}" == *"upgrade"* && "${headers["upgrade"]}" == "websocket" ]]; then @@ -264,7 +266,12 @@ if [[ "${r[post]}" == true ]] && [[ "${r[status]}" == 200 || "${r[status]}" == if [[ "${r[payload_type]}" == "urlencoded" ]]; then unset IFS - _param_parse "${data}&" post_data + while read -r -d'&' i; do + name="${i%%=*}" + value="${i#*=}" + post_data[$name]="$(url_decode "$value")" + echo post_data[$name]="$value" >/dev/stderr + done <<< "${data}&" else # this is fine? post_data[0]="${data%\&}" diff --git a/tests/01-http-basic.sh b/tests/01-http-basic.sh index 3b327ef..e89b6c5 100644 --- a/tests/01-http-basic.sh +++ b/tests/01-http-basic.sh @@ -30,26 +30,19 @@ EOF match="nyaa" } -server_get_array() { +server_get_random() { prepare() { cat <<"EOF" > app/webroot/meow.shs #!/bin/bash -http_array meow ref -echo "${ref[1]}" +echo "${get_data[meow]}" EOF } tst() { - curl -s "localhost:1337/meow.shs?meow=nyaa&meow=second+element&meow=meow" + curl -s "localhost:1337/meow.shs?meow=nyaa" } - match="second element" -} - -server_post_array() { - tst() { - curl -s "localhost:1337/meow.shs" -d 'meow=nyaa&meow=second+element&meow=meow' - } + match="nyaa" } server_post_param() { @@ -209,9 +202,6 @@ subtest_list=( server_get_param server_post_param - server_get_array - server_post_array - # currently functionally equivalent server_patch_dummy server_put_dummy