diff --git a/src/ISADotNet.XLSX/AssayFile/AnnotationNode.fs b/src/ISADotNet.XLSX/AssayFile/AnnotationNode.fs
index 8f904fa8..99db4266 100644
--- a/src/ISADotNet.XLSX/AssayFile/AnnotationNode.fs
+++ b/src/ISADotNet.XLSX/AssayFile/AnnotationNode.fs
@@ -105,7 +105,7 @@ module AnnotationNode =
(termAccessionGetter matrix i)
(termSourceGetter matrix i)
- let category = mergeOntology category1 category2 |> Option.map (Some >> ProtocolParameter.create None)
+ let category = mergeOntology h.Term category1 |> mergeOntology category2 |> Option.map (Some >> ProtocolParameter.create None)
category,
fun (matrix : System.Collections.Generic.Dictionary<(string * int),string>) i ->
@@ -157,7 +157,7 @@ module AnnotationNode =
(termSourceGetter matrix i)
let factor =
- mergeOntology category1 category2
+ mergeOntology h.Term category1 |> mergeOntology category2
|> Option.map (fun oa -> Factor.create None (oa.Name |> Option.map AnnotationValue.toString) (Some oa) None)
factor,
@@ -186,6 +186,7 @@ module AnnotationNode =
| Some v -> Some v
| _ -> None
| None -> None, fun _ _ -> None
+
let category2, termSourceGetter =
match Seq.tryPick (tryParseTermSourceReferenceHeader h) headers with
| Some h ->
@@ -210,7 +211,7 @@ module AnnotationNode =
(termAccessionGetter matrix i)
(termSourceGetter matrix i)
- let characteristic = mergeOntology category1 category2 |> Option.map (Some >> MaterialAttribute.create None)
+ let characteristic = mergeOntology h.Term category1 |> mergeOntology category2 |> Option.map (Some >> MaterialAttribute.create None)
characteristic,
fun (matrix : System.Collections.Generic.Dictionary<(string * int),string>) i ->
diff --git a/src/ISADotNet.XLSX/Conversions.fs b/src/ISADotNet.XLSX/Conversions.fs
index 2ccf06cb..b3577d18 100644
--- a/src/ISADotNet.XLSX/Conversions.fs
+++ b/src/ISADotNet.XLSX/Conversions.fs
@@ -153,6 +153,17 @@ module ProtocolParameter =
sprintf "%s%c%s" sources separator source
)
+module MaterialAttribute =
+
+ /// Create a ISAJson MaterialAttribute from ISATab string entries
+ let fromString (term:string) (accession:string) (source:string) =
+ OntologyAnnotation.fromString term accession source
+ |> Option.fromValueWithDefault OntologyAnnotation.empty
+ |> MaterialAttribute.create None
+
+ /// Get ISATab string entries from an ISAJson MaterialAttribute object
+ let toString (ma : MaterialAttribute) =
+ ma.CharacteristicType |> Option.map OntologyAnnotation.toString |> Option.defaultValue ("","","")
module Value =
diff --git a/src/ISADotNet.XLSX/ISADotNet.XLSX.fsproj b/src/ISADotNet.XLSX/ISADotNet.XLSX.fsproj
index 6b596cbd..fa4459bb 100644
--- a/src/ISADotNet.XLSX/ISADotNet.XLSX.fsproj
+++ b/src/ISADotNet.XLSX/ISADotNet.XLSX.fsproj
@@ -29,12 +29,16 @@
-
+
+
+
+
+
nfdi4plants, Lukas Weil, Kevin Frey
diff --git a/src/ISADotnet/ISADotNet.fsproj b/src/ISADotnet/ISADotNet.fsproj
index d4f3aa89..a80b7397 100644
--- a/src/ISADotnet/ISADotNet.fsproj
+++ b/src/ISADotnet/ISADotNet.fsproj
@@ -50,6 +50,10 @@
+
+
+
+
diff --git a/src/ISADotnet/JsonIO/IO.fs b/src/ISADotnet/JsonIO/IO.fs
index b02334ec..784f25ff 100644
--- a/src/ISADotnet/JsonIO/IO.fs
+++ b/src/ISADotnet/JsonIO/IO.fs
@@ -5,6 +5,21 @@ open System.Text.Json
open System.IO
open FSharp.SystemTextJson
+module OntologyAnnotation =
+
+ let fromString (s:string) =
+ JsonSerializer.Deserialize(s,JsonExtensions.options)
+
+ let toString (oa:OntologyAnnotation) =
+ JsonSerializer.Serialize(oa,JsonExtensions.options)
+
+ let fromFile (path : string) =
+ File.ReadAllText path
+ |> fromString
+
+ let toFile (path : string) (oa:OntologyAnnotation) =
+ File.WriteAllText(path,toString oa)
+
module Protocol =
let fromString (s:string) =
diff --git a/tests/ISADotNet.Tests/ISADotNet.XLSX/AssayFileTests.fs b/tests/ISADotNet.Tests/ISADotNet.XLSX/AssayFileTests.fs
index 1591ab8c..b59fdc8b 100644
--- a/tests/ISADotNet.Tests/ISADotNet.XLSX/AssayFileTests.fs
+++ b/tests/ISADotNet.Tests/ISADotNet.XLSX/AssayFileTests.fs
@@ -7,6 +7,7 @@ open ISADotNet
open Expecto
open TestingUtils
+open ISADotNet
open ISADotNet.XLSX
open ISADotNet.XLSX.AssayFile
@@ -142,6 +143,88 @@ let testHeaderSplittingFunctions =
)
]
+[]
+let testNodeGetterFunctions =
+
+ let sourceDirectory = __SOURCE_DIRECTORY__ + @"/TestFiles/"
+
+ let assayFilePath = System.IO.Path.Combine(sourceDirectory,"AssayTableTestFile.xlsx")
+
+ let doc = Spreadsheet.fromFile assayFilePath false
+ let sst = Spreadsheet.tryGetSharedStringTable doc
+ let wsp = Spreadsheet.tryGetWorksheetPartBySheetIndex 0u doc |> Option.get
+ let table = Table.tryGetByNameBy (fun s -> s.Contains "annotationTable") wsp |> Option.get
+
+ let m = Table.toSparseValueMatrix sst (Worksheet.getSheetData wsp.Worksheet) table
+
+ testList "NodGetterTests" [
+ testCase "RetreiveValueFromMatrix" (fun () ->
+ let tryGetValue k (dict:System.Collections.Generic.Dictionary<'K,'V>) =
+ let b,v = dict.TryGetValue(k)
+ if b then Some v
+ else None
+
+ let v = tryGetValue ("Unit [square centimeter] (#h; #tUO:0000081; #u)",0) m
+
+ Expect.isSome v "Value could not be retrieved from matrix"
+
+ let expectedValue = "square centimeter"
+
+ Expect.equal v.Value expectedValue "Value retrieved from matrix is not correct"
+
+ )
+
+ testCase "GetUnitGetter" (fun () ->
+
+ let headers = ["Unit [square centimeter] (#h; #tUO:0000081; #u)";"Term Source REF [square centimeter] (#h; #tUO:0000081; #u)";"Term Accession Number [square centimeter] (#h; #tUO:0000081; #u)"]
+
+ let unitGetterOption = AnnotationNode.tryGetUnitGetterFunction headers
+
+ Expect.isSome unitGetterOption "Unit Getter was not returned even though headers should have matched"
+
+ let unitGetter = unitGetterOption.Value
+
+ let unit = unitGetter m 0
+
+ let expectedUnit = OntologyAnnotation.fromString "square centimeter" "http://purl.obolibrary.org/obo/UO_0000081" "UO"
+
+ Expect.equal unit expectedUnit "Retrieved Unit is wrong"
+ )
+ testCase "GetUnitGetterWrongHeaders" (fun () ->
+
+ let headers = ["Parameter [square centimeter] (#h; #tUO:0000081; #u)";"Term Source REF [square centimeter] (#h; #tUO:0000081; #u)";"Term Accession Number [square centimeter] (#h; #tUO:0000081; #u)"]
+
+ let unitGetterOption = AnnotationNode.tryGetUnitGetterFunction headers
+
+ Expect.isNone unitGetterOption "Unit Getter was returned even though headers should not have matched"
+ )
+ testCase "GetCharacteristicsGetter" (fun () ->
+
+ let headers = ["Characteristics [leaf size]";"Term Source REF [leaf size] (#h; #tTO:0002637)";"Term Accession Number [leaf size] (#h; #tTO:0002637)";"Unit [square centimeter] (#h; #tUO:0000081; #u)";"Term Source REF [square centimeter] (#h; #tUO:0000081; #u)";"Term Accession Number [square centimeter] (#h; #tUO:0000081; #u)"]
+
+ let characteristicGetterOption = AnnotationNode.tryGetCharacteristicGetterFunction headers
+
+ Expect.isSome characteristicGetterOption "Characteristic Getter was not returned even though headers should have matched"
+
+ let characteristic,characteristicValue = characteristicGetterOption.Value
+
+ //let unit = unitGetter m 0
+
+ let expectedCharacteristic = MaterialAttribute.fromString "leaf size" "0002637" "TO"
+
+ Expect.equal characteristic.Value expectedCharacteristic "Retrieved Characteristic is wrong"
+ )
+ testCase "GetCharacteristicsGetterWrongHeaders" (fun () ->
+
+ let headers = ["Parameter [square centimeter] (#h; #tUO:0000081; #u)";"Term Source REF [square centimeter] (#h; #tUO:0000081; #u)";"Term Accession Number [square centimeter] (#h; #tUO:0000081; #u)"]
+
+ let unitGetterOption = AnnotationNode.tryGetCharacteristicGetterFunction headers
+
+ Expect.isNone unitGetterOption "Characteristic Getter was returned even though headers should not have matched"
+ )
+ ]
+
+
[]
let testProcessComparisonFunctions =
@@ -250,6 +333,21 @@ let testProcessComparisonFunctions =
Expect.sequenceEqual mergedProcess2.Outputs.Value [ProcessOutput.Sample sample2;ProcessOutput.Sample sample4] "Inputs were not merged correctly for mergedProcess2"
)
+ testCase "IndexIdenticalProcessesByProtocolName" (fun () ->
+
+ let process1 = Process.create None None (Some protocol1) (Some parameterValues1) None None None None (Some [Source source1]) (Some [Sample sample1]) None
+ let process2 = Process.create None None (Some protocol1) (Some parameterValues2) None None None None (Some [Source source2]) (Some [Sample sample2]) None
+ let process3 = Process.create None None (Some protocol2) (Some parameterValues1) None None None None (Some [Source source3]) (Some [Sample sample3]) None
+ let process4 = Process.create None None (Some protocol2) (Some parameterValues2) None None None None (Some [Source source4]) (Some [Sample sample4]) None
+
+ let indexedProcesses = AnnotationTable.indexRelatedProcessesByProtocolName [process1;process2;process3;process4]
+
+ let names = indexedProcesses |> Seq.map (fun p -> Option.defaultValue "" p.Name)
+
+ let expectedNames = ["Protocol1_0";"Protocol1_1";"Protocol2_0";"Protocol2_1"]
+
+ Expect.sequenceEqual names expectedNames "Processes were not indexed correctly"
+ )
]
@@ -257,8 +355,7 @@ let testProcessComparisonFunctions =
let testMetaDataFunctions =
let sourceDirectory = __SOURCE_DIRECTORY__ + @"/TestFiles/"
- let sinkDirectory = System.IO.Directory.CreateDirectory(__SOURCE_DIRECTORY__ + @"/TestResult/").FullName
- let referenceAssayFilePath = System.IO.Path.Combine(sourceDirectory,"AssayTestFile.xlsx")
+ let referenceAssayFilePath = System.IO.Path.Combine(sourceDirectory,"AssayMetadataTestFile.xlsx")
testList "MetaDataTests" [
testCase "CanReadMetaData" (fun () ->
diff --git a/tests/ISADotNet.Tests/ISADotNet.XLSX/TestFiles/AssayTestFile.xlsx b/tests/ISADotNet.Tests/ISADotNet.XLSX/TestFiles/AssayMetadataTestFile.xlsx
similarity index 100%
rename from tests/ISADotNet.Tests/ISADotNet.XLSX/TestFiles/AssayTestFile.xlsx
rename to tests/ISADotNet.Tests/ISADotNet.XLSX/TestFiles/AssayMetadataTestFile.xlsx
diff --git a/tests/ISADotNet.Tests/ISADotNet.XLSX/TestFiles/AssayTableTestFile.xlsx b/tests/ISADotNet.Tests/ISADotNet.XLSX/TestFiles/AssayTableTestFile.xlsx
new file mode 100644
index 00000000..f05c86d0
Binary files /dev/null and b/tests/ISADotNet.Tests/ISADotNet.XLSX/TestFiles/AssayTableTestFile.xlsx differ