-
Notifications
You must be signed in to change notification settings - Fork 25
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* lets start with this * Be able to get files and identify directory * log the full path, needed later for the recursion * we need to trim this to look good * Return matched files in the same way list does it * simplify some logic * fix search in the middle of the file name * we have recursion! * move search in to its own file and add some config values * use Contains for blacklist * remove debug print & lowercase the blacklist * make folders show first in the filesystem * handle relative config path * fix: symlinks detecting * fix: config loading with default values * Revert: e8ef74a as it does not work
- Loading branch information
1 parent
5858856
commit c2d1b27
Showing
7 changed files
with
168 additions
and
20 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,135 @@ | ||
package router | ||
|
||
import ( | ||
"net/http" | ||
"path/filepath" | ||
"strings" | ||
|
||
"github.com/gin-gonic/gin" | ||
|
||
"github.com/pelican-dev/wings/config" | ||
"github.com/pelican-dev/wings/internal/ufs" | ||
"github.com/pelican-dev/wings/router/middleware" | ||
"github.com/pelican-dev/wings/server" | ||
"github.com/pelican-dev/wings/server/filesystem" | ||
) | ||
|
||
// Structs needed to respond with the matched files and all their info | ||
type customFileInfo struct { | ||
ufs.FileInfo | ||
newName string | ||
} | ||
|
||
func (cfi customFileInfo) Name() string { | ||
return cfi.newName // Return the custom name (i.e., with the directory prefix) | ||
} | ||
|
||
// Helper function to append matched entries | ||
func appendMatchedEntry(matchedEntries *[]filesystem.Stat, fileInfo ufs.FileInfo, fullPath string, fileType string) { | ||
*matchedEntries = append(*matchedEntries, filesystem.Stat{ | ||
FileInfo: customFileInfo{ | ||
FileInfo: fileInfo, | ||
newName: fullPath, | ||
}, | ||
Mimetype: fileType, | ||
}) | ||
} | ||
|
||
// todo make this config value work as now it cause a panic | ||
//var blacklist = config.Get().SearchRecursion.BlacklistedDirs | ||
|
||
var blacklist = []string{"node_modules", ".wine", "appcache", "depotcache", "vendor"} | ||
|
||
// Helper function to check if a directory name is in the blacklist | ||
func isBlacklisted(dirName string) bool { | ||
for _, blacklisted := range blacklist { | ||
if strings.Contains(dirName, strings.ToLower(blacklisted)) { | ||
return true | ||
} | ||
} | ||
return false | ||
} | ||
|
||
// Recursive function to search through directories | ||
func searchDirectory(s *server.Server, dir string, patternLower string, depth int, matchedEntries *[]filesystem.Stat, matchedDirectories *[]string, c *gin.Context) { | ||
if depth > config.Get().SearchRecursion.MaxRecursionDepth { | ||
return // Stop recursion if depth exceeds | ||
} | ||
|
||
stats, err := s.Filesystem().ListDirectory(dir) | ||
if err != nil { | ||
c.JSON(http.StatusOK, gin.H{"message": "Directory not found"}) | ||
return | ||
} | ||
|
||
for _, fileInfo := range stats { | ||
fileName := fileInfo.Name() | ||
fileType := fileInfo.Mimetype | ||
fileNameLower := strings.ToLower(fileName) | ||
fullPath := filepath.Join(dir, fileName) | ||
|
||
// Store directories separately | ||
if fileType == "inode/directory" { | ||
if isBlacklisted(fileNameLower) { | ||
continue // Skip blacklisted directories | ||
} | ||
*matchedDirectories = append(*matchedDirectories, fullPath) | ||
|
||
// Recursive search in the matched directory | ||
searchDirectory(s, fullPath, patternLower, depth+1, matchedEntries, matchedDirectories, c) | ||
} | ||
|
||
// Wildcard or exact matching logic | ||
if strings.ContainsAny(patternLower, "*?") { | ||
if match, _ := filepath.Match(patternLower, fileNameLower); match { | ||
appendMatchedEntry(matchedEntries, fileInfo, fullPath, fileType) | ||
} | ||
} else { | ||
// Check for substring matches (case-insensitive) | ||
if strings.Contains(fileNameLower, patternLower) { | ||
appendMatchedEntry(matchedEntries, fileInfo, fullPath, fileType) | ||
} else { | ||
// Extension matching logic | ||
ext := filepath.Ext(fileNameLower) | ||
if strings.HasPrefix(patternLower, ".") || !strings.Contains(patternLower, ".") { | ||
// Match extension without dot | ||
if strings.TrimPrefix(ext, ".") == strings.TrimPrefix(patternLower, ".") { | ||
appendMatchedEntry(matchedEntries, fileInfo, fullPath, fileType) | ||
} | ||
} else if fileNameLower == patternLower { // Full name match | ||
appendMatchedEntry(matchedEntries, fileInfo, fullPath, fileType) | ||
} | ||
} | ||
} | ||
} | ||
} | ||
|
||
func getFilesBySearch(c *gin.Context) { | ||
s := middleware.ExtractServer(c) | ||
dir := strings.TrimSuffix(c.Query("directory"), "/") | ||
pattern := c.Query("pattern") | ||
|
||
// Convert the pattern to lowercase for case-insensitive comparison | ||
patternLower := strings.ToLower(pattern) | ||
|
||
// Check if the pattern length is at least 3 characters | ||
if len(pattern) < 3 { | ||
c.JSON(http.StatusBadRequest, gin.H{"error": "Pattern must be at least 3 characters long"}) | ||
return | ||
} | ||
|
||
// Prepare slices to store matched stats and directories | ||
matchedEntries := []filesystem.Stat{} | ||
matchedDirectories := []string{} | ||
|
||
// Start the search from the initial directory | ||
searchDirectory(s, dir, patternLower, 0, &matchedEntries, &matchedDirectories, c) | ||
|
||
// Return the matched stats (only those that matched the pattern) and directories separately | ||
if len(matchedEntries) == 0 && len(matchedDirectories) != 0 { | ||
c.JSON(http.StatusOK, gin.H{"message": "No matches found."}) | ||
} else { | ||
// Return all matched files with their stats and the name now included the directory | ||
c.JSON(http.StatusOK, matchedEntries) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters