package org.forkalsrud.album.exif;

import java.io.File;
import java.util.LinkedList;

public class SearchEngine {

    DirectoryEntry root;
    SearchResults results;
    LinkedList<DirectoryEntry> queue;

    int rootPathLen;

    public SearchEngine(DirectoryEntry root) {
        this.root = root;
        this.results = new SearchResults(root);
        this.queue = new LinkedList<DirectoryEntry>();
        this.queue.add(root);
        this.rootPathLen = root.file.getAbsolutePath().length();
    }

    public SearchResults search(String query) {

        while (!queue.isEmpty()) {
            DirectoryEntry next = queue.removeFirst();
            processDirectory(next, query);
        }
        results.sort();
        results.fillLinkedList();
        return results;
    }


    void processDirectory(DirectoryEntry dir, String query) {

        tryAttribute(dir, dir.getName(), query);
        tryAttribute(dir, dir.getCaption(), query);
        tryPath(dir, dir.getPath(), query);

        for (Entry e : dir.getContents()) {
            if ("dir".equals(e.getType())) {
                queue.add((DirectoryEntry)e);
                continue;
            }
            FileEntry file = (FileEntry)e;
            tryAttribute(file, file.getName(), query);
            tryAttribute(file, file.getCaption(), query);
            tryPath(file, file.getPath(), query);
        }
    }

    void tryPath(Entry entry, File path, String query) {
        tryAttribute(entry, path.getAbsolutePath().substring(rootPathLen), query);
    }

    void tryAttribute(Entry entry, String attr, String query) {
        if (isMatch(attr, query)) {
            results.addMatch(entry);
        }
    }

    boolean isMatch(String candidate, String query) {
        return candidate != null && candidate.toUpperCase().contains(query.toUpperCase());
    }

}
