2016-11-12 82 views
0

我想要一個名爲_contextPath的變量,它是JSP中的Javascript評估變量,當前可用於systemjs.config.js - 我試圖讓此_contextPath變量可用在打字稿服務中。將Web應用程序上下文傳遞給Angular2服務

我想知道,如果_contextPath變量可以被傳遞到打字稿服務稱爲job.service.ts

這裏是我的文件夾結構:

├── scripts 
│   └── mec-irs 
│    ├── app 
|  | ├── app.component.ts 
|  | ├── app.module.ts 
|  | ├── app.routes.ts 
|  | └── jobs 
|  |    ├── job.ts 
|  |    ├── job.routes.ts 
|  |     └── job.service.ts  
│    ├── db.json 
│    ├── GruntFile.js 
│    ├── index.html 
│    ├── node 
│    ├── node_modules 
│    ├── package.json 
│    ├── style.css 
│    ├── systemjs.config.js 
│    ├── tsconfig.json 
│    ├── typings 
│    └── typings.json 
├── views 
│   ├── mec.jsp 

mec.jsp獲得通過JavaScript調用和存儲上下文它在一個變量被稱爲_contextPath:

<html> 
<head> 
    <title>MEC IRS</title> 
    <script>document.write('<base href="' + document.location + '" />');</script> 
    <script>var _contextPath = "${pageContext.request.contextPath}";</script> 
    <meta charset="UTF-8"> 
    <meta name="viewport" content="width=device-width, initial-scale=1"> 
    <link rel="stylesheet" href="..<%=request.getContextPath()%>/scripts/mec-irs/style.css"> 

    <!-- 1. Load libraries --> 
    <!-- Polyfill(s) for older browsers --> 
    <script src="..<%=request.getContextPath()%>/scripts/mec-irs/node_modules/core-js/client/shim.min.js"></script> 
    <script src="..<%=request.getContextPath()%>/scripts/mec-irs/node_modules/zone.js/dist/zone.js"></script> 
    <script src="..<%=request.getContextPath()%>/scripts/mec-irs/node_modules/reflect-metadata/Reflect.js"></script> 
    <script src="..<%=request.getContextPath()%>/scripts/mec-irs/node_modules/systemjs/dist/system.src.js"></script> 

    <!-- 2. Configure SystemJS --> 
    <script src="..<%=request.getContextPath()%>/scripts/mec-irs/systemjs.config.js"></script> 
    <script> 
    System.import('app').catch(function(err){ console.error(err); }); 
    </script> 
</head> 

<!-- 3. Display the application --> 
<body> 
<my-app>Loading...</my-app> 
</body> 
</html> 

_contextPath用於在systemjs.config.js

/** 
* System configuration for Angular samples 
* Adjust as necessary for your application needs. 
*/ 
(function (global) { 
    System.config({ 
    paths: { 
     // paths serve as alias 
     'npm:': _contextPath + '/scripts/mec-irs/node_modules/' 
    }, 
    // map tells the System loader where to look for things 
    map: { 
     // our app is within the app folder 
     app: _contextPath + '/scripts/mec-irs/app', 
     // angular bundles 
     '@angular/core': 'npm:@angular/core/bundles/core.umd.js', 
     '@angular/common': 'npm:@angular/common/bundles/common.umd.js', 
     '@angular/compiler': 'npm:@angular/compiler/bundles/compiler.umd.js', 
     '@angular/platform-browser': 'npm:@angular/platform-browser/bundles/platform-browser.umd.js', 
     '@angular/platform-browser-dynamic': 'npm:@angular/platform-browser-dynamic/bundles/platform-browser-dynamic.umd.js', 
     '@angular/http': 'npm:@angular/http/bundles/http.umd.js', 
     '@angular/router': 'npm:@angular/router/bundles/router.umd.js', 
     '@angular/forms': 'npm:@angular/forms/bundles/forms.umd.js', 
     // other libraries 
     'rxjs':      'npm:rxjs', 
     'angular-in-memory-web-api': 'npm:angular-in-memory-web-api', 
    }, 
    // packages tells the System loader how to load when no filename and/or no extension 
    packages: { 
     app: { 
     main: './main.js', 
     defaultExtension: 'js' 
     }, 
     rxjs: { 
     defaultExtension: 'js' 
     }, 
     'angular-in-memory-web-api': { 
     main: './index.js', 
     defaultExtension: 'js' 
     } 
    } 
    }); 
})(this); 

的Java Web應用程序上下文被硬編碼雖然job.service.tsmec。我想知道如何通過_contextPath這個打字稿服務job.service.ts請。由於上下文mec下面看到的是硬編碼爲/mec/admin/irs/jobs/,它是一個網絡服務端點:

import {Injectable, Inject} from '@angular/core'; 
import {Http, Headers} from '@angular/http'; 
import 'rxjs/add/operator/map'; 

// Decorator to tell Angular that this class can be injected as a service to another class 
@Injectable() 
export class JobService { 

     // Class constructor with Jsonp injected 
     constructor(@Inject (Http)private http:Http) { } 

     // Base URI for Spring Batch Admin 
     private jobsUrl = '/batch/'; 

     //TODO wish not to have hardcoded context, like below 
     //private mecUrl = '/' + _contextPath + '/admin/irs/jobs/'; 
     private mecUrl = '/mec/admin/irs/jobs/'; 

     // Stop Spring Batch Job by its name 
     stopJobByName(name: string) { 
     const endPoint = name + '/stopIrsJobPoller'; 
     return this.http.get(this.mecUrl + endPoint) 
      .map(res => res.json()); 
    } 
. 
. 
.  
+0

爲什麼你需要這個變量? –

+0

我需要這個變量,因爲在服務中,我希望通過http:// hostname/_contextPath/someRestfulWS –

回答

0

你需要的東西,這將在應用程序初始化運行,讓你的服務器端的設置。這是我如何做到這一點。

創建一個類來存儲你的服務器端配置:

export class AppConfig { 
    public ContextPath: string; 
}; 

創建服務,從你的JSP讓您的後端配置:

import { Injectable } from '@angular/core'; 
import { Http } from '@angular/http'; 

import { AppConfig } from './app.config'; 

@Injectable() 
export class ConfigService { 
    private _config: AppConfig; 

    constructor(private http: Http, private config: AppConfig) { 
    } 

    public Load(): Promise<AppConfig> { 
     return new Promise((resolve) => { 
      this.http.get('./views/mec.jspn').map(res=>res.json()) 
       .subscribe((config: AppConfig) => { 
        this._config = data; 
        resolve(this._config); 
       }, (error: any) => { 
        this._config = new AppConfig(); 
        resolve(this._config); 
       }); 
     }); 
    } 

    public Get(key: any): any { 
     return this._config[key]; 
    } 
} 

然後在你的應用程序模塊的初始化自舉其通過提供ConfigService作爲APP_INITIALIZER的提供者:

import { BrowserModule } from '@angular/platform-browser'; 
import { NgModule } from '@angular/core'; 
import { FormsModule } from '@angular/forms'; 
import { Http, HttpModule } from '@angular/http'; 
import { APP_INITIALIZER } from '@angular/core'; 

import { AppComponent } from './app.component'; 
import { AppRoutingModule } from './app-routing.module'; 
import { ConfigService } from './shared/services/index'; 
import { AppConfig } from './app.config'; 

@NgModule({ 
    declarations: [ 
     AppComponent, 
    ], 
    imports: [ 
     BrowserModule, 
     FormsModule, 
     HttpModule 
    ], 
    providers: [ 
     { 
      provide: APP_INITIALIZER, 
      useFactory: (configService: ConfigService) =>() => configService.Load(), 
      deps: [ConfigService, Http, AppConfig], 
      multi: true 
     }, 
     ConfigService, 
     AppConfig 
    ], 
    bootstrap: [AppComponent] 
}) 
export class AppModule { 
} 

然後簡單地通過在任何其他服務中注入ConfigService來使用它:

import { Http, Headers, RequestOptions, Response } from '@angular/http'; 
import { Injectable } from '@angular/core'; 

import { ConfigService } from './config.service'; 

@Injectable() 
export class AppService { 
    constructor(
     private _http: Http, 
     private _config: ConfigService 
    ) { 
     console.log(_config.Get('ContextPath')); 
    } 
} 
+0

調用Web服務我故意無法使用GET訪問我的JSP,以http:// localhost:8080/mec/views/mec.jsp。即使我通過GET公開了http:// localhost:8080/mec/views/mec.jsp,您能否解釋ConfigService如何確定Java Web應用程序的上下文? –

+0

我不確定你想要達到的目標。配置服務需要知道從哪裏獲取配置。我認爲你可以通過使用this.http.get('./ views/mec.jspn')或this.http.get('http://someUrl/mec.jspn')來獲取它。如果沒有,你可以創建一個JSON文件存放在你的應用程序中/並使用它。另一方面,您不需要在SystemJS內設置上下文路徑,只需在index.html中設置baseHref即可。 –

+0

嗨,本,你會如何在今天的Angular v4中處理這個問題?因爲Angular中沒有更多的APP_INITIALIZER。我可以爲此目的簡單地創建另一個問題,但是您的答案與我在過去3天內一直在尋找的最接近。我正在研究Rails + Angular + Shopify應用程序。我找不到一種方法來訪問Response Params,特別是Angular客戶端的access_token。請幫助我。謝謝。 – mayorsanmayor