package filemanager

import (
	"archive/zip"
	"crypto/md5"
	"crypto/sha256"
	"encoding/base64"
	"encoding/hex"
	"fmt"
	"io"
	"os"
	"path/filepath"
	"runtime"
	"sort"
	"strings"
	"sync"
	"time"
)

// FileManager - Dosya yönetim servisi
type FileManager struct {
	mu              sync.RWMutex
	currentPath     string
	clipboard       []ClipboardItem
	clipboardOp     string // "copy" veya "cut"
	transfers       map[string]*FileTransfer
	maxChunkSize    int64
	allowedPaths    []string // İzin verilen yollar (güvenlik)
	blockedPaths    []string // Engellenen yollar
}

// FileInfo - Dosya bilgisi
type FileInfo struct {
	Name         string    `json:"name"`
	Path         string    `json:"path"`
	Size         int64     `json:"size"`
	IsDir        bool      `json:"isDir"`
	IsHidden     bool      `json:"isHidden"`
	IsSystem     bool      `json:"isSystem"`
	IsReadOnly   bool      `json:"isReadOnly"`
	Extension    string    `json:"extension"`
	MimeType     string    `json:"mimeType"`
	ModTime      time.Time `json:"modTime"`
	CreateTime   time.Time `json:"createTime"`
	AccessTime   time.Time `json:"accessTime"`
	Permissions  string    `json:"permissions"`
	Owner        string    `json:"owner"`
	Group        string    `json:"group"`
	SymLink      string    `json:"symLink,omitempty"`
	ChildCount   int       `json:"childCount,omitempty"` // Klasör için
	Icon         string    `json:"icon,omitempty"`
}

// DirectoryContents - Klasör içeriği
type DirectoryContents struct {
	Path       string     `json:"path"`
	ParentPath string     `json:"parentPath"`
	Items      []FileInfo `json:"items"`
	TotalSize  int64      `json:"totalSize"`
	FileCount  int        `json:"fileCount"`
	DirCount   int        `json:"dirCount"`
	Error      string     `json:"error,omitempty"`
}

// DriveInfo - Sürücü bilgisi
type DriveInfo struct {
	Name       string  `json:"name"`
	Path       string  `json:"path"`
	Label      string  `json:"label"`
	FileSystem string  `json:"fileSystem"`
	Type       string  `json:"type"` // "fixed", "removable", "network", "cdrom"
	TotalSize  uint64  `json:"totalSize"`
	FreeSize   uint64  `json:"freeSize"`
	UsedSize   uint64  `json:"usedSize"`
	UsedPercent float64 `json:"usedPercent"`
}

// ClipboardItem - Pano öğesi
type ClipboardItem struct {
	Path  string `json:"path"`
	IsDir bool   `json:"isDir"`
}

// FileTransfer - Dosya transfer durumu
type FileTransfer struct {
	ID           string    `json:"id"`
	FileName     string    `json:"fileName"`
	FilePath     string    `json:"filePath"`
	FileSize     int64     `json:"fileSize"`
	Transferred  int64     `json:"transferred"`
	ChunkSize    int64     `json:"chunkSize"`
	ChunkCount   int       `json:"chunkCount"`
	CurrentChunk int       `json:"currentChunk"`
	Direction    string    `json:"direction"` // "upload" veya "download"
	Status       string    `json:"status"`    // "pending", "transferring", "completed", "error", "cancelled"
	Error        string    `json:"error,omitempty"`
	StartTime    time.Time `json:"startTime"`
	EndTime      time.Time `json:"endTime,omitempty"`
	Speed        float64   `json:"speed"` // Bytes per second
	Hash         string    `json:"hash,omitempty"`
}

// FileChunk - Dosya parçası
type FileChunk struct {
	TransferID string `json:"transferId"`
	ChunkIndex int    `json:"chunkIndex"`
	Data       string `json:"data"` // Base64 encoded
	Size       int    `json:"size"`
	Hash       string `json:"hash"` // Chunk hash (MD5)
}

// NewFileManager - Yeni dosya yöneticisi
func NewFileManager() *FileManager {
	fm := &FileManager{
		currentPath:  getHomePath(),
		transfers:    make(map[string]*FileTransfer),
		maxChunkSize: 512 * 1024, // 512 KB
		blockedPaths: []string{
			"C:\\Windows\\System32\\config",
			"/etc/shadow",
			"/etc/passwd",
		},
	}
	return fm
}

