From 2cd9f1657aac57ffa3b8da83c3f2d1413fe288b1 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Henrik=20tom=20W=C3=B6rden?= <henrik@trineo.org>
Date: Mon, 27 Apr 2020 14:29:32 +0200
Subject: [PATCH] MAINT: included test for im und export

---
 integrationtests/full_test/example_table.csv  |  3 ++
 integrationtests/full_test/test.sh            |  1 +
 .../full_test/test_im_und_export.py           | 34 +++++++++++++++++++
 src/caosadvancedtools/export_related.py       | 22 ++++++++----
 src/caosadvancedtools/import_from_xml.py      | 10 ++++--
 5 files changed, 61 insertions(+), 9 deletions(-)
 create mode 100644 integrationtests/full_test/example_table.csv
 create mode 100644 integrationtests/full_test/test_im_und_export.py

diff --git a/integrationtests/full_test/example_table.csv b/integrationtests/full_test/example_table.csv
new file mode 100644
index 00000000..5af49105
--- /dev/null
+++ b/integrationtests/full_test/example_table.csv
@@ -0,0 +1,3 @@
+firstName,lastName,email
+Henrik,tom Wörden,henrik@indiscale.com
+Max,Mustermann,max@mustermann.eu
diff --git a/integrationtests/full_test/test.sh b/integrationtests/full_test/test.sh
index f107b7a8..7546e893 100755
--- a/integrationtests/full_test/test.sh
+++ b/integrationtests/full_test/test.sh
@@ -2,3 +2,4 @@ ls
 rm -rf cache.db
 ./filldb.sh
 py.test-3 test_crawler.py
+python3 test_im_und_export.py
diff --git a/integrationtests/full_test/test_im_und_export.py b/integrationtests/full_test/test_im_und_export.py
new file mode 100644
index 00000000..a1558a8b
--- /dev/null
+++ b/integrationtests/full_test/test_im_und_export.py
@@ -0,0 +1,34 @@
+#!/usr/bin/env python3
+import os
+import unittest
+from tempfile import TemporaryDirectory
+
+import caosdb as db
+
+from caosadvancedtools.export_related import export
+from caosadvancedtools.import_from_xml import import_xml
+
+if __name__ == "__main__":
+    rec = db.execute_query("FIND 2019-02-03_really_cool_finding", unique=True)
+    directory = TemporaryDirectory()
+    export(rec.id, directory=directory.name)
+    # delete everything
+    rec = db.execute_query("FIND record which was inserted by me")
+    prop = db.execute_query("FIND property which was inserted by me")
+    rt = db.execute_query("FIND recordtype which was inserted by me")
+    fi = db.execute_query("FIND file which was inserted by me")
+    c = db.Container()
+    c.extend(rec+prop+rt+fi)
+    c.delete()
+    assert 0 == len(db.execute_query("FIND File which is stored at "
+                                     "**/poster.pdf"))
+    import_xml(os.path.join(directory.name, "caosdb_data.xml"), interactive=False)
+
+    # The following tests the existence of some required entities.
+    # However, this is not a full list.
+    db.execute_query("FIND 2019-02-03_really_cool_finding", unique=True)
+    db.execute_query("FIND RecordType Poster", unique=True)
+    db.execute_query("FIND RecordType Analysis", unique=True)
+    db.execute_query("FIND RecordType Person", unique=True)
+    db.execute_query("FIND Record Person with firstname=Only", unique=True)
+    db.execute_query("FIND File which is stored at **/poster.pdf", unique=True)
diff --git a/src/caosadvancedtools/export_related.py b/src/caosadvancedtools/export_related.py
index cca1335f..47fe2f49 100755
--- a/src/caosadvancedtools/export_related.py
+++ b/src/caosadvancedtools/export_related.py
@@ -96,16 +96,21 @@ def invert_ids(entities):
     apply_to_ids(entities, lambda x: x*-1)
 
 
-def main(rec_id):
+def export(rec_id, directory="."):
+    if not isinstance(rec_id, int):
+        raise ValueError("rec_id needs to be an integer")
     ent = db.execute_query("FIND {}".format(rec_id), unique=True)
     cont = recursively_collect_related(ent)
 
-    if not os.path.exists("downloads"):
-        os.makedirs("downloads")
+    directory = os.path.abspath(directory)
+    dl_dir = os.path.join(directory, "downloads")
+
+    if not os.path.exists(dl_dir):
+        os.makedirs(dl_dir)
 
     for el in cont:
         if isinstance(el, db.File) and el.size < 1e6:
-            target = os.path.join("downloads", el.path[1:])
+            target = os.path.join(dl_dir, el.path[1:])
             os.makedirs(os.path.dirname(target), exist_ok=True)
             try:
                 el.download(target)
@@ -117,7 +122,7 @@ def main(rec_id):
     xml = etree.tounicode(cont.to_xml(
         local_serialization=True), pretty_print=True)
 
-    with open("caosdb_data.xml", "w") as fi:
+    with open(os.path.join(directory, "caosdb_data.xml"), "w") as fi:
         fi.write(xml)
 
 
@@ -129,6 +134,11 @@ def defineParser():
         type=int,
         required=True,
         help='the id of the record that shall be copied and then changed')
+    parser.add_argument(
+        '-d',
+        '--directory',
+        default=".",
+        help='the directory where the xml file and the downloads are saved')
 
     return parser
 
@@ -137,4 +147,4 @@ if __name__ == "__main__":
     parser = defineParser()
     args = parser.parse_args()
 
-    main(args.id)
+    export(args.id, directory=args.directory)
diff --git a/src/caosadvancedtools/import_from_xml.py b/src/caosadvancedtools/import_from_xml.py
index 565e6b6a..9942a9a9 100755
--- a/src/caosadvancedtools/import_from_xml.py
+++ b/src/caosadvancedtools/import_from_xml.py
@@ -45,7 +45,11 @@ def create_dummy_file(text="Please ask the administrator for this file."):
     return tmpfile.name
 
 
-def main(filename, rerun=False):
+def import_xml(filename, rerun=False, interactive=True):
+    """
+    filename: path to the xml file with the data to be inserted
+    rerun: boolean; if true, files are not inserted as paths would conflict.
+    """
     cont = db.Container()
     with open(filename) as fi:
         cont = cont.from_xml(fi.read())
@@ -84,7 +88,7 @@ def main(filename, rerun=False):
     # insert/update the model
     datamodel = DataModel()
     datamodel.extend(model)
-    datamodel.sync_data_model()
+    datamodel.sync_data_model(noquestion=not interactive)
 
     # insert files
 
@@ -122,4 +126,4 @@ if __name__ == "__main__":
     parser = defineParser()
     args = parser.parse_args()
 
-    main(args.file, args.rerun)
+    import_xml(args.file, args.rerun)
-- 
GitLab