Commits

Serge Zaitsev committed 09e6c4c

added more options, using nicer command line syntax

Comments (0)

Files changed (3)

 #include <dirent.h>
 #include <sys/stat.h>
 #include <errno.h>
-#include <limits.h>
 
 #include "index.h"
 
+#ifndef PATH_MAX
+#define PATH_MAX 4096
+#endif
+
 uint32_t *trigrams_create(const char *s) {
 	uint32_t *trigrams = malloc(sizeof(uint32_t *) * (strlen(s) - 1));
 	memset(trigrams, 0, sizeof(uint32_t *) * (strlen(s) - 1));
 	printf("%s\n", file);
 }
 
+void usage() {
+	fprintf(stderr, "USAGE:\n");
+	fprintf(stderr, "  codehound index  <PROJECT> <DIR> [DIR...]\n");
+	fprintf(stderr, "  codehound locate [-p PROJECT] TEXT ...\n");
+	fprintf(stderr, "  codehound find   [-p PROJECT] TEXT ...\n");
+	fprintf(stderr, "  codehound list\n");
+	fprintf(stderr, "\n");
+}
+
+static const char *codehound_project_path(const char *name) {
+	static char path[PATH_MAX];
+	char *codehound = getenv("CODEHOUND");
+	if (codehound == NULL) {
+		char *home = getenv("HOME");
+		codehound = ".codehound";
+		snprintf(path, sizeof(path)-1, "%s/%s/", home, codehound);
+	} else {
+		strncpy(path, codehound, sizeof(path)-1);
+	}
+
+	int r = mkdir(path, 0755);
+	if (r < 0 && errno != EEXIST) {
+		fprintf(stderr, "failed to create codehound directory: %s, errno=%d\n", 
+				path, errno);
+		return NULL;
+	}
+
+	if (path[strlen(path) - 1] != '/') {
+		path[strlen(path)] = '\0';
+		path[strlen(path)-1] = '/';
+	}
+
+	if (name != NULL) {
+		strncat(path, name, sizeof(path)-1);
+	}
+
+	return path;
+}
+
 int main(int argc, char *argv[]) {
-	if (argc < 2) {
-		return 0;
-	}
-	//struct index index;
-	if (strcmp(argv[1], "index") == 0) {
-		struct index_writer *writer = index_writer_create("index.cache");
-		/*if (root[strlen(root)-1] == '/') {
-			root[strlen(root)-1] = '\0';
-		}*/
-		scandirs(argv[2], scan_file_cb, writer);
-		printf("writign index file...\n");
+	if (argc > 3 && strcmp(argv[1], "index") == 0) {
+		/* index: create a new project index by scanning given dirs */
+		int i;
+		char *project = argv[2];
+		struct index_writer *writer = 
+			index_writer_create(codehound_project_path(project));
+		for (i = 3; i < argc; i++) {
+			scandirs(argv[i], scan_file_cb, writer);
+		}
+		fprintf(stderr, "Writing index file, please wait...\n");
 		index_writer_write(writer);
 		index_writer_destroy(writer);
-	} else if (strcmp(argv[1], "find") == 0) {
-		struct index *index = index_open("index.cache");
-		uint32_t *trigrams = trigrams_create(argv[2]);
-		index_search(index, trigrams, find_cb, argv[2]);
-		trigrams_destroy(trigrams);
-		index_destroy(index);
-	} else if (strcmp(argv[1], "locate") == 0) {
-		struct index *index = index_open("index.cache");
-		uint32_t *trigrams = trigrams_create(argv[2]);
-		index_search(index, trigrams, locate_cb, argv[2]);
-		trigrams_destroy(trigrams);
-		index_destroy(index);
+		fprintf(stderr, "Done.\n");
+	} else if (argc == 2 && strcmp(argv[1], "list") == 0) {
+		/* list: display brief info about all indexed projects */
+		const char *dirpath = codehound_project_path(NULL);
+		struct dirent *entry;
+
+		DIR *dir = opendir(dirpath);
+		if (dir == NULL) {
+			fprintf(stderr, "Failed to open directory: %s, errno=%d\n", 
+					dirpath, errno);
+			exit(EXIT_FAILURE);
+		}
+
+		char path[PATH_MAX];
+		while ((entry = readdir(dir)) != NULL) {
+			char *name = entry->d_name;
+			if (strcmp(name, "..") == 0 || strcmp(name, ".") == 0) continue;
+			snprintf(path, PATH_MAX-1, "%s/%s", dirpath, name);
+			struct index *index = index_open(path);
+			if (index != NULL) {
+				printf("%s: %d files, %d trigrams\n", name, 
+						index_get_files_count(index), index_get_trigrams_count(index));
+				index_close(index);
+			}
+		}
+	} else if ((argc > 2 && strcmp(argv[1], "locate") == 0)
+			|| (argc > 2 && strcmp(argv[1], "find") == 0)) {
+		/* locate/find: display a list of files potenitally containing given text */
+		if (strcmp(argv[2], "-p") == 0) {
+				if (argc > 3) {
+					char *project = argv[3];
+					struct index *index = index_open(codehound_project_path(project));
+					if (index == NULL) {
+						fprintf(stderr, "Failed to open project index: %s\n", project);
+						exit(EXIT_FAILURE);
+					}
+					uint32_t *trigrams = trigrams_create(argv[4]);
+					if (strcmp(argv[1], "locate") == 0) {
+						index_search(index, trigrams, locate_cb, argv[4]);
+					} else {
+						index_search(index, trigrams, find_cb, argv[4]);
+					}
+					trigrams_destroy(trigrams);
+					index_destroy(index);
+				} else {
+					usage();
+					exit(EXIT_FAILURE);
+				}
+		} else {
+			/* locate/find: scan all project indices */
+			/* TODO */
+		}
+	} else {
+		usage();
+		exit(0);
 	}
 	return 0;
 }
 	return index;
 }
 
+void index_close(struct index *index) {
+	index_destroy(index);
+}
+
+int index_get_files_count(struct index *index) {
+	return index->files_count;
+}
+
+int index_get_trigrams_count(struct index *index) {
+	return index->entries_count;
+}
+
 int index_search(struct index *index, uint32_t *trigrams, 
 		index_search_cb cb, void *arg) {
 	unsigned int i;
 struct index *index_open(const char *name);
 void index_close(struct index *index);
 int index_search(struct index *index, uint32_t *trigrams, index_search_cb cb, void *arg);
+int index_get_trigrams_count(struct index *index);
+int index_get_files_count(struct index *index);
 
 #endif /* __INDEX_H__ */