Skip to content
This repository was archived by the owner on Apr 8, 2020. It is now read-only.
This repository was archived by the owner on Apr 8, 2020. It is now read-only.

Angular2 server-side rendering not working with matrix-formatted URLs #250

Description

@colltoaction

Hi,

I have started a new angular2 project with the yeoman generator. I'm setting up the routing but I'm having an issue with the query parameters in matrix URL notation (angular's default) with server-side prerendering.

I'm trying to render http://localhost:5000/shop;page=1;genres=Alternative,Rock, but the = are being encoded and it breaks angular's parsing.

I'm posting here because the first message from the dotnet cli output seems to indicate there's an issue with how the URL is being sent to node from the aspnet side. Having said that, maybe I'm wrong and this is an issue with https://github.com/angular/universal, so let me know!

PS C:> dotnet run
Project MyProject (.NETCoreApp,Version=v1.0) was previously compiled. Skipping compilation.
Hosting environment: Production
Content root path: C:\Users\............
Now listening on: http://localhost:5000
Application started. Press Ctrl+C to shut down.
info: Microsoft.AspNetCore.Hosting.Internal.WebHost[1]
      Request starting HTTP/1.1 GET http://localhost:5000/shop;page%3D1;genres%3DAlternative,Rock

If you need a repro I can work on that, but maybe you already know where and how the urls are being encoded and can easily spot the issue :).

Thanks!

Activity

  1. MarkPieszak commented on Aug 8, 2016

    @MarkPieszak
    Contributor

    I do believe on the Universal-side, you shouldn't have a problem with these URLs, it may be being encoded before its sent to node since it believes it's a Querystring?

    Not by a computer at the moment but I can try and take a look at the code tomorrow !

  2. colltoaction commented on Aug 11, 2016

    @colltoaction
    Author
    1. Run yo aspnetcore-spa and choose Angular2
    2. Replace home.ts with:
    import * as ng from '@angular/core';
    import { ActivatedRoute } from '@angular/router';
    
    @ng.Component({
      selector: 'home',
      template: require('./home.html')
    })
    export class Home {
      constructor(private route: ActivatedRoute) {
        this.route.params.subscribe((p: any) => console.log("params: ", p));
      }
    }
    1. Go to /home;test=hello!
    2. See the logged params in the server (params: { 'test%3Dhello!': 'true' })
    3. Compare to the browser's (params: Object {test: "hello!"})
  3. SteveSandersonMS commented on Aug 15, 2016

    @SteveSandersonMS
    Member

    Thanks for the clear repro info.

    The issue comes down to the fact when ASP.NET gets incoming path segments containing reserved characters (like =), then HttpContext.Request.Path returns them with URL encoding, whereas JavaScript's location.pathname API returns them without URL encoding.

    One workaround you could do right now would be to edit your boot-server.ts file and change this line:

    ngCore.provide(REQUEST_URL, { useValue: params.url }),
    

    to this:

    ngCore.provide(REQUEST_URL, { useValue: decodeURIComponent(params.url) }),
    

    However, I'm still discussing with colleagues on the ASP.NET team whether this is really a good idea and what would be the right way to reconcile ASP.NET's behaviour with Node/browser-based-JS. I want to get more feedback from people on whether the use of decodeURIComponent like that could constitute any security issue in any scenario we can imagine.

  4. colltoaction commented on Aug 15, 2016

    @colltoaction
    Author

    Amazing! Please keep us posted if you come to any conclusion.

  5. SteveSandersonMS commented on Aug 16, 2016

    @SteveSandersonMS
    Member

    OK, I've pushed a change (c53bd8f) that should make the URL encoding (or lack thereof) consistent between server and client, so the problem should go away in your example at least. I'll publish updated NuGet packages shortly.

    I'm still curious about how these matrix URLs are meant to work though. What is supposed to happen if an embedded key or value contains a space? It looks to me like this would be broken (not because of JavaScriptServices, but even just with a client-only app), because although the HTML5 pushState APIs let you set a URL with a space, if you tried to reload the page or navigate to it from somewhere else, Chrome at least will change the space to %20, and then location.pathname will see it as the characters %20 rather than a space. Does Angular 2 do something to fix this?

  6. colltoaction commented on Aug 16, 2016

    @colltoaction
    Author

    You're right, I'm getting %20 instead of spaces. Not only with matrix notation, but also with regular params. I'll have to do a replace I guess.

  7. added a commit that references this issue on Aug 17, 2016
    e7b7d33
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions