1 /* |
1 /* |
2 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. |
2 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. |
3 * |
3 * |
4 * Copyright 2016 Olaf Wintermann. All rights reserved. |
4 * Copyright 2018 Olaf Wintermann. All rights reserved. |
5 * |
5 * |
6 * Redistribution and use in source and binary forms, with or without |
6 * Redistribution and use in source and binary forms, with or without |
7 * modification, are permitted provided that the following conditions are met: |
7 * modification, are permitted provided that the following conditions are met: |
8 * |
8 * |
9 * 1. Redistributions of source code must retain the above copyright |
9 * 1. Redistributions of source code must retain the above copyright |
342 locked = TRUE; |
343 locked = TRUE; |
343 locktokenfile = create_locktoken_file(dir->name, lock->token); |
344 locktokenfile = create_locktoken_file(dir->name, lock->token); |
344 } |
345 } |
345 |
346 |
346 int ret = 0; |
347 int ret = 0; |
347 DavResource *ls = dav_query(sn, "select D:getetag,idav:status from / with depth = infinity"); |
348 DavResource *ls = dav_query(sn, "select D:getetag,idav:status,idav:tags from / with depth = infinity"); |
348 if(!ls) { |
349 if(!ls) { |
349 print_resource_error(sn, "/"); |
350 print_resource_error(sn, "/"); |
350 if(locked) { |
351 if(locked) { |
351 if(dav_unlock(root)) { |
352 if(dav_unlock(root)) { |
352 print_resource_error(sn, "/"); |
353 print_resource_error(sn, "/"); |
582 local = calloc(1, sizeof(LocalResource)); |
583 local = calloc(1, sizeof(LocalResource)); |
583 local->path = util_concat_path(res->path, "/"); |
584 local->path = util_concat_path(res->path, "/"); |
584 local->last_modified = 0; |
585 local->last_modified = 0; |
585 ucx_map_cstr_put(db->resources, local->path, local); |
586 ucx_map_cstr_put(db->resources, local->path, local); |
586 } |
587 } |
|
588 |
|
589 sync_store_tags(dir, local_path, local, res); |
587 } |
590 } |
588 } else { |
591 } else { |
589 if(!tmp_path) { |
592 if(!tmp_path) { |
590 fprintf(stderr, "Cannot create tmp path for %s\n", local_path); |
593 fprintf(stderr, "Cannot create tmp path for %s\n", local_path); |
591 free(local_path); |
594 free(local_path); |
601 printf("get: %s\n", res->path); |
604 printf("get: %s\n", res->path); |
602 if(dav_get_content(res, out, (dav_write_func)fwrite)) { |
605 if(dav_get_content(res, out, (dav_write_func)fwrite)) { |
603 ret = -1; |
606 ret = -1; |
604 } |
607 } |
605 fclose(out); |
608 fclose(out); |
|
609 |
|
610 sync_store_tags(dir, tmp_path, local, res); |
606 |
611 |
607 if(ret == 0) { |
612 if(ret == 0) { |
608 (*counter)++; |
613 (*counter)++; |
609 |
614 |
610 if(dir->trash && dir->backuppull) { |
615 if(dir->trash && dir->backuppull) { |
1232 } |
1237 } |
1233 |
1238 |
1234 |
1239 |
1235 int sync_set_status(DavResource *res, char *status) { |
1240 int sync_set_status(DavResource *res, char *status) { |
1236 DavResource *resource = dav_resource_new(res->session, res->path); |
1241 DavResource *resource = dav_resource_new(res->session, res->path); |
1237 dav_set_property(resource, "idav:status", status); |
1242 dav_set_string_property(resource, "idav:status", status); |
1238 int ret = dav_store(resource); |
1243 int ret = dav_store(resource); |
1239 dav_resource_free(resource); |
1244 dav_resource_free(resource); |
1240 return ret; |
1245 return ret; |
1241 } |
1246 } |
1242 |
1247 |
1244 DavResource *resource = dav_resource_new(res->session, res->path); |
1249 DavResource *resource = dav_resource_new(res->session, res->path); |
1245 dav_remove_property(resource, "idav:status"); |
1250 dav_remove_property(resource, "idav:status"); |
1246 int ret = dav_store(resource); |
1251 int ret = dav_store(resource); |
1247 dav_resource_free(resource); |
1252 dav_resource_free(resource); |
1248 return ret; |
1253 return ret; |
|
1254 } |
|
1255 |
|
1256 int sync_store_tags(SyncDirectory *dir, const char *path, LocalResource *local, DavResource *res) { |
|
1257 if(!dir->tagconfig) { |
|
1258 return 0; |
|
1259 } |
|
1260 |
|
1261 UcxList *tags = NULL; |
|
1262 if(dir->tagconfig) { |
|
1263 DavXmlNode *tagsprop = dav_get_property_ns(res, DAV_NS, "tags"); |
|
1264 if(tagsprop) { |
|
1265 tags = parse_dav_xml_taglist(tagsprop); |
|
1266 } |
|
1267 } |
|
1268 |
|
1269 if(!tags) { |
|
1270 return 0; |
|
1271 } |
|
1272 |
|
1273 int ret = 0; |
|
1274 if(dir->tagconfig->store == TAG_STORE_XATTR) { |
|
1275 UcxBuffer *data = NULL; |
|
1276 switch(dir->tagconfig->local_format) { |
|
1277 default: break; |
|
1278 case TAG_FORMAT_TEXT: { |
|
1279 data = create_text_taglist(tags); |
|
1280 break; |
|
1281 } |
|
1282 case TAG_FORMAT_CSV: { |
|
1283 data = create_csv_taglist(tags); |
|
1284 break; |
|
1285 } |
|
1286 } |
|
1287 |
|
1288 if(data) { |
|
1289 ret = xattr_set(path, "tags", data->space, data->pos); |
|
1290 ucx_buffer_free(data); |
|
1291 } else { |
|
1292 ret = -1; |
|
1293 } |
|
1294 } |
|
1295 |
|
1296 // TODO: free stuff |
|
1297 |
|
1298 return ret; |
|
1299 } |
|
1300 |
|
1301 UcxList* sync_get_file_tags(SyncDirectory *dir, LocalResource *res) { |
|
1302 UcxList *tags = NULL; |
|
1303 |
|
1304 if(!dir->tagconfig) { |
|
1305 return NULL; |
|
1306 } |
|
1307 if(dir->tagconfig->store == TAG_STORE_XATTR) { |
|
1308 ssize_t tag_length = 0; |
|
1309 char *local_path = util_concat_path(dir->path, res->path); |
|
1310 char* tag_data = xattr_get(local_path, "tags", &tag_length); |
|
1311 free(local_path); |
|
1312 |
|
1313 if(tag_length > 0) { |
|
1314 switch(dir->tagconfig->local_format) { |
|
1315 default: break; |
|
1316 case TAG_FORMAT_TEXT: { |
|
1317 tags = parse_text_taglist(tag_data, tag_length); |
|
1318 break; |
|
1319 } |
|
1320 case TAG_FORMAT_CSV: { |
|
1321 tags = parse_csv_taglist(tag_data, tag_length); |
|
1322 break; |
|
1323 } |
|
1324 } |
|
1325 } |
|
1326 } |
|
1327 |
|
1328 return tags; |
1249 } |
1329 } |
1250 |
1330 |
1251 int sync_put_resource( |
1331 int sync_put_resource( |
1252 SyncDirectory *dir, |
1332 SyncDirectory *dir, |
1253 DavResource *res, |
1333 DavResource *res, |
1270 free(local_path); |
1350 free(local_path); |
1271 return -1; |
1351 return -1; |
1272 } |
1352 } |
1273 |
1353 |
1274 dav_set_content(res, in, (dav_read_func)fread); |
1354 dav_set_content(res, in, (dav_read_func)fread); |
|
1355 |
|
1356 if(dir->tagconfig) { |
|
1357 UcxList *tags = sync_get_file_tags(dir, local); |
|
1358 DavXmlNode *prop = create_xml_taglist(tags); |
|
1359 if(prop) { |
|
1360 dav_set_property_ns(res, DAV_NS, "tags", prop); |
|
1361 } |
|
1362 } |
1275 |
1363 |
1276 int ret = -1; |
1364 int ret = -1; |
1277 int created = 0; |
1365 int created = 0; |
1278 for(int i=0;i<=dir->max_retry;i++) { |
1366 for(int i=0;i<=dir->max_retry;i++) { |
1279 if(!created && dav_create(res)) { |
1367 if(!created && dav_create(res)) { |