Fri, 30 Nov 2018 18:06:48 +0100
adds rename command
dav/main.c | file | annotate | diff | comparison | revisions | |
dav/main.h | file | annotate | diff | comparison | revisions |
--- a/dav/main.c Fri Nov 16 12:46:31 2018 +0100 +++ b/dav/main.c Fri Nov 30 18:06:48 2018 +0100 @@ -122,6 +122,8 @@ ret = cmd_move(args, true); } else if(!strcasecmp(cmd, "move") || !strcasecmp(cmd, "mv")) { ret = cmd_move(args, false); + } else if(!strcasecmp(cmd, "rename")) { + ret = cmd_rename(args); } else if(!strcasecmp(cmd, "export")) { ret = cmd_get(args, TRUE); } else if(!strcasecmp(cmd, "import")) { @@ -213,6 +215,7 @@ "remove [-pc] [-L <lock>] <url>", "copy [-pcO] [-L <lock>] <url> <url>", "move [-pcO] [-L <lock>] <url> <url>", + "rename [-pcO] [-L <lock>] <url> <name>", "export [-pc] [-o <file>] [-u <date>] <url>", "import [-pc] [-k <key>] [-L <lock>] <url> <file>", "get-property [-pcx] [-V <version>] [-n <uri>] <url> <property>", @@ -1531,6 +1534,7 @@ } free(path); + dav_session_destroy(sn); return 0; } @@ -1604,6 +1608,94 @@ return 0; } +int cmd_rename(CmdArgs *a) { + if(a->argc != 2) { + // TODO: change, when creation of multiple dirs is supported + fprintf(stderr, "Too %s arguments\n", a->argc < 2 ? "few":"many"); + fprintf(stderr, "Usage: dav %s\n", find_usage_str("rename")); + return -1; + } + + char *name = a->argv[1]; + size_t namelen = strlen(name); + for(size_t i=0;i<namelen;i++) { + char c = name[i]; + if(c == '/') { + fprintf(stderr, "Illegal character in name: '/'\n"); + return 1; + } + } + + char *url = a->argv[0]; + char *path = NULL; + Repository *repo = url2repo(url, &path); + DavSession *sn = connect_to_repo(repo, path, a); + + if(set_session_config(sn, a)) { + return -1; + } + set_session_lock(sn, a); + + int ret = 0; + DavResource *res = dav_get(sn, path, NULL); + if(res) { + char *cryptoname = dav_get_string_property_ns(res, DAV_NS, "crypto-name"); + char *cryptokey = dav_get_string_property_ns(res, DAV_NS, "crypto-key"); + if(cryptoname && cryptokey) { + // encrypted resource with an encrypted name + // renaming is done by simply setting the crypto-name property + + DavKey *key = dav_context_get_key(ctx, cryptokey); + if(key) { + // check if a resource with this name already exists + char *parent = util_parent_path(res->path); + char *newpath = util_concat_path(parent, name); + DavResource *testres = dav_resource_new(sn, newpath); + if(dav_exists(testres)) { + fprintf(stderr, "A resource with this name already exists.\nAbort.\n"); + ret = 1; + } else { + char *crname = aes_encrypt(name, namelen, key); + dav_set_string_property_ns(res, DAV_NS, "crypto-name", crname); + free(crname); + if(dav_store(res)) { + print_resource_error(sn, res->path); + fprintf(stderr, "Cannot store crypto-name property.\n"); + ret = 1; + } + } + free(parent); + free(newpath); + } else { + fprintf(stderr, "Key %s not found.\n", cryptokey); + } + } else { + // rename the resource by changing the url mapping with MOVE + + char *parent = util_parent_path(res->href); + char *new_href = util_concat_path(parent, name); + char *dest = util_get_url(sn, new_href); + free(parent); + free(new_href); + if(dav_moveto(res, dest, false)) { + print_resource_error(sn, path); + fprintf(stderr, "Cannot rename resource.\n"); + ret = 1; + } + free(dest); + } + } else { + print_resource_error(sn, path); + fprintf(stderr, "Cannot rename resource.\n"); + ret = 1; + } + + + dav_session_destroy(sn); + free(path); + return ret; +} + static size_t get_date_header_cb(void *header, int s, int n, void *data) { char **date_str = (char**)data;