Queue์ผ๋ก ์์ ์คํ
๐ Task ๋ฅผ Queue๋ฅผ ์ด์ฉํ์ฌ ์์ ์ฒ๋ฆฌ ํ๊ธฐ
ํ์ฌ์์ ์์ ์ ํ๋ ๋์ค ํด๋น์๊ฐ์ด ๋๋ฉด Queue์ ๋ด๊ธด ์์๋๋ก ์์ ์ ์ฒ๋ฆฌํด์ผ ํ๋ ๊ฒฝ์ฐ๊ฐ ๋ฐ์ํ์๋ค.
๋ก์ง์ ์๋์ ๊ฐ๋ค
- A์์ ์คํ
- ํน์ ์๊ฐ์ด ๋๋ฉด B ์์ ์์
- B์์์ด ๋๋๋ฉด C์์ ์์
- C์์ ๋๋๋ฉด D์์ ์์
- D์์ ๋๋๋ฉด ๋ค์ A์์ ์์
๋จ 2~4๋ A์์์ด ์์๊ฑฐ๊ฐ ๋์ด์ผ ํ๋ค
๐คฟ TaskQueue ํด๋์ค ์์ฑ
class TaskQueue {
constructor() {
this.queue = [];
this.isRunning = false;
}
add(task) {
this.queue.push(task);
this.runNext();
}
isLast() {
return this.queue.length === 0;
}
async runNext() {
if (this.isRunning || this.queue.length === 0) return;
this.isRunning = true;
const task = this.queue.shift();
if (task) {
try {
await task();
} catch (error) {
console.error('์์
์คํ ์ค ์๋ฌ:', error);
}
}
this.isRunning = false;
this.runNext();
}
}
export const taskQueue = new TaskQueue();
add ํจ์ : Queue์ ์์ ์ ๋ฃ๋ ํจ์์ด๋ฉฐ, ์์ ์ ๋ฃ๋ ์๊ฐ runNext ํจ์๋ฅผ ์คํํ๋ค
runNext ํจ์ : ํ์ฌ ๋งจ ์์ ์๋ task๋ฅผ ์ถ์ถํ์ฌ, task๋ฅผ ์คํํ๊ณ ๋ค์ ์คํํ task๊ฐ ์์ผ๋ฉด ์คํํ๊ณ ์๋๋ฉด ์ข ๋ฃํ๋ค
โฝ๏ธ TaskQueue๋ฅผ ์ด์ฉํ์ฌ ์์ ๋ด๊ธฐ
taskQueue์ ์์ ์ ๋ค์๊ณผ ๊ฐ๋ค
- FadeOut
- B์์ ์์(B์์์ด ๋๋๋ฉด C,D์์์ด ์์๋๋ค)
TaskQueue์ addํจ์์ ๋ด๊ธฐ
์ฒซ๋ฒ์งธ๋ก TaskQueue์ fadeOut, playVideo ํจ์๋ฅผ ์์ฐจ์ ์ผ๋ก ์คํ์ํจ๋ค
import { taskQueue } from './utils/taskQueue';
// ๊ฐ์ง API
dummyVideoList().then(res => {
if (Array.isArray(res)) {
res.forEach((item, index) => {
const { id, url } = item;
/* Task Add๋ฅผ ํตํ์ฌ ํจ์ ๋ด๊ธฐ */
taskQueue.add(async () => {
await fadeOut(this.$refs.streamingvideo, 5000);
await this.playVideo(url);
});
});
}
});
TaskQueue์ add ํจ์์ ๋ด๊ธฐ๋ฉด, runNext ์คํ
addํจ์์ ๋ด๊ธฐ๋ฉด, runNext์์ queue์ ๋งจ์์ ์์ ์ ์ถ์ถํ์ฌ ์คํํ๋ค
add(task) {
this.queue.push(task);
this.runNext();
}
/* TaskQueue ํด๋์ค์ runNext ํจ์ */
async runNext() {
if (this.isRunning || this.queue.length === 0) return;
this.isRunning = true;
/*
queue์ ๋งจ์ ์์
์ ์ถ์ถํ๋ค.
์ถ์ถํ๋ ํจ์๋ ์๋์ ๊ฐ๋ค
async () => {
await fadeOut(this.$refs.streamingvideo, 5000);
await this.playVideo(url);
}
*/
const task = this.queue.shift();
if (task) {
try {
await task();
} catch (error) {
console.error('์์
์คํ ์ค ์๋ฌ:', error);
}
}
this.isRunning = false;
this.runNext();
}
playVideo๋ฅผ ์คํ์ํจํ ๋ค์ Task๋ฅผ ์ด๋ป๊ฒ ํธ๋ฆฌ๊ฑฐ์ํฌ๊ฒ์ธ๊ฐ
์ฌ๊ธฐ์ playVideo์ ํจ์์ ๋ํ ์ค๋ช ์ ์ ์ง ์์๋๋ฐ, playVideo๊ฐ์ ๊ฒฝ์ฐ video ํ๊ทธ์ url์ ์ธํ ํ๊ณ video playํจ์๋ฅผ ์คํํ๋ค.
์ฌ๊ธฐ์ playVideo๊ฐ Promise๋ก ๊ด๋ฆฌ๋์ด ์๋ค. Promise์์๋ resolveํจ์๋ฅผ ํธ์ถํ์ฌ Promise๊ฐ ์ข ๋ฃ๊ฐ ๋๋ค
๊ทธ๋ฆฌํ์ฌ resolve๋ฅผ ์ธ๋ถ ๋ณ์์ธ this.currentResolve์ ๋ด๋๋ค
playVideo(src) {
return new Promise(resolve => {
const video = this.$refs.videoPlayer;
// resolve ํจ์ ๋ด๊ธฐ
this.currentResolve = resolve;
video.src = src;
video.load();
video.play();
});
},
๊ทธ๋ฆฌ๊ณ ๋น๋์ค endEvent์์ ์ธ๋ถ๋ณ์์ธ currentResolve๋ฅผ ํธ์ถํ๋ค
onVideoEnded() {
if (this.currentResolve) {
this.currentResolve(); // ํ์ฌ ๋น๋์ค ๋๋๋ฉด ํ ๋ค์ ์์
์คํ
this.currentResolve = null;
if (taskQueue.isLast()) {
fadeIn(this.$refs.streamingvideo, 5000, 1);
}
}
},
๋น๋์ค endEvent์์ ์ธ๋ถ๋ณ์์ธ currentResolve๋ฅผ ์คํ์ํค๋ฉด
1. fadeOut ํจ์ ์คํ
2. playVideo ํจ์ ์คํ, ์ฌ๊ธฐ์ resolve๋ฅผ ์ธ๋ถ ๋ณ์์ธ currentResolve์ ๋ด๊ธฐ
3. video EndEvent์์ currentResolve ํจ์ ์คํ
4. taskํจ์๊ฐ ์ข ๋ฃ๋๋ฉฐ, ๋ค์ ์ค ์คํ(๋ค์ task๊ฐ ์์ผ๋ฉด 1~3๋ฐ๋ณต)
add(task) {
this.queue.push(task);
this.runNext();
}
/* TaskQueue ํด๋์ค์ runNext ํจ์ */
async runNext() {
if (this.isRunning || this.queue.length === 0) return;
this.isRunning = true;
const task = this.queue.shift();
if (task) {
try {
/*
1. fadeOut ์คํ
2. playVideo ์คํ
3. video endevent์์ playVideo์ resolveํจ์ ์คํ
async () => {
await fadeOut(this.$refs.streamingvideo, 5000);
await this.playVideo(url);
}
*/
await task();
} catch (error) {
console.error('์์
์คํ ์ค ์๋ฌ:', error);
}
}
// 4. ๋ค์ ์ค ์คํ
this.isRunning = false;
this.runNext();
}
ํ๊ธฐ
์์๊ฐ์ด Task๋ฅผ Queue๋ก ์์ ํ์๋๋ฐ, ๋ค๋ง ์ธ๋ถ๋ณ์๋ฅผ ๊ด๋ฆฌํด์ผํ๋ ์ฝ๊ฐ์ ๋ฌธ์ ๊ฐ ์์ง๋ง,
Queue๋ฅผ ์ด์ฉํ๋ ๋์๋ค๋ฐ์ Task๊ฐ ์์ ์ด ๋ฐ์ํ ๋, ๊ด๋ฆฌ๊ฐ ์ฉ์ดํ๋ค