test: specs and ProjectDependency() in a project file's static initialisers
ProjectArgs gets a sibling that makes its own sibling's spec at namespace scope. Before the fix that spec took the args the file was first loaded with; now it takes none on every load. The checks go through one CheckLoaded helper, which prints what each sibling was given, so a failure says which args a wrong frame handed over. ProjectDependency loads a fixture whose static initialiser asks for its pragma dependency, in a child, because a throw there terminates the process: before the fix it found none. The check that the dependency gets none of the consumer's args moves into the first load, which now passes the app an arg it ignores; the separate load could not fail its own check, and its early return skipped every later one. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
060ab4380f
commit
e6363b95fe
5 changed files with 102 additions and 36 deletions
|
|
@ -6,12 +6,14 @@ import Crafter.Build;
|
|||
using namespace Crafter;
|
||||
|
||||
// Loads the same sibling three ways: with its args left at their default,
|
||||
// with nothing forwarded, and with a list of its own. The test reads what
|
||||
// each copy received back out of cfg.dependencies.
|
||||
// with nothing forwarded, and with a list of its own. Then a sibling that
|
||||
// makes its own sibling's spec at namespace scope. The test reads what each
|
||||
// copy received back out of cfg.dependencies.
|
||||
extern "C" Configuration CrafterBuildProject(std::span<const std::string_view> args) {
|
||||
Configuration* inherited = LocalProject({ .projectFile = "../lib/project.cpp" });
|
||||
Configuration* none = LocalProject({ .projectFile = "../lib/project.cpp", .args = {} });
|
||||
Configuration* replaced = LocalProject({ .projectFile = "../lib/project.cpp", .args = { "--only" } });
|
||||
Configuration* fromStatic = LocalProject({ .projectFile = "../static/project.cpp" });
|
||||
|
||||
Configuration cfg;
|
||||
cfg.path = "./";
|
||||
|
|
@ -19,7 +21,7 @@ extern "C" Configuration CrafterBuildProject(std::span<const std::string_view> a
|
|||
cfg.outputName = "app";
|
||||
cfg.type = ConfigurationType::Executable;
|
||||
ApplyStandardArgs(cfg, args);
|
||||
cfg.dependencies = { inherited, none, replaced };
|
||||
cfg.dependencies = { inherited, none, replaced, fromStatic };
|
||||
// GitProjectSpec takes the same default. Checked on the spec itself,
|
||||
// since a GitProject would need a repository to clone.
|
||||
const GitProjectSpec git{ .source = { .url = "unused" } };
|
||||
|
|
|
|||
26
tests/ProjectArgs/fixture/static/project.cpp
Normal file
26
tests/ProjectArgs/fixture/static/project.cpp
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
// SPDX-License-Identifier: LGPL-3.0-only
|
||||
// SPDX-FileCopyrightText: Copyright (C) 2026 Catcrafts®
|
||||
|
||||
import std;
|
||||
import Crafter.Build;
|
||||
using namespace Crafter;
|
||||
|
||||
// Makes its sibling's spec at namespace scope, so the spec's args default
|
||||
// while LoadProject dlopens this file: before CrafterBuildProject is called,
|
||||
// and on the first load of the file only.
|
||||
namespace {
|
||||
const LocalProjectSpec LeafSpec{ .projectFile = "../leaf/project.cpp" };
|
||||
}
|
||||
|
||||
extern "C" Configuration CrafterBuildProject(std::span<const std::string_view> args) {
|
||||
Configuration* leaf = LocalProject(LeafSpec);
|
||||
|
||||
Configuration cfg;
|
||||
cfg.path = "./";
|
||||
cfg.name = "static";
|
||||
cfg.outputName = "static";
|
||||
cfg.type = ConfigurationType::LibraryStatic;
|
||||
ApplyStandardArgs(cfg, args);
|
||||
cfg.dependencies = { leaf };
|
||||
return cfg;
|
||||
}
|
||||
Loading…
Reference in a new issue