Javascript 角度网址加号转换为空格

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/45428842/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-23 03:03:43  来源:igfitidea点击:

Angular url plus sign converting to space

javascriptangularurl

提问by Manwal

I have angular application where i want to pass plus sign +in query string like:

我有 angular 应用程序,我想在查询字符串中传递加号+,例如:

http://localhost:3000/page?name=xyz+manwal

When I am hitting this URL its converting to:

当我点击这个 URL 时,它会转换为:

http://localhost:3000/page?name=xyz%20manwal

Where %20refer to space . How can I prevent this conversion?

其中%20指的是空间。如何防止这种转换?

采纳答案by Manwal

I have found solution and posting it for future reference. Angular js was converting +sign into %2B.

我找到了解决方案并将其发布以供将来参考。Angular js 正在将+符号转换为%2B.

Following code prevented that:

以下代码阻止了:

.config([
    '$provide', function($provide) {
      $provide.decorator('$browser', function($delegate) {
        let superUrl = $delegate.url;
        $delegate.url = (url, replace) => {
          if(url !== undefined) {
            return superUrl(url.replace(/\%2B/g,"+"), replace);
          } else {
            return superUrl().replace(/\+/g,"%2B");
          }
        };
        return $delegate;
      });
    }
  ])

回答by Piotr Korlaga

You can override default angular encoding with adding Interceptor which fixes this:

您可以通过添加修复此问题的拦截器来覆盖默认角度编码:

import { HttpInterceptor, HttpRequest, HttpEvent, HttpHandler, HttpParams, HttpParameterCodec } from "@angular/common/http";
import { Injectable } from "@angular/core";
import { Observable } from "rxjs";

@Injectable()
export class EncodeHttpParamsInterceptor implements HttpInterceptor {
  intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    const params = new HttpParams({encoder: new CustomEncoder(), fromString: req.params.toString()});
    return next.handle(req.clone({params}));
  }
}


class CustomEncoder implements HttpParameterCodec {
  encodeKey(key: string): string {
    return encodeURIComponent(key);
  }

  encodeValue(value: string): string {
    return encodeURIComponent(value);
  }

  decodeKey(key: string): string {
    return decodeURIComponent(key);
  }

  decodeValue(value: string): string {
    return decodeURIComponent(value);
  }
}

and declare it in providers section of in app.module.ts

并在 app.module.ts 的 providers 部分声明它

providers: [
    {
      provide: HTTP_INTERCEPTORS,
      useClass: EncodeHttpParamsInterceptor,
      multi: true
    }
]

回答by Faisal

This ia a common problem. The +character is used by the URL to separate two words. In order to use the +character in the parameter values, you need to encode your parameter values before adding them as part of the URL. Javascript / TypeScript provide a encodeURI()function for that specific purpose.

这是一个常见的问题。+URL 使用该字符来分隔两个单词。为了+在参数值中使用该字符,您需要在将参数值添加为 URL 的一部分之前对其进行编码。Javascript / TypeScriptencodeURI()为该特定目的提供了一个函数。

URL encoding converts characters into a format that can be transmitted over the Internet. [w3Schools Reference]

URL 编码将字符转换为可以通过 Internet 传输的格式。[w3Schools 参考]

Here is how you can fix this problem:

以下是解决此问题的方法:

let encodedName = encodeURI('xyz+manwal');
let encodedURI = 'http://localhost:3000/page?name='+encodedName;

//.. OR using string interpolation
let encodedURI = `http://localhost:3000/page?name=${ encodedName }`;

In the same way, you can decode the parameters using decodeURI()method.

同样,您可以使用decodeURI()方法对参数进行解码。

let decodedValue = decodeURI(encodedValue);

回答by abahet

In Angular 5.2.7+ the "+" is replaced with space " " in a query string.

在 Angular 5.2.7+ 中,查询字符串中的“+”被替换为空格“”。

Here is the corresponding commit : fix(router): fix URL serialization

这是相应的提交:fix(router): fix URL serialization

If you want to change this behaviour and replace the "+" with "%2B" you can create a custom url serializer and provide it in the AppModule providers.

如果您想更改此行为并将“+”替换为“%2B”,您可以创建一个自定义 url 序列化程序并在 AppModule 提供程序中提供它。

import { DefaultUrlSerializer, UrlSerializer, UrlTree } from '@angular/router';

export default class CustomUrlSerializer implements UrlSerializer {
    private _defaultUrlSerializer: DefaultUrlSerializer = new DefaultUrlSerializer();

    parse(url: string): UrlTree {
        // Encode "+" to "%2B"
        url = url.replace(/\+/gi, '%2B');
        // Use the default serializer.
        return this._defaultUrlSerializer.parse(url);
    }

    serialize(tree: UrlTree): string {
        return this._defaultUrlSerializer.serialize(tree).replace(/\+/gi, '%2B');
    }
}

@NgModule({
    imports: [
        BrowserModule,
        BrowserAnimationsModule,
        AppRoutingModule
    ],
    declarations: [
        AppComponent
    ],
    providers: [
        { provide: UrlSerializer, useClass: CustomUrlSerializer }
    ],

    entryComponents: [],
    bootstrap: [AppComponent]
})
export class AppModule {
}

http://localhost:3000/page?name=xyz+manwal

http://localhost:3000/page?name=xyz+manwal

The URL will be converted to:

URL 将被转换为:

http://localhost:3000/page?name=xyz%2Bmanwal

http://localhost:3000/page?name=xyz%2Bmanwal

Hope this will help.

希望这会有所帮助。

回答by Aleksandar

This is a quite common problem. You can pass it normally in application/x-www-form-urlencoded request. No other request will be able to correctly parse +. They will always parse it into %20 instead of %2B.

这是一个很常见的问题。您可以在 application/x-www-form-urlencoded 请求中正常传递它。没有其他请求将能够正确解析 +。他们将始终将其解析为 %20 而不是 %2B。

You would need to manually manipulate the query parameter, there are 2 ways:

您需要手动操作查询参数,有两种方法:

  • Encode the parameter into base64 encoding, this way no special character can break you application, but you would need to handle it also on the receiving part (decoding).
  • A simplier solutions would be, before hitting the URL, replace all + signs with %2B. This way the other side will be able to decode it normaly, without the need of a special routine.
  • 将参数编码为 base64 编码,这样没有特殊字符可以破坏您的应用程序,但您还需要在接收部分(解码)处理它。
  • 一个更简单的解决方案是,在点击 URL 之前,用 %2B 替换所有 + 符号。这样对方就可以正常解码了,不需要特殊的程序。

For more info you should reffer to hthe following stack overflow questions Android: howto parse URL String with spaces to URI object?and URL encoding the space character: + or %20?

有关更多信息,您应该参考以下堆栈溢出问题Android:如何将带有空格的 URL 字符串解析为 URI 对象?URL 编码空格字符:+ 或 %20?

回答by Wellspring

In Angular v6.1.10, if you just need to fix the "+" sign encoding in one spot, this is what worked for me.

在 Angular v6.1.10 中,如果您只需要在一处修复“+”号编码,这对我有用。

getPerson(data: Person) {

  const httpParams = new HttpParams({
    fromObject: {
      id: data.id,
      name: data.name,
      other: "xyz+manwal"
    }
  });

  // manually encode all "+" characters from the person details
  let url = BASE_URL + "/select?" + httpParams.toString().replace(/\+/gi, '%2B');

  return this.http.get(url);
}

I found if you try to replace the "+" signs when initializing the httpParamsobject it doesn't work. You have to do the replacement after converting httpParamsto a string, as shown on this line:

我发现如果您在初始化httpParams对象时尝试替换“+”号,则它不起作用。您必须在转换httpParams为字符串后进行替换,如这一行所示:

let url = BASE_URL + "/select?" + httpParams.toString().replace(/\+/gi, '%2B');

回答by ddc

I am using Angular 7, the +(this one "xyz+manwal") is replaced with a space(like this "xyz manwal") in the URI when it reaches to back-end code.

我正在使用 Angular 7,当它到达后端代码时,URI 中的+(这个“xyz+manwal”)被替换为一个空格(就像这个“xyz manwal”)。

encodeURI() dindn't work for me, I used encodeURIComponent()it converted +to %2B

encodeURI() 对我不起作用,我使用了encodeURIComponent()+转换为%2B

     encodeURIComponent("xyz+manwal") => "xyz%2Bmanwal"

below is the example code

下面是示例代码

    // filter = xyz+manwal
    let filterString =  encodeURIComponent(filter); // filterString = xyz%2Bmanwal

    return this.http.get<ListResults>("http://website/query-results?" + filterString ).pipe(
      retry(3),
      catchError(........)
    )