Skip to content

Commit

Permalink
Fix path comparison logic
Browse files Browse the repository at this point in the history
  • Loading branch information
chinarjoshi committed Sep 21, 2023
1 parent 724976b commit 645546d
Show file tree
Hide file tree
Showing 6 changed files with 46 additions and 28 deletions.
28 changes: 18 additions & 10 deletions src/subcmds/helpers.c
Original file line number Diff line number Diff line change
Expand Up @@ -16,21 +16,28 @@ bool is_valid_dir(const char *dir) {
return !stat(dir, &statbuf) && S_ISDIR(statbuf.st_mode);
}

// Returns whether 'child_path' is a subdirectory of 'parent_path'. If 'reverse', return
// the inverse.
bool is_child_path(const char *child_path, const char *parent_path, bool reverse) {
if (strlen(child_path) > strlen(parent_path))
return false;
enum PathCmp compare_paths(const char *env_fname, const char *directory) {
int env_fname_len = strlen(env_fname) - 5;
int directory_len = strlen(directory);

int len = strlen(reverse ? parent_path : child_path);
// Compare length - 6 characters of the paths (-5 because of /.env at the end)
return strncmp(child_path, parent_path, len - 5) == 0;
int cmp_env_fname_len = !strncmp(env_fname, directory, env_fname_len);
int cmp_directory_len = !strncmp(env_fname, directory, directory_len);

if (env_fname_len == directory_len && cmp_env_fname_len) {
return PATH_EQ;
} else if (env_fname_len < directory_len && cmp_env_fname_len) {
return PATH_CHILD;
} else if (env_fname_len > directory_len && cmp_directory_len) {
return PATH_PARENT;
}

return PATH_UNRELATED;
}

// Returns an array of .env paths that are children or parents of 'start', according to
// 'return_parents', in the form of 'num_paths' char pointers that must be freed.
// The array is ordered from shortest to longest path.
char **get_env_paths(const char *start, int *num_paths, bool return_parents) {
char **get_env_paths(const char *start, int *num_paths) {
const char *auth_fname = getenv("AUTOENV_AUTH_FILE");
FILE *auth_f = fopen(auth_fname, "r");
if (!auth_f) {
Expand All @@ -44,7 +51,8 @@ char **get_env_paths(const char *start, int *num_paths, bool return_parents) {

while (fgets(line, sizeof(line), auth_f)) {
char* path = strtok(line, ":");
if (path && is_child_path(path, start, return_parents)) {
enum PathCmp pcmp = compare_paths(path, start);
if (path && (pcmp == PATH_EQ || pcmp == PATH_CHILD)) {
if (path_count + 1 > max_paths) {
max_paths *= 2;
paths = realloc(paths, max_paths * sizeof(char *));
Expand Down
2 changes: 1 addition & 1 deletion src/subcmds/show.c
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ bool show_cmd(Cli *cli) {

// Get a list of .env file paths from AUTOENV_AUTH_FILE
int num_paths;
char **env_paths = get_env_paths(cwd, &num_paths, false);
char **env_paths = get_env_paths(cwd, &num_paths);
if (!env_paths)
return false;

Expand Down
11 changes: 10 additions & 1 deletion src/subcmds/subcmds.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,27 @@
#include "../parse_args/parse_args.h"
#include "../hash_table/hash_table.h"

enum PathCmp {
PATH_EQ,
PATH_CHILD,
PATH_PARENT,
PATH_UNRELATED
};

extern const char *AUTOENV_FNAME;
extern char TMP_FNAME[64];
extern char TOML_FNAME[64];
extern char ALIAS_FNAME[64];

bool add_cmd(Cli *cli);
bool remove_cmd(Cli *cli);
bool tree_cmd(Cli *cli);
bool show_cmd(Cli *cli);
bool edit_cmd(Cli *cli);
bool is_valid_dir(const char *dir);
void set_alias_and_autoenv_fnames();
char **get_env_paths(const char *start, int *num_paths, bool return_parents);
char **get_env_paths(const char *start, int *num_paths);
enum PathCmp compare_paths(const char *env_fname, const char *directory);
int cleanup(const char *message, const char *message_arg,
HashTable *ht, FILE *f, const char *fname_to_remove);

Expand Down
9 changes: 0 additions & 9 deletions tests/.test_show_data/.env

This file was deleted.

7 changes: 0 additions & 7 deletions tests/.test_show_data/inner/.env

This file was deleted.

17 changes: 17 additions & 0 deletions tests/test_subcmds.c
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,20 @@ START_TEST(test_tree_cmd_all) {
}
END_TEST

START_TEST(test_compare_paths) {
char *env_file = "/home/c/projects/.env";
char *path1 = "/home/c/projects";
char *outside_path = "/home/c/asdf";
char *child_path = "/home/c/projects/acronym";
char *parent_path = "/home/c";

ck_assert(compare_paths(env_file, path1) == PATH_EQ);
ck_assert(compare_paths(env_file, outside_path) == PATH_UNRELATED);
ck_assert(compare_paths(env_file, child_path) == PATH_CHILD);
ck_assert(compare_paths(env_file, parent_path) == PATH_PARENT);
}
END_TEST

Suite *subcmds_suite(void) {
Suite *s = suite_create("Subcmds");

Expand All @@ -176,5 +190,8 @@ Suite *subcmds_suite(void) {
tcase_add_test(tc_tree, test_tree_cmd_all);
suite_add_tcase(s, tc_tree);

TCase *tc_helpers = tcase_create("Subcmd helpers");
tcase_add_test(tc_helpers, test_compare_paths);
suite_add_tcase(s, tc_helpers);
return s;
}

0 comments on commit 645546d

Please sign in to comment.