Gad D Lord
Gad D Lord

Reputation: 6772

How to use TNetEncoding.URL.Encode for encoding spaces in query string parameters?

In Delphi XE7 it is advised to use TNetEncoding.URL.Encode

So far I have been using a custom routine:

class function THttp.UrlEncode(const S: string; const InQueryString: Boolean): string;
var
  I: Integer;
begin
  Result := EmptyStr;
  for i := 1 to Length(S) do
    case S[i] of
    // The NoConversion set contains characters as specificed in RFC 1738 and
    // should not be modified unless the standard changes.
    'A'..'Z', 'a'..'z', '*', '@', '.', '_', '-', '0'..'9', 
    '$', '!', '''', '(', ')':
       Result := Result + S[i];
    '—': Result := Result + '%E2%80%94';
    ' ' :
      if InQueryString then
        Result := Result + '+'
      else
        Result := Result + '%20';
   else
     Result := Result + '%' + System.SysUtils.IntToHex(Ord(S[i]), 2);
   end;
end;

Using the method above I have been able to manually specify whether the encoded parameter S is a part of the Path or a part of the Query string.

The spaces should be encoded as + if found in the Path and as %20 is part of the Query parameters.

The function above emits properly

Url := 'http://something/?q=' + THttp.UrlEncode('koko jambo', true);
// Url := http://something/?q=koko%20jambo

but the following is returning different value

Url := 'http://something/?q=' + TNetEncoding.URL.Encode('koko jambo;);
// Url := http://something/?q=koko+jambo

Please elaborate in what way TNetEncoding.URL.Encode should be properly used for encoding query parameters containing spaces as %20?

Upvotes: 0

Views: 8602

Answers (2)

Paul McGee
Paul McGee

Reputation: 114

As of currently (from what initial version I am not sure), System.NetEncoding.TURLEncoding.URL.Encode has a SpaceAsPlus option.

(Quoting) "Encode (unsafe) characters (^{}<>"'│~), and space will be encoded as %NN when SpaceAsPlus is not specified. If SpaceAsPlus is specified, spaces will be encoded as plus signs: +."

function Encode(const AInput: string; const ASet: TUnsafeChars; const AOptions: TEncodeOptions; AEncoding: TEncoding = nil): string; overload;

https://docwiki.embarcadero.com/Libraries/Athens/en/System.NetEncoding.TURLEncoding

Upvotes: 1

Remy Lebeau
Remy Lebeau

Reputation: 597941

Read the documentation:

System.NetEncoding.TURLEncoding

TURLEncoding only encodes spaces (as plus signs: +) and the following reserved URL encoding characters: ;:&=+,/?%#[].

It is not possible to make TNetEncoding.URL.Encode encode spaces as %20.

Normally, I would suggest Indy's TIdURI class, as it has separate PathEncode() and ParamsEncode() methods, but they both encode spaces as %20 as well, which does not satisfy your "encoded as + if found in the Path" requirement.

Upvotes: 2

Related Questions