Lua Academy · Les

Beveiligde aanroepen met pcall

Vang fouten veilig op met pcall en interpreteer de retourwaarden

Les 2 van 412 stappen

Beveiligde aanroepen met pcall is een gratis Lua Academy-les op CoddyKit. Dit is les 2 van 4. Je kunt 3 lessen uit dit leerpad gratis volledig lezen — daarna ontgrendelt CoddyKit PRO alle lessen, plus praktische oefeningen met een ingebouwde code-editor en een AI-tutor die 24/7 beschikbaar is. Deze les maakt deel uit van het leertraject Lua Academy. Je voortgang wordt gesynchroniseerd op het web en in de CoddyKit-app. De cursus Lua Academy bevat in totaal 4 lessen.

Basisprincipes van pcall

pcall(f, ...) roept functie f aan met de argumenten ... in beschermde modus. Als f slaagt, geeft pcall true terug, gevolgd door alle retourwaarden. Als f een fout veroorzaakt, geeft pcall false terug, gevolgd door het foutbericht. Het programma gaat in beide gevallen verder.

local function risky(x)
  if x < 0 then error("negative input: " .. x) end
  return math.sqrt(x)
end

local ok, result = pcall(risky, 9)
print(ok, result)    -- true  3.0

ok, result = pcall(risky, -1)
print(ok, result)    -- false  ...: negative input: -1

Specifieke fouten afvangen

Controleer na pcall het type van de foutwaarde om verschillende soorten fouten verschillend af te handelen. Fouten in tabellen bevatten gestructureerde gegevens; tekenreeksfouten bevatten een bericht. Handel altijd beide gevallen af.

local function op(errType)
  if errType == "table" then
    error({code=42, msg="structured error"})
  else
    error("plain string error")
  end
end

local ok, err = pcall(op, "table")
if not ok then
  if type(err) == "table" then
    print("Code:", err.code, "Msg:", err.msg)
  else
    print("String error:", err)
  end
end

Meerdere retourwaarden bij succes

Bij succes geeft pcall alle retourwaarden van de beschermde functie terug na de eerste true. Vang ze op in meerdere variabelen.

local function compute(a, b)
  return a + b, a * b, a - b
end

local ok, sum, product, diff = pcall(compute, 6, 4)
if ok then
  print("sum:", sum, "product:", product, "diff:", diff)
  -- sum: 10  product: 24  diff: 2
end

pcall nesten

Aanroepen van pcall kunnen worden genest. Elke pcall maakt een onafhankelijk beschermd bereik. Een fout in een interne pcall wordt opgevangen door de interne pcall, niet door de buitenste. Zo kun je terugvalstrategieën implementeren.

local function tryPrimary()
  error("primary failed")
end

local function tryFallback()
  return "fallback result"
end

local ok, result = pcall(tryPrimary)
if not ok then
  print("Primary failed:", result)
  ok, result = pcall(tryFallback)
end

if ok then print("Got:", result) end  -- fallback result

pcall met methoden

Als je een methode (syntaxis met dubbele punt) via pcall wilt aanroepen, geef je de functie en het object als eerste argument door. pcall(obj.method, obj, args...) of wikkel de aanroep in een afsluiting.

local obj = {
  x = 10,
  compute = function(self, n)
    if n == 0 then error("zero divisor") end
    return self.x / n
  end
}

-- Pass method + self explicitly
local ok, v = pcall(obj.compute, obj, 2)
print(ok, v)   -- true  5.0

-- Or use a closure
ok, v = pcall(function() return obj:compute(0) end)
print(ok, v)   -- false  ...zero divisor

pcall voor veilige IO

Wikkel IO-bewerkingen in pcall om onverwachte fouten van het besturingssysteem af te vangen. Geef een consistent resultaat/fout-paar terug, zodat aanroepers fouten netjes kunnen afhandelen.

local function safeRead(path)
  local ok, result = pcall(function()
    local f = assert(io.open(path, "r"))
    local content = f:read("a")
    f:close()
    return content
  end)
  if ok then return result
  else return nil, result
  end
end

