@ttsc/banner 0.16.7 → 0.16.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/driver/banner.go +74 -2
- package/package.json +2 -2
package/driver/banner.go
CHANGED
|
@@ -364,7 +364,7 @@ function toSerializableBanner(value) {
|
|
|
364
364
|
// build runs with `--no-plugins` so evaluating the config never triggers the
|
|
365
365
|
// host project's transform/check plugins against the loader tsconfig.
|
|
366
366
|
func loadBannerTypeScriptConfigFile(location string) (any, error) {
|
|
367
|
-
tempDir, err := os.MkdirTemp(
|
|
367
|
+
tempDir, err := os.MkdirTemp(loaderTempBase(location, os.TempDir()), "ttsc-banner-config-")
|
|
368
368
|
if err != nil {
|
|
369
369
|
return nil, fmt.Errorf("@ttsc/banner: create config loader tempdir: %w", err)
|
|
370
370
|
}
|
|
@@ -507,7 +507,7 @@ func typeScriptConfigLoaderTsconfig(loader, location, outDir string) string {
|
|
|
507
507
|
"moduleResolution": "bundler",
|
|
508
508
|
"outDir": filepath.ToSlash(filepath.Join(outDir, "out")),
|
|
509
509
|
"rewriteRelativeImportExtensions": true,
|
|
510
|
-
"rootDir":
|
|
510
|
+
"rootDir": loaderRootDir(outDir),
|
|
511
511
|
"skipLibCheck": true,
|
|
512
512
|
"strict": true,
|
|
513
513
|
"target": "ES2022",
|
|
@@ -521,6 +521,78 @@ func typeScriptConfigLoaderTsconfig(loader, location, outDir string) string {
|
|
|
521
521
|
return string(body)
|
|
522
522
|
}
|
|
523
523
|
|
|
524
|
+
// loaderRootDir returns the widest rootDir that still contains the loader
|
|
525
|
+
// tsconfig's inputs: the volume root of the loader temp dir (`C:/` on
|
|
526
|
+
// Windows, `/` elsewhere). A literal "/" is not an ancestor of drive-letter
|
|
527
|
+
// paths, so tsgo rejects every input with TS6059 (#299, #304). The temp dir
|
|
528
|
+
// is created on the same volume as the config file (see loaderTempBase), so
|
|
529
|
+
// its volume root spans both `files` entries.
|
|
530
|
+
func loaderRootDir(outDir string) string {
|
|
531
|
+
vol := filepath.VolumeName(outDir)
|
|
532
|
+
if vol == "" {
|
|
533
|
+
return "/"
|
|
534
|
+
}
|
|
535
|
+
return filepath.ToSlash(vol + `\`)
|
|
536
|
+
}
|
|
537
|
+
|
|
538
|
+
// loaderTempBase picks the parent directory for the ephemeral config-loader
|
|
539
|
+
// tree. The system temp dir is the default, but when it sits on a different
|
|
540
|
+
// volume than the config file (Windows: TEMP on `C:`, project on `D:`) the
|
|
541
|
+
// loader cannot work from there — no single tsconfig rootDir spans two
|
|
542
|
+
// volumes and filepath.Rel cannot produce a relative import across drives
|
|
543
|
+
// (#305) — so the tree is created under the config's nearest
|
|
544
|
+
// node_modules/.cache instead, falling back to the config's own directory
|
|
545
|
+
// when no node_modules exists (or its .cache cannot be created): any location
|
|
546
|
+
// on the config's volume beats the system temp dir, which is guaranteed to
|
|
547
|
+
// fail. Returns "" (the os.MkdirTemp default) when the volumes already match.
|
|
548
|
+
func loaderTempBase(location, systemTemp string) string {
|
|
549
|
+
// A relative location has no volume; "" must not be read as "a volume
|
|
550
|
+
// other than the system temp's" — it keeps the historical default (and
|
|
551
|
+
// the Rel-failure contract for relative config paths).
|
|
552
|
+
vol := filepath.VolumeName(location)
|
|
553
|
+
if vol == "" || strings.EqualFold(filepath.VolumeName(systemTemp), vol) {
|
|
554
|
+
return ""
|
|
555
|
+
}
|
|
556
|
+
nodeModules := findNearestNodeModules(filepath.Dir(location))
|
|
557
|
+
if nodeModules == "" {
|
|
558
|
+
return filepath.Dir(location)
|
|
559
|
+
}
|
|
560
|
+
// Resolve a linked node_modules (junction/symlink — common in managed
|
|
561
|
+
// setups) before descending into it: the ESM runtime realpaths the loader
|
|
562
|
+
// module at import time, and a relative config specifier computed from the
|
|
563
|
+
// link-form path would resolve against the wrong directory. NTFS junctions
|
|
564
|
+
// defeat filepath.EvalSymlinks, so the link component is chased by hand
|
|
565
|
+
// first. Realpathing may also land on another volume, which defeats the
|
|
566
|
+
// whole point — fall back to the config's directory then.
|
|
567
|
+
base := filepath.Join(resolveDirLink(nodeModules), ".cache")
|
|
568
|
+
if err := os.MkdirAll(base, 0o755); err != nil {
|
|
569
|
+
return filepath.Dir(location)
|
|
570
|
+
}
|
|
571
|
+
real, err := filepath.EvalSymlinks(base)
|
|
572
|
+
if err != nil || !strings.EqualFold(filepath.VolumeName(real), filepath.VolumeName(location)) {
|
|
573
|
+
return filepath.Dir(location)
|
|
574
|
+
}
|
|
575
|
+
return real
|
|
576
|
+
}
|
|
577
|
+
|
|
578
|
+
// resolveDirLink chases a directory that is itself a symlink or NTFS junction
|
|
579
|
+
// to its target (bounded against link cycles). os.Readlink is the probe:
|
|
580
|
+
// it resolves junctions, which report neither ModeSymlink nor an
|
|
581
|
+
// EvalSymlinks-traversable path.
|
|
582
|
+
func resolveDirLink(dir string) string {
|
|
583
|
+
for i := 0; i < 8; i++ {
|
|
584
|
+
target, err := os.Readlink(dir)
|
|
585
|
+
if err != nil {
|
|
586
|
+
return dir
|
|
587
|
+
}
|
|
588
|
+
if !filepath.IsAbs(target) {
|
|
589
|
+
target = filepath.Join(filepath.Dir(dir), target)
|
|
590
|
+
}
|
|
591
|
+
dir = target
|
|
592
|
+
}
|
|
593
|
+
return dir
|
|
594
|
+
}
|
|
595
|
+
|
|
524
596
|
// ttsxCommand builds an exec.Cmd that runs ttsx with the given args.
|
|
525
597
|
// When TTSC_TTSX_BINARY has a script extension (.js, .ts, …) the binary is
|
|
526
598
|
// invoked via the Node runtime so it is executed correctly on all platforms.
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ttsc/banner",
|
|
3
|
-
"version": "0.16.
|
|
3
|
+
"version": "0.16.8",
|
|
4
4
|
"description": "First-party ttsc plugin that adds package-documentation JSDoc banners during emit.",
|
|
5
5
|
"main": "lib/index.js",
|
|
6
6
|
"types": "lib/index.d.ts",
|
|
@@ -35,7 +35,7 @@
|
|
|
35
35
|
"@types/node": "^25.3.0",
|
|
36
36
|
"rimraf": "^6.1.2",
|
|
37
37
|
"typescript": "7.0.1-rc",
|
|
38
|
-
"ttsc": "0.16.
|
|
38
|
+
"ttsc": "0.16.8"
|
|
39
39
|
},
|
|
40
40
|
"repository": {
|
|
41
41
|
"type": "git",
|