Migrate command line import to new storage api

This commit is contained in:
Jeremy Lakeman 2012-12-19 16:16:49 +10:30
parent 9a78e16625
commit 181d1363f1
4 changed files with 140 additions and 104 deletions

View File

@ -1214,42 +1214,9 @@ int app_rhizome_add_file(int argc, const char *const *argv, const struct command
m->payloadEncryption=0;
rhizome_manifest_set_ll(m,"crypt",m->payloadEncryption?1:0);
m->fileLength = 0;
if (filepath[0]) {
struct stat stat;
if (lstat(filepath,&stat))
return WHYF("Could not stat() payload file '%s'",filepath);
m->fileLength = stat.st_size;
}
rhizome_manifest_set_ll(m, "filesize", m->fileLength);
if (m->fileLength){
// Stream the file directly into the database, encrypting & hashing as we go.
struct rhizome_write write;
bzero(&write, sizeof(write));
if (rhizome_open_write(&write, NULL, m->fileLength, RHIZOME_PRIORITY_DEFAULT))
if (rhizome_add_file(m, filepath))
return -1;
if (rhizome_write_file(&write, filepath)){
rhizome_fail_write(&write);
return -1;
}
if (rhizome_finish_write(&write))
return -1;
m->fileHashedP = 1;
strlcpy(m->fileHexHash, write.id, SHA512_DIGEST_STRING_LENGTH);
rhizome_manifest_set(m, "filehash", m->fileHexHash);
} else {
m->fileLength = 0;
m->fileHexHash[0] = '\0';
rhizome_manifest_del(m, "filehash");
m->fileHashedP = 0;
}
/* Add the manifest and its associated file to the Rhizome database,
generating an "id" in the process.
PGS @20121003 - Hang on, didn't we create the ID above? Presumably the
@ -1349,7 +1316,75 @@ int app_rhizome_import_bundle(int argc, const char *const *argv, const struct co
cli_arg(argc, argv, o, "manifestpath", &manifestpath, NULL, "");
if (rhizome_opendb() == -1)
return -1;
int status=rhizome_import_from_files(manifestpath,filepath);
rhizome_manifest *m = rhizome_new_manifest();
if (!m)
return WHY("Out of manifests.");
int status=0;
if (rhizome_read_manifest_file(m, manifestpath, 0) == -1) {
status = WHY("could not read manifest file");
goto cleanup;
}
if (rhizome_manifest_verify(m)){
status = WHY("could not verify manifest");
goto cleanup;
}
/* Make sure we store signatures */
// TODO, why do we need this? Why isn't the state correct from rhizome_read_manifest_file?
// This feels like a hack...
m->manifest_bytes=m->manifest_all_bytes;
status = rhizome_import_file(m, filepath);
if (status<0)
goto cleanup;
status = rhizome_manifest_check_duplicate(m, NULL);
if (status<0)
goto cleanup;
if (status==0){
if (rhizome_add_manifest(m, 1) == -1) { // ttl = 1
status = WHY("rhizome_add_manifest() failed");
goto cleanup;
}
}else
INFO("Duplicate found in store");
const char *service = rhizome_manifest_get(m, "service", NULL, 0);
if (service) {
cli_puts("service");
cli_delim(":");
cli_puts(service);
cli_delim("\n");
}
{
cli_puts("manifestid");
cli_delim(":");
cli_puts(alloca_tohex(m->cryptoSignPublic, RHIZOME_MANIFEST_ID_BYTES));
cli_delim("\n");
}
cli_puts("filesize");
cli_delim(":");
cli_printf("%lld", m->fileLength);
cli_delim("\n");
if (m->fileLength != 0) {
cli_puts("filehash");
cli_delim(":");
cli_puts(m->fileHexHash);
cli_delim("\n");
}
const char *name = rhizome_manifest_get(m, "name", NULL, 0);
if (name) {
cli_puts("name");
cli_delim(":");
cli_puts(name);
cli_delim("\n");
}
cleanup:
rhizome_manifest_free(m);
return status;
}

View File

@ -617,5 +617,7 @@ int rhizome_flush(struct rhizome_write *write);
int rhizome_write_file(struct rhizome_write *write, const char *filename);
int rhizome_fail_write(struct rhizome_write *write);
int rhizome_finish_write(struct rhizome_write *write);
int rhizome_import_file(rhizome_manifest *m, const char *filepath);
int rhizome_add_file(rhizome_manifest *m, const char *filepath);
#endif //__SERVALDNA__RHIZOME_H