// getHomePath - Ana dizini al
func getHomePath() string {
	if home, err := os.UserHomeDir(); err == nil {
		return home
	}
	if runtime.GOOS == "windows" {
		return "C:\\"
	}
	return "/"
}

// GetDrives - Sürücüleri listele (Windows)
func (fm *FileManager) GetDrives() []DriveInfo {
	var drives []DriveInfo

	if runtime.GOOS == "windows" {
		for _, drive := range "ABCDEFGHIJKLMNOPQRSTUVWXYZ" {
			path := string(drive) + ":\\"
			if _, err := os.Stat(path); err == nil {
				info := DriveInfo{
					Name: string(drive) + ":",
					Path: path,
				}

				// Disk boyutlarını al
				if usage := getDiskUsage(path); usage != nil {
					info.TotalSize = usage.Total
					info.FreeSize = usage.Free
					info.UsedSize = usage.Used
					if info.TotalSize > 0 {
						info.UsedPercent = float64(info.UsedSize) / float64(info.TotalSize) * 100
					}
				}

				drives = append(drives, info)
			}
		}
	} else {
		// Linux/macOS
		drives = append(drives, DriveInfo{
			Name: "Root",
			Path: "/",
		})

		// Mount noktalarını ekle
		homeDir := getHomePath()
		drives = append(drives, DriveInfo{
			Name: "Home",
			Path: homeDir,
		})
	}

	return drives
}

// ListDirectory - Klasör içeriğini listele
func (fm *FileManager) ListDirectory(path string, showHidden bool, sortBy string, sortDesc bool) (*DirectoryContents, error) {
	if path == "" {
		path = fm.currentPath
	}

	// Güvenlik kontrolü
	if !fm.isPathAllowed(path) {
		return nil, fmt.Errorf("erişim engellendi: %s", path)
	}

	// Path'i düzelt
	path = filepath.Clean(path)

	info, err := os.Stat(path)
	if err != nil {
		return nil, err
	}

	if !info.IsDir() {
		return nil, fmt.Errorf("bu bir klasör değil: %s", path)
	}

	entries, err := os.ReadDir(path)
	if err != nil {
		return nil, err
	}

	contents := &DirectoryContents{
		Path:       path,
		ParentPath: filepath.Dir(path),
		Items:      make([]FileInfo, 0),
	}

	for _, entry := range entries {
		info, err := entry.Info()
		if err != nil {
			continue
		}

		// Gizli dosyaları kontrol et
		isHidden := isHiddenFile(entry.Name(), path)
		if !showHidden && isHidden {
			continue
		}

		fileInfo := fm.createFileInfo(path, info, isHidden)
		contents.Items = append(contents.Items, fileInfo)

		if info.IsDir() {
			contents.DirCount++
		} else {
			contents.FileCount++
			contents.TotalSize += info.Size()
		}
	}

	// Sıralama
	fm.sortItems(contents.Items, sortBy, sortDesc)

	fm.mu.Lock()
	fm.currentPath = path
	fm.mu.Unlock()

	return contents, nil
}

// createFileInfo - FileInfo oluştur
func (fm *FileManager) createFileInfo(basePath string, info os.FileInfo, isHidden bool) FileInfo {
	fullPath := filepath.Join(basePath, info.Name())

	fileInfo := FileInfo{
		Name:        info.Name(),
		Path:        fullPath,
		Size:        info.Size(),
		IsDir:       info.IsDir(),
		IsHidden:    isHidden,
		ModTime:     info.ModTime(),
		Permissions: info.Mode().String(),
	}

	if !info.IsDir() {
		fileInfo.Extension = strings.ToLower(filepath.Ext(info.Name()))
		fileInfo.MimeType = getMimeType(fileInfo.Extension)
		fileInfo.Icon = getFileIcon(fileInfo.Extension)
	} else {
		fileInfo.Icon = "folder"
		// Alt öğe sayısını al
		if entries, err := os.ReadDir(fullPath); err == nil {
			fileInfo.ChildCount = len(entries)
		}
	}

	// Symlink kontrolü
	if info.Mode()&os.ModeSymlink != 0 {
		if target, err := os.Readlink(fullPath); err == nil {
			fileInfo.SymLink = target
		}
	}

	return fileInfo
}

// sortItems - Öğeleri sırala
func (fm *FileManager) sortItems(items []FileInfo, sortBy string, sortDesc bool) {
	sort.Slice(items, func(i, j int) bool {
		// Klasörler her zaman önce
		if items[i].IsDir != items[j].IsDir {
			return items[i].IsDir
		}

		var result bool
		switch sortBy {
		case "size":
			result = items[i].Size < items[j].Size
		case "date", "modTime":
			result = items[i].ModTime.Before(items[j].ModTime)
		case "type", "extension":
			result = items[i].Extension < items[j].Extension
		default: // "name"
			result = strings.ToLower(items[i].Name) < strings.ToLower(items[j].Name)
		}

		if sortDesc {
			return !result
		}
		return result
	})
}

// GetFileInfo - Tek dosya bilgisi
func (fm *FileManager) GetFileInfo(path string) (*FileInfo, error) {
	if !fm.isPathAllowed(path) {
		return nil, fmt.Errorf("erişim engellendi: %s", path)
	}

	info, err := os.Stat(path)
	if err != nil {
		return nil, err
	}

	isHidden := isHiddenFile(info.Name(), filepath.Dir(path))
	fileInfo := fm.createFileInfo(filepath.Dir(path), info, isHidden)

	// Hash hesapla (küçük dosyalar için)
	if !info.IsDir() && info.Size() < 10*1024*1024 { // 10 MB altı
		if hash, err := fm.calculateFileHash(path); err == nil {
			fileInfo.Owner = hash // Hash'i owner alanına koy (geçici)
		}
	}

	return &fileInfo, nil
}

// CreateDirectory - Klasör oluştur
func (fm *FileManager) CreateDirectory(path string) error {
	if !fm.isPathAllowed(filepath.Dir(path)) {
		return fmt.Errorf("erişim engellendi: %s", path)
	}
	return os.MkdirAll(path, 0755)
}

// CreateFile - Boş dosya oluştur
func (fm *FileManager) CreateFile(path string) error {
	if !fm.isPathAllowed(filepath.Dir(path)) {
		return fmt.Errorf("erişim engellendi: %s", path)
	}

	file, err := os.Create(path)
	if err != nil {
		return err
	}
	return file.Close()
}

// Delete - Dosya veya klasör sil
func (fm *FileManager) Delete(path string, permanent bool) error {
	if !fm.isPathAllowed(path) {
		return fmt.Errorf("erişim engellendi: %s", path)
	}

	if permanent {
		return os.RemoveAll(path)
	}

	// Çöp kutusuna taşı (Windows)
	if runtime.GOOS == "windows" {
		return moveToRecycleBin(path)
	}

	// Linux/macOS için doğrudan sil
	return os.RemoveAll(path)
}

// Rename - Yeniden adlandır
func (fm *FileManager) Rename(oldPath, newName string) error {
	if !fm.isPathAllowed(oldPath) {
		return fmt.Errorf("erişim engellendi: %s", oldPath)
	}

	dir := filepath.Dir(oldPath)
	newPath := filepath.Join(dir, newName)

	return os.Rename(oldPath, newPath)
}

// Move - Taşı
func (fm *FileManager) Move(src, dst string) error {
	if !fm.isPathAllowed(src) || !fm.isPathAllowed(dst) {
		return fmt.Errorf("erişim engellendi")
	}

	// Hedef klasör mü kontrol et
	dstInfo, err := os.Stat(dst)
	if err == nil && dstInfo.IsDir() {
		dst = filepath.Join(dst, filepath.Base(src))
	}

	return os.Rename(src, dst)
}

// Copy - Kopyala
func (fm *FileManager) Copy(src, dst string) error {
	if !fm.isPathAllowed(src) || !fm.isPathAllowed(dst) {
		return fmt.Errorf("erişim engellendi")
	}

	srcInfo, err := os.Stat(src)
	if err != nil {
		return err
	}

	// Hedef klasör mü kontrol et
	dstInfo, err := os.Stat(dst)
	if err == nil && dstInfo.IsDir() {
		dst = filepath.Join(dst, filepath.Base(src))
	}

	if srcInfo.IsDir() {
		return fm.copyDirectory(src, dst)
	}
	return fm.copyFile(src, dst)
}

// copyFile - Dosya kopyala
func (fm *FileManager) copyFile(src, dst string) error {
	srcFile, err := os.Open(src)
	if err != nil {
		return err
	}
	defer srcFile.Close()

	dstFile, err := os.Create(dst)
	if err != nil {
		return err
	}
	defer dstFile.Close()

	_, err = io.Copy(dstFile, srcFile)
	if err != nil {
		return err
	}

	// İzinleri kopyala
	srcInfo, _ := os.Stat(src)
	return os.Chmod(dst, srcInfo.Mode())
}

// copyDirectory - Klasör kopyala
func (fm *FileManager) copyDirectory(src, dst string) error {
	srcInfo, err := os.Stat(src)
	if err != nil {
		return err
	}

	if err := os.MkdirAll(dst, srcInfo.Mode()); err != nil {
		return err
	}

	entries, err := os.ReadDir(src)
	if err != nil {
		return err
	}

	for _, entry := range entries {
		srcPath := filepath.Join(src, entry.Name())
		dstPath := filepath.Join(dst, entry.Name())

		if entry.IsDir() {
			if err := fm.copyDirectory(srcPath, dstPath); err != nil {
				return err
			}
		} else {
			if err := fm.copyFile(srcPath, dstPath); err != nil {
				return err
			}
		}
	}

	return nil
}

// ReadFile - Dosya oku (metin)
func (fm *FileManager) ReadFile(path string, maxSize int64) (string, error) {
	if !fm.isPathAllowed(path) {
		return "", fmt.Errorf("erişim engellendi: %s", path)
	}

	if maxSize <= 0 {
		maxSize = 1024 * 1024 // 1 MB
	}

	info, err := os.Stat(path)
	if err != nil {
		return "", err
	}

	if info.Size() > maxSize {
		return "", fmt.Errorf("dosya çok büyük: %d bytes (max: %d)", info.Size(), maxSize)
	}

	data, err := os.ReadFile(path)
	if err != nil {
		return "", err
	}

	return string(data), nil
}

// WriteFile - Dosyaya yaz
func (fm *FileManager) WriteFile(path, content string, append bool) error {
	if !fm.isPathAllowed(path) {
		return fmt.Errorf("erişim engellendi: %s", path)
	}

	flag := os.O_WRONLY | os.O_CREATE
	if append {
		flag |= os.O_APPEND
	} else {
		flag |= os.O_TRUNC
	}

	file, err := os.OpenFile(path, flag, 0644)
	if err != nil {
		return err
	}
	defer file.Close()

	_, err = file.WriteString(content)
	return err
}

// Search - Dosya ara
func (fm *FileManager) Search(path, pattern string, maxResults int, includeHidden bool) ([]FileInfo, error) {
	if !fm.isPathAllowed(path) {
		return nil, fmt.Errorf("erişim engellendi: %s", path)
	}

	if maxResults <= 0 {
		maxResults = 100
	}

	var results []FileInfo
	pattern = strings.ToLower(pattern)

	err := filepath.WalkDir(path, func(p string, d os.DirEntry, err error) error {
		if err != nil {
			return nil // Hataları atla
		}

		if len(results) >= maxResults {
			return filepath.SkipAll
		}

		name := strings.ToLower(d.Name())
		if !strings.Contains(name, pattern) {
			return nil
		}

		isHidden := isHiddenFile(d.Name(), filepath.Dir(p))
		if !includeHidden && isHidden {
			return nil
		}

		info, err := d.Info()
		if err != nil {
			return nil
		}

		fileInfo := fm.createFileInfo(filepath.Dir(p), info, isHidden)
		results = append(results, fileInfo)

		return nil
	})

	return results, err
}

// Compress - Sıkıştır (ZIP)
func (fm *FileManager) Compress(paths []string, outputPath string) error {
	for _, p := range paths {
		if !fm.isPathAllowed(p) {
			return fmt.Errorf("erişim engellendi: %s", p)
		}
	}

	if !fm.isPathAllowed(outputPath) {
		return fmt.Errorf("erişim engellendi: %s", outputPath)
	}

	zipFile, err := os.Create(outputPath)
	if err != nil {
		return err
	}
	defer zipFile.Close()

	zipWriter := zip.NewWriter(zipFile)
	defer zipWriter.Close()

	for _, path := range paths {
		err := fm.addToZip(zipWriter, path, filepath.Base(path))
		if err != nil {
			return err
		}
	}

	return nil
}

// addToZip - ZIP'e ekle
func (fm *FileManager) addToZip(zipWriter *zip.Writer, path, basePath string) error {
	info, err := os.Stat(path)
	if err != nil {
		return err
	}

	if info.IsDir() {
		entries, err := os.ReadDir(path)
		if err != nil {
			return err
		}

		for _, entry := range entries {
			entryPath := filepath.Join(path, entry.Name())
			entryBase := filepath.Join(basePath, entry.Name())
			if err := fm.addToZip(zipWriter, entryPath, entryBase); err != nil {
				return err
			}
		}
		return nil
	}

	file, err := os.Open(path)
	if err != nil {
		return err
	}
	defer file.Close()

	writer, err := zipWriter.Create(basePath)
	if err != nil {
		return err
	}

	_, err = io.Copy(writer, file)
	return err
}

// Extract - Çıkart (ZIP)
func (fm *FileManager) Extract(zipPath, outputPath string) error {
	if !fm.isPathAllowed(zipPath) || !fm.isPathAllowed(outputPath) {
		return fmt.Errorf("erişim engellendi")
	}

	reader, err := zip.OpenReader(zipPath)
	if err != nil {
		return err
	}
	defer reader.Close()

	for _, file := range reader.File {
		path := filepath.Join(outputPath, file.Name)

		// Zip slip koruması
		if !strings.HasPrefix(path, filepath.Clean(outputPath)+string(os.PathSeparator)) {
			return fmt.Errorf("geçersiz dosya yolu: %s", file.Name)
		}

		if file.FileInfo().IsDir() {
			os.MkdirAll(path, file.Mode())
			continue
		}

		if err := os.MkdirAll(filepath.Dir(path), 0755); err != nil {
			return err
		}

		dstFile, err := os.OpenFile(path, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, file.Mode())
		if err != nil {
			return err
		}

		srcFile, err := file.Open()
		if err != nil {
			dstFile.Close()
			return err
		}

		_, err = io.Copy(dstFile, srcFile)
		srcFile.Close()
		dstFile.Close()

		if err != nil {
			return err
		}
	}

	return nil
}

// StartDownload - Dosya indirme başlat
func (fm *FileManager) StartDownload(path string) (*FileTransfer, error) {
	if !fm.isPathAllowed(path) {
		return nil, fmt.Errorf("erişim engellendi: %s", path)
	}

	info, err := os.Stat(path)
	if err != nil {
		return nil, err
	}

	if info.IsDir() {
		return nil, fmt.Errorf("klasör indirilemez, önce sıkıştırın")
	}

	transfer := &FileTransfer{
		ID:         generateTransferID(),
		FileName:   info.Name(),
		FilePath:   path,
		FileSize:   info.Size(),
		ChunkSize:  fm.maxChunkSize,
		ChunkCount: int((info.Size() + fm.maxChunkSize - 1) / fm.maxChunkSize),
		Direction:  "download",
		Status:     "pending",
		StartTime:  time.Now(),
	}

	fm.mu.Lock()
	fm.transfers[transfer.ID] = transfer
	fm.mu.Unlock()

	return transfer, nil
}

// GetDownloadChunk - İndirme chunk'ı al
func (fm *FileManager) GetDownloadChunk(transferID string, chunkIndex int) (*FileChunk, error) {
	fm.mu.RLock()
	transfer, ok := fm.transfers[transferID]
	fm.mu.RUnlock()

	if !ok {
		return nil, fmt.Errorf("transfer bulunamadı: %s", transferID)
	}

	if chunkIndex < 0 || chunkIndex >= transfer.ChunkCount {
		return nil, fmt.Errorf("geçersiz chunk index: %d", chunkIndex)
	}

	file, err := os.Open(transfer.FilePath)
	if err != nil {
		return nil, err
	}
	defer file.Close()

	offset := int64(chunkIndex) * transfer.ChunkSize
	file.Seek(offset, 0)

	buffer := make([]byte, transfer.ChunkSize)
	n, err := file.Read(buffer)
	if err != nil && err != io.EOF {
		return nil, err
	}

	data := buffer[:n]
	hash := md5.Sum(data)

	chunk := &FileChunk{
		TransferID: transferID,
		ChunkIndex: chunkIndex,
		Data:       base64.StdEncoding.EncodeToString(data),
		Size:       n,
		Hash:       hex.EncodeToString(hash[:]),
	}

	// Transfer durumunu güncelle
	fm.mu.Lock()
	transfer.CurrentChunk = chunkIndex
	transfer.Transferred = offset + int64(n)
	transfer.Status = "transferring"
	if chunkIndex == transfer.ChunkCount-1 {
		transfer.Status = "completed"
		transfer.EndTime = time.Now()
	}
	fm.mu.Unlock()

	return chunk, nil
}

