【问题标题】:angular app in kubernetes using nginx ingress pathKubernetes中使用nginx入口路径的角度应用程序
【发布时间】:2020-09-12 11:37:04
【问题描述】:

经过一番挖掘,我决定发布这个问题,希望会出现一个正确的答案:)

目标:在 k8s 中部署一个 Angular 应用程序,并通过可自定义路径和参数化路由的 nginx 入口将其公开。 应该有效的调用:

http://my-url/my-app/
http://my-url/my-app/a
http://my-url/my-app/b
http://my-url/my-app/c
http://my-url/my-app/c/my-id

问题:不支持参数化路由/c/:id。未调用工厂,因此未设置动态APP_BASE_HREF。调用不正常:

http://my-url/my-app/c/my-id

在那里,APP_BASE_URL 未被正确检测到,并且 Angular 尝试从 http://my-url/my-app/c/runtime.js 加载资源。

提供完整的代码示例会很困难很长,但会提供一些sn-ps

Kubernetes

nginx

helm uninstall -n ingress-nginx nginx-ingress; helm install --namespace ingress-nginx nginx-ingress stable/nginx-ingress(图表版本:nginx-ingress-1.33.5;应用版本:0.30.0)

入口配置

---
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: {{ template "my-app.ui.fullname" . }}
  labels:
    app: {{ template "my-app.name" . }}
    component: "{{ .Values.ui.name }}"
  annotations:
      kubernetes.io/ingress.class: "nginx"
      ingress.kubernetes.io/rewrite-target: /$2
      ingress.kubernetes.io/ssl-redirect: "false"
      ingress.kubernetes.io/use-regex: "true"
spec:
  rules:
  - host: "{{ .Values.root_url }}"
    http:
      paths:
      - path: "{{ .Values.ui.ingress.path }}(/|$)(.*)"
        backend:
          serviceName: {{ template "my-app.ui.fullname" . }}
          servicePort: 8085

{{ .Values.ui.ingress.path }} 可以是 /my-app 之类的任何东西

角度应用

src/index.html
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <title></title>

    <meta name="viewport" content="width=device-width, initial-scale=1">
    <link rel="icon" type="image/x-icon" href="favicon.ico">
  </head>
  <body>
    <app-root></app-root>
  </body>
</html>
src/app/routing.module.ts

我们拥有的路线。


const routes: Routes = [
    { path: '',
        redirectTo: '/overview',
        data: { title: 'Overview'},
        pathMatch: 'full' },
    { path: 'overview',
        data: { title: 'Overview'},
        component:  AComponent },
    { path: 'b',
        data: { title: 'B'},
        component: BComponent },
    { path: 'c/:id',
        data: { title: 'C detail'},
        component: CComponent },
    { path: 'c',
        data: { title: 'C detail'},
        component: CComponent },
    { path: '**',
        component: PageNotFoundComponent }

];


@NgModule({
  imports: [ RouterModule.forRoot(routes,
        {enableTracing: false}
    ) ],
  exports: [ RouterModule ]
})
export class RoutingModule { }

export const ROUTES_PATH = routes.map(p => p["path"])
src/app/app.module.ts

只需使用APP_BASE_HREF 修饰符:

import { getBaseLocation } from './common-utils';


/**
 * Modules
 */

@NgModule({
    declarations: [
        AppComponent,
...

    ],
    imports: [
        BrowserModule,
        RoutingModule
...
    ],
    providers: [
        Title,
        {
            provide: APP_BASE_HREF,
            useFactory: getBaseLocation
        }
    ],
    bootstrap: [ AppComponent ],
    entryComponents: [ t ]
})
export class AppModule { }

src/app/common-utils.ts
import { ROUTES_PATH } from './routing.module';

export function getBaseLocation() {
    let paths: string[] = location.pathname.split('/');
    let basePath: string = (paths && !ROUTES_PATH.includes(paths[1]) && paths[1]) || ''; // Default: ''
    return '/' + basePath;
}

参考文献

Providerfactory for APP_BASE_HREF token is called before APP_INITIALIZER is done

https://github.com/angular/angular/issues/25932

Angular 2 Set APP_BASE_HREF with a value from a Promise / Observable

【问题讨论】:

    标签: angular nginx kubernetes nginx-ingress


    【解决方案1】:

    根据@aakash 的建议,我分析了HashStrategy

    要支持/:id,我们可以在路由配置src/app/routing.module.ts 中使用HashStrategy。带有HashStrategy的,所谓的哈希分片,不会被发送到服务器。

    src/app/routing.module

    ...
    @NgModule({
      imports: [ RouterModule.forRoot(routes, {useHash: true}) ],
      exports: [ RouterModule ]
    })
    
    

    在这种情况下,请求将如下所示:

    http://my-url/my-app/
    http://my-url/my-app/#/a
    http://my-url/my-app/#/b
    http://my-url/my-app/#/c
    http://my-url/my-app/#/c/my-id
    

    【讨论】:

      【解决方案2】:

      你想用 :/ 支持路径吗?您可以将哈希策略与路由器模块一起使用。这样你的额外路由就不会去服务器了

      【讨论】:

      • 一切都应该交给 kubernetes 入口控制器。
      猜你喜欢
      • 2021-05-15
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-02-27
      • 2020-08-31
      • 1970-01-01
      • 2021-05-23
      相关资源
      最近更新 更多