From 9cb89d4153eb6294fd13655c21e9a9f863b7443f Mon Sep 17 00:00:00 2001
From: Kelvin Rodriguez <krodriguez@usgs.gov>
Date: Sun, 27 Oct 2024 19:09:31 -0700
Subject: [PATCH] fixing bugs in the time search (#41)

* merge conflicts

* test fixes

* forgot to update kernel list
---
 SpiceQL/db/lro.json                           |  3 --
 SpiceQL/src/inventoryimpl.cpp                 | 49 ++++++++++++-------
 SpiceQL/src/query.cpp                         | 17 +++++++
 SpiceQL/src/spice_types.cpp                   |  3 +-
 SpiceQL/src/utils.cpp                         | 24 ++++-----
 SpiceQL/tests/Fixtures.cpp                    | 12 +++--
 SpiceQL/tests/FunctionalTestsSpiceQueries.cpp |  4 +-
 SpiceQL/tests/KernelTests.cpp                 |  2 +-
 SpiceQL/tests/QueryTests.cpp                  | 15 +++---
 SpiceQL/tests/data/isisKernelList.txt         | 16 ------
 bindings/python/pyspiceql.i                   |  3 ++
 bindings/python/tests/test_pyspiceql.py       |  2 +-
 12 files changed, 81 insertions(+), 69 deletions(-)

diff --git a/SpiceQL/db/lro.json b/SpiceQL/db/lro.json
index 1570bdc..cf3421b 100644
--- a/SpiceQL/db/lro.json
+++ b/SpiceQL/db/lro.json
@@ -1,8 +1,5 @@
 {
   "lro" : {
-    "ik" : {
-      "kernels" : ["lro_instruments_v[0-9]{2}.ti$"]
-    },
     "iak" : {
       "kernels" : ["lro_instrumentAddendum_v[0-9]{2}.ti$"]
     },
diff --git a/SpiceQL/src/inventoryimpl.cpp b/SpiceQL/src/inventoryimpl.cpp
index d3848eb..52416aa 100644
--- a/SpiceQL/src/inventoryimpl.cpp
+++ b/SpiceQL/src/inventoryimpl.cpp
@@ -42,7 +42,9 @@ namespace SpiceQL {
   string DB_START_TIME_KEY = "starttime"; 
   string DB_STOP_TIME_KEY = "stoptime"; 
   string DB_TIME_FILES_KEY = "path_index"; 
-  string DB_SS_TIME_INDICES_KEY = "ss_index"; 
+  string DB_START_TIME_INDICES_KEY = "start_kindex"; 
+  string DB_STOP_TIME_INDICES_KEY = "stop_kindex"; 
+
 
   string getCacheDir() { 
       static std::string  CACHE_DIRECTORY = "";
@@ -90,7 +92,7 @@ namespace SpiceQL {
     
     json timeJson = conf.getRecursive(type);
     json ckKernelGrp = timeJson[type][quality]["kernels"];
-    
+
     for(auto &arr : ckKernelGrp) {
       for(auto &subArr : arr) {
         for (auto &kernel : subArr) {
@@ -141,15 +143,19 @@ namespace SpiceQL {
       json json_kernels = getLatestKernels(config.get()); 
 
       // load time kernels for creating the timed kernel DataBase 
-      json sclk_json = getLatestKernels(config.getRecursive("sclk")); 
-      json lsk_json = getLatestKernels(config.getRecursive("lsk")); 
-      
-      m_required_kernels.load(sclk_json); 
+      json lsk_json = getLatestKernels(config["base"].getRecursive("lsk")); 
+
+      SPDLOG_TRACE("InventoryImpl LSKs: {}", lsk_json.dump(4));
+
       m_required_kernels.load(lsk_json); 
 
       for (auto &[mission, kernels] : json_kernels.items()) {
         fmt::print("mission: {}\n", mission);    
 
+        json sclk_json = getLatestKernels(config[mission].getRecursive("sclk")); 
+        SPDLOG_TRACE("{} SCLKs: {}", mission, sclk_json.dump(4)); 
+        KernelSet sclks_ks(sclk_json); 
+
         for(auto &[kernel_type, kernel_obj] : kernels.items()) { 
           if (kernel_type == "ck" || kernel_type == "spk") { 
             // we need to log the times
@@ -272,15 +278,18 @@ namespace SpiceQL {
 
               vector<double> start_times_v = getKey<vector<double>>(DB_SPICE_ROOT_KEY+"/"+key+"/"+DB_START_TIME_KEY); 
               vector<double> stop_times_v = getKey<vector<double>>(DB_SPICE_ROOT_KEY+"/"+key+"/"+DB_STOP_TIME_KEY);
-              vector<size_t> file_index_v = getKey<vector<size_t>>(DB_SPICE_ROOT_KEY+"/"+key+"/"+DB_SS_TIME_INDICES_KEY); 
+              vector<size_t> start_file_index_v = getKey<vector<size_t>>(DB_SPICE_ROOT_KEY+"/"+key+"/"+DB_START_TIME_INDICES_KEY); 
+              vector<size_t> stop_file_index_v = getKey<vector<size_t>>(DB_SPICE_ROOT_KEY+"/"+key+"/"+DB_STOP_TIME_INDICES_KEY); 
               vector<string> file_paths_v = getKey<vector<string>>(DB_SPICE_ROOT_KEY+"/"+key+"/"+DB_TIME_FILES_KEY); 
 
               time_indices->file_paths = file_paths_v;
-              SPDLOG_TRACE("Index, start time, stop time sizes: {}, {}, {}", file_index_v.size(), start_times_v.size(), stop_times_v.size());
+              SPDLOG_TRACE("Index, start time, stop time sizes: {}, {}, {}", start_file_index_v.size(), start_times_v.size(), stop_times_v.size());
               // load start_times 
               for(size_t i = 0; i < start_times_v.size(); i++) {
-                time_indices->start_times[start_times_v[i]] = file_index_v[i];
-                time_indices->stop_times[stop_times_v[i]] = file_index_v[i];
+                time_indices->start_times[start_times_v[i]] = start_file_index_v[i];
+              }
+              for(size_t i = 0; i < stop_times_v.size(); i++) {
+                time_indices->stop_times[stop_times_v[i]] = stop_file_index_v[i];
               }
             }
             catch (runtime_error &e) { 
@@ -313,6 +322,7 @@ namespace SpiceQL {
           }
           for(auto it = time_indices->start_times.begin() ;it != start_upper_bound; it++) {
             iterations++;
+            SPDLOG_TRACE("Inserting {} with the start time {}", time_indices->file_paths.at(it->second), it->first);
             start_time_kernels.insert(it->second);             
           }
 
@@ -320,15 +330,15 @@ namespace SpiceQL {
 
           // Get everything stopping after the start_time; 
           auto stop_lower_bound = time_indices->stop_times.lower_bound(start_time);
-          SPDLOG_TRACE("IS {} in the array? {}", stop_lower_bound->second, start_time_kernels.contains(stop_lower_bound->second)); 
           if(time_indices->stop_times.end() == stop_lower_bound && stop_lower_bound->first >= stop_time && start_time_kernels.contains(stop_lower_bound->second)) { 
+            SPDLOG_TRACE("Is {} in the array? {}", stop_lower_bound->second, start_time_kernels.contains(stop_lower_bound->second)); 
             final_time_kernels.push_back(time_indices->file_paths.at(stop_lower_bound->second));
           }
           else { 
-            for(auto &it = stop_lower_bound;it != time_indices->stop_times.end(); it++) { 
+            for(auto it = stop_lower_bound;it != time_indices->stop_times.end(); it++) { 
               // if it's also in the start_time set, add it to the list
               iterations++;
-              SPDLOG_TRACE("IS {} in the array? {}", it->second, start_time_kernels.contains(it->second)); 
+              SPDLOG_TRACE("Is {} with stop time {} in the array? {}", time_indices->file_paths.at(it->second), it->first, start_time_kernels.contains(it->second)); 
               if (start_time_kernels.contains(it->second)) {
                 final_time_kernels.push_back(data_dir / time_indices->file_paths.at(it->second));
               }
@@ -394,21 +404,26 @@ namespace SpiceQL {
         start_times_v.reserve(kernels->start_times.size());
         vector<double> stop_times_v;
         stop_times_v.reserve(kernels->stop_times.size());
-        vector<size_t> indices_v;
-        indices_v.reserve(kernels->start_times.size());
+        vector<size_t> start_indices_v;
+        start_indices_v.reserve(kernels->start_times.size());
+        vector<size_t> stop_indices_v;
+        stop_indices_v.reserve(kernels->stop_times.size());
+
 
         for (const auto &[k, v] : kernels->start_times) { 
           start_times_v.push_back(k);
-          indices_v.push_back(v);
+          start_indices_v.push_back(v);
         }
 
         for (const auto &[k, v] : kernels->stop_times) { 
           stop_times_v.push_back(k);
+          stop_indices_v.push_back(v);
         } 
 
         H5Easy::dump(file, DB_SPICE_ROOT_KEY + "/"+kernel_key+"/"+DB_START_TIME_KEY, start_times_v, H5Easy::DumpMode::Overwrite);
         H5Easy::dump(file, DB_SPICE_ROOT_KEY + "/"+kernel_key+"/"+DB_STOP_TIME_KEY, stop_times_v, H5Easy::DumpMode::Overwrite);
-        H5Easy::dump(file, DB_SPICE_ROOT_KEY + "/"+kernel_key+"/"+DB_SS_TIME_INDICES_KEY, indices_v, H5Easy::DumpMode::Overwrite);
+        H5Easy::dump(file, DB_SPICE_ROOT_KEY + "/"+kernel_key+"/"+DB_START_TIME_INDICES_KEY, start_indices_v, H5Easy::DumpMode::Overwrite);
+        H5Easy::dump(file, DB_SPICE_ROOT_KEY + "/"+kernel_key+"/"+DB_STOP_TIME_INDICES_KEY, stop_indices_v, H5Easy::DumpMode::Overwrite);
       }
     }
 
diff --git a/SpiceQL/src/query.cpp b/SpiceQL/src/query.cpp
index e8694da..a03c0e1 100644
--- a/SpiceQL/src/query.cpp
+++ b/SpiceQL/src/query.cpp
@@ -230,6 +230,13 @@ namespace SpiceQL {
     }
     if (pointers.empty() && kernels.is_object()) { 
       // Assume it's in the format {"sclk" : ["path1", "path2"], "ck" : ["path1"], ...}  
+      
+      json iaks = {};
+      // we want to furnish them last
+      if(kernels.contains("iak")) { 
+        iaks = kernels["iak"]; 
+        kernels.erase("iak");
+      }
       for (auto& [key, val] : kernels.items()) { 
         SPDLOG_TRACE("Getting Kernels of Type: {}", key);
         if(!val.empty()) { 
@@ -240,6 +247,16 @@ namespace SpiceQL {
           } 
         }
       }
+
+      // add iaks at the end
+      if(!iaks.empty()) { 
+        vector<string> ks = jsonArrayToVector(iaks);
+        for (auto &kernel : ks) { 
+            SPDLOG_TRACE("Adding: {}", kernel);
+            kernelVect.push_back(kernel);
+        }  
+      }
+
     }
     else {
       for (auto & p : pointers) {
diff --git a/SpiceQL/src/spice_types.cpp b/SpiceQL/src/spice_types.cpp
index a5e5200..69a67c5 100644
--- a/SpiceQL/src/spice_types.cpp
+++ b/SpiceQL/src/spice_types.cpp
@@ -80,8 +80,7 @@ namespace SpiceQL {
       return static_cast<Kernel::Quality>(res.second);
     }
 
-    std::string qualities = std::accumulate(Kernel::QUALITIES.begin(), Kernel::QUALITIES.end(), std::string(", "));
-    throw invalid_argument(fmt::format("{} is not a valid kernel type, available types are: {}", qa, qualities));
+    throw invalid_argument(fmt::format("{} is not a valid kernel type, available types are: {}", qa, fmt::join(Kernel::QUALITIES, ", ")));
   }
 
 
diff --git a/SpiceQL/src/utils.cpp b/SpiceQL/src/utils.cpp
index 438d074..75308c3 100644
--- a/SpiceQL/src/utils.cpp
+++ b/SpiceQL/src/utils.cpp
@@ -176,6 +176,8 @@ namespace SpiceQL {
 
 
   vector<double> getTargetState(double et, string target, string observer, string frame, string abcorr) {
+    SPDLOG_TRACE("getTargetState(et={}, target={}, observer={}, frame={}, abcorr={})", et, target, observer, frame, abcorr);
+
     // convert params to spice types
     ConstSpiceChar *target_spice = target.c_str();  // better way to do this?
     ConstSpiceChar *observer_spice = observer.c_str();
@@ -185,7 +187,6 @@ namespace SpiceQL {
     // define outputs
     SpiceDouble lt;
     SpiceDouble starg_spice[6];
-
     checkNaifErrors();
     spkezr_c( target_spice, et, frame_spice, abcorr_spice, observer_spice, starg_spice, &lt );
     checkNaifErrors();
@@ -208,26 +209,19 @@ namespace SpiceQL {
     }
 
     json ephemKernels = {};
-    json lskKernels = {};
-    json pckKernels = {};
-    json spkKernels = {};
+    json baseKernels = {};
 
     if (searchKernels) {
-      ephemKernels = Inventory::search_for_kernelset(mission, {"sclk", "ck", "spk", "pck", "tspk"}, ets.front(), ets.back(), ckQuality, spkQuality);
-      lskKernels = Inventory::search_for_kernelset("base", {"lsk"});
-      pckKernels = Inventory::search_for_kernelset("base", {"pck"});
-      spkKernels = Inventory::search_for_kernelset("base", {"spk"});
-      SPDLOG_DEBUG("LSK Kernels : {}", lskKernels.dump(4));
+      ephemKernels = Inventory::search_for_kernelset(mission, {"sclk", "ck", "spk", "pck", "tspk", "fk"}, ets.front(), ets.back(), ckQuality, spkQuality);
+      baseKernels = Inventory::search_for_kernelset("base", {"lsk", "pck", "spk"});
+      SPDLOG_DEBUG("Base Kernels : {}", baseKernels.dump(4));
       SPDLOG_DEBUG("{} Kernels : {}", mission, ephemKernels.dump(4));
-      SPDLOG_DEBUG("PCK Kernels : {}", pckKernels.dump(4));
-      SPDLOG_DEBUG("SPK Kernels : {}", spkKernels.dump(4)); 
     }
 
     auto start = high_resolution_clock::now();
+    KernelSet baseSet(baseKernels);
     KernelSet ephemSet(ephemKernels);
-    KernelSet lskSet(lskKernels);
-    KernelSet pckSet(pckKernels);
-    KernelSet spkSet(spkKernels);
+
     auto stop = high_resolution_clock::now();
     auto duration = duration_cast<microseconds>(stop - start);
     SPDLOG_INFO("Time in microseconds to furnish kernel sets: {}", duration.count());
@@ -1102,7 +1096,7 @@ namespace SpiceQL {
           ssize_c(200000, &cover);
 
           // A SPICE SEGMENT is composed of SPICE INTERVALS
-          ckcov_c(kpath.c_str(), body, SPICEFALSE, "SEGMENT", 0.0, "TDB", &cover);
+          ckcov_c(kpath.c_str(), body, SPICEFALSE, "INTERVAL", 0.0, "TDB", &cover);
 
           getStartStopFromInterval(cover);
         }
diff --git a/SpiceQL/tests/Fixtures.cpp b/SpiceQL/tests/Fixtures.cpp
index c995525..7763e93 100644
--- a/SpiceQL/tests/Fixtures.cpp
+++ b/SpiceQL/tests/Fixtures.cpp
@@ -54,9 +54,9 @@ void TempTestingFiles::SetUp() {
 
 
 void TempTestingFiles::TearDown() {
-    // if(!fs::remove_all(tempDir)) {
-    //   throw runtime_error("Could not delete temporary files");
-    // }
+    if(!fs::remove_all(tempDir)) {
+      throw runtime_error("Could not delete temporary files");
+    }
 }
 
 
@@ -273,9 +273,11 @@ void LroKernelSet::SetUp() {
   writeSpk(spkPath3, positions, times1, bodyCode/1000, 301, referenceFrame, "SPK ID 3", 1, velocities, "SPK 3");
 
   // Write IK1 -------------------------------------------
+  fs::create_directory(root / "iak");
   fs::create_directory(root / "ik");
+ 
 
-  ikPath1 = root / "ik" / "lro_instruments_v10.ti";
+  ikPath1 = root / "iak" / "lro_instrumentAddendum_v11.ti";
   nlohmann::json jKeywords = {
     {"INS-85600_PIXEL_SAMPLES", { 5064 }},
     {"INS-85600_PIXEL_LINES", { 1 }},
@@ -286,7 +288,7 @@ void LroKernelSet::SetUp() {
   writeTextKernel(ikPath1, "ik", jKeywords);
 
   // Write IK2 -------------------------------------------
-  ikPath2 = root / "ik" / "lro_instruments_v11.ti";
+  ikPath2 = root / "ik" / "lro_lroc_v11.ti";
   jKeywords = {
     {"INS-85600_PIXEL_SAMPLES", { 5063 }},
     {"INS-85600_PIXEL_LINES", { 1 }},
diff --git a/SpiceQL/tests/FunctionalTestsSpiceQueries.cpp b/SpiceQL/tests/FunctionalTestsSpiceQueries.cpp
index 7b23090..f5cae1a 100644
--- a/SpiceQL/tests/FunctionalTestsSpiceQueries.cpp
+++ b/SpiceQL/tests/FunctionalTestsSpiceQueries.cpp
@@ -15,11 +15,11 @@ using namespace SpiceQL;
 
 TEST_F(LroKernelSet, FunctionalTestSearchMissionKernels) {
   // do a time query
-  nlohmann::json kernels = Inventory::search_for_kernelset("lroc", {"lsk", "sclk", "ck", "spk", "ik", "fk"}, 110000000, 140000001);
+  nlohmann::json kernels = Inventory::search_for_kernelset("lroc", {"lsk", "sclk", "ck", "spk", "iak", "fk"}, 110000000, 140000001);
   cout << kernels.dump(4) << endl;
   ASSERT_EQ(kernels["ck"].size(), 2);
   EXPECT_EQ(fs::path(kernels["ck"][0].get<string>()).filename(), "soc31_1111111_1111111_v21.bc" );
-  EXPECT_EQ(fs::path(kernels["ik"][0].get<string>()).filename(), "lro_instruments_v11.ti");
+  EXPECT_EQ(fs::path(kernels["iak"][0].get<string>()).filename(), "lro_instrumentAddendum_v11.ti");
   EXPECT_EQ(fs::path(kernels["fk"][0].get<string>()).filename(), "lro_frames_1111111_v01.tf");
   EXPECT_EQ(fs::path(kernels["sclk"][0].get<string>()).filename(), "lro_clkcor_2020184_v00.tsc");
 }
\ No newline at end of file
diff --git a/SpiceQL/tests/KernelTests.cpp b/SpiceQL/tests/KernelTests.cpp
index fa30d9b..28d3e1c 100644
--- a/SpiceQL/tests/KernelTests.cpp
+++ b/SpiceQL/tests/KernelTests.cpp
@@ -146,7 +146,7 @@ TEST_F(LroKernelSet, UnitTestFindMissionKeywords) {
   nlohmann::json keywords = findMissionKeywords("INS-85600_CCD_CENTER", "lro");
 
   nlohmann::json expectedResults;
-  expectedResults["INS-85600_CCD_CENTER"] = {2531.3, 0.4};
+  expectedResults["INS-85600_CCD_CENTER"] = {2531.5, 0.5};
 
   EXPECT_EQ(keywords, expectedResults);
 }
diff --git a/SpiceQL/tests/QueryTests.cpp b/SpiceQL/tests/QueryTests.cpp
index 9083a5c..421a185 100644
--- a/SpiceQL/tests/QueryTests.cpp
+++ b/SpiceQL/tests/QueryTests.cpp
@@ -231,41 +231,42 @@ TEST_F(IsisDataDirectory, FunctionalTestLroConf) {
   mocks.OnCallFunc(ls).Return(files);
   
   nlohmann::json res = listMissionKernels("doesn't matter", conf);
-  
+  SPDLOG_DEBUG("Kernel Results: {}", res.dump(4));
   // check a kernel from each regex exists in their quality groups
   vector<string> kernelToCheck =  SpiceQL::getKernelsAsVector(res.at("moc").at("ck").at("reconstructed").at("kernels"));
   vector<string> expected = {"moc42r_2016305_2016336_v01.bc"};
-  
+  SPDLOG_DEBUG("Checking CKs");
   for (auto &e : expected) { 
     auto it = find(kernelToCheck.begin(), kernelToCheck.end(), e);
     if (it == kernelToCheck.end()) {
-      FAIL() << e << " was not found in the kernel results";
+      throw runtime_error(e+" was not found in the kernel results");
     }
   }
   
+  SPDLOG_DEBUG("Checking Recon SPKs");
   kernelToCheck = getKernelsAsVector(res.at("moc").at("spk").at("reconstructed")); 
   expected = {"fdf29r_2018305_2018335_v01.bsp", "fdf29_2021327_2021328_b01.bsp"};
   for (auto &e : expected) { 
     auto it = find(kernelToCheck.begin(), kernelToCheck.end(), e);
     if (it == kernelToCheck.end()) {
-      FAIL() << e << " was not found in the kernel results";
+      throw runtime_error(e+" was not found in the kernel results");
     }
   }
 
-
+  SPDLOG_DEBUG("Checking Smithed SPKs");
   kernelToCheck = getKernelsAsVector(res.at("moc").at("spk").at("smithed")); 
   expected = {"LRO_ES_05_201308_GRGM660PRIMAT270.bsp", "LRO_ES_16_201406_GRGM900C_L600.BSP"};
   for (auto &e : expected) { 
     auto it = find(kernelToCheck.begin(), kernelToCheck.end(), e);
     if (it == kernelToCheck.end()) {
-      FAIL() << e << " was not found in the kernel results";
+      throw runtime_error(e+" was not found in the kernel results");
     }
   }
 
+  SPDLOG_DEBUG("Checking IAKs");
   kernelToCheck = getKernelsAsVector(res.at("minirf").at("iak"));
   expected = {"mrflroAddendum002.ti"};
   EXPECT_EQ(kernelToCheck, expected);
-
 }
 
 
diff --git a/SpiceQL/tests/data/isisKernelList.txt b/SpiceQL/tests/data/isisKernelList.txt
index d91f6d1..614e5c0 100644
--- a/SpiceQL/tests/data/isisKernelList.txt
+++ b/SpiceQL/tests/data/isisKernelList.txt
@@ -12202,26 +12202,10 @@
 /home/ec2-user/efs_prod/isis_data/lro/kernels/pck/moon_080317.tf
 /home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_lroc_v13.ti
 /home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_lroc_v15.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v07.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v11.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v10.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v03.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v04.ti
 /home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_lroc_v16.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v02.ti
 /home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_lroc_v18.ti
 /home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_lroc_v14.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v09.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v05.ti
 /home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_lroc_v17.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v12.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v06.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/ik/lro_instruments_v08.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/iak/lro_instrumentAddendum_v02.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/iak/lro_instrumentAddendum_v00.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/iak/lro_instrumentAddendum_v01.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/iak/lro_instrumentAddendum_v03.ti
-/home/ec2-user/efs_prod/isis_data/lro/kernels/iak/lro_instrumentAddendum_v04.ti
 /home/ec2-user/efs_prod/isis_data/lro/kernels/iak/mrflroAddendum002.ti
 /home/ec2-user/efs_prod/isis_data/lro/kernels/spk/fdf29r_2018305_2018335_v01.bsp
 /home/ec2-user/efs_prod/isis_data/lro/kernels/spk/fdf29r_2014091_2014121_v01.bsp
diff --git a/bindings/python/pyspiceql.i b/bindings/python/pyspiceql.i
index 1100ec1..80cd1f0 100644
--- a/bindings/python/pyspiceql.i
+++ b/bindings/python/pyspiceql.i
@@ -16,6 +16,9 @@
   #include <vector> 
 %}
 
+%template(DoublePair) std::pair<double, double>;
+
+
 %typemap(in) nlohmann::json {
   if (PyDict_Check($input) || PyList_Check($input)) {
     PyObject* module = PyImport_ImportModule("json");
diff --git a/bindings/python/tests/test_pyspiceql.py b/bindings/python/tests/test_pyspiceql.py
index 259301c..20f56a5 100644
--- a/bindings/python/tests/test_pyspiceql.py
+++ b/bindings/python/tests/test_pyspiceql.py
@@ -4,7 +4,7 @@ from pyspiceql import getMissionConfig, Config, getKernelStringValue
 def test_jsonConversion():
     lro_config = getMissionConfig('lro')
     assert isinstance(lro_config, dict)
-    kernel_list = lro_config["lro"]["ik"]["kernels"]
+    kernel_list = lro_config["lro"]["iak"]["kernels"]
     assert isinstance(kernel_list, list)
 
 def test_config():
-- 
GitLab