-
Notifications
You must be signed in to change notification settings - Fork 0
Diagnostics
Hatchet fails loudly rather than guessing. When it cannot resolve a type — a typo, a missing
import, or a type declared outside the --src scope — it reports an error and does not generate that
module, instead of silently emitting wrong C++ (e.g. a class rendered by value instead of as a
pointer). Errors are collected across all files and reported together; modules that transpiled cleanly
are still written, and the run exits non-zero:
error: Widget.hx:14: unresolved type `Button` in parameter `b` of `new` — is it declared and within the --src scope?
Generated 6 file(s); 1 module(s) skipped due to errors.
hatchet: 1 error(s); 1 module(s) were not generated
The same discipline applies to unsupported Haxe idioms: valid Haxe that Hatchet does not yet
transpile fails with an invitation to contribute upstream (the repository URL is in
src/diag.rs). This distinguishes
"your input is wrong" (fix the Haxe) from "Hatchet doesn't do this yet" (raise a PR).
Currently flagged as unsupported:
- a lambda used outside a top-level
finalbinding or anArray.map(...)argument; -
Haxe macros (a
macrofunction, or the macro AST typeExpr); -
regular expressions (both the
~/pattern/flagsliteral and theERegtype); -
usingstatic extensions; -
function types as values (
var cb:Int->Intin a field, parameter, return, or typedef — first-class function values have no C++98 lowering; the one lowered position is a top-levelfinallambda binding, which becomes a free function); -
rest parameters (
...vals:Intand thehaxe.Resttype, Haxe 4.2 varargs); -
recursive enum payloads (
Node(child:Tree)— a by-value tagged class cannot contain itself); - the
isruntime type-check operator (Haxe 4.2); -
generics (a type-parameterized
class Box<T>,interface I<T>,enum Tree<T>, generic methodfirst<T>(…), ortypedef Pair<T>— type parameters have no C++98 template lowering, so each is flagged rather than emitted withTas a bare unknown type); -
non-constant
switchpatterns (a capturecase x:, a literal or nested payload sub-pattern incase Add(0, b):, or a destructuring pattern combined with other alternatives in one case); -
(get, default)properties anddynamicaccess (every other accessor pair is lowered — see Members & Access — and a strayget_x/set_xwhose field does not declare the matching access kind is flagged rather than silently dropped); -
generic /
@:multiTypeabstracts (a plainabstract X(T)newtype is supported — see Value Types & Abstracts — but a type-parameterized or multitype one is not); - an anonymous struct as a container element (
Array<{x:Int}>) — it would lower to a uselessstd::vector<void*>, so it is flagged; give the struct atypedefand use that named type as the element; - and
@:opforms with no C++98 operator (the two-arg@:op([])write,@:op(a.b),@:op(a()), postfix).
These are parsed but not transpiled, so they are reported with a clean diagnostic rather than a parse
error. Relatedly, iteration that cannot be lowered fails loudly: a for loop (or comprehension)
over a value that is not a range, Array, Map, or a type implementing the Iterator/Iterable
protocol on itself — including a protocol reached only through a typedef alias or inherited from a
base class (which Hatchet does not consult), and key => value over a value-only custom iterator —
is a hard error rather than a guess, each with a message naming the specific cause.
Likewise, comparing a value String to null is a hard error (a value std::string is never
null): test != "" for emptiness, or use Null<String> for a nullable string (see
Types & Nullability). An optional ?s:String parameter is exempt — it defaults
to "", so its null check legitimately lowers to s.empty().
Assigning through a value-struct parameter is a hard error: a value-struct parameter lowers to
const T&, so a write through it is reported up front rather than emitted as non-compiling C++.
Non-fatal warnings flag a lowering that still compiles but is deprecated:
- the empty structure
{}used as avoid*type is deprecated — useDynamic(opaque value) orcpp.RawPointer<cpp.Void>(opaque pointer). See Raw-Pointer Interop.
Hatchet is licensed under the MIT License — see LICENSE. (c) 2026 Andrew Grant Lind
Getting Started
Language Support
- Declarations
- Value Types & Abstracts
- Members & Access
- Statements & Expressions
- Types & Nullability
- Conditional Compilation
- Memory Ownership
Semantics & Interop
Internals