I am making the CURD API of .net core and Try to Use that API in Angular 2 application
1)Service File EmployeeService.ts
import { Injectable } from '#angular/core';
import { Http, Response, RequestOptions, Headers } from '#angular/http';
import 'rxjs/Rx';
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/operator/map';
import { employee } from "../employee/emp"
#Injectable()
export class empservice {
//step 1: Add url of the .net api (get that by running .net api using F5)
private _url: string = "http://localhost:65088/api/Employee";
constructor(private _http: Http) { }
//step 2 : Method to get value from url
GetAllEmployee(): Observable<employee[]> {
return this._http.get(this._url).map((res: Response) => { return
<employee[]>res.json() });;
}
}
2)Component File Employee.Component.ts
import { Component, Input } from '#angular/core';
import { RouterModule, Router, ActivatedRoute, Data } from '#angular/router';
import { empservice } from './emp.service';
#Component({
selector: 'my-emp',
templateUrl: 'app/employee/Emp.html',
styleUrls: ['app/CSS/stylesheet.css', 'app/CSS/media.css'],
})
export class Employee {
public employee: employee[];
public ngOnInit() {
this.AllEmployee();
$(document).ready(function () {
$('#emptble').DataTable();
});
}
AllEmployee() {
this._employeeservice.GetAllEmployee().subscribe(empdata =>
this.employee = empdata);
}
}
export interface employee {
ID: any;
Fname: string;
Lname: string;
Age: any;
Mobile: any;
Phone: any;
}
3)HTML Code
<table>
<tr *ngFor="let emp of employee">
<td scope="row">{{emp.ID}}</td>
<td>{{emp.Fname}}</td>
<td>{{emp.Lname}}</td>
<td>{{emp.Age}}</td>
<td>{{emp.Mobile}}</td>
<td>{{emp.Phone}}</td>
<td>
<i style="cursor:pointer;" class="glyphicon glyphicon-edit
pointer"
(click)="Update(employee.ID)" title="Edit" data-
target="#update"></i>
<i style="cursor:pointer;" class="glyphicon glyphicon-trash
pointer"
(click)=" delete(employee.ID)" title="Delete">
</i>
<i style="cursor:pointer;" class="glyphicon glyphicon-user
pointer"
(click)="openModal(employee.ID)" title="Details" data-
target="#details"></i>
</td>
</tr>
</table>
I didn't get expected output of this code.
It's not show the employee name,id,age..etc Details of employee in the table cell.
API call is done correctly and data come from API to angular but i can't understand why that data not bind with angular html page.
You don't seem to call your AllEmployee() method at all, so no API call seems to be made.
Instead you should put this in the ngOnInit() lifecycle hook.
export class Employee implements OnInit {
public employee: employee[];
ngOnInit() {
this._employeeservice.GetAllEmployee()
.subscribe((data) => this.employee = <employee[]>data);
}
Side note: You're still using the Http service which was deprecated in version 4.3. You should switch to the new HttpClient.
You should use ngOnInit() lifecycle hook
ngOnInit() {
//call here in your data binding method
}
Related
I am writing an Angular9 app with a use case where I am buffering data across 3 pages (with forms taking data input).
Then, on the 4th page, I display a summary of the details gathered across the 3 pages as read only text.
I have implemented the data buffering using the following article:
https://www.infragistics.com/community/blogs/b/infragistics/posts/simplest-way-to-share-data-between-two-unrelated-components-in-angular
Which uses the BehaviorSubject
Below is my data service logic:
import { Injectable } from '#angular/core';
import { HttpClient, HttpHeaders } from '#angular/common/http';
import { Observable, BehaviorSubject, throwError } from 'rxjs';
import { retry, catchError } from 'rxjs/operators';
import { UserResponse } from './user-response';
#Injectable({
providedIn: 'root'
})
export class UserService {
//Details Page 1
public salutation: BehaviorSubject<string>;
public firstName: BehaviorSubject<string>;
// Base url
baseurl = 'https://localhost:8080/rest';
constructor(private http: HttpClient) { }
// Http Headers
httpOptions = {
headers: new HttpHeaders({
'Content-Type': 'application/json'
})
}
// POST
createUser(data): Observable<UserResponse> {
alert('user - details = '+ data);
return this.http.post<UserResponse>(this.baseurl + '/user', JSON.stringify(data), this.httpOptions)
.pipe(
retry(1),
catchError(this.errorHandler)
)
}
// Error handling
errorHandler(error) {
let errorMessage = '';
if(error.error instanceof ErrorEvent) {
// Get client-side error
errorMessage = error.error.message;
} else {
// Get server-side error
errorMessage = `Error Code: ${error.status}\nMessage: ${error.message}`;
}
console.log(errorMessage);
return throwError(errorMessage);
}
}
Below is my first view component:
import { Component, OnInit } from '#angular/core';
import { NgForm } from '#angular/forms';
import { UserService } from '../service/user.service';
import { BehaviorSubject } from 'rxjs';
#Component({
selector: 'app-details1',
templateUrl: './details1.component.html',
styleUrls: ['./details1.component.css']
})
export class Details1Component implements OnInit {
salutation: string;
firstName: string;
constructor(private userService: UserService) { }
ngOnInit(): void {
}
goToDetails2(form : NgForm) {
this.userService.salutation = new BehaviorSubject(form.value.salutation);
this.userService.firstName = new BehaviorSubject(form.value.firstName);
}
}
Below is a snippet of my final/summary view component
import { Component, OnInit} from '#angular/core';
import { Router } from '#angular/router';
import { UserService } from '../service/user.service';
#Component({
selector: 'app-summary',
templateUrl: './summary.component.html',
styleUrls: ['./summary.component.css']
})
export class SummaryComponent implements OnInit {
salutation: string;
firstName: string;
constructor(
private router: Router,
public userService: UserService
) {
}
ngOnInit(): void {
this.userService.salutation.subscribe(c => { this.salutation = c; });
this.userService.firstName.subscribe(c => { this.firstName = c; });
}
}
On the final page my html excerpts is as follows:
<form #detailsForm4="ngForm">
<div class="govuk-form-group">
<table class="govuk-table">
<thead class="govuk-table__head">
<tr class="govuk-table__row"></tr>
</thead>
<tbody class="govuk-table__body" align="left">
<tr class="govuk-table__row">
<th scope="row" class="govuk-table__header">Salutation</th>
<td class="govuk-table__cell"> {{salutation}} </td>
<td class="govuk-table__cell"> </td>
</tr>
<tr class="govuk-table__row">
<th scope="row" class="govuk-table__header">First name</th>
<td class="govuk-table__cell"> {{firstName}} </td>
<td class="govuk-table__cell"> </td>
</tr>
The data is displayed on the summary page as captured on the forms in pages 1-3,
BUT the data is lost on page refresh or when my machine hibernates etc
I have read about local and session storage persistence and used it since the angularjs 1.x days.
Ages ago, I was actually surprised when the data disappeared on my summary screen!
I guess that an ideal solution will involve storing the data in client side storage when the user navigates away from the relevant form, then retrieving the data on the summary page.
I guess, when the summary page is refreshed or displayed for the first time,
I will check storage for the data and display if it exist.
If storage is empty, then I will be using data from previous page at runtime.
Please, I need help with a best practice and stable solution, which is cross browser friendly and intelligent for a commercial application.
Also, an approach that fits into Angular9 BehaviorSubject - rxjs stack OR Any recent features, because I know Angular has evolved since AngularJs 1.x ?
The summary details is only changed when the user navigates back to any of the pages 1-3 to change the form details.
I will appreciate any code snippet or reference to keep the data on the summary page.
Thanks a lot.
I will propose you to use localStorage within your SummaryComponent within ngOnDestroy lifecycle hook. It will always set your data within localStorage before component will be destroyed due to refresh. Then when you are trying to retrieve data from the service, if it will be empty try to get it from localStorage.
export class SummaryComponent implements OnInit, OnDestroy {
salutation: string;
firstName: string;
constructor(
private router: Router,
public userService: UserService
) {
}
ngOnInit(): void {
this.userService.salutation.subscribe(c => { this.salutation = c || localStorage.get('salutation'); });
this.userService.firstName.subscribe(c => { this.firstName = c || localStorage.get('firstName'); });
}
ngOnDestroy(): void {
localStorage.setItem('salutation', this.salutation));
localStorage.setItem('firstName', this.firstName));
}
}
Similar implementation you can do in the component where this values are set and you expect that user can refresh the page before go to the next page.
EDIT
Sorry, you are right that ngOnDestory will not trigger on page refresh to do that you will need to handle window:beforeunload.
#HostListener('window:beforeunload', ['$event'])
beforeunload($event: Event): void {
// set localStorage here
}
Going forward with your solution, the best option to set items to the localStorage is the place where you set values to the service. It's probably goToDetails2 method.
goToDetails2(form : NgForm) {
this.userService.salutation = new BehaviorSubject(form.value.salutation);
this.userService.firstName = new BehaviorSubject(form.value.firstName);
localStorage.setItem('salutation', form.value.salutation));
localStorage.setItem('firstName', form.value.firstName));
}
EDIT-2 to your problem described in the comment
I will propose you to initialize your BehaviorSubject directly inside of the service.
#Injectable({
providedIn: 'root'
})
export class UserService {
//Details Page 1
public salutation: BehaviorSubject<string> = new BehaviorSubject('');
public firstName: BehaviorSubject<string> = new BehaviorSubject('');
And then within your Details1Component set values on them using next
goToDetails2(form : NgForm) {
this.userService.salutation.next(form.value.salutation);
this.userService.firstName.next(form.value.firstName);
localStorage.setItem('salutation', form.value.salutation));
localStorage.setItem('firstName', form.value.firstName));
}
I am trying to create a form in angular that takes a name, passes it to a URL, and returns a portion of a .json file. I can't figure out why the url is not getting updated though.
The HTML:
<form (ngSubmit)="processForm($engineer)">
<div class="form-group">
<label for="engineerselectform">Engineer Name</label>
<select class="form-control" id="engineerselectform" name="engineer" [(ngModel)]="engineer">
<option></option>
<option>Smith</option>
<option>Jones</option>
<option>Clark</option>
</select>
</div>
<input class="btn btn-primary" type="submit" value="submit" aria-pressed="true">
</form>
The Component:
import { Component, OnInit } from '#angular/core';
import { ScheduleService } from '../schedule.service';
import { ActivatedRoute } from '#angular/router';
#Component({
selector: 'app-schedule',
templateUrl: './schedule.component.html',
styleUrls: ['./schedule.component.scss']
})
export class ScheduleComponent implements OnInit {
engineer;
constructor(
private scheduleService: ScheduleService,
private route: ActivatedRoute
) { }
ngOnInit() {}
processForm(engineer: string) {
this.route.params.subscribe(params=> { const engineer = params["engineer"];
this.scheduleService.getschedule(engineer).subscribe(engineer => this.engineer = engineer);
});
}
}
The Service:
import { Injectable } from '#angular/core';
import { HttpClient } from '#angular/common/http';
#Injectable({
providedIn: 'root'
})
export class ScheduleService {
apiUrl ='http://127.0.0.1:5000/schedule'
engineer;
constructor(private http: HttpClient) { }
getschedule(engineer: string){
return this.http.get(`${this.apiUrl}?engineer=${this.engineer}`);
}
}
The Flask API backend:
#app.route('/schedule', methods = ['GET'])
def engineer_location_api():
if "engineer" in request.args:
print ('did this')
engineer_name = request.args["engineer"]
print ("engineer name:", engineer_name)
else:
return "not found, sorry"
answer = {}
with open(LOC1, "r") as file:
check_loc1 = json.load(file)
for item in check_loc1["LOC1"]:
if engineer_name in item["Engineer"]:
answer.update(item)
else:
continue
with open(LOC2, "r") as file:
check_loc2 = json.load(file)
for item in check_loc2:
if engineer_name in item:
answer.update(item)
else:
continue
if answer:
return answer
else:
return 'engineer not found'
app.run()
the error:
ERROR
Object { headers: {…}, status: 200, statusText: "OK", url: "http://127.0.0.1:5000/schedule?engineer=undefined", ok: false, name: "HttpErrorResponse", message: "Http failure during parsing for http://127.0.0.1:5000/schedule?engineer=undefined", error: {…} }
core.js:6014:19
As I understand it, when I hit submit the process form function should send the engineer variable to the component where it sets it as a parameter that it provides to the service which should fill out the URL. But regardless of how I play around with it, the engineer always comes back as undefined. Clearly I'm missing something core to passing the variable.
Also, I'm super new and therefore there are probably other things in this code that are ugly or not best practice, feel free to rip into it, I figure my understanding can only go up.
You don't have to subscribe to activated url if your data is coming from form. You have to remove the $event from processForm because we will add the global variable in your service function. Please have a look on below example
<form (ngSubmit)="processForm()">
<div class="form-group">
<label for="engineerselectform">Engineer Name</label>
<select class="form-control" id="engineerselectform" name="engineer" [(ngModel)]="engineer">
<option></option>
<option value="smith">Smith</option>
<option value="jones">Jones</option>
<option value="clark">Clark</option>
</select>
</div>
<input class="btn btn-primary" type="submit" value="submit" aria-pressed="true">
</form>
import { Component, OnInit } from '#angular/core';
import { ScheduleService } from '../schedule.service';
import { ActivatedRoute } from '#angular/router';
#Component({
selector: 'app-schedule',
templateUrl: './schedule.component.html',
styleUrls: ['./schedule.component.scss']
})
export class ScheduleComponent implements OnInit {
engineer;
receivedEngineers;
constructor(
private scheduleService: ScheduleService,
private route: ActivatedRoute
) { }
ngOnInit() {}
processForm() {
this.scheduleService.getschedule(this.engineer).subscribe(engineer => this.receivedEngineers = engineer);
});
}
}
getschedule(engineer: string){
return this.http.get(`${this.apiUrl}?engineer=${engineer}`);
}
The engineer is now accessed from parameter of getSchedule() function.
There are many examples around the web on this subject but none of them helped me. This is the scenario: I've got 2 components and a service. The two components aren't parent/children but are 2 independent components. One of them has a list of names, the other should load a table when one of the names is clicked. This is my home.html with both components
<div class="material-docs-app">
<div class="docs-primary-header">
<h1>Yep!</h1>
</div>
<div fxLayout="row" fxLayout.xs="column" class="component-layout-body">
<app-heroes-sidenav></app-heroes-sidenav>
<app-heroes-table #heroesTable fxFlex="1 2 calc(15em + 20px)" style="width: 100%"></app-heroes-table>
</div>
</div>
Heroes sidenav component:
<div *ngIf="loadingData == true">
<mat-progress-bar mode="indeterminate"></mat-progress-bar>
</div>
<nav *ngIf="loadingData == false">
<p *ngFor="let item of heroesNames.results let i = index" [attr.data-index]="i">
<button mat-button (click)="getHero(i)">
{{item.name}}
</button>
</p>
</nav>
On click getHero() is called correctly. This is the sidenav component ts:
import { Component, OnInit, Input } from '#angular/core';
import {SwCharactersServiceService} from '../sw-characters-service.service';
import {HeroesTableComponent} from '../heroes-table/heroes-table.component';
#Component({
selector: 'app-heroes-sidenav',
templateUrl: './heroes-sidenav.component.html',
styleUrls: ['./heroes-sidenav.component.css']
})
export class HeroesSidenavComponent implements OnInit {
heroesNames: any;
heroData:any;
loadingData = true;
#Input() heroesTable: HeroesTableComponent;
constructor(private _swService: SwCharactersServiceService) { }
ngOnInit() {
this.getHeroes();
}
getHeroes() {
this._swService.getCharacters().then(result => {
this.loadingData = false;
this.heroesNames = result;
});
}
getHero(index) {
this._swService.getHero(index);
}
}
and this is the service:
import { Injectable } from '#angular/core';
import { HttpClient, HttpHeaders } from '#angular/common/http';
import 'rxjs/add/operator/map'
import {Observable} from 'rxjs/Observable';
#Injectable({
providedIn: 'root'
})
export class SwCharactersServiceService {
param:any;
constructor(private http: HttpClient) { }
getCharacters(): Promise<any[]> {
return this.http.get<any[]>("https://swapi.co/api/people/")
.toPromise()
.then(result => result)
.catch(this.handleError);
}
getHero(index): Observable<any>{
console.log(index);
let headers = new HttpHeaders();
headers.append('Content-Type', 'application/json');
return this.http.get("https://swapi.co/api/people/" + index, {
headers: headers
}).map(res => res );
}
private handleError(error: any): Promise<any> {
console.error('An error occurred', error); // for demo purposes only
return Promise.reject(error.message || error);
}
}
I can correctly see the console.log(index) but the request doesn't work. There is no request initiated in chrome console network tab.
This is the component with the table:
import { Component, OnInit, Input, Output, EventEmitter } from '#angular/core';
import { Subscription } from 'rxjs/Subscription';
import {SwCharactersServiceService} from '../sw-characters-service.service';
#Component({
selector: 'app-heroes-table',
templateUrl: './heroes-table.component.html',
styleUrls: ['./heroes-table.component.css']
})
export class HeroesTableComponent implements OnInit {
loadingData = true;
heroData :any;
subscription: Subscription;
constructor(private _swService: SwCharactersServiceService) {
this.subscription = this._swService.getHero(1).subscribe(result => { this.heroData = result; });
console.log(this.heroData);
}
ngOnInit() {
}
ngOnDestroy() {
// unsubscribe to ensure no memory leaks
this.subscription.unsubscribe();
}
}
There are 2 problems now:
1) As you can see I wrote this._swService.getHero(1) without passing a dynamic param. How does it work? How can I pass the correct index?
2) The service doesn't fire and I haven't got any result.
Is there any other way to do that?
Thanks.
you can use BehaviourSubject to pass the index value and send the query request as the list is cliked
in the service
import { BehaviorSubject } from 'rxjs/BehaviorSubject';
public index: BehaviorSubject<number> = new BehaviorSubject<number>(null);
in the sidenav component
getHero(index) {
this._swService.index.next(index);
}
in the hero table component
ngAfterViewInit(){
this._swService.index.subscribe(index=>{
if(index){
this._swService.getHero(index).subscribe(result => { this.heroData = result; });
}
})
}
You missed to subscribe to _swService.getHero(). If not subscribed to a method which returns an Observable, then it wont be invoked.
getHero(index) {
this._swService.getHero(index).subscribe(
(resp) => {
// manipulate your response here
console.log(resp);
},
(err) => {}
);
}
Transfer single item from a list item to cart list.
I am developing an Angular web app and want that when I click a button the single item of an array gets transferred from one service to another service and is also transferred on another component. I have successfully implemented it with a transfer of whole array but I am facing problem with a single item.Please help.
What I want is that when I click on Add to cart button the list item which is clicked only gets transferred and not the array of list items.
buyGame.html file
<div class="col-xs-6">
<a class="list-group-item clearfix" style="background-color:rgb(3, 0, 48)" *ngFor="let buying of buy">
<div class="pull-left" style="max-width:330px">
<h5 style="color:white">{{buying.names}}</h5>
<p style="color:white">{{buying.desc}}</p>
<button class="btn btn-danger ; pull-left" (click)= "onAddToCart()">Add To Cart</button>
</div>
<div>
<span class="pull-right">
<img [src]="buying.getImg" alt="image not loaded" class="img-responsive" style="max-height:100px">
</span>
</div>
</a>
</div>
buygame.service.ts file :
import { gameBuy } from "./buygame.model";
import { Injectable,EventEmitter } from "#angular/core";
import { cartService } from "./cart.service";
#Injectable()
export class gameService{
private gameServ: gameBuy[] = [
new gameBuy('batman','Batmobile and enhancements to signature features',"https://www.geek.com/wp-content/uploads/2016/02/batmans-625x352.jpg"),
new gameBuy('GTA 5',
"PlayStation 3 or Xbox 360 will be able to transfer their current Grand Theft Auto Online characters and progression to their choice of PlayStation 4 Xbox One or PC",
"http://onlysp.com/wp-content/uploads/2015/01/maxresdefault.jpg")
];
constructor(private cartSer: cartService){}
getBuyingList(){
return this.gameServ.slice();
}
addItemToCart(game:gameBuy[]){
this.cartSer.addItem(game);
}
}
buyGame.component.ts:
import { Component, OnInit,Input } from '#angular/core';
import { gameBuy } from '../shared/buygame.model';
import { gameService } from '../shared/buygame.service';
#Component({
selector: 'app-buy-game',
templateUrl: './buy-game.component.html',
styleUrls: ['./buy-game.component.css'],
})
export class BuyGameComponent implements OnInit {
#Input() buy:gameBuy[];
constructor(private service: gameService) { }
ngOnInit() {
this.buy = this.service.getBuyingList();
}
onAddToCart(){
this.service.addItemToCart(this.buy);
}
}
cart.component.ts:
import { Component, OnInit} from '#angular/core';
import { cartModel } from '../shared/cart.model';
import { cartService } from '../shared/cart.service';
import { gameBuy } from '../shared/buygame.model';
#Component({
selector: 'app-cart',
templateUrl: './cart.component.html',
styleUrls: ['./cart.component.css'],
})
export class CartComponent implements OnInit {
cart:gameBuy[];
constructor(private service: cartService) { }
ngOnInit() {
this.cart = this.service.getCartItem();
}
}
cart.service.ts:
import { cartModel } from "./cart.model";
import { EventEmitter } from "#angular/core";
import { gameBuy } from "./buygame.model";
export class cartService{
cartChanged = new EventEmitter<gameBuy[]>();
private cart: gameBuy[] = [
new gameBuy('Batman','Batman is a cool game','https://images-na.ssl-images-amazon.com/images/I/91lu5KHSm3L._SY445_.jpg'),
new gameBuy('Gta 5','online game of GTA','https://www.rockstargames.com/V/img/global/order/mobile-cover.jpg')
];
getCartItem(){
return this.cart.slice();
}
addItem(cart:gameBuy[]){
this.cart.push(...cart);
this.cartChanged.emit(this.cart.slice());
}
}
cart.model.ts:
export class cartModel{
constructor(public cartName: string,public cartDesc: string,public cartImage:string){}
}
buygame.model.ts:
export class gameBuy{
constructor(public names:string, public desc:string, public getImg:string){}
}
You need to specify exact item you want to be added to the cart in the temlate:
(click)= "onAddToCart(buying)"
And then pass it right to your service as onAddToCart method parameter:
onAddToCart(buying: gameBuy){
this.service.addItemToCart(buying);
}
Also, your buygame service method should accept a single item, not a list:
addItemToCart(game: gameBuy){
this.cartSer.addItem(game);
}
Atl last, cart service should be updated too (just to push a single item)
addItem(cart:gameBuy){
this.cart.push(cart);
this.cartChanged.emit([...this.cart]); // slice() is ok too if you need a copy
}
Try providing the index in your call (click)= "onAddToCart(index)" and get it from your array.
OR provide the single object in (click)= "onAddToCart(buying)"
then receive it on TS
EDIT: Comment by OP:
"Sorry , but I think I had had slight typo in enviroment/environment, sorry for wasting your time ,it seems to work now"
I have having trouble passing data from app components to child component in angular 2 . I recently started toying with angular 2 and trying to understand how it works. I tried to used the concept shown in this tutorial to do pass data to child component
https://angular.io/docs/ts/latest/tutorial/toh-pt3.html
But I think I am missing something
Here is my project: App component:
import { Component, ViewChild } from '#angular/core';
import { WorkflowService } from './components/workflow_display/workflow.service';
import { WorkflowDisplayComponent } from './components/workflow_display/workflow-display.component';
import { PropertyService } from './shared/property.service';
import '../../public/css/styles.css';
#Component({
selector: 'my-app',
template: require('./app.component.html')
})
export class AppComponent {
title = 'Hello World';
#ViewChild("taskDisplay") workflowDisplay: WorkflowDisplayComponent;
myEnvironment: String; //the variable I am trying to bind from
errorMessage: String;
workbenchBaseUrl : String = 'workbenchBaseUrl';
public selectedNavID : String = 'workspace_control_workStreamView';
public isWorkOrdersCollapsed = false;
public isWorkStreamsCollapsed = false;
constructor(private _propertyService : PropertyService){
}
ngOnInit(): void {
this._propertyService.getValue(this.workbenchBaseUrl)
.subscribe(environment => this.myEnvironment = environment,
error => this.errorMessage = <any>error);
}
}
app.component.html
<div>
<div>
<div>
<!--some html-->
<main class="col-sm-9 offset-sm-3 col-md-10 offset-md-2 pt-3 mh-100">
<workflow-display [environment] ="myEnvironment" #taskDisplay></workflow-display>
</main>
</div>
</div>
</div>
WorkDisplay component
import { Component, Input} from '#angular/core';
import { OnInit } from '#angular/core';
import { IGrcTask } from './grc-task';
import { WorkflowService } from './workflow.service';
import { PropertyService } from '../../shared/property.service';
#Component({
selector: 'workflow-display',
template: require('./workflow-display.component.html')
})
export class WorkflowDisplayComponent implements OnInit {
taskMode: string = 'workstream'; // 'workorder' or 'workstream' to currently identify the columns to display
taskQuery: string = 'process=workstream&taskStatus=RUNNING'; // the query parameters to pass to the tasks web service
workbenchUrl: string = 'http://localhost:8081'; // workbench URL
workbenchTaskPage: string = 'wsIndex'; // workbench page to use to open tasks
infoMessage: string;
errorMessage: string;
tasks: IGrcTask[];
currentTask: IGrcTask;
#Input()
environment: String; //the variable I am trying to bind to
workbenchBaseUrl : String = 'workbenchBaseUrl';
constructor() {
}
//called when user clicks a row
openTask(event: any, task: any) {
// this.environment is still undefined
window.open(this.environment + this.workbenchTaskPage + "?taskId=" + task.taskId + "&activitiWorkflow=true");
}
}
WorkDisplay.component.html
<--!some html-->
<tbody *ngIf='(taskMode == "workorder") && tasks && tasks.length'>
<ng-container *ngFor='let task of tasks; let i=index'>
<tr (click)="setCurrentTask($event, task)" (dblclick)="openTask($event, task)"
<--!some html-->
Property.service.ts
import { Injectable } from '#angular/core';
import { Http, Response } from '#angular/http';
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/operator/catch';
import 'rxjs/add/operator/do';
import 'rxjs/add/operator/map';
/**
* Service return Property value/values from the project property file
*
*/
#Injectable()
export class PropertyService {
//ReST Url for the PopertyService on the back end
private _url = '/grcworkflow/resources/grcWorkflow/environment/';
constructor(private _http: Http) {}
/**
* Method return an Observable<String -> Value> for any property
* Method make an http get call to the server to fetch the property
* #Param key for the property in the property file
*/
getValue(key: String): Observable<String> {
return this._http.get(this._url+key)
.map((response: Response) => <String> response.text())
.do(data => console.log('All: ' + data))
.catch(this.handleError);
}
private handleError(error: Response) {
return Observable.throw(error.json().error || 'Server error');
}
}
NOTE I have removed some function definitions and variable from the components which might be irrelevant.
I am trying to bind myEnviroment value of the app.component enviroment value. myEnviroment get set when proerty service returns a string. Although enviroment value still stays undefined .
I am looking for one way binding i.e when myEnvironment(parent) changes environment(child) should change too. But this doesn't seem to happen. Please help out here