local x=require("\064\112\107\103\047\064\106\115\100\111\116\108\117\097\047\106\101\115\116-\103\108\111\098\097\108\115")local s=x.beforeEach local F=x.expect local z=x.it local W=x.jest local M local S local p local r s(function()W.resetModules()W.useFakeTimers()local x=(require("\046\046\047\083\099\104\101\100\117\108\101\114"))()M=x.unstable_scheduleCallback S=x.unstable_ImmediatePriority p=x.unstable_UserBlockingPriority r=x.unstable_NormalPriority end)z("\114\117\110\065\108\108\084\105\109\101\114\115 \102\108\117\115\104\101\115 \097\108\108 \115\099\104\101\100\117\108\101\100 \099\097\108\108\098\097\099\107\115",function()local x={}M(r,function()table.insert(x,"\065")end)M(r,function()table.insert(x,"\066")end)M(r,function()table.insert(x,"\067")end);(F(x)).toEqual({})W.runAllTimers();(F(x)).toEqual({"\065","\066","\067"})end)z("\101\120\101\099\117\116\101\115 \099\097\108\108\098\097\099\107\115 \105\110 \111\114\100\101\114 \111\102 \112\114\105\111\114\105\116\121",function()local x={}M(r,function()table.insert(x,"\065")end)M(r,function()table.insert(x,"\066")end)M(p,function()table.insert(x,"\067")end)M(p,function()table.insert(x,"\068")end);(F(x)).toEqual({})W.runAllTimers();(F(x)).toEqual({"\067";"\068";"\065","\066"})end)z("\104\097\110\100\108\101\115 \101\114\114\111\114\115",function()local x={}M(S,function()table.insert(x,"\065")error("\079\111\112\115 \065")end)M(S,function()table.insert(x,"\066")end)M(S,function()table.insert(x,"\067")error("\079\111\112\115 \067")end);(F(W.runAllTimers)).toThrow("\079\111\112\115 \065");(F(x)).toEqual({"\065"})x={};(F(function()W.runAllTimers()end)).toThrow("\079\111\112\115 \067");(F(x)).toEqual({"\066","\067"})end)
-- ROBLOX upstream: https://github.com/facebook/react/blob/3e94bce765d355d74f6a60feb4addb6d196e3482/packages/scheduler/src/__tests__/SchedulerNoDOM-test.js
--[[*
* Copyright (c) Facebook, Inc. and its affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
* @emails react-core
]]

local JestGlobals = require("@pkg/@jsdotlua/jest-globals")
local beforeEach = JestGlobals.beforeEach
local jestExpect = JestGlobals.expect
local it = JestGlobals.it
local jest = JestGlobals.jest

local scheduleCallback
local ImmediatePriority
local UserBlockingPriority
local NormalPriority

beforeEach(function()
	jest.resetModules()
	jest.useFakeTimers()
	local Scheduler = require("../Scheduler")()

	scheduleCallback = Scheduler.unstable_scheduleCallback
	ImmediatePriority = Scheduler.unstable_ImmediatePriority
	UserBlockingPriority = Scheduler.unstable_UserBlockingPriority
	NormalPriority = Scheduler.unstable_NormalPriority
end)

it("runAllTimers flushes all scheduled callbacks", function()
	local log = {}
	scheduleCallback(NormalPriority, function()
		table.insert(log, "A")
	end)
	scheduleCallback(NormalPriority, function()
		table.insert(log, "B")
	end)
	scheduleCallback(NormalPriority, function()
		table.insert(log, "C")
	end)

	jestExpect(log).toEqual({})

	jest.runAllTimers()

	jestExpect(log).toEqual({ "A", "B", "C" })
end)

it("executes callbacks in order of priority", function()
	local log = {}

	scheduleCallback(NormalPriority, function()
		table.insert(log, "A")
	end)
	scheduleCallback(NormalPriority, function()
		table.insert(log, "B")
	end)
	scheduleCallback(UserBlockingPriority, function()
		table.insert(log, "C")
	end)
	scheduleCallback(UserBlockingPriority, function()
		table.insert(log, "D")
	end)

	jestExpect(log).toEqual({})
	jest.runAllTimers()
	jestExpect(log).toEqual({ "C", "D", "A", "B" })
end)

it("handles errors", function()
	local log = {}

	scheduleCallback(ImmediatePriority, function()
		table.insert(log, "A")
		error("Oops A")
	end)
	scheduleCallback(ImmediatePriority, function()
		table.insert(log, "B")
	end)
	scheduleCallback(ImmediatePriority, function()
		table.insert(log, "C")
		error("Oops C")
	end)

	jestExpect(jest.runAllTimers).toThrow("Oops A")
	jestExpect(log).toEqual({ "A" })

	log = {}

	-- B and C flush in a subsequent event. That way, the second error is not
	-- swallowed.
	jestExpect(function()
		jest.runAllTimers()
	end).toThrow("Oops C")
	jestExpect(log).toEqual({ "B", "C" })
end)