// StartUpload - Dosya yükleme başlat
func (fm *FileManager) StartUpload(path string, fileName string, fileSize int64) (*FileTransfer, error) {
	if !fm.isPathAllowed(path) {
		return nil, fmt.Errorf("erişim engellendi: %s", path)
	}

	fullPath := filepath.Join(path, fileName)

	transfer := &FileTransfer{
		ID:         generateTransferID(),
		FileName:   fileName,
		FilePath:   fullPath,
		FileSize:   fileSize,
		ChunkSize:  fm.maxChunkSize,
		ChunkCount: int((fileSize + fm.maxChunkSize - 1) / fm.maxChunkSize),
		Direction:  "upload",
		Status:     "pending",
		StartTime:  time.Now(),
	}

	// Dosyayı oluştur
	file, err := os.Create(fullPath)
	if err != nil {
		return nil, err
	}
	file.Close()

	fm.mu.Lock()
	fm.transfers[transfer.ID] = transfer
	fm.mu.Unlock()

	return transfer, nil
}

// UploadChunk - Yükleme chunk'ı al
func (fm *FileManager) UploadChunk(chunk *FileChunk) error {
	fm.mu.RLock()
	transfer, ok := fm.transfers[chunk.TransferID]
	fm.mu.RUnlock()

	if !ok {
		return fmt.Errorf("transfer bulunamadı: %s", chunk.TransferID)
	}

	data, err := base64.StdEncoding.DecodeString(chunk.Data)
	if err != nil {
		return err
	}

	// Hash kontrolü
	hash := md5.Sum(data)
	if hex.EncodeToString(hash[:]) != chunk.Hash {
		return fmt.Errorf("chunk hash eşleşmiyor")
	}

	file, err := os.OpenFile(transfer.FilePath, os.O_WRONLY, 0644)
	if err != nil {
		return err
	}
	defer file.Close()

	offset := int64(chunk.ChunkIndex) * transfer.ChunkSize
	file.Seek(offset, 0)
	file.Write(data)

	// Transfer durumunu güncelle
	fm.mu.Lock()
	transfer.CurrentChunk = chunk.ChunkIndex
	transfer.Transferred = offset + int64(len(data))
	transfer.Status = "transferring"
	if chunk.ChunkIndex == transfer.ChunkCount-1 {
		transfer.Status = "completed"
		transfer.EndTime = time.Now()
	}
	fm.mu.Unlock()

	return nil
}

// GetTransfer - Transfer durumu
func (fm *FileManager) GetTransfer(transferID string) *FileTransfer {
	fm.mu.RLock()
	defer fm.mu.RUnlock()
	return fm.transfers[transferID]
}

// CancelTransfer - Transfer iptal
func (fm *FileManager) CancelTransfer(transferID string) {
	fm.mu.Lock()
	defer fm.mu.Unlock()
	if transfer, ok := fm.transfers[transferID]; ok {
		transfer.Status = "cancelled"
		transfer.EndTime = time.Now()
	}
}

// calculateFileHash - Dosya hash'i hesapla
func (fm *FileManager) calculateFileHash(path string) (string, error) {
	file, err := os.Open(path)
	if err != nil {
		return "", err
	}
	defer file.Close()

	hash := sha256.New()
	if _, err := io.Copy(hash, file); err != nil {
		return "", err
	}

	return hex.EncodeToString(hash.Sum(nil)), nil
}

// isPathAllowed - Yol izinli mi
func (fm *FileManager) isPathAllowed(path string) bool {
	path = filepath.Clean(path)

	// Engellenen yolları kontrol et
	for _, blocked := range fm.blockedPaths {
		if strings.HasPrefix(strings.ToLower(path), strings.ToLower(blocked)) {
			return false
		}
	}

	// İzin verilen yollar varsa kontrol et
	if len(fm.allowedPaths) > 0 {
		for _, allowed := range fm.allowedPaths {
			if strings.HasPrefix(strings.ToLower(path), strings.ToLower(allowed)) {
				return true
			}
		}
		return false
	}

	return true
}

// SetAllowedPaths - İzin verilen yolları ayarla
func (fm *FileManager) SetAllowedPaths(paths []string) {
	fm.mu.Lock()
	defer fm.mu.Unlock()
	fm.allowedPaths = paths
}

// GetCurrentPath - Mevcut yolu al
func (fm *FileManager) GetCurrentPath() string {
	fm.mu.RLock()
	defer fm.mu.RUnlock()
	return fm.currentPath
}

// Helper fonksiyonları
func isHiddenFile(name, path string) bool {
	if strings.HasPrefix(name, ".") {
		return true
	}
	// Windows için gizli dosya kontrolü
	if runtime.GOOS == "windows" {
		// Dosya özniteliklerini kontrol et
		// Bu basitleştirilmiş bir versiyon
	}
	return false
}

func getMimeType(ext string) string {
	mimeTypes := map[string]string{
		".txt":  "text/plain",
		".html": "text/html",
		".css":  "text/css",
		".js":   "application/javascript",
		".json": "application/json",
		".xml":  "application/xml",
		".pdf":  "application/pdf",
		".zip":  "application/zip",
		".tar":  "application/x-tar",
		".gz":   "application/gzip",
		".jpg":  "image/jpeg",
		".jpeg": "image/jpeg",
		".png":  "image/png",
		".gif":  "image/gif",
		".svg":  "image/svg+xml",
		".mp3":  "audio/mpeg",
		".wav":  "audio/wav",
		".mp4":  "video/mp4",
		".avi":  "video/x-msvideo",
		".mkv":  "video/x-matroska",
		".doc":  "application/msword",
		".docx": "application/vnd.openxmlformats-officedocument.wordprocessingml.document",
		".xls":  "application/vnd.ms-excel",
		".xlsx": "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
		".ppt":  "application/vnd.ms-powerpoint",
		".pptx": "application/vnd.openxmlformats-officedocument.presentationml.presentation",
	}

	if mime, ok := mimeTypes[ext]; ok {
		return mime
	}
	return "application/octet-stream"
}

func getFileIcon(ext string) string {
	icons := map[string]string{
		".txt": "file-text", ".md": "file-text",
		".html": "file-code", ".css": "file-code", ".js": "file-code",
		".json": "file-code", ".xml": "file-code", ".go": "file-code",
		".py": "file-code", ".java": "file-code", ".ts": "file-code",
		".pdf": "file-pdf",
		".zip": "file-archive", ".tar": "file-archive", ".gz": "file-archive",
		".rar": "file-archive", ".7z": "file-archive",
		".jpg": "file-image", ".jpeg": "file-image", ".png": "file-image",
		".gif": "file-image", ".svg": "file-image", ".bmp": "file-image",
		".mp3": "file-audio", ".wav": "file-audio", ".flac": "file-audio",
		".mp4": "file-video", ".avi": "file-video", ".mkv": "file-video",
		".doc": "file-word", ".docx": "file-word",
		".xls": "file-excel", ".xlsx": "file-excel",
		".ppt": "file-powerpoint", ".pptx": "file-powerpoint",
		".exe": "file-binary", ".dll": "file-binary",
	}

	if icon, ok := icons[ext]; ok {
		return icon
	}
	return "file"
}

func generateTransferID() string {
	return fmt.Sprintf("%d-%d", time.Now().UnixNano(), time.Now().UnixMicro()%10000)
}

// getDiskUsage - Disk kullanımı (platform bağımsız stub)
type DiskUsage struct {
	Total uint64
	Used  uint64
	Free  uint64
}

func getDiskUsage(path string) *DiskUsage {
	// Bu fonksiyon platform özel implementasyona ihtiyaç duyar
	// Basitleştirilmiş versiyon
	return nil
}

// moveToRecycleBin - Çöp kutusuna taşı (Windows)
func moveToRecycleBin(path string) error {
	// Windows Shell API kullanımı gerektirir
	// Şimdilik doğrudan sil
	return os.RemoveAll(path)
}
