在PHP中解码查询字符串

cod*_*key 4 php api rest formencode query-string

好的,所以我使用mod_rewrite和PHP编写了一个REST API实现.我通过HTTP DELETE请求(...集体呻吟?)接受一个查询字符串.关于前两个语句的智慧的争论不谈,我发现PHP不会自动解析DELETE请求的请求体(即,尽管形式编码的查询字符串出现在请求体中,$ _POST仍为空).这并不特别让我感到惊讶.我发现令人惊讶的是,我一直无法找到用于解析查询字符串的内置PHP函数?我只是忽略了什么?我可以这样做:

public function parseQS($queryString, &$postArray){
  $queryArray = explode('&', $queryString);
  for($i = 0; $i < count($queryArray); $i++) {
    $thisElement = split('=', $queryArray[$i]);
    $postArray[$thisElement[0]] = htmlspecialchars(urldecode($thisElement[1]));
  }
}
Run Code Online (Sandbox Code Playgroud)

...奇怪的是,没有PHP内置来处理这个问题.另外,我怀疑我不应该使用htmlspecialcharacters和urldecode来擦除表单编码的值...这是一种不同的编码,但是我也无法识别我应该使用哪种PHP函数来解码表单编码数据.

任何建议将不胜感激.

Ion*_*tan 8

parse_str.不好的名字,但做你想要的.并注意它没有返回任何内容,第二个参数通过引用传递.


Ali*_*man 5

有一个函数可以做到 - http://php.net/parse_str.由于PHP必须为自己做这件事,所以没有理由不打开它以便在API中使用.

将字符串解析为变量void parse_str(string $ str [,array&$ arr])

解析str,好像它是通过URL传递的查询字符串,并在当前范围中设置变量.

<?php
$str = "first=value&arr[]=foo+bar&arr[]=baz";

parse_str($str, $output);
echo $output['first'];  // value
echo $output['arr'][0]; // foo bar
echo $output['arr'][1]; // baz
Run Code Online (Sandbox Code Playgroud)


Ken*_*ins 5

parse_str对于简单的东西来说很好,但它与 PHP 创建魔术变量的构建方式不同$_GET。为什么?!?我不知道。我已经开发了自己的版本,我相信它与 PHP 的解析完全匹配(如果您能找到任何其他情况的示例,请告诉我)。

function betterParseStr( $string )
{
    return array_reduce( explode( "&", $string ), function( $array, $string_piece ) {
        if( $string_piece === "" ) return $array;
        $equal_offset = strpos( $string_piece, "=" );
        if( $equal_offset === FALSE ) {
            $key = urldecode( $string_piece );
            $value = "";
        } else {
            $key = urldecode( substr( $string_piece, 0, $equal_offset ) );
            $value = urldecode( substr( $string_piece, $equal_offset + 1 ) );
        }
        if( preg_match( "/^([^\[]*)\[([^\]]*)](.*)$/", $key, $matches ) ) {
            $key_path = array( $matches[1], $matches[2] );
            $rest = $matches[3];
            while( preg_match( "/^\[([^\]]*)](.*)$/", $rest, $matches ) ) {
                $key_path[] = $matches[1];
                $rest = $matches[2];
            }
        } else {
            //replace first [ for _
            //why?!? idk ask PHP it does
            //Example: ?key[[=value -> array( "key_[" => "value" )
            $key_path = array( preg_replace('/\[/', '_', $key, 1 ) );
        }
        if( strlen( $key_path[0] ) > 0 && substr( $key_path[0], 0, 1 ) !== "[" ) {
            $current_node = &$array;
            $last_key = array_pop( $key_path );
            $resolve_key = function( $key, array $array ) {
                if( $key === "" || $key === " " ) {
                    $int_array = array_filter( array_keys( $array ), function( $key ) { return is_int( $key ); } );
                    $key = $int_array ? max( $int_array ) + 1 : 0;
                }
                return $key;
            };
            foreach( $key_path as $key_path_piece ) {
                $key_path_piece = $resolve_key( $key_path_piece, $current_node );
                if( ! array_key_exists( $key_path_piece, $current_node ) || ! is_array( $current_node[$key_path_piece] ) ) {
                    $current_node[$key_path_piece] = array();
                }
                $current_node = &$current_node[$key_path_piece];
            }
            $current_node[$resolve_key( $last_key, $current_node )] = $value;
        }
        return $array;
    }, array() );
}
Run Code Online (Sandbox Code Playgroud)