앵귤러의 http모듈은 서버에 정보를 요청할 때 사용됩니다.
목차
사용방법
모듈사용을 위해 해당 모듈을 추가합니다.
// app.module.ts
import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
import { CommentComponent } from './components/comment/comment.component';
import { HttpClientModule } from '@angular/common/http';
@NgModule({
declarations: [AppComponent, CommentComponent],
imports: [BrowserModule, AppRoutingModule, HttpClientModule],
providers: [],
bootstrap: [AppComponent],
})
export class AppModule {}
필수는 아니지만 사용을 편의를 위해 서비스 파일과 모델파일을 추가합니다(아래 명령어를 통해 생성가능).
ng g s services/comment
ng g i models/comment
※ 모델을 생성하는 이유는 타입제약이 강한 앵귤러의 특성상 서버에서 요청한 데이터를 다른 변수에 지정할 때 일일이 지정해야 하는 수고를 덜어 주기 때문입니다.
컴포넌트 하나에서 하는 것보다 각 기능을 담당하는 컴포넌트를 만들어서 하는 게 조금 더 실질적일 것 같아서 컴포넌트를 만들겠습니다. 아래 명령어를 사용하여 컴포넌트를 추기하고
ng g c components/comment
ng g c components/comment/comment-add
ng g c components/comment/comment-edit
경로를 지정합니다
// app-routing.module.ts
import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { CommentAddComponent } from './components/comment/comment-add/comment-add.component';
import { CommentEditComponent } from './components/comment/comment-edit/comment-edit.component';
import { CommentComponent } from './components/comment/comment.component';
const routes: Routes = [
{ path: 'comment-add', component: CommentAddComponent },
{ path: 'comment-edit/:id', component: CommentEditComponent },
{ path: '', component: CommentComponent },
];
@NgModule({
imports: [RouterModule.forRoot(routes)],
exports: [RouterModule],
})
export class AppRoutingModule {}
※ 요청할 서버
JSONPlaceholder - Free Fake REST API (typicode.com)
활용하기
1. GET
데이터를 불러오는 메서드로 서버에 대한 요청을 비동기 식으로 이루어지기 때문에 Observable을 활용하는 것이 편리합니다.
// comment.service.ts
import { HttpClient } from '@angular/common/http';
import { Injectable } from '@angular/core';
import { Observable, Subject } from 'rxjs';
import { Comment } from '../models/comment';
@Injectable({
providedIn: 'root'
})
export class CommentService {
URL = 'https://jsonplaceholder.typicode.com/comments/'
constructor(private http:HttpClient) { }
getComments():Observable<Comment[]> {
return this.http.get<Comment[]>(this.URL)
}
}
// comment.component.ts
import { Component, OnInit } from '@angular/core';
import { Comment } from 'src/app/models/comment';
import { CommentService } from 'src/app/services/comment.service';
@Component({
selector: 'app-comment',
templateUrl: './comment.component.html',
styleUrls: ['./comment.component.css'],
})
export class CommentComponent implements OnInit {
comments: Comment[] = [];
constructor(private commentService: CommentService) {}
ngOnInit(): void {
this.commentService.getComments().subscribe((comments) => {
this.comments = comments;
});
}
}
<!-- comment.component.html -->
<div class="container">
<div class="card" style="display: flex; flex-direction: column; justify-content: space-around; height: 150px; width: 600px; font-family: Arial, Helvetica, sans-serif; padding: 10px; background-color: antiquewhite; margin: 10px auto;" *ngFor="let i of comments">
<p>{{i.id}}</p>
<p>{{i.body}}</p>
<div>
<p>{{i.name}}</p>
<p>{{i.email}}</p>
</div>
</div>
</div>
2. POST
데이터를 추가하는 메서드입니다.
// comment.service.ts
import { HttpClient } from '@angular/common/http';
import { Injectable } from '@angular/core';
import { Observable, Subject } from 'rxjs';
import { Comment } from '../models/comment';
@Injectable({
providedIn: 'root',
})
export class CommentService {
URL = 'https://jsonplaceholder.typicode.com/comments/';
constructor(private http: HttpClient) {}
getComments(): Observable<Comment[]> {
return this.http.get<Comment[]>(this.URL);
}
addComment(body: string, name: string, email: string) {
const comment: Comment = {
body: body,
email: email,
name: name,
};
this.http.post(this.URL, comment).subscribe(result => {
console.log(result)
});
}
}
// Comment-add.component.ts
import { Component, OnInit } from '@angular/core';
import { CommentService } from 'src/app/services/comment.service';
@Component({
selector: 'app-comment-add',
templateUrl: './comment-add.component.html',
styleUrls: ['./comment-add.component.css'],
})
export class CommentAddComponent implements OnInit {
constructor(private commentService: CommentService) {}
ngOnInit(): void {}
onSubmit(name: string, email: string, body: string) {
this.commentService.addComment(body, email, name);
}
}
<!-- comment-add.component.html -->
<form (submit)="onSubmit(name.value, email.value, body.value)" style="padding: 20px;">
<input #name style="width: 100%; font-size: 1.4rem;" type="text" placeholder="name">
<input #email style="width: 100%; font-size: 1.4rem;" type="text" placeholder="email">
<textarea #body style="width: 100%; font-size: 1.4rem;" placeholder="content"></textarea>
<button>Submit</button>
</form>
3. DELETE
목록을 보여주는 컴포넌트로 가서 삭제 버튼을 추가합니다
<!-- comment.component.html -->
<a routerLink="/comment-add">Add</a>
<div class="container">
<div class="card"
style="display: flex; flex-direction: column; justify-content: space-around; height: 150px; width: 600px; font-family: Arial, Helvetica, sans-serif; padding: 10px; background-color: antiquewhite; margin: 10px auto;"
*ngFor="let i of comments">
<p>{{i.id}}</p>
<p>{{i.body}}</p>
<div>
<p>{{i.name}}</p>
<p>{{i.email}}</p>
</div>
<button (click)="onDelete(i.id)">Delete</button>
</div>
</div>
// comment.service.ts
import { HttpClient } from '@angular/common/http';
import { Injectable } from '@angular/core';
import { Observable, Subject } from 'rxjs';
import { Comment } from '../models/comment';
@Injectable({
providedIn: 'root',
})
export class CommentService {
URL = 'https://jsonplaceholder.typicode.com/comments/';
constructor(private http: HttpClient) {}
getComments(): Observable<Comment[]> {
return this.http.get<Comment[]>(this.URL);
}
addComment(body: string, name: string, email: string) {
const comment: Comment = {
body: body,
email: email,
name: name,
};
this.http.post(this.URL, comment).subscribe(result => {
console.log(result)
});
}
deleteComment(id:string) {
this.http.delete(this.URL + id).subscribe(result => {
console.log(result)
})
}
}
// comment.component.ts
import { Component, OnInit } from '@angular/core';
import { Comment } from 'src/app/models/comment';
import { CommentService } from 'src/app/services/comment.service';
@Component({
selector: 'app-comment',
templateUrl: './comment.component.html',
styleUrls: ['./comment.component.css'],
})
export class CommentComponent implements OnInit {
comments: Comment[] = [];
constructor(private commentService: CommentService) {}
ngOnInit(): void {
this.commentService.getComments().subscribe((comments) => {
this.comments = comments;
});
}
onDelete(id: string | undefined) {
this.commentService.deleteComment(id as string);
}
}
<!-- comment.component.html -->
<a routerLink="/comment-add">Add</a>
<div class="container">
<div class="card"
style="display: flex; flex-direction: column; justify-content: space-around; height: 150px; width: 600px; font-family: Arial, Helvetica, sans-serif; padding: 10px; background-color: antiquewhite; margin: 10px auto;"
*ngFor="let i of comments">
<p>{{i.id}}</p>
<p>{{i.body}}</p>
<div>
<p>{{i.name}}</p>
<p>{{i.email}}</p>
</div>
<button (click)="onDelete(i.id)">Delete</button>
<button>Edit</button>
</div>
</div>
4. PUT
데이터를 업데이트하는 메서드로 업데이트에 PUT과 FETCH를 사용가능합니다. 둘의 차이는 수정이 필요한 부분만 업데이트하는 FETCH와 달리 PUT은 모든 값을 새로운 값으로 대체한다는 점입니다.
목록을 보여주는 컴포넌트로 가서 편집버튼을 추가합니다. 이때 해당 아이템의 아이디를 경로에 포함해서 이동합니다.
<!-- comment.component.html -->
<a routerLink="/comment-add">Add</a>
<div class="container">
<div class="card"
style="display: flex; flex-direction: column; justify-content: space-around; height: 150px; width: 600px; font-family: Arial, Helvetica, sans-serif; padding: 10px; background-color: antiquewhite; margin: 10px auto;"
*ngFor="let i of comments">
<p>{{i.id}}</p>
<p>{{i.body}}</p>
<div>
<p>{{i.name}}</p>
<p>{{i.email}}</p>
</div>
<button (click)="onDelete(i.id)">Delete</button>
<button>
<a [routerLink]="['/comment-edit', i.id]">
Edit
</a>
</button>
</div>
</div>
PUT 메서드와 더불어 개별 아이템을 가져오는 GET메서드도 추가합니다(편집 페이지에서 기존 데이터를 보여주기 위해 사용).
// comment.service.ts
import { HttpClient } from '@angular/common/http';
import { Injectable } from '@angular/core';
import { Observable, Subject } from 'rxjs';
import { Comment } from '../models/comment';
@Injectable({
providedIn: 'root',
})
export class CommentService {
URL = 'https://jsonplaceholder.typicode.com/comments/';
constructor(private http: HttpClient) {}
getComments(): Observable<Comment[]> {
return this.http.get<Comment[]>(this.URL);
}
addComment(body: string, name: string, email: string) {
const comment: Comment = {
body: body,
email: email,
name: name,
};
this.http.post(this.URL, comment).subscribe(result => {
console.log(result)
});
}
deleteComment(id:string) {
this.http.delete(this.URL + id).subscribe(result => {
console.log(result)
})
}
getComment(id:string):Observable<Comment> {
return this.http.get<Comment>(this.URL + id)
}
editComment(id:string, body: string, name: string, email: string) {
const comment: Comment = {
body: body,
email: email,
name: name,
};
this.http.put(this.URL + id, comment).subscribe(result => {
console.log(result)
})
}
}
Edit 컴포넌트 클래스에서 ActivatedRoute 모듈을 활용하여 전송된 아이디를 수집하고 이를 활용하여 개별 아이템을 가져와
// component-edit.component.ts
import { Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
import { Comment } from 'src/app/models/comment';
import { CommentService } from 'src/app/services/comment.service';
@Component({
selector: 'app-comment-edit',
templateUrl: './comment-edit.component.html',
styleUrls: ['./comment-edit.component.css'],
})
export class CommentEditComponent implements OnInit {
id!: string;
comment!: Comment;
constructor(
private commentService: CommentService,
private activatedRoute: ActivatedRoute
) {}
ngOnInit(): void {
this.id = this.activatedRoute.snapshot.params['id'];
this.commentService.getComment(this.id).subscribe((comment) => {
this.comment = {
name: comment.name,
body: comment.body,
email: comment.email,
};
});
}
onSubmit(name: string, email: string, body: string) {
this.commentService.editComment(this.id, body, email, name);
}
}
템플릿과 연결하면
<!-- comment-add.component.html -->
<form (submit)="onSubmit(name.value, email.value, body.value)" style="padding: 20px;">
<input #name style="width: 100%; font-size: 1.4rem;" type="text" placeholder="name" [value]="comment.name">
<input #email style="width: 100%; font-size: 1.4rem;" type="text" placeholder="email" [value]="comment.email">
<textarea #body style="width: 100%; font-size: 1.4rem;" placeholder="content" [value]="comment.body"></textarea>
<button>Submit</button>
</form>
아래와 같이 기존 아이템 정보가 표시됩니다.
마지막으로 정보를 입력하고 전송하면 아래와 같이 업데이트가 된 것을 확인가능합니다 (개발자 도구 네트워크 탭)
이상으로 앵귤러 http를 활용해 보았습니다.
폼 업데이트하기 (템플릿 폼)
소스코드
https://github.com/jin-co/web-mobile/tree/master/Angular/cheat-sheet/http
참고
'프론트엔드 > 앵귤러' 카테고리의 다른 글
앵귤러 라이브러리 - Angular PWA (0) | 2022.12.22 |
---|---|
앵귤러 라이브러리 - Angular Animations (0) | 2022.12.22 |
앵귤러 라이브러리 - Angular Forms (0) | 2022.12.22 |
앵귤러 라이브러리 - Angular Router (0) | 2022.12.22 |
앵귤러 라이브러리 (0) | 2022.12.21 |