[javascript] fetch와 async/await의 활용
자바스크립트(javascript)에서 콜백 대안이라고 프로미스(promise) 내놨을 때는 뭐 하는 짓인가 싶었는데....
다른 언어들처럼 어싱크/어웨이크(async/await)가 생기면서 이제야 좀 비동기 관리가 편해졌네요 ㅎㅎㅎ
테스트 한번 해봅시다.
1. 패치(fetch)
기존의 XMLHttpRequest대신 패치(fetch)를 사용하는 것이 좋습니다.
패치(fetch)로 네트워크 통신을 하면 프로미스(promise)처리가 가능한 리스폰스가 리턴됩니다.
(MDN - Fetch API, Using Fetch, XMLHttpRequest )
예>
fetch('http://example.com/movies.json')
.then(response => response.json())
.then(data => console.log(data));
2. 어싱크/어웨이크(async/await)
어싱크/어웨이크(async/await)는 함수 자체를 비동기/동기로 선택하여 사용할 수 있도록 하는 키워드입니다.
함수를 어싱크(async)로 선언하면 비동기 함수가 됩니다.
이 어싱크로 선언된 함수를 어웨이크(await)로 호출하면 동기 함수로 사용하게 됩니다.
(MDN - async function , await )
예>
async function AsyncTest()
{
console.log(new Date());
}
AsyncTest();
await AsyncTest();
AsyncTest();
테스트 만들기
테스트할 내용은 어웨이크가 제대로 작동하는지을 알아볼 겁니다.
이러면 같은 함수를 한쪽은 어웨이크로 호출하고
다른 한쪽은 그냥 호출하여 타이밍이 어떻게 되는지를 확인하면 됩니다.
아래 코드를 실행해 봅시다.
let LogCount = 0;
async function Call(bAwait)
{
let nCount = ++LogCount;
console.log("start(" + nCount + "), bAwait(" + bAwait + ") : " + new Date());
if (true === bAwait)
{
await AsyncTest(bAwait, nCount);
}
else if (false === bAwait)
{
AsyncTest(bAwait, nCount);
}
console.log("end(" + nCount + "), bAwait(" + bAwait + ") : " + new Date());
}
async function AsyncTest(bAwait, nCount)
{
sleep(3000);
console.log("run(" + nCount + "), bAwait(" + bAwait + ") : " + new Date());
}
function sleep(ms)
{
return new Promise(resolve => setTimeout(resolve, ms));
}
테스트하면 어웨이크가 잘 작동하는 것을 알 수 있습니다.
3. 패치(fetch)에 어웨이크(await) 사용하기
API서버를 만들어서 패치로 호출해봅시다.
저는 ASP.NET Core 서버를 만들었습니다.
[Route("api/[controller]/[action]")]
[ApiController]
public class TestController : ControllerBase
{
/// <summary>
/// 지정된 시간 만큼 대기했다가 결과가 전달 된다.
/// </summary>
/// <param name="nDelay">대기할 시간(ms)</param>
/// <returns></returns>
[HttpGet]
public ActionResult<TestModel02> Delay(int nDelay)
{
Thread.Sleep(nDelay);
//리턴용 모델
TestModel02 tmResult = new TestModel02();
tmResult.nTest001 = 3;
tmResult.sTest002 = "Delay : " + nDelay;
return tmResult;
}
/// <summary>
///
/// </summary>
/// <param name="nDelay">대기할 시간(ms)</param>
/// <returns></returns>
[HttpPost]
public ActionResult<TestModel02> DelayPost([FromForm] int nDelay)
{
Thread.Sleep(nDelay);
//리턴용 모델
TestModel02 tmResult = new TestModel02();
tmResult.nTest001 = 3;
tmResult.sTest002 = "Delay : " + nDelay;
return tmResult;
}
}
테스트해 봅시다.
마무리
테스트 프로젝트 : dang-gun/DotNetSamples/JsFetchApiTest/
자바스크립트가 다른 언어의 기능을 넣으면서 예상과 다르게 동작하는 경우가 있어서 테스트를 한번 해봤습니다.
잘 동작하네요.