0

I have a multi-tenant application, being segmented into multiple "Portals"

On app load we reach out to the db and match the url to find which portal we're supposed to be. So http://www.mywebsite.com/customerA sets some innards for the app.

const portal: Portal = await this.templateService.addressLookup(url);

We then have a default route per portal, which I'm trying to route to on load via

this.router.navigateByUrl(portal.routeTo, { skipLocationChange: true });

This works great, taking me to the new route.

What I want to accomplish is instead of naving to http://www.mywebsite.com/route I want the user to see http://www.mywebsite.com/customerA/route in the URL bar, but have that resolve to the route in the app as http://www.mywebsite.com/route

-- I think I can just manually set the url but I'm not sure how to handle this

To expound on how it's setup:

1) User goes to http://www.mywebsite.com/customerA, on app load that hits the database and says "okay you're customerA, go to default route /defaultRoute".

2) We set an internal context that saves portalId to drive some functionality, and include with all API calls.

3) Now I want to route to http://www.mywebsite.com/customerA/defaultRoute, but have angular router actually resolve it as just /defaultRoute

Joshua Ohana
  • 5,613
  • 12
  • 56
  • 112

1 Answers1

2

Seems that what you need is Base URL. It's a URL that you usually set the <base> tag inside HTML's <head> and it acts like a origin path for all relative links in the app.

Put this function in your index.html, so it'll run on each app start (approach taken from here, just add your own logic to determine the base URL according to the URL in the address bar):

<base href="/">
<script>
  (function() {
    window['_app_base'] = //your logic to determine a base from the current URL;
  })();
</script>

afterwards, in your App.module, let Angular know about it (attention to providers):

import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { APP_BASE_HREF, Location } from '@angular/common';

import { AppComponent } from './';
import { getBaseLocation } from './shared/common-functions.util';

@NgModule({
  declarations: [AppComponent],
  imports: [
    BrowserModule,
    HttpModule,
  ],
  bootstrap: [AppComponent],
  providers: [
    {
        provide: APP_BASE_HREF,
        useValue: window['_app_base'] || '/'
    },
  ]
})
export class AppModule { }

If somewhere in your app you'll need to get it, use this:

import { APP_BASE_HREF } from '@angular/common'; 

...

constructor(@Inject(APP_BASE_HREF) private baseHref:string) {
  console.log(this.baseHref);
}
Mr Lister
  • 45,515
  • 15
  • 108
  • 150
grreeenn
  • 2,287
  • 1
  • 20
  • 27
  • I'm not sure if that'll work? I don't see how I can get that into my solution... I want to manually set the base href after load and an ngOnInit so I can ping the db for what portal we're on. I expanded my question with more specifics of how it's setup in my situation. – Joshua Ohana Dec 01 '18 at 16:20
  • sorry @grreeenn once I set base href manually, it's almost behaving exaaactly how I want so this might work. But how can I dynamically set the base href after the app has loaded? – Joshua Ohana Dec 01 '18 at 16:23
  • @JoshuaOhana I've edited my answer to be more intuitive. You're also welcome to go through links that I've provided, you'll find more info there :) this is solution by sharpmachine, I've used it and checked that it works. – grreeenn Dec 01 '18 at 16:41
  • Hey grreeenn I might be super confused. I want to SET base href I don't care about reading it so much. I see your way to read it and that's great, but I'm having issues setting it from within AppComponent – Joshua Ohana Dec 01 '18 at 16:48
  • @JoshuaOhana did you put the change function into your index.html as described in the first code block? – grreeenn Dec 01 '18 at 16:54
  • I'm not sure that can work. I need the app already loaded and to make an api call, THEN set the base href. It's not based only on the url, I need to hit the api first to determine what the base href should be. I'm using now the providers APP_BASE_HREF with a factory to provide, but I can't make it work async – Joshua Ohana Dec 01 '18 at 17:03
  • I made a new question that's more directed at the issue I"m having, https://stackoverflow.com/questions/53572834/change-base-href-after-angular-app-has-loaded – Joshua Ohana Dec 01 '18 at 17:07