local function dbg_info(n: number): any return debug.info(n, "s") end local function throw(msg: string) local s = 1 local root = dbg_info(1) repeat s += 1 until dbg_info(s) ~= root if warn then error(msg, s) else print(`[jecs] error: {msg}\n`) end end local function ASSERT(v: T, msg: string) if v then return end throw(msg) end local function runtime_lints_add(world) local function get_name(id) return world_get_one_inline(world, id, EcsName) end local function bname(id): string local name: string if ECS_IS_PAIR(id) then local first = get_name(world, ecs_pair_first(world, id)) local second = get_name(world, ecs_pair_second(world, id)) name = `pair({first}, {second})` else return get_name(world, id) end if name then return name else return `${id}` end end local function ID_IS_TAG(world: World, id) if ECS_IS_PAIR(id) then id = ecs_pair_first(world, id) end return not world_has_one_inline(world, id, EcsComponent) end World.query = function(world: World, ...) ASSERT((...), "Requires at least a single component") return world_query(world, ...) end World.set = function(world: World, entity: i53, id: i53, value: any): () local is_tag = ID_IS_TAG(world, id) if is_tag and value == nil then local _1 = bname(world, entity) local _2 = bname(world, id) local why = "cannot set component value to nil" throw(why) return elseif value ~= nil and is_tag then local _1 = bname(world, entity) local _2 = bname(world, id) local why = `cannot set a component value because {_2} is a tag` why ..= `\n[jecs] note: consider using "world:add({_1}, {_2})" instead` throw(why) return end world_set(world, entity, id, value) end World.add = function(world: World, entity: i53, id: i53, value: any) if value ~= nil then local _1 = bname(world, entity) local _2 = bname(world, id) throw("You provided a value when none was expected. " .. `Did you mean to use "world:add({_1}, {_2})"`) end world_add(world, entity, id) end World.get = function(world: World, entity: i53, ...) local length = select("#", ...) ASSERT(length < 5, "world:get does not support more than 4 components") local _1 for i = 1, length do local id = select(i, ...) local id_is_tag = not world_has(world, id, EcsComponent) if id_is_tag then local name = get_name(world, id) if not _1 then _1 = get_name(world, entity) end throw( `cannot get (#{i}) component {name} value because it is a tag.` .. `\n[jecs] note: If this was intentional, use "world:has({_1}, {name}) instead"` ) end end return world_get(world, entity, ...) end end