Dagger TypeScript SDK 中 DirectoryExistsOpts 详解:按类型校验文件存在性与符号链接控制 Dagger TypeScript SDK 中 DirectoryExistsOpts 详解按类型校验文件存在性与符号链接控制【免费下载链接】daggerAutomation engine to build, test and ship any codebase. Runs locally, in CI, or directly in the cloud项目地址: https://gitcode.com/GitHub_Trending/da/daggerDirectoryExistsOpts是 Dagger TypeScript SDK 中用于调用Directory.exists()方法的可选参数集合。它通过doNotFollowSymlinks与expectedType两个可选字段把一次路径是否存在的简单判断扩展为路径存在且类型符合预期的类型化校验可广泛应用于构建管线的存在性前置检查、产物结构断言与符号链接安全检测等场景。读完本文你将掌握这两个参数的语义、底层执行逻辑与真实测试用例并能直接在 Dagger 模块中写出类型安全的文件存在性判断代码。一、类型定义一次看清全部字段DirectoryExistsOpts是一个object类型的 TypeScript 类型别名定义于 Dagger TypeScript SDK 参考文档type-aliases/DirectoryExistsOpts完整结构如下type DirectoryExistsOpts { /** * If specified, do not follow symlinks. */ doNotFollowSymlinks?: boolean; /** * If specified, also validate the type of file * (e.g. REGULAR_TYPE, DIRECTORY_TYPE, or SYMLINK_TYPE). */ expectedType?: ExistsType; };两个字段均为可选optional这意味着DirectoryExistsOpts可以被整体省略——此时 Dagger 仅回答该路径是否存在等价于一个布尔开关。两个字段的典型组合语义如下参数类型默认行为作用doNotFollowSymlinksbooleanfalse跟随符号链接为true时只检查符号链接本身不解析其指向的目标expectedTypeExistsType不限制类型要求路径必须匹配指定的文件类型否则判定为不存在二、doNotFollowSymlinks决定符号链接如何被对待在类 Unix 文件系统语义中判断一个路径是否存在天然存在两种视角跟随符号链接dereference与不跟随。doNotFollowSymlinks字段就是这两种视角的开关false默认跟随符号链接。若路径是一个指向真实文件的符号链接则按目标文件的真实类型进行判断。这一行为刻意对齐了 Shell 内建test命令的语义——正如源码注释所引用的man test说明all FILE-related tests dereference symbolic links (except -h and -L)core/integration/directory_test.go。true不跟随符号链接。此时路径本身若是一个符号链接检查结果以链接自身为准类型为SYMLINK_TYPE即使其指向的目标不存在链接本身仍然存在。该字段在 GraphQL 层面对应exists查询的参数doNotFollowSymlinks: Boolean false见 core/schema/testdata/base_schema.graphqls默认值false与 TypeScript 侧缺省即跟随的行为完全一致。三、expectedType把存在性升级为类型校验expectedType接收一个ExistsType枚举值可选值及源码定义core/directory.go如下枚举值含义源码文档ExistsType.RegularTypeREGULAR_TYPE路径必须是常规文件Tests path is a regular fileExistsType.DirectoryTypeDIRECTORY_TYPE路径必须是目录Tests path is a directoryExistsType.SymlinkTypeSYMLINK_TYPE路径必须是符号链接Tests path is a symlink从源码结构看该枚举在 Go 侧命名为ExistsType并带有_TYPE后缀注释解释了原因若注册为DIRECTORY会与已有的type Directory struct产生命名冲突因此统一加后缀规避core/directory.go。这也解释了 SDK 客户端中ExistsTypeDirectoryType这类冗长命名的由来。需要留意的是源码中留有// TODO deprecate ExistsType in favor of FileTypecore/directory.go的迁移标记即未来该枚举可能被更通用的FileType取代编写新代码时值得关注这一演进方向。expectedType 与符号链接的隐含联动当expectedType为SymlinkType时引擎会自动启用不跟随符号链接模式无需再显式设置doNotFollowSymlinks。这一逻辑在Exists实现中体现为两者取或stat, err : dir.Stat(ctx, self, srv, targetPath, doNotFollowSymlinks || targetType ExistsTypeSymlink)见 core/directory.go。原因很直接想判断路径本身是符号链接就必须先不跟随它否则永远只能看到链接目标的类型。四、底层实现一次 Stat 完成全部判断DirectoryExistsOpts的语义在 Dagger 引擎侧最终落在Directory.Exists方法上core/directory.go其执行流程如下执行 Stat以doNotFollowSymlinks || targetType ExistsTypeSymlink为参数对目标路径做一次状态查询处理不存在若 Stat 返回fs.ErrNotExist立即返回false路径不存在无需类型判断类型匹配根据targetType对 Stat 结果的FileType字段做精确比对DirectoryType→FileType FileTypeDirectoryRegularType→FileType FileTypeRegularSymlinkType→FileType FileTypeSymlink空字符串未指定→ 直接返回true即只做存在性判断兜底遇到未知类型值返回错误invalid path type %s。对应的 GraphQL 参数与 Schema 层接线位于 core/schema/directory.godirectoryExistsArgs中DoNotFollowSymlinks bool带有default:false标签ExpectedType为dagql.Optional[core.ExistsType]exists处理器最终把布尔结果包装为dagql.Boolean返回。返回类型在 GraphQL 模式中为Boolean!非空布尔因此 TypeScript 客户端中该方法的返回类型是确定的Promiseboolean可以直接用于if判断。五、实战示例在 Dagger 模块中组合使用两个参数以下 TypeScript 模块展示了如何在真实 Dagger 模块中使用DirectoryExistsOpts完整覆盖仅存在性判断、目录校验、文件校验、符号链接校验四种典型场景import { dag, Directory, object, func } from dagger.io/dagger; object() class ExistsChecker { /** * 检查给定目录下的路径并报告其存在性与类型。 */ func() async check(dir: Directory): Promisestring { // 场景 1只判断存在性不传 opts或传空对象 const anyExists await dir.exists(README.md); console.log(README.md exists:, anyExists); // 场景 2必须是目录 const isDir await dir.exists(src, { expectedType: DIRECTORY_TYPE, }); console.log(src is a directory:, isDir); // 场景 3必须是常规文件 const isFile await dir.exists(package.json, { expectedType: REGULAR_TYPE, }); console.log(package.json is a regular file:, isFile); // 场景 4必须是不跟随目标解析的符号链接 const isSymlink await dir.exists(current, { expectedType: SYMLINK_TYPE, doNotFollowSymlinks: true, }); console.log(current is a symlink:, isSymlink); return ${anyExists}/${isDir}/${isFile}/${isSymlink}; } }实际使用中有几点可以注意expectedType不满足时返回false而非抛出异常——例如路径存在但是目录却以REGULAR_TYPE校验结果只是false见 core/directory.go因此适合作为构建管线的条件分支依据校验失败与路径不存在结果相同都为false若需要区分两者可进一步调用Directory.stat()获取详细状态返回Stat对象含fileType、size、permissions等字段expectedType: SYMLINK_TYPE时无需同时传doNotFollowSymlinks: true引擎会自动切换为不跟随模式。六、测试用例印证边界行为一览Dagger 的集成测试 core/integration/directory_test.go 用一张表驱动用例完整覆盖了DirectoryExistsOpts的边界行为可直接作为行为契约参考不存在即 false引用不存在的路径无类型限制时返回false目录存在quotes无类型限制返回trueDIRECTORY_TYPE校验返回true目录校验对文件失效对文件quotes/descartes做DIRECTORY_TYPE校验返回false文件校验对目录失效对目录quotes做REGULAR_TYPE校验返回false符号链接跟随语义i-am是指向文件的符号链接REGULAR_TYPE校验返回true默认跟随SYMLINK_TYPE校验返回true链接自身不跟随符号链接对i-am设置doNotFollowSymlinks: true后REGULAR_TYPE校验返回false链接自身不是常规文件悬空符号链接仍然存在nothing是指向不存在目标quotes/does-not-exist的符号链接doNotFollowSymlinks: true时无类型限制的检查返回true——这是不跟随语义最直观的体现也是检测悬空链接的实用技巧。测试构造目录的方式为Directory().WithNewFile(...).WithSymlink(...)core/integration/directory_test.go读者可在自己的模块中复现同样的目录结构验证上述行为。七、与其他 API 的关系与使用建议DirectoryExistsOpts服务于Directory.exists()而与其密切相关的Directory.stat()同样接受doNotFollowSymlinks参数core/schema/directory.go两者的符号链接语义完全一致。在选择 API 时可以参考以下建议仅需是/否结论时用exists()需要文件大小、权限等元数据时用stat()需要一次性断言多种类型时可对同一路径并发发起多次exists()调用Dagger 引擎具备 DAG 缓存与合并执行能力在 CI 中做构建产物校验时优先为expectedType显式指定期望类型这样能在早期发现本应是目录的路径变成了文件这类结构漂移问题若需要遍历目录做批量存在性检查可结合Directory.entries()与Directory.directory()逐层深入将exists()用于叶子节点判断。通过合理组合doNotFollowSymlinks与expectedTypeDirectoryExistsOpts让文件系统断言在 Dagger 中变得类型安全且语义明确是编写健壮构建逻辑时值得优先使用的能力。【免费下载链接】daggerAutomation engine to build, test and ship any codebase. Runs locally, in CI, or directly in the cloud项目地址: https://gitcode.com/GitHub_Trending/da/dagger创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考