프로그래밍에서 콜백 또는 콜애프터 함수는 다른 코드의 인수로서 넘겨주는 실행 가능한 코드를 말한다. 콜백을 넘겨받는 코드는 이 콜백을 필요에 따라 즉시 실행할 수도 있고, 아니면 나중에 실행할 수도 있다. (위키백과)
앞서 공부했듯이 자바스트립트는 호이스팅 이후 코드가 나타는대로 동기적으로 실행된다
동기적과 비동기적에 대해 간단하게 설명하자면
동기적은 작업이 요청되면 끝나고나서 바로 실행하는 것이고
비동기적은 작업이 요청되면 그 작업이 끝나지 않았지만 다른 작업을 수행하다가
요청했던 작업이 완료되면 작업을 수행하는 것이다.
먼저 콜백함수를 동기적으로 처리하는 코드를 보자
function printImmediately(print) {
print();
}
printImmediately(()=> console.log('hello'));
이 코드를 보면
printImmediately 함수에 인자로 console.log('hello') 작업을
처리하는 함수를 콜백함수로 넘겨주었다.
이때 printImmediately 함수는 입력받은 콜백함수를 바로 실행하므로
동기적으로 실행된다.
이번에는 콜백함수를 비동기적으로 처리하는 코드를 보자
console.log('1');
setTimeout{() => {
console.log('2');
},1000);// 지정한 시간(m second)이 지나면 콜백함수를 실행하는 함수
console.log('3');
위 코드를 실행하면
1 -> 3 -> 2 형태로 출력이 된다.
그 이유는 setTimeout 이라는 함수가
입력받은 시간이 지난 후에 입력받은 함수를 수행하는 방식인데
여기서 () => {console.log('2')} 가 전달받은 콜백함수이다.
이때 setTimeout은 지정한 시간이 지나면 콜백함수를
실행하는 함수이므로 비동기적 함수이다.
콜백함수를 이런식으로 동기적, 비동기적 처리하도록 사용할 수 있는데
이 콜백함수를 사용할 때 가장 주의해야할 것이 바로
콜백지옥에 빠지지 않는 것이다.
콜백지옥 함수의 예제를 한번 살펴보자.
// Callback Hell example
class UserStroage {
// api1
loginUser(id, password, onSuccess, onError) {
// backend 대신 settimeout 사용해보자
setTimeout(() => {
if (
(id === 'ellie' && password === 'dream') ||
(id === 'coder' && password === 'academy')
) {
onSuccess(id);
} else {
onEroor(new Error('not found'));
}
},2000);
}
//api2
getRoles(user, onSuccess, onError) {
setTimeout(() => {
if (user === 'ellie') {
onSuccess({ name: 'ellie', role: 'admin'});
} else {
onError(new Error('no access'));
}
}, 1000);
}
}
// id password 입력받고 role을 출력해보자
const userStroage = new UserStroage();
const id = prompt('enter your id');
const password = prompt('enter your password');
userStroage.loginUser(id,
password,
user => {
userStroage.getRoles(user, (userwithRole) => {
alert(`Hello ${userwithRole.name}, you hava a ${userwithRole.role} role`);
},
error => {
console.log(error);
})
},
error => {
console.log(error);
}
);
위 코드는 userStroage라는 인스턴스를 만들어서
id와 passward를 입력받고 userStroage.loginUser에 대한 콜백함수를 전달하고 그 콜백함수를 수행했을 때 또 다른 콜백함수를 연결하는 방식으로
코드를 전개한다.
이렇게 콜백함수를 겹쳐서 작성할 경우 이해하기 어렵고,
가독성이 매우 떨어지는 단점이 생기게 된다.