feat(types): add core data structures

PackageIndex, Recipe, DepConstraint, BuildPlan, BuildResult, CacheManifest, BinaryCheckResult structs. Pool/BuildSystem/DepOp/Source enums. DepConstraint.parse() ported from ZETA vercmp.lua. TypesException for parsing errors. All @safe, all strings default to empty string.
This commit is contained in:
2026-08-08 17:17:20 -04:00
parent 3fb03b23d7
commit 348f0e3bac
3 changed files with 725 additions and 0 deletions
+160
View File
@@ -0,0 +1,160 @@
Warning
Warning ## Warning for package tofu ##
Warning
Warning The following compiler flags have been specified in the package description
Warning file. They are handled by DUB and direct use in packages is discouraged.
Warning Alternatively, you can set the DFLAGS environment variable to pass custom flags
Warning to the compiler, or use one of the suggestions below:
Warning
Warning warningsAsErrors: Use "buildRequirements" to control the warning level
Warning
Generating test runner configuration 'tofu-test-application' for 'application' (executable).
Warning Excluding main source file src/main.d from test.
Starting Performing "unittest" build using /usr/bin/dmd for x86_64.
Up-to-date toml 1.0.0: target for configuration [library] is up to date.
Building tofu ~main: building configuration [tofu-test-application]
src/tofu/config.d(125,9): Error: found `private` instead of statement
private @trusted void warn() {
^
src/tofu/config.d(132,1): Error: unmatched closing brace
}
^
src/tofu/types.d(147,13): Error: variable name expected after type `string`, not `version`
string version = "";
^
src/tofu/types.d(147,13): `version` is a keyword, perhaps append `_` to make it an identifier
src/tofu/types.d(147,21): Error: declaration expected, not `=`
string version = "";
^
src/tofu/types.d(159,16): Error: variable name expected after type `string`, not `version`
string version = "";
^
src/tofu/types.d(159,16): `version` is a keyword, perhaps append `_` to make it an identifier
src/tofu/types.d(159,29): Error: declaration expected, not `=`
string version = "";
^
src/tofu/types.d(185,12): Error: variable name expected after type `string`, not `version`
string version = "";
^
src/tofu/types.d(185,12): `version` is a keyword, perhaps append `_` to make it an identifier
src/tofu/types.d(185,20): Error: declaration expected, not `=`
string version = "";
^
src/tofu/types.d(268,16): Error: identifier or `new` expected following `.`, not `version`
result.version = spec[verStart .. verEnd];
^
src/tofu/types.d(326,12): Error: variable name expected after type `string`, not `version`
string version = "";
^
src/tofu/types.d(326,12): `version` is a keyword, perhaps append `_` to make it an identifier
src/tofu/types.d(326,22): Error: declaration expected, not `=`
string version = "";
^
src/tofu/types.d(366,12): Error: variable name expected after type `string`, not `version`
string version = "";
^
src/tofu/types.d(366,12): `version` is a keyword, perhaps append `_` to make it an identifier
src/tofu/types.d(366,22): Error: declaration expected, not `=`
string version = "";
^
src/tofu/types.d(405,18): Error: identifier or `new` expected following `.`, not `version`
assert(d.version == "");
^
src/tofu/types.d(411,18): Error: identifier or `new` expected following `.`, not `version`
assert(d.version == "");
^
src/tofu/types.d(422,18): Error: identifier or `new` expected following `.`, not `version`
assert(d.version == "2.0");
^
src/tofu/types.d(428,18): Error: identifier or `new` expected following `.`, not `version`
assert(d.version == "2.0");
^
src/tofu/types.d(434,18): Error: identifier or `new` expected following `.`, not `version`
assert(d.version == "2.0");
^
src/tofu/types.d(440,18): Error: identifier or `new` expected following `.`, not `version`
assert(d.version == "2.0");
^
src/tofu/types.d(446,18): Error: identifier or `new` expected following `.`, not `version`
assert(d.version == "2.0");
^
error limit (20) reached, use `-verrors=0` to show all
Error /usr/bin/dmd failed with exit code 1.
Warning
Warning ## Warning for package tofu ##
Warning
Warning The following compiler flags have been specified in the package description
Warning file. They are handled by DUB and direct use in packages is discouraged.
Warning Alternatively, you can set the DFLAGS environment variable to pass custom flags
Warning to the compiler, or use one of the suggestions below:
Warning
Warning warningsAsErrors: Use "buildRequirements" to control the warning level
Warning
Generating test runner configuration 'tofu-test-application' for 'application' (executable).
Warning Excluding main source file src/main.d from test.
Starting Performing "unittest" build using /usr/bin/dmd for x86_64.
Up-to-date toml 1.0.0: target for configuration [library] is up to date.
Building tofu ~main: building configuration [tofu-test-application]
src/tofu/config.d(126,20): Error: function `fprintf` is not callable using argument types `(File, string, immutable(char)*, immutable(char)*, int)`
fprintf(stderr, "Warning: invalid %s '%s', using default %d\n",
^
src/tofu/config.d(126,20): cannot pass argument `makeGlobal()` of type `File` to parameter `shared(_IO_FILE)* stream`
/usr/include/dlang/dmd/core/stdc/stdio.d(1347,13): `core.stdc.stdio.fprintf(shared(_IO_FILE)* stream, scope const(char*) format, scope const ...)` declared here
int fprintf(FILE* stream, scope const char* format, scope const ...);
^
src/tofu/config.d(182,32): Error: `@safe` function `tofu.config.load` cannot call `@system` function `toml.toml.parseTOML`
doc = parseTOML(content);
^
../../.dub/packages/toml/1.0.0/toml/src/toml/toml.d(431,14): `toml.toml.parseTOML` is declared here
TOMLDocument parseTOML(string data, TOMLOptions options=TOMLOptions.none) {
^
src/tofu/config.d(187,28): Error: function `fprintf` is not callable using argument types `(File, string, immutable(char)*, immutable(char)*)`
fprintf(stderr, "Warning: malformed TOML config at %s: %s\n",
^
src/tofu/config.d(187,28): cannot pass argument `makeGlobal()` of type `File` to parameter `shared(_IO_FILE)* stream`
/usr/include/dlang/dmd/core/stdc/stdio.d(1347,13): `core.stdc.stdio.fprintf(shared(_IO_FILE)* stream, scope const(char*) format, scope const ...)` declared here
int fprintf(FILE* stream, scope const char* format, scope const ...);
^
src/tofu/config.d(194,28): Error: function `fprintf` is not callable using argument types `(File, string, immutable(char)*)`
fprintf(stderr, "Warning: unreadable TOML config at %s, "
^
src/tofu/config.d(194,28): cannot pass argument `makeGlobal()` of type `File` to parameter `shared(_IO_FILE)* stream`
/usr/include/dlang/dmd/core/stdc/stdio.d(1347,13): `core.stdc.stdio.fprintf(shared(_IO_FILE)* stream, scope const(char*) format, scope const ...)` declared here
int fprintf(FILE* stream, scope const char* format, scope const ...);
^
Error /usr/bin/dmd failed with exit code 1.
Warning
Warning ## Warning for package tofu ##
Warning
Warning The following compiler flags have been specified in the package description
Warning file. They are handled by DUB and direct use in packages is discouraged.
Warning Alternatively, you can set the DFLAGS environment variable to pass custom flags
Warning to the compiler, or use one of the suggestions below:
Warning
Warning warningsAsErrors: Use "buildRequirements" to control the warning level
Warning
Generating test runner configuration 'tofu-test-application' for 'application' (executable).
Warning Excluding main source file src/main.d from test.
Starting Performing "unittest" build using /usr/bin/dmd for x86_64.
Up-to-date toml 1.0.0: target for configuration [library] is up to date.
Building tofu ~main: building configuration [tofu-test-application]
Linking tofu-test-application
Finished To force a rebuild of up-to-date targets, run again with --force
Running tofu-test-application
Warning: malformed TOML config at /tmp/tofu-test-config-bad-173904.toml: Invalid table key declaration (2:0)
Warning: invalid TOFU_DEFAULT_JOBS 'not-a-number', using default 1
3 modules passed unittests
Warning
Warning ## Warning for package tofu ##
Warning
Warning The following compiler flags have been specified in the package description
Warning file. They are handled by DUB and direct use in packages is discouraged.
Warning Alternatively, you can set the DFLAGS environment variable to pass custom flags
Warning to the compiler, or use one of the suggestions below:
Warning
Warning warningsAsErrors: Use "buildRequirements" to control the warning level
Warning
Starting Performing "debug" build using /usr/bin/dmd for x86_64.
Up-to-date toml 1.0.0: target for configuration [library] is up to date.
Up-to-date tofu ~main: target for configuration [application] is up to date.
Finished To force a rebuild of up-to-date targets, run again with --force
+24
View File
@@ -0,0 +1,24 @@
# Decisions — tofu-core
Architectural choices and rationales discovered during work on this plan.
_Auto-scaffolded by /start-work. Append new entries below - never overwrite._
---
### Task 4: `version` → `ver` rename
`version` is a reserved keyword in D (conditional compilation). All struct fields bearing this name are renamed to `ver` — PackageIndex.ver, Recipe.ver, DepConstraint.ver, CacheManifest.ver, BinaryCheckResult.ver. This keeps the API readable while avoiding the keyword conflict. Downstream modules referencing these structs must use `.ver` for the version field.
### Task 4: DepConstraint uses typed `DepOp` enum, not string op
The Lua reference stores `op` as a string (`nil`, `">="`, `"=="`, etc.). In D we use a typed `DepOp` enum (`ge, le, eq, ne, gt, lt, none`) for type safety and exhaustive switching. The `parse` factory handles string-to-enum conversion at parse time.
### Task 4: BuildPlan is a plain container — no sorting
The plan specifies that `order()` returns entries in deps-first order *guaranteed by the caller*. The struct itself is just a container with `add()` and `order()` — no topological sort or dependency resolution. Sorting logic belongs in a later module (`tofu.resolver` or similar).
### Task 4: Single exception type `TypesException`
One exception class for the entire types module — no separate subclasses per error category. The parse failures (bad dep spec, invalid pool) all throw `TypesException` with a descriptive message. Callers catch `TypesException` for all type-parsing errors.
### Task 4: Manual char scanning for dep spec parsing
Rather than pulling in `std.regex`, the parser uses hand-written `isNameChar()` and `isWhite()` helpers with a simple position cursor. This keeps the module dependency-light (only `std.ascii`). The logic is a direct 1:1 port of the Lua reference patterns: `[A-Za-z0-9_.+-]` for names/versions, whitespace `[ \t]` for separators.
---