local data, err = safeRead("config.txt")
if data then print("Read", #data, "bytes")
else print("Error:", err)
end

Patroon voor opnieuw proberen met pcall

Probeer een onbetrouwbare bewerking (netwerkverzoek, schrijven naar een bestand) maximaal N keer opnieuw en gebruik pcall om fouten af te vangen. Wacht in echte code tussen pogingen (of gebruik coroutines).

local function retry(fn, maxAttempts)
  local attempts = 0
  while attempts < maxAttempts do
    attempts = attempts + 1
    local ok, result = pcall(fn)
    if ok then
      print("Succeeded on attempt", attempts)
      return result
    end
    print("Attempt", attempts, "failed:", result)
  end
  error("all " .. maxAttempts .. " attempts failed")
end

local n = 0
retry(function()
  n = n + 1
  if n < 3 then error("not ready") end
  return "done"
end, 5)

pcall-resultaten opslaan in een tabel

Wanneer je pcall in een lus gebruikt, sla je de resultaten op in een tabel voor latere analyse. Dit is nuttig voor batchbewerkingen waarbij je alle items wilt verwerken en fouten wilt verzamelen in plaats van te stoppen bij de eerste mislukking.

local jobs = {10, -5, 25, 0, 16}
local results = {}

for _, n in ipairs(jobs) do
  local ok, v = pcall(function()
    if n < 0 then error("negative") end
    return math.sqrt(n)
  end)
  results[#results+1] = {input=n, ok=ok, value=v}
end

for _, r in ipairs(results) do
  if r.ok then
    print(r.input, "->", string.format("%.3f", r.value))
  else
    print(r.input, "-> ERROR:", r.value)
  end
end

pcall versus xpcall

pcall vangt de fout af, maar geeft je alleen de foutwaarde. Met xpcall kun je een berichtafhandelingsfunctie opgeven die wordt uitgevoerd terwijl de stack nog intact is, zodat stacktraces mogelijk zijn. Kies xpcall wanneer je traceringen nodig hebt.

-- pcall: simple, no traceback
local ok1, err1 = pcall(function()
  error("simple error")
end)
print(err1)   -- only the error message

-- xpcall: with traceback handler
local ok2, err2 = xpcall(
  function() error("traced error") end,
  function(e) return debug.traceback(e, 2) end
)
print(err2)   -- full stack trace

Retourconventie van pcall

Gebruik pcall als basis voor een consistente API: geef bij succes altijd value terug en bij mislukking nil, errorMessage. Bouw je functies op deze manier op, zodat aanroepers altijd weten wat ze kunnen verwachten.

local function loadJSON(path)
  local ok, result = pcall(function()
    local f = assert(io.open(path, "r"))
    local text = f:read("a")
    f:close()
    -- Fake JSON parse for demo
    return {data = text, path = path}
  end)
  if ok then return result
  else return nil, result
  end
end

local data, err = loadJSON("data.json")
if data then print("Loaded:", data.path)
else print("Failed:", err)
end

Korte controle

Wat geeft pcall terug wanneer de beschermde functie slaagt?

Samenvatting: pcall

Samenvatting:

  • pcall(f, ...) → true, results... of false, err
  • Controleer de eerste retourwaarde om succes of mislukking te bepalen
  • Bij succes volgen er meerdere retourwaarden na true
  • Geneste pcall: elke aanroep vangt onafhankelijk zijn eigen fouten af
  • Patroon voor opnieuw proberen: gebruik een lus met pcall voor onbetrouwbare bewerkingen
  • Gebruik xpcall wanneer je stacktraces nodig hebt
Gratis beginnen

Leer Lua met een AI-tutor — gratis

Schrijf echte code en voer die uit in je browser, krijg direct hulp van een AI-tutor die 24/7 beschikbaar is en ga verder waar je gebleven bent op het web of in de app.

Cursussen
40
Lessen
159

Veelgestelde vragen

Is de les “Beveiligde aanroepen met pcall” gratis?

Ja — je kunt hier op het web alle 3 lessen van het leerpad Lua Academy, waaronder “Beveiligde aanroepen met pcall”, gratis volledig lezen. Daarna ontgrendelt CoddyKit PRO alle lessen, plus interactieve oefeningen met een ingebouwde code-editor en een AI-tutor die 24/7 beschikbaar is. De cursus Lua Academy bevat in totaal 4 lessen.

Wat leer ik in “Beveiligde aanroepen met pcall”?

Vang fouten veilig op met pcall en interpreteer de retourwaarden Je oefent met Lua Academy door code rechtstreeks in de browser uit te voeren. Een AI-begeleider die 24/7 beschikbaar is beantwoordt je vragen terwijl je de les doorwerkt.

Heb ik ervaring nodig om met Lua Academy te beginnen?

Ervaring vooraf is niet nodig. Lua Academy op CoddyKit is opgebouwd voor beginners tot gevorderden, zodat je hier of bij het begin kunt starten en in je eigen tempo kunt leren. Dit is les 2 van 4.

Hoe lang duurt de les “Beveiligde aanroepen met pcall”?

De meeste lessen van CoddyKit duren ongeveer 5–10 minuten. Elke les is kort en interactief, zodat je gestaag vooruitgaat en op het web en in de app precies verdergaat waar je was gebleven.

Kan ik code schrijven en uitvoeren in deze les over Lua Academy?

Ja. Elke les over Lua Academy bevat een ingebouwde code-editor, zodat je rechtstreeks in je browser echte code kunt schrijven en uitvoeren en direct feedback van AI krijgt — lokale installatie is niet nodig.

Alle lessen in deze cursus

  1. De functie error()
  2. Beveiligde aanroepen met pcall
  3. xpcall en meldingshandlers
  4. Gestructureerde foutobjecten
← Terug naar Lua Academy