axios를 이용한 API 호출
설치
npm i axios --save
실행
// Terminal
jskim@DESKTOP-SI6DJ17 MINGW64 /d/dev/study/vue-advanced/vue-news (master)
$ npm i axios --save
구현
1. src/api/index.js
생성
import axios from 'axios';
// 1. HTTP Request & Response와 관련된 기본 설정
const config = {
baseUrl: "https://api.hnpwa.com/v0/",
};
// 2. API 함수들을 정리
function fetchNewsList() {
// ES6 문법
// 문자열 중간에 변수 대입하기
// `${변수명}나머지 문자열`
// 기존 변수명 + 문자열 과 동일
return axios.get(`${config.baseUrl}news/1.json`);
}
function fetchAskList() {
return axios.get(`${config.baseUrl}ask/1.json`);
}
function fetchJobsList() {
return axios.get(`${config.baseUrl}jobs/1.json`);
}
// 3. 다른 곳에서 사용하기 위해 export
export {
fetchNewsList
, fetchAskList
, fetchJobsList
}
2. NewsView.vue
, AskView.vue
, JobsView.vue
에 index.js
import 및 API 함수 사용
<!-- NewsView.vue -->
<template>
<div>
<div v-for="user in users">{{ user.title }}</div>
</div>
</template>
<script>
import { fetchNewsList } from "../api/index.js";
export default {
data() {
return {
users: [],
};
},
created() {
var vm = this;
fetchNewsList()
.then(function (response) {
vm.users = response.data;
})
.catch(function (error) {
console.log(error);
});
},
};
</script>
<!-- AskView.vue -->
<template>
<div>
<div v-for="item in ask">{{ item.title }}</div>
</div>
</template>
<script>
import { fetchAskList } from "../api/index.js";
export default {
data() {
return {
ask: [],
};
},
created() {
var vm = this;
fetchAskList()
.then(function (response) {
vm.ask = response.data;
})
.catch(function (error) {
console.log(error);
});
},
};
</script>
<!-- JobsView.vue -->
<template>
<div>
<div v-for="job in jobs">{{ job.title }}</div>
</div>
</template>
<script>
import { fetchJobsList } from "../api/index.js";
export default {
data() {
return {
jobs: [],
};
},
created() {
fetchJobsList()
.then(response => this.jobs = response.data)
.catch(error => console.log(error));
},
};
</script>
this
함수의 실행 컨텍스트(함수가 실행될 때의 컨텍스트)를 가리키는 예약어
상황에 따른 this
다른 언어와는 다르게 자바스크립트의 this
는 상황에 따라 가리키는 값이 다르다.
첫번째 상황 this
console.log(this); // window 객체를 가리킨다.
가장 기본적인 컨텍스트로 글로벌(전역) 컨텍스트이다. 여기서 window
는 자바스크립트의 최상위 객체를 말한다.
두번째 상황 this
var obj = {
num: 10,
printNum: function() {
console.log(this.num);
}
};
obj.printNum(); // 10이 출력된다.
객체 속성 함수 안에서의 this
는 기본적으로 해당 객체를 가리킨다.
세번째 상황 this
function showComment() {
console.log(this);
}
showComment(); // window 객체를 가리킨다.
함수 선언문의 경우 실행시키면 window
객체를 가리키는 것을 알 수 있다. 따라서 일반 함수의 this
는 전역 컨텍스트임을 알 수 있다.
function Developer() {
console.log(this);
}
var dev = new Developer(); // Developer {} 가 출력된다.
생성자 함수의 경우 실행시키면 Developer {}
가 출력된다. 왜냐하면 new
로 인스턴스를 생성하는 순간 함수가 실행되기 때문에 결론적으로 생성자 함수의 this
는 함수의 내부를 가리킨다.
※ 자바스크립트는 프로토타입 기반 언어이기 때문에 클래스 없이 함수를 이용하여 인스턴스를 생성할 수 있다.
네번째 상황 this
function fetchData() {
axios.get('domain.com/products')
.then(function() {
console.log(this);
});
}
fetchData(); // window 객체를 가리킨다.
웹 개발 시 많이 마주하는 this
상황으로 데이터를 받아올 때 사용하는 HTTP 요청과 같은 비동기 처리 코드이다.
비동기 처리 코드의 콜백 함수를 실행시키면 window
객체를 가리키는 것을 알 수 있다. 따라서 비동기 처리 코드의 콜백 함수는 전역 컨텍스트를 가리키는 것을 알 수 있다.
자바스크립트 비동기 처리
Callback
함수 안에서 어떤 특정한 시점에 호출되는 함수. 보통 콜백 함수는 함수의 매개변수로 전달하여 특정 시점에서 콜백 함수를 호출하도록 한다.
예제
1. 익명 함수를 콜백 함수로 사용
// sum 함수 정의
function sum(a, b, callback) {
var sum = a + b;
callback(sum);
}
// sum 함수 호출 시 익명 함수를 콜백 함수로 사용
sum(1, 2, function(rst) {
console.log(rst);
});
// 결과
3
2. 정의된 함수를 콜백 함수로 사용
// sum 함수 정의
function sum(a, b, callback) {
var sum = a + b;
callback(sum);
}
// 콜백 함수 정의
function print(rst) {
console.log(rst);
}
// sum 함수 호출
sum(1, 2, print);
// 결과
3
콜백 함수 사용 이유
예제 코드를 보았을 때 콜백 함수를 사용하지 않고 순차적으로 호출하여 사용해도 같은 결과를 나타내기 때문에 굳이 콜백 함수의 필요성을 느끼기 어렵다.
그렇다면 예제를 순차적 처리로 구현하여 sum 함수
의 리턴값을 print 함수
의 매개변수로 전달한다고 할 때 sum 함수
가 복잡한 로직으로 되어있어 시간이 오래 걸릴 경우 print 함수
는 sum 함수
의 동작이 끝나야 동작을 하기 때문에 print 함수
의 동작이 지연되면서 다른 자바스크립트의 동작들을 할 수 없게 된다.
따라서 비동기 처리의 콜백 함수를 사용하여 동작이 끝날때 까지 기다리는 것이 아니라 종료되는 시점에 호출을 함으로써 효율성이 높고 여러 다른 동작을 할 수 있게 한다.
콜백 함수 사용의 문제점
- 콜백 지옥(Callback Hell)
- Code Indenting(코드 정렬)
- 절차적 사고의 위배
Promise
비동기 작업이 맞이할 미래의 완료 또는 실패와 그 결과 값
상태
- 대기(
pending
) : 이행하거나 거부되지 않은 초기 상태 - 이행(
fulfilled
) : 연산이 성공적으로 완료됨 - 거부(
rejected
) : 연산이 실패함
예제
function callAjax() {
// Promise 객체 리턴
return new Promise(function(resolve, reject) {
$.ajax({
url: 'https://api.hnpwa.com/v0/news/1.json',
success: function(data) {
// resolve() : 주어진 값으로 이행하는 Promise 객체 반환
// reject() : 주어진 이유로 거부하는 Promise 객체 반환
resolve(data);
}
});
});
}
function fetchData() {
var result = [];
callAjax()
// then() : Promise가 성공적으로 이뤄진 후 다음 작업 진행
.then(function(data) {
console.log('데이터 호출 결과', data);
result = data;
})
// catch() : 에러 및 예외상황 발생으로 이뤄진 작업 진행
.catch(function(error) {
console.log(error);
}); // 추가적인 체이닝 가능 (.then().catch()....)
}
참고
developer.mozilla.org/ko/docs/Web/JavaScript/Reference/Global_Objects/Promise
'Dev > Vue.js' 카테고리의 다른 글
[Vue.js] Hacker News - 라우터 실전 (0) | 2020.09.21 |
---|---|
[Vue.js] Hacker News - 스토어 구현 (0) | 2020.09.18 |
[Vue.js] Hacker News - 라우터 기본 (0) | 2020.09.17 |
[Vue.js] Hacker News - 소개 및 프로젝트 설정 (0) | 2020.09.17 |
[Vue.js] Todo App 최종 리팩토링 (0) | 2020.09.14 |
댓글