Skip to content

Commit a18017b

Browse files
committed
fix: recursive scanning for packages with slashes in domain names
- Fixed buildPkgConfigPaths, buildIncludePaths, buildLibraryPaths, and createBuildEnvironmentScript to use recursive scanning - Now properly finds packages like github.com/kkos/oniguruma - Added depth limit (3) to prevent infinite recursion - All environment variables now include packages with nested domain structures
1 parent 482e658 commit a18017b

File tree

1 file changed

+161
-109
lines changed

1 file changed

+161
-109
lines changed

packages/launchpad/src/install-helpers.ts

Lines changed: 161 additions & 109 deletions
Original file line numberDiff line numberDiff line change
@@ -85,108 +85,147 @@ export async function createShims(packageDir: string, installPath: string, domai
8585
}
8686

8787
// Add library paths from all installed packages in the environment
88-
try {
89-
const domains = fs.readdirSync(installPath, { withFileTypes: true })
90-
.filter(dirent => dirent.isDirectory()
91-
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
92-
93-
for (const domainEntry of domains) {
94-
const domainPath = path.join(installPath, domainEntry.name)
95-
if (fs.existsSync(domainPath)) {
96-
const versions = fs.readdirSync(domainPath, { withFileTypes: true })
97-
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
98-
99-
for (const versionEntry of versions) {
100-
const versionPath = path.join(domainPath, versionEntry.name)
101-
const depLibDirs = [
102-
path.join(versionPath, 'lib'),
103-
path.join(versionPath, 'lib64'),
104-
]
105-
106-
for (const libDir of depLibDirs) {
107-
if (fs.existsSync(libDir) && !libraryPaths.includes(libDir)) {
108-
libraryPaths.push(libDir)
88+
function scanDirectory(dir: string, depth = 0) {
89+
try {
90+
const entries = fs.readdirSync(dir, { withFileTypes: true })
91+
.filter(dirent => dirent.isDirectory()
92+
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
93+
94+
for (const entry of entries) {
95+
const entryPath = path.join(dir, entry.name)
96+
97+
// Check if this directory contains version directories (v*)
98+
const hasVersionDirs = fs.readdirSync(entryPath, { withFileTypes: true })
99+
.some(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
100+
101+
if (hasVersionDirs) {
102+
// This is a package directory, scan for library files
103+
const versions = fs.readdirSync(entryPath, { withFileTypes: true })
104+
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
105+
106+
for (const versionEntry of versions) {
107+
const versionPath = path.join(entryPath, versionEntry.name)
108+
const depLibDirs = [
109+
path.join(versionPath, 'lib'),
110+
path.join(versionPath, 'lib64'),
111+
]
112+
113+
for (const libDir of depLibDirs) {
114+
if (fs.existsSync(libDir) && !libraryPaths.includes(libDir)) {
115+
libraryPaths.push(libDir)
116+
}
109117
}
110118
}
119+
} else if (depth < 3) {
120+
// Recursively scan subdirectories (limit depth to avoid infinite recursion)
121+
scanDirectory(entryPath, depth + 1)
111122
}
112123
}
113124
}
114-
}
115-
catch {
116-
// Ignore errors reading directories
125+
catch {
126+
// Ignore errors reading directories
127+
}
117128
}
118129

130+
scanDirectory(installPath)
131+
119132
return libraryPaths
120133
}
121134

122135
// Helper function to build pkg-config paths for all installed packages
123136
function buildPkgConfigPaths(installPath: string): string[] {
124137
const pkgConfigPaths: string[] = []
125138

126-
try {
127-
const domains = fs.readdirSync(installPath, { withFileTypes: true })
128-
.filter(dirent => dirent.isDirectory()
129-
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
130-
131-
for (const domainEntry of domains) {
132-
const domainPath = path.join(installPath, domainEntry.name)
133-
if (fs.existsSync(domainPath)) {
134-
const versions = fs.readdirSync(domainPath, { withFileTypes: true })
135-
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
136-
137-
for (const versionEntry of versions) {
138-
const versionPath = path.join(domainPath, versionEntry.name)
139-
const pkgConfigDirs = [
140-
path.join(versionPath, 'lib', 'pkgconfig'),
141-
path.join(versionPath, 'lib64', 'pkgconfig'),
142-
]
143-
144-
for (const pkgConfigDir of pkgConfigDirs) {
145-
if (fs.existsSync(pkgConfigDir) && !pkgConfigPaths.includes(pkgConfigDir)) {
146-
pkgConfigPaths.push(pkgConfigDir)
139+
function scanDirectory(dir: string, depth = 0) {
140+
try {
141+
const entries = fs.readdirSync(dir, { withFileTypes: true })
142+
.filter(dirent => dirent.isDirectory()
143+
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
144+
145+
for (const entry of entries) {
146+
const entryPath = path.join(dir, entry.name)
147+
148+
// Check if this directory contains version directories (v*)
149+
const hasVersionDirs = fs.readdirSync(entryPath, { withFileTypes: true })
150+
.some(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
151+
152+
if (hasVersionDirs) {
153+
// This is a package directory, scan for pkg-config files
154+
const versions = fs.readdirSync(entryPath, { withFileTypes: true })
155+
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
156+
157+
for (const versionEntry of versions) {
158+
const versionPath = path.join(entryPath, versionEntry.name)
159+
const pkgConfigDirs = [
160+
path.join(versionPath, 'lib', 'pkgconfig'),
161+
path.join(versionPath, 'lib64', 'pkgconfig'),
162+
]
163+
164+
for (const pkgConfigDir of pkgConfigDirs) {
165+
if (fs.existsSync(pkgConfigDir) && !pkgConfigPaths.includes(pkgConfigDir)) {
166+
pkgConfigPaths.push(pkgConfigDir)
167+
}
147168
}
148169
}
149170
}
171+
else if (depth < 3) {
172+
// Recursively scan subdirectories (limit depth to avoid infinite recursion)
173+
scanDirectory(entryPath, depth + 1)
174+
}
150175
}
151176
}
152-
}
153-
catch {
154-
// Ignore errors reading directories
177+
catch {
178+
// Ignore errors reading directories
179+
}
155180
}
156181

182+
scanDirectory(installPath)
157183
return pkgConfigPaths
158184
}
159185

160186
// Helper function to build include paths for all installed packages
161187
function buildIncludePaths(installPath: string): string[] {
162188
const includePaths: string[] = []
163189

164-
try {
165-
const domains = fs.readdirSync(installPath, { withFileTypes: true })
166-
.filter(dirent => dirent.isDirectory()
167-
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
190+
function scanDirectory(dir: string, depth = 0) {
191+
try {
192+
const entries = fs.readdirSync(dir, { withFileTypes: true })
193+
.filter(dirent => dirent.isDirectory()
194+
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
168195

169-
for (const domainEntry of domains) {
170-
const domainPath = path.join(installPath, domainEntry.name)
171-
if (fs.existsSync(domainPath)) {
172-
const versions = fs.readdirSync(domainPath, { withFileTypes: true })
173-
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
196+
for (const entry of entries) {
197+
const entryPath = path.join(dir, entry.name)
174198

175-
for (const versionEntry of versions) {
176-
const versionPath = path.join(domainPath, versionEntry.name)
177-
const includeDir = path.join(versionPath, 'include')
199+
// Check if this directory contains version directories (v*)
200+
const hasVersionDirs = fs.readdirSync(entryPath, { withFileTypes: true })
201+
.some(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
178202

179-
if (fs.existsSync(includeDir) && !includePaths.includes(includeDir)) {
180-
includePaths.push(includeDir)
203+
if (hasVersionDirs) {
204+
// This is a package directory, scan for include files
205+
const versions = fs.readdirSync(entryPath, { withFileTypes: true })
206+
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
207+
208+
for (const versionEntry of versions) {
209+
const versionPath = path.join(entryPath, versionEntry.name)
210+
const includeDir = path.join(versionPath, 'include')
211+
212+
if (fs.existsSync(includeDir) && !includePaths.includes(includeDir)) {
213+
includePaths.push(includeDir)
214+
}
181215
}
182216
}
217+
else if (depth < 3) {
218+
// Recursively scan subdirectories (limit depth to avoid infinite recursion)
219+
scanDirectory(entryPath, depth + 1)
220+
}
183221
}
184222
}
185-
}
186-
catch {
187-
// Ignore errors reading directories
223+
catch {
224+
// Ignore errors reading directories
225+
}
188226
}
189227

228+
scanDirectory(installPath)
190229
return includePaths
191230
}
192231

@@ -566,60 +605,73 @@ export async function createBuildEnvironmentScript(installPath: string): Promise
566605
const includePaths: string[] = []
567606
const binPaths: string[] = []
568607

569-
try {
570-
const domains = fs.readdirSync(installPath, { withFileTypes: true })
571-
.filter(dirent => dirent.isDirectory()
572-
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
573-
574-
for (const domainEntry of domains) {
575-
const domainPath = path.join(installPath, domainEntry.name)
576-
if (fs.existsSync(domainPath)) {
577-
const versions = fs.readdirSync(domainPath, { withFileTypes: true })
578-
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
579-
580-
for (const versionEntry of versions) {
581-
const versionPath = path.join(domainPath, versionEntry.name)
582-
583-
// Add library paths
584-
const libDirs = [
585-
path.join(versionPath, 'lib'),
586-
path.join(versionPath, 'lib64'),
587-
]
588-
for (const libDir of libDirs) {
589-
if (fs.existsSync(libDir) && !libraryPaths.includes(libDir)) {
590-
libraryPaths.push(libDir)
608+
function scanDirectory(dir: string, depth = 0) {
609+
try {
610+
const entries = fs.readdirSync(dir, { withFileTypes: true })
611+
.filter(dirent => dirent.isDirectory()
612+
&& !['bin', 'sbin', 'lib', 'lib64', 'share', 'include', 'etc', 'pkgs', '.tmp', '.cache'].includes(dirent.name))
613+
614+
for (const entry of entries) {
615+
const entryPath = path.join(dir, entry.name)
616+
617+
// Check if this directory contains version directories (v*)
618+
const hasVersionDirs = fs.readdirSync(entryPath, { withFileTypes: true })
619+
.some(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
620+
621+
if (hasVersionDirs) {
622+
// This is a package directory, scan for all paths
623+
const versions = fs.readdirSync(entryPath, { withFileTypes: true })
624+
.filter(dirent => dirent.isDirectory() && dirent.name.startsWith('v'))
625+
626+
for (const versionEntry of versions) {
627+
const versionPath = path.join(entryPath, versionEntry.name)
628+
629+
// Add library paths
630+
const libDirs = [
631+
path.join(versionPath, 'lib'),
632+
path.join(versionPath, 'lib64'),
633+
]
634+
for (const libDir of libDirs) {
635+
if (fs.existsSync(libDir) && !libraryPaths.includes(libDir)) {
636+
libraryPaths.push(libDir)
637+
}
591638
}
592-
}
593639

594-
// Add pkg-config paths
595-
const pkgConfigDirs = [
596-
path.join(versionPath, 'lib', 'pkgconfig'),
597-
path.join(versionPath, 'lib64', 'pkgconfig'),
598-
]
599-
for (const pkgConfigDir of pkgConfigDirs) {
600-
if (fs.existsSync(pkgConfigDir) && !pkgConfigPaths.includes(pkgConfigDir)) {
601-
pkgConfigPaths.push(pkgConfigDir)
640+
// Add pkg-config paths
641+
const pkgConfigDirs = [
642+
path.join(versionPath, 'lib', 'pkgconfig'),
643+
path.join(versionPath, 'lib64', 'pkgconfig'),
644+
]
645+
for (const pkgConfigDir of pkgConfigDirs) {
646+
if (fs.existsSync(pkgConfigDir) && !pkgConfigPaths.includes(pkgConfigDir)) {
647+
pkgConfigPaths.push(pkgConfigDir)
648+
}
602649
}
603-
}
604650

605-
// Add include paths
606-
const includeDir = path.join(versionPath, 'include')
607-
if (fs.existsSync(includeDir) && !includePaths.includes(includeDir)) {
608-
includePaths.push(includeDir)
609-
}
651+
// Add include paths
652+
const includeDir = path.join(versionPath, 'include')
653+
if (fs.existsSync(includeDir) && !includePaths.includes(includeDir)) {
654+
includePaths.push(includeDir)
655+
}
610656

611-
// Add bin paths
612-
const binDir = path.join(versionPath, 'bin')
613-
if (fs.existsSync(binDir) && !binPaths.includes(binDir)) {
614-
binPaths.push(binDir)
657+
// Add bin paths
658+
const binDir = path.join(versionPath, 'bin')
659+
if (fs.existsSync(binDir) && !binPaths.includes(binDir)) {
660+
binPaths.push(binDir)
661+
}
615662
}
663+
} else if (depth < 3) {
664+
// Recursively scan subdirectories (limit depth to avoid infinite recursion)
665+
scanDirectory(entryPath, depth + 1)
616666
}
617667
}
618668
}
669+
catch {
670+
// Ignore errors reading directories
671+
}
619672
}
620-
catch {
621-
// Ignore errors reading directories
622-
}
673+
674+
scanDirectory(installPath)
623675

624676
// Create the environment setup script
625677
let scriptContent = `#!/bin/sh

0 commit comments

Comments
 (0)