> For the complete documentation index, see [llms.txt](https://docs.decentraland.org/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.decentraland.org/creator/content-creator-ko/sdk7/programming-patterns/async-functions.md).

# 비동기 함수

씬 코드에서 비동기 함수를 언제 어떻게 실행하는지 알아보세요.

## 개요

장면의 대부분의 코드는 단일 스레드를 사용해 동기적으로 실행됩니다. 즉, 명령은 한 줄씩 순차적으로 실행됩니다. 각 명령은 시작할 수 있기 전에 먼저 이전 명령의 실행이 끝날 때까지 기다려야 합니다.

장면의 시스템에 있는 함수들도 다음을 따라 하나씩 실행됩니다 [우선순위 순서](/creator/content-creator-ko/sdk7/architecture/systems.md#system-execution-order).

코드를 동기적으로 실행하면 일관성이 보장됩니다. 코드의 명령이 어떤 순서로 실행되는지 항상 알 수 있기 때문입니다.

반면에 장면은 다음 프레임을 만들기 위해 초당 여러 번 업데이트되어야 합니다. 코드의 일부가 응답하는 데 너무 오래 걸리면 메인 스레드 전체가 멈추게 되고, 그 결과 프레임 속도가 느려집니다.

그래서 어떤 경우에는 일부 명령을 비동기적으로 실행하고 싶을 때가 있습니다. 즉, 작업을 시작해 두고 그동안 장면은 다음 코드 줄들을 계속 실행할 수 있습니다. 장면은 여전히 모든 것을 단일 스레드에서 실행하지만, 비동기 작업이 응답을 기다리는 동안 나머지 코드는 차단되지 않습니다.

이는 응답하는 데 시간이 걸릴 수 있는 외부 서비스에 의존하는 작업에 특히 유용합니다. 그 응답을 기다리는 유휴 시간이 다른 작업을 막지 않도록 하고 싶기 때문입니다.

예를 들면:

* REST API에서 데이터를 가져올 때
* 블록체인에서 거래를 수행할 때

{% hint style="warning" %}
**📔 참고**: 작업이 끝나기 전에 장면의 여러 프레임이 렌더링될 수 있다는 점을 기억하세요. 비동기 작업이 완료되는 동안 중간 상황을 처리할 수 있도록 장면의 코드가 충분히 유연한지 확인하세요.
{% endhint %}

## 비동기 함수 실행

모든 함수를 `async` 로 표시하면 비동기적으로 실행되어, 기다리는 동안 장면의 나머지 코드를 차단하지 않습니다.

```ts
// 비동기 함수 선언
async function myAsyncTask() {
	// 함수의 단계 실행
}

// 비동기 함수 호출
myAsyncTask()

// 나머지 코드는 계속 실행됨
```

## executeTask 함수

그 `executeTask()` 함수는 람다 함수를 비동기적으로 실행합니다. `executeTask()` 함수를 선언하고 실행하는 것을 하나의 동일한 문장에 모두 담을 수 있게 해줍니다.

```ts
executeTask(async () => {
	let data = await myAsyncTask()
	console.log(data)
})

// 나머지 코드는 계속 실행됨
```

## then 함수

그 `then` 함수는 인수로 람다 함수를 받으며, 이전 문장이 끝난 뒤에만 실행됩니다. 이 람다 함수는 선택적으로 이전 문장이 반환하는 값에 매핑된 입력을 가질 수 있습니다.

```ts
myAsyncTask().then((data) => {
	console.log(data)
})
```

{% hint style="warning" %}
**📔 참고**: 일반적으로 다음을 사용하는 것이 더 좋습니다 `executeTask` 방식이 `then` then `then` 함수보다 낫습니다. then 함수를 여러 중첩된 수준에서 너무 많이 의존하면, "callback hell"이라고 불리는 상황에 빠질 수 있으며, 코드가 읽고 유지보수하기 매우 어려워질 수 있습니다.
{% endhint %}

## PointerEvents 및 RayCast 함수

장면이 `PointerEvent` 또는 `RayCast` 컴포넌트를 사용할 때, 충돌 계산은 엔진에서 비동기적으로 수행됩니다. 그런 다음 엔진은 장면에 결과 이벤트를 반환하는데, 이는 이벤트가 호출된 시점보다 게임 루프의 한 번 또는 여러 번의 틱 뒤에 도착할 수 있습니다.

그다음에는 이러한 결과가 도착한 프레임에서 이를 처리할 시스템을 만들어야 합니다.

{% hint style="warning" %}
**📔 참고**: 다음 방식으로 클릭을 처리한다면 [**콜백 등록**](/creator/content-creator-ko/sdk7/interactivity/button-events/register-callback.md) 방식, 이를 처리하기 위해 시스템을 명시적으로 만들 필요는 없지만, 백그라운드에서는 같은 일이 일어납니다.
{% endhint %}

참고 [클릭 이벤트](/creator/content-creator-ko/sdk7/interactivity/button-events/click-events.md) 및 [레이캐스팅](/creator/content-creator-ko/sdk7/interactivity/raycasting.md).

{% hint style="info" %}
**💡 팁**: 레이캐스트 결과를 처리하는 데 많은 계산이 필요하다면(예: 경로 탐색 알고리즘 실행) 그 계산을 비동기 함수에서 실행하고 싶을 수 있습니다.
{% endhint %}

## await 문

다음은 `await` 문은 다음 코드 줄로 넘어가기 전에 응답을 기다리도록 실행을 강제합니다. `await` 문은 비동기 코드 블록 안에서만 사용할 수 있습니다.

```ts
// 함수 선언
async function myAsyncTask() {
	try {
		let response = await fetch(callUrl)
		let json = await response.json()
		console.log(json)
	} catch {
		console.log('URL에 도달하지 못했습니다')
	}
}

// 함수 호출
myAsyncTask()

// 나머지 코드는 계속 실행됨
```

위 예제는 다음을 포함하는 함수를 실행합니다 `fetch()` 외부 API에서 데이터를 가져오는 작업입니다. 이 `fetch()` 작업은 비동기적입니다. 서버가 응답하는 데 얼마나 걸릴지 예측할 수 없기 때문입니다. 그러나 다음 줄은 이를 JSON으로 파싱하기 전에 이 작업의 출력이 준비되어 있어야 합니다. 이 `await` 문장은 해당 작업이 값을 반환한 뒤에만 다음 줄이 실행되도록 보장합니다. 마찬가지로, `response.json()` 함수도 비동기적이지만, 다음 줄은 이를 로그로 출력하기 전에 JSON이 파싱되어 있어야 합니다. 두 번째 `await` 문장은 JSON 파싱이 끝난 뒤에만 다음 줄이 호출되도록 강제하며, 시간이 얼마나 걸리든 상관없습니다.

## 함수 호출에 타임아웃 설정하기

사용: `setTimeout` 을 사용하면 특정 코드 줄이 실행되기 전에 일정 시간을 기다릴 수 있습니다. 이는 두 개의 인수를 받습니다:

* 실행할 함수
* 해당 함수를 실행하기 전에 기다릴 밀리초 수

아래 예제는 콘솔에 메시지를 출력하는 간단한 함수를 실행하기 전에 1000밀리초(1초) 동안 기다립니다.

```ts
import { timers } from '@dcl/sdk/ecs'

console.log('이것은 바로 출력됩니다')

timers.setTimeout(() => {
	// 지연 후 실행할 함수
    console.log('이것은 1초 후에 출력됩니다')
}, 1000)
```

그 `clearTimeout` 은 아직 실행을 기다리고 있는 `setTimeout` 함수의 실행을 취소하는 데 사용할 수 있습니다. `setTimeout` 는 타이머 ID(숫자)를 반환하며, 이를 나중에 다음에 전달할 수 있습니다 `clearTimeout`. 이 경우 변수 `timeoutId` 는 다음을 수행할 때 얻어집니다: `setTimeout`, 그런 다음 다음에 전달됩니다 `clearTimeout` 이를 취소하기 위해

```ts
import { timers } from '@dcl/sdk/ecs'

const timeoutId = timers.setTimeout(() => {
    console.log('이 함수를 실행하기까지 1초 기다리세요')
}, 1000)

timers.clearTimeout(timeoutId)
```


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.decentraland.org/creator/content-creator-ko/sdk7/programming-patterns/async-functions.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