View File

@ -1625,71 +1625,3 @@ int rhizome_retrieve_file(const char *fileid, const char *filepath, const unsign
sqlite3_finalize(statement);
return ret;
}
int rhizome_import_from_files(const char *manifestpath,const char *filepath)
{
rhizome_manifest *m = rhizome_new_manifest();
if (!m)
return WHY("Out of manifests.");
int status = -1;
if (rhizome_read_manifest_file(m, manifestpath, 0) == -1) {
status = WHY("could not read manifest file");
} else if (rhizome_manifest_verify(m) == -1) {
status = WHY("Could not verify manifest file.");
} else {
/* Make sure we store signatures */
m->manifest_bytes=m->manifest_all_bytes;
/* Add the manifest and its associated file to the Rhizome database. */
m->dataFileName = strdup(filepath);
if (rhizome_manifest_check_file(m))
status = WHY("file does not belong to manifest");
else {
int ret = rhizome_manifest_check_duplicate(m, NULL);
if (ret == -1)
status = WHY("rhizome_manifest_check_duplicate() failed");
else if (ret) {
INFO("Duplicate found in store");
status = 1;
} else if (rhizome_add_manifest(m, 1) == -1) { // ttl = 1
status = WHY("rhizome_add_manifest() failed");
} else {
status = 0;
}
if (status != -1) {
const char *service = rhizome_manifest_get(m, "service", NULL, 0);
if (service) {
cli_puts("service");
cli_delim(":");
cli_puts(service);
cli_delim("\n");
}
{
cli_puts("manifestid");
cli_delim(":");
cli_puts(alloca_tohex(m->cryptoSignPublic, RHIZOME_MANIFEST_ID_BYTES));
cli_delim("\n");
}
cli_puts("filesize");
cli_delim(":");
cli_printf("%lld", m->fileLength);
cli_delim("\n");
if (m->fileLength != 0) {
cli_puts("filehash");
cli_delim(":");
cli_puts(m->fileHexHash);
cli_delim("\n");
}
const char *name = rhizome_manifest_get(m, "name", NULL, 0);
if (name) {
cli_puts("name");
cli_delim(":");
cli_puts(name);
cli_delim("\n");
}
}
}
}
rhizome_manifest_free(m);
return status;
}

View File

@ -237,3 +237,70 @@ failure:
rhizome_fail_write(write);
return -1;
}
// import a file for an existing bundle with a known file hash
int rhizome_import_file(rhizome_manifest *m, const char *filepath)
{
if (m->fileLength<=0)
return 0;
/* Import the file first, checking the hash as we go */
struct rhizome_write write;
bzero(&write, sizeof(write));
int ret=rhizome_open_write(&write, m->fileHexHash, m->fileLength, RHIZOME_PRIORITY_DEFAULT);
if (ret!=0)
return ret;
// file payload is not in the store yet
if (rhizome_write_file(&write, filepath)){
rhizome_fail_write(&write);
return -1;
}
if (rhizome_finish_write(&write))
return -1;
return 0;
}
// import a file for a new bundle with an unknown file hash
// update the manifest with the details of the file
int rhizome_add_file(rhizome_manifest *m, const char *filepath)
{
m->fileLength = 0;
if (filepath[0]) {
struct stat stat;
if (lstat(filepath,&stat))
return WHYF("Could not stat() payload file '%s'",filepath);
m->fileLength = stat.st_size;
}
rhizome_manifest_set_ll(m, "filesize", m->fileLength);
if (m->fileLength == 0){
m->fileHexHash[0] = '\0';
rhizome_manifest_del(m, "filehash");
m->fileHashedP = 0;
return 0;
}
// Stream the file directly into the database, encrypting & hashing as we go.
struct rhizome_write write;
bzero(&write, sizeof(write));
if (rhizome_open_write(&write, NULL, m->fileLength, RHIZOME_PRIORITY_DEFAULT))
return -1;
if (rhizome_write_file(&write, filepath)){
rhizome_fail_write(&write);
return -1;
}
if (rhizome_finish_write(&write))
return -1;
m->fileHashedP = 1;
strlcpy(m->fileHexHash, write.id, SHA512_DIGEST_STRING_LENGTH);
rhizome_manifest_set(m, "filehash", m->fileHexHash);
return 0;
}