func (sorter PicSorter) Sort(dirPath string) error {
	var unsupportedPaths []string
	log.Println("[INFO]", "Scanning incoming files from", dirPath)
	err := filepath.Walk(dirPath, func(path string, info os.FileInfo, err error) error {
		if err != nil {
			return err
		}
		if !info.IsDir() {
			if isUnsupportedFile(path) {
				log.Println("[INFO] Skipping unsupported file", path)
				unsupportedPaths = append(unsupportedPaths, path)
				return nil
			}

			googleMetadata := sorter.getGooglePhotoMetadata(path)
			if googleMetadata != nil && googleMetadata.IsTrashed {
				err = sorter.handleTrashed(path, dirPath)
				if err != nil {
					log.Println("[WARN]", path, "Failed to check/handle trashed:", err)
				}
				return nil
			}

			newPath, err := sorter.deriveNewPathFromFileMetadata(path)
			if err != nil {
				if googleMetadata != nil {
					newPath, err = sorter.deriveNewPathFromGoogleMetadata(path, googleMetadata)
				}
				if err != nil {
					// The file is unsupported.  Nevertheless, check for duplicates.
					// This is realy only useful with eager deduping, but it could save us from having to care about why the file is unsupported.
					isDuplicate, _ := sorter.checkAndHandleIndexedDupes(path, dirPath)
					if !isDuplicate {
						unsupportedPaths = append(unsupportedPaths, path)
					}
					return nil
				}
			}

			isDuplicate, err := sorter.checkAndHandleDupes(path, dirPath, newPath)
			if err != nil {
				log.Println("[WARN]", path, "Failed to check/handle duplicates:", err)
				return nil
			} else if isDuplicate {
				return nil
			}

			destPath, err := sorter.fileMover.MoveFileWithRename(path, newPath)
			if err != nil {
				log.Println("[WARN]", path, "Failed to sort file:", err)
				return nil
			}

			err = sorter.deduper.AddFileToIndex(destPath)
			if err != nil {
				if !sorter.isDryRun {
					log.Println("[WARN]", path, "Failed to index file:", err)
				}
				return nil
			}
		}
		return nil
	})

	log.Println("[INFO]", "Cleaning up unsupported files.")
	for _, unsupportedPath := range unsupportedPaths {
		_, err := sorter.fileMover.MoveFileWithPreservedPath(unsupportedPath, dirPath, sorter.unsupportedDir)
		if err != nil {
			log.Println("[WARN]", unsupportedPath, "Failed to move unsupported file:", err)
		}
	}
	sorter.fileMover.DeleteEmptyDirectories(dirPath)

	return err
}
// Sort sorts pictures in the specified directory into the library.  Extracts duplicates, trashed, and unsupported files to a special location.
Sort sorts pictures in the specified directory into the library.  Extracts duplicates, trashed, and unsupported files to a special location.
// Sort sorts pictures in the specified directory into the library . Extracts duplicates trashed and unsupported files to a special location .
func (sorter PicSorter) Sort(dirPath string) error {
	var unsupportedPaths []string
	log.Println("[INFO]", "Scanning incoming files from", dirPath)
	err := filepath.Walk(dirPath, func(path string, info os.FileInfo, err error) error {
		if err != nil {
			return err
		}
		if !info.IsDir() {
			if isUnsupportedFile(path) {
				log.Println("[INFO] Skipping unsupported file", path)
				unsupportedPaths = append(unsupportedPaths, path)
				return nil
			}
			googleMetadata := sorter.getGooglePhotoMetadata(path)
			if googleMetadata != nil && googleMetadata.IsTrashed {
				err = sorter.handleTrashed(path, dirPath)
				if err != nil {
					log.Println("[WARN]", path, "Failed to check/handle trashed:", err)
				}
				return nil
			}
			newPath, err := sorter.deriveNewPathFromFileMetadata(path)
			if err != nil {
				if googleMetadata != nil {
					newPath, err = sorter.deriveNewPathFromGoogleMetadata(path, googleMetadata)
				}
				if err != nil {
					isDuplicate, _ := sorter.checkAndHandleIndexedDupes(path, dirPath)
					if !isDuplicate {
						unsupportedPaths = append(unsupportedPaths, path)
					}
					return nil
				}
			}
			isDuplicate, err := sorter.checkAndHandleDupes(path, dirPath, newPath)
			if err != nil {
				log.Println("[WARN]", path, "Failed to check/handle duplicates:", err)
				return nil
			} else if isDuplicate {
				return nil
			}
			destPath, err := sorter.fileMover.MoveFileWithRename(path, newPath)
			if err != nil {
				log.Println("[WARN]", path, "Failed to sort file:", err)
				return nil
			}
			err = sorter.deduper.AddFileToIndex(destPath)
			if err != nil {
				if !sorter.isDryRun {
					log.Println("[WARN]", path, "Failed to index file:", err)
				}
				return nil
			}
		}
		return nil
	})
	log.Println("[INFO]", "Cleaning up unsupported files.")
	for _, unsupportedPath := range unsupportedPaths {
		_, err := sorter.fileMover.MoveFileWithPreservedPath(unsupportedPath, dirPath, sorter.unsupportedDir)
		if err != nil {
			log.Println("[WARN]", unsupportedPath, "Failed to move unsupported file:", err)
		}
	}
	sorter.fileMover.DeleteEmptyDirectories(dirPath)
	return err
}
func ( sorter PicSorter ) Sort ( dirPath string ) error { var unsupportedPaths [ ] string log . Println ( " " , " " , dirPath ) err := filepath . Walk ( dirPath , func ( path string , info os . FileInfo , err error ) error { if err != nil { return err } if ! info . IsDir ( ) { if isUnsupportedFile ( path ) { log . Println ( " " , path ) unsupportedPaths = append ( unsupportedPaths , path ) return nil } googleMetadata := sorter . getGooglePhotoMetadata ( path ) if googleMetadata != nil && googleMetadata . IsTrashed { err = sorter . handleTrashed ( path , dirPath ) if err != nil { log . Println ( " " , path , " " , err ) } return nil } newPath , err := sorter . deriveNewPathFromFileMetadata ( path ) if err != nil { if googleMetadata != nil { newPath , err = sorter . deriveNewPathFromGoogleMetadata ( path , googleMetadata ) } if err != nil { isDuplicate , _ := sorter . checkAndHandleIndexedDupes ( path , dirPath ) if ! isDuplicate { unsupportedPaths = append ( unsupportedPaths , path ) } return nil } } isDuplicate , err := sorter . checkAndHandleDupes ( path , dirPath , newPath ) if err != nil { log . Println ( " " , path , " " , err ) return nil } else if isDuplicate { return nil } destPath , err := sorter . fileMover . MoveFileWithRename ( path , newPath ) if err != nil { log . Println ( " " , path , " " , err ) return nil } err = sorter . deduper . AddFileToIndex ( destPath ) if err != nil { if ! sorter . isDryRun { log . Println ( " " , path , " " , err ) } return nil } } return nil } ) log . Println ( " " , " " ) for _ , unsupportedPath := range unsupportedPaths { _ , err := sorter . fileMover . MoveFileWithPreservedPath ( unsupportedPath , dirPath , sorter . unsupportedDir ) if err != nil { log . Println ( " " , unsupportedPath , " " , err ) } } sorter . fileMover . DeleteEmptyDirectories ( dirPath ) return err }
Sort sorts pictures in the specified directory into the library.
Sort sorts pictures in the specified directory into the library .
// The file is unsupported.  Nevertheless, check for duplicates. // This is realy only useful with eager deduping, but it could save us from having to care about why the file is unsupported.