0Pricing
Lua Academy · Lesson

Promise-Like Patterns

Implement deferred/promise objects using coroutines and callbacks.

Promise-Like Patterns is a free Lua Academy lesson on CoddyKit — lesson 3 of 4. You can read the complete lesson below for free — then practise it hands-on in the browser with a built-in code editor and a 24/7 AI tutor. It is part of the Lua Academy learning path, one of 4 lessons in the course, and your progress syncs across the web and the CoddyKit app.

What Is a Promise?

A promise represents a value that will be available in the future. It can be pending, fulfilled (with a value), or rejected (with an error).

Lua Promise Table

Implement a minimal promise as a table with state, value, and callback lists.

local function newPromise()
  return {
    state    = "pending",
    value    = nil,
    _resolve = {},
    _reject  = {},
  }
end

resolve and reject

Fulfilling a promise calls all resolve callbacks. Rejecting it calls all reject callbacks.

local function resolve(p, value)
  if p.state ~= "pending" then return end
  p.state = "fulfilled"; p.value = value
  for _, cb in ipairs(p._resolve) do cb(value) end
end
local function reject(p, reason)
  if p.state ~= "pending" then return end
  p.state = "rejected"; p.value = reason
  for _, cb in ipairs(p._reject) do cb(reason) end
end

andThen Chaining

A :andThen(onFulfill, onReject) method returns a new promise, enabling chaining.

function promise:andThen(onFulfill, onReject)
  local next = newPromise()
  self._resolve[#self._resolve+1] = function(v)
    local ok, result = pcall(onFulfill, v)
    if ok then resolve(next, result)
    else reject(next, result) end
  end
  if onReject then
    self._reject[#self._reject+1] = function(e)
      local ok, result = pcall(onReject, e)
      if ok then resolve(next, result)
      else reject(next, result) end
    end
  end
  return next
end

Coroutine-Backed Promise

Combine promises with coroutines: a coroutine awaits a promise by yielding, and the promise's resolve callback resumes it.

Promise.all

Wait for multiple promises to all complete.

local function all(promises)
  local results = {}
  local count = #promises
  local combined = newPromise()
  for i, p in ipairs(promises) do
    p:andThen(function(v)
      results[i] = v; count = count - 1
      if count == 0 then resolve(combined, results) end
    end, function(e) reject(combined, e) end)
  end
  return combined
end

Promise.race

Resolve with the first promise that completes (fulfilled or rejected).

local function race(promises)
  local combined = newPromise()
  for _, p in ipairs(promises) do
    p:andThen(
      function(v) resolve(combined, v) end,
      function(e) reject(combined, e) end
    )
  end
  return combined
end

Error Propagation in Chains

If any step in a chain throws, the error propagates to the next rejection handler. Unhandled rejections should be logged at the end of the chain.

Cancellable Promises

Add a :cancel() method that transitions to a special cancelled state, preventing callbacks from firing.

Lazy Promises

A lazy promise only starts its work when the first andThen is attached — useful for optional async operations.

When to Use Promises vs Coroutines

Promises are callback-based and composable. Coroutines make async code look synchronous. In Lua, coroutine-backed promises give both: the composability of promises and the readability of sync code.

Promise Question

What does a promise's andThen method return?

Recap: Promise-Like Patterns

Promises represent pending values with pending/fulfilled/rejected states. Chain operations with andThen. Combine with coroutines for async/await-style code. Use all and race for parallel coordination.

Frequently asked questions

Is the “Promise-Like Patterns” lesson free?

Yes — the full text of “Promise-Like Patterns” is free to read here on the web, and the Lua Academy course includes 4 lessons in total. To practise it interactively (a built-in code editor and a 24/7 AI tutor) and unlock the rest of the Lua Academy course, upgrade to CoddyKit PRO.

What will I learn in “Promise-Like Patterns”?

Implement deferred/promise objects using coroutines and callbacks. You practise Lua Academy with hands-on code you run directly in the browser, and a 24/7 AI tutor answers your questions as you work through the lesson.

Do I need any experience to start Lua Academy?

No prior experience is required. Lua Academy on CoddyKit is structured for beginners through advanced learners; this is — lesson 3 of 4, so you can start here or from the beginning and move at your own pace.

How long does the “Promise-Like Patterns” lesson take?

Most CoddyKit lessons take about 5–10 minutes. Each one is bite-sized and interactive, so you make steady progress and pick up exactly where you left off across the web and the app.

Can I write and run code in this Lua Academy lesson?

Yes. Every Lua Academy lesson includes a built-in code editor, so you write and run real code right in your browser and get instant AI feedback — no local setup required.

All lessons in this course

  1. Building a Simple Event Loop
  2. Async/Await with Coroutines
  3. Promise-Like Patterns
  4. Non-Blocking I/O with luasocket
← Back to Lua Academy