yarrrml_template_builder 0.1.54
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +8 -0
- data/Changelog.md +1 -0
- data/Gemfile +8 -0
- data/Gemfile.lock +39 -0
- data/LICENSE.txt +21 -0
- data/README.md +139 -0
- data/bin/console +15 -0
- data/bin/setup +8 -0
- data/config/height_yarrrml_template.yaml +190 -0
- data/data/height.csv +2 -0
- data/doc/YARRRMLTemplateBuilder.html +121 -0
- data/doc/YARRRML_Template_Builder.html +6392 -0
- data/doc/YARRRML_Transform.html +1940 -0
- data/doc/_index.html +117 -0
- data/doc/class_list.html +51 -0
- data/doc/css/common.css +1 -0
- data/doc/css/full_list.css +58 -0
- data/doc/css/style.css +497 -0
- data/doc/file.README.html +214 -0
- data/doc/file_list.html +56 -0
- data/doc/frames.html +17 -0
- data/doc/index.html +214 -0
- data/doc/js/app.js +314 -0
- data/doc/js/full_list.js +216 -0
- data/doc/js/jquery.js +4 -0
- data/doc/method_list.html +459 -0
- data/doc/top-level-namespace.html +112 -0
- data/examples/example_output_timerange.rb +56 -0
- data/examples/example_timed_process.rb +56 -0
- data/examples/example_timeinstant_process.rb +56 -0
- data/examples/example_two_linked_processes.rb +88 -0
- data/exemplar_docker_compose.yml +36 -0
- data/lib/yarrrml-template-builder.rb +2 -0
- data/lib/yarrrml_template_builder/version.rb +5 -0
- data/lib/yarrrml_template_builder/yarrrml_template_builder.rb +1485 -0
- data/lib/yarrrml_template_builder/yarrrml_transform.rb +181 -0
- data/lib/yarrrmltemplatebuilder.rb +5 -0
- data/run_me_to_test.rb +26 -0
- data/yarrrml_template_builder.gemspec +39 -0
- metadata +115 -0
@@ -0,0 +1,1485 @@
|
|
1
|
+
require_relative 'version'
|
2
|
+
require 'tempfile'
|
3
|
+
require 'rest-client'
|
4
|
+
require 'yaml'
|
5
|
+
require 'digest'
|
6
|
+
|
7
|
+
class YARRRML_Template_Builder
|
8
|
+
|
9
|
+
attr_accessor :prefix_map
|
10
|
+
attr_accessor :baseURI
|
11
|
+
attr_accessor :sio_verbose
|
12
|
+
attr_accessor :source_tag
|
13
|
+
attr_accessor :sources_module
|
14
|
+
attr_accessor :mappings
|
15
|
+
|
16
|
+
SIO = {
|
17
|
+
"entity" => ["http://semanticscience.org/resource/SIO_000000", "http://semanticscience.org/resource/entity"],
|
18
|
+
"day" => ["http://semanticscience.org/resource/SIO_000430", "http://semanticscience.org/resource/day"],
|
19
|
+
"has-attribute" => ["http://semanticscience.org/resource/SIO_000008", "http://semanticscience.org/resource/has-attribute"],
|
20
|
+
"has-measurement-value" => ["http://semanticscience.org/resource/SIO_000216", "http://semanticscience.org/resource/has-measurement-value"],
|
21
|
+
"has-quality" => ["http://semanticscience.org/resource/SIO_000217", "http://semanticscience.org/resource/has-quality"],
|
22
|
+
"has-unit" => ["http://semanticscience.org/resource/SIO_000221", "http://semanticscience.org/resource/has-unit"],
|
23
|
+
"has-value" => ["http://semanticscience.org/resource/SIO_000300", "http://semanticscience.org/resource/has-value"],
|
24
|
+
"has-part" => ["http://semanticscience.org/resource/SIO_000028", "http://semanticscience.org/resource/has-part"],
|
25
|
+
"has-role" => ["http://semanticscience.org/resource/SIO_000228", "http://semanticscience.org/resource/has-role"],
|
26
|
+
"has-agent" => ["http://semanticscience.org/resource/SIO_000139", "http://semanticscience.org/resource/has-agent"],
|
27
|
+
"has-target" => ["http://semanticscience.org/resource/SIO_000291", "http://semanticscience.org/resource/has-target"],
|
28
|
+
"is-participant-in" => ["http://semanticscience.org/resource/SIO_000062", "http://semanticscience.org/resource/is-participant-in"],
|
29
|
+
"is-about" => ["http://semanticscience.org/resource/SIO_000332", "http://semanticscience.org/resource/is-about"],
|
30
|
+
"has-output" => ["http://semanticscience.org/resource/SIO_000229", "http://semanticscience.org/resource/has-output"],
|
31
|
+
"denotes" => ["http://semanticscience.org/resource/SIO_000020", "http://semanticscience.org/resource/denotes"],
|
32
|
+
"is-realized-in" => ["http://semanticscience.org/resource/SIO_000356", "http://semanticscience.org/resource/is-realized-in"],
|
33
|
+
"is-causally-related-to" => ["http://semanticscience.org/resource/SIO_000294", "http://semanticscience.org/resource/is-causally-related-to"],
|
34
|
+
"is-causally-related-from" => ["http://semanticscience.org/resource/SIO_000352", "http://semanticscience.org/resource/is-causally-related-from"],
|
35
|
+
"is-specified-by" => ["http://semanticscience.org/resource/SIO_000339", "http://semanticscience.org/resource/is-specified-by"],
|
36
|
+
"has-component-part" => ["http://semanticscience.org/resource/SIO_000369", "http://semanticscience.org/resource/has-component-part"],
|
37
|
+
# predicates
|
38
|
+
# for processs
|
39
|
+
"has-start-time" => ["http://semanticscience.org/resource/SIO_000680", "http://semanticscience.org/resource/has-start-time"],
|
40
|
+
"exists-at" => ["http://semanticscience.org/resource/SIO_000687", "http://semanticscience.org/resource/exists-at"],
|
41
|
+
"has-end-time" => ["http://semanticscience.org/resource/SIO_000681", "http://semanticscience.org/resource/has-end-time"],
|
42
|
+
"has-time-boundary" => ["http://semanticscience.org/resource/SIO_000679", "http://semanticscience.org/resource/has-time-boundary"],
|
43
|
+
# for information artifact
|
44
|
+
"measured-at" => ["http://semanticscience.org/resource/SIO_000793", "http://semanticscience.org/resource/measured-at"],
|
45
|
+
# objects
|
46
|
+
"start-time" => ["http://semanticscience.org/resource/SIO_000669", "http://semanticscience.org/resource/start-time"],
|
47
|
+
"end-time" => ["http://semanticscience.org/resource/SIO_000670", "http://semanticscience.org/resource/end-time"],
|
48
|
+
"start-date" => ["http://semanticscience.org/resource/SIO_000031", "http://semanticscience.org/resource/start-date"],
|
49
|
+
"end-date" => ["http://semanticscience.org/resource/SIO_000032", "http://semanticscience.org/resource/end-date"],
|
50
|
+
"time-instant" => ["http://semanticscience.org/resource/SIO_000418", "http://semanticscience.org/resource/time-instant"],
|
51
|
+
#
|
52
|
+
|
53
|
+
|
54
|
+
|
55
|
+
"is-component-part-of" => ["http://semanticscience.org/resource/SIO_000313", "http://semanticscience.org/resource/is-component-part-of"],
|
56
|
+
"drug" => ["http://semanticscience.org/resource/SIO_010038", "http://semanticscience.org/resource/drug"],
|
57
|
+
"specialized-object" => ["http://semanticscience.org/resource/SIO_001353", "http://semanticscience.org/resource/specialized-object"],
|
58
|
+
"object" => ["http://semanticscience.org/resource/SIO_000776", "http://semanticscience.org/resource/object"],
|
59
|
+
"is-base-for" => ["http://semanticscience.org/resource/SIO_000642", "http://semanticscience.org/resource/is-base-for"],
|
60
|
+
"has-concretization" => ["http://semanticscience.org/resource/SIO_000213", "http://semanticscience.org/resource/has-concretization"],
|
61
|
+
"realizable-entity" => ["http://semanticscience.org/resource/SIO_000340", "http://semanticscience.org/resource/realizable-entity"],
|
62
|
+
"information-content-entity" => ["http://semanticscience.org/resource/SIO_000015", "http://semanticscience.org/resource/information-content-entity"],
|
63
|
+
"measurement-value" => ["http://semanticscience.org/resource/SIO_000070", "http://semanticscience.org/resource/measurement-value"],
|
64
|
+
"refers-to" => ["http://semanticscience.org/resource/SIO_000628", "http://semanticscience.org/resource/refers-to"],
|
65
|
+
"has-input" => ["http://semanticscience.org/resource/SIO_000230", "http://semanticscience.org/resource/has-input"],
|
66
|
+
"person" => ["http://semanticscience.org/resource/SIO_000498", "http://semanticscience.org/resource/person"],
|
67
|
+
"identifier" => ["http://semanticscience.org/resource/SIO_000115", "http://semanticscience.org/resource/identifier"],
|
68
|
+
"role" => ["http://semanticscience.org/resource/SIO_000016", "http://semanticscience.org/resource/role"],
|
69
|
+
"process" => ["http://semanticscience.org/resource/SIO_000006", "http://semanticscience.org/resource/process"],
|
70
|
+
"attribute" => ["http://semanticscience.org/resource/SIO_000614", "http://semanticscience.org/resource/attribute"],
|
71
|
+
"conforms-to" => ["https://semanticscience.org/resource/CHEMINF_000047", "http://semanticscience.org/resource/conforms-to"],
|
72
|
+
|
73
|
+
}
|
74
|
+
|
75
|
+
|
76
|
+
|
77
|
+
# all params are passed as a hash, and retrieved by params.fetch(paramName)
|
78
|
+
#
|
79
|
+
# @param params [Hash] params a Hash of options
|
80
|
+
# @option params [String] :baseURI a URL that will become the base for "urls owned by the data provider" e.g. "https://my.dataset.org/thisdataset/records/"
|
81
|
+
# @option params [String] :source_name a "short name" (i.e. a single word, no spaces) for the kind of data being transformed. e.g. height_data
|
82
|
+
# @option params [Integer] :sio_verbose (0) "1" means to use http://semanticscience.org/resource/has-value instead of http://semanticscience.org/resource/SIO_000300 for all sio. Default is 0
|
83
|
+
#
|
84
|
+
# @return [YARRRML_Template_BuilderII]
|
85
|
+
def initialize(params = {}) # get a name from the "new" call, or set a default
|
86
|
+
|
87
|
+
@baseURI = params.fetch(:baseURI, "|||BASE|||")
|
88
|
+
@sio_verbose = params.fetch(:sio_verbose, 0)
|
89
|
+
abort "must have a baseURI parameter" unless self.baseURI
|
90
|
+
@mappings = []
|
91
|
+
|
92
|
+
@source_tag = params.fetch(:source_tag, nil)
|
93
|
+
abort "must have a source_name parameter" unless self.source_tag
|
94
|
+
|
95
|
+
@prefix_map = {
|
96
|
+
"rdf" => "http://www.w3.org/1999/02/22-rdf-syntax-ns#",
|
97
|
+
"rdfs" => "http://www.w3.org/2000/01/rdf-schema#",
|
98
|
+
"ex" => "https://ejp-rd.eu/ids/",
|
99
|
+
"obo" => "http://purl.obolibrary.org/obo/",
|
100
|
+
"sio" => "http://semanticscience.org/resource/",
|
101
|
+
"vocab" => "https://ejp-rd.eu/vocab/",
|
102
|
+
"pico" => "https://data.cochrane.org/ontologies/pico/",
|
103
|
+
"ndfrt" => "http://purl.bioontology.org/ontology/NDFRT/",
|
104
|
+
"edam" => "http://purl.bioontology.org/ontology/EDAM/",
|
105
|
+
"ordo" => "http://www.orpha.net/ORDO/",
|
106
|
+
}
|
107
|
+
|
108
|
+
self.add_prefixes(prefixesHash: {"this" => self.baseURI})
|
109
|
+
sources_module()
|
110
|
+
|
111
|
+
end
|
112
|
+
|
113
|
+
|
114
|
+
|
115
|
+
|
116
|
+
# adds new Prefixes to the prefix map
|
117
|
+
#
|
118
|
+
# Parameters passed as the value to the key :prefixesHash
|
119
|
+
#
|
120
|
+
# @param params [Hash]
|
121
|
+
# @option params [Hash] :prefixesHash ({}) hash of shortname to URL prefix mappings
|
122
|
+
#
|
123
|
+
# a hash of prefix [String] => URL prefix
|
124
|
+
#
|
125
|
+
# e.g. {"mydata" => "https://my.dataset.org/thisdataset/records/"}
|
126
|
+
#
|
127
|
+
# you can send it an empty hash to simply return the existing hash
|
128
|
+
#
|
129
|
+
# @return [Hash] the current hash of prefixes
|
130
|
+
#
|
131
|
+
def add_prefixes(params = {})
|
132
|
+
|
133
|
+
prefixesHash = params.fetch(:prefixesHash, {})
|
134
|
+
$stderr.puts prefixesHash
|
135
|
+
@prefix_map.merge!(prefixesHash)
|
136
|
+
return self.prefix_map
|
137
|
+
|
138
|
+
end
|
139
|
+
|
140
|
+
|
141
|
+
# Generate the YARRRML Template
|
142
|
+
#
|
143
|
+
# No input parameters
|
144
|
+
#
|
145
|
+
# @return [YAML] represents the YARRRML template
|
146
|
+
#
|
147
|
+
def generate
|
148
|
+
output = Hash.new
|
149
|
+
output["prefixes"] = @prefix_map
|
150
|
+
output["sources"] = @sources_module
|
151
|
+
|
152
|
+
clauses = Hash.new
|
153
|
+
|
154
|
+
self.mappings.each {|m| clauses.merge!(m)}#; $stderr.puts m; $stderr.puts "CLAUSES: #{clauses}\n\n"}
|
155
|
+
output["mappings"] = clauses
|
156
|
+
|
157
|
+
#$stderr.puts output.inspect
|
158
|
+
return YAML::dump(output)
|
159
|
+
|
160
|
+
end
|
161
|
+
|
162
|
+
|
163
|
+
|
164
|
+
|
165
|
+
def sources_module
|
166
|
+
|
167
|
+
@sources_module = {
|
168
|
+
"#{self.source_tag}-source" =>
|
169
|
+
{
|
170
|
+
"access" => "|||DATA|||",
|
171
|
+
"referenceFormulation" => "|||FORMULATION|||",
|
172
|
+
"iterator" => "$"
|
173
|
+
}
|
174
|
+
}
|
175
|
+
|
176
|
+
end
|
177
|
+
|
178
|
+
|
179
|
+
|
180
|
+
|
181
|
+
|
182
|
+
# creates a single clause of the YARRRML (one subject, [p, o; p,o;....] mapping)
|
183
|
+
#
|
184
|
+
# DO NOT use this externally! I will eventually make it private...
|
185
|
+
#
|
186
|
+
# @param name [String] a unique name for that YARRRRML component (e.g. thisRole_realized_in_SomeProcess)
|
187
|
+
# @param source [String] the YARRRML source identifier
|
188
|
+
# @param s [String] URI of the subject
|
189
|
+
# @param pots [Array] An array of arrays of [Predicate-object-datatype] (datatype is "iri" if it is a Node, rather than a literal)
|
190
|
+
#
|
191
|
+
# @return [String] the mapping_clause in YAML format
|
192
|
+
#
|
193
|
+
def mapping_clause(name, source, s, pots)
|
194
|
+
pos = []
|
195
|
+
pots.each do |pot|
|
196
|
+
#$stderr.puts pot.class
|
197
|
+
(pred, obj, type) = pot
|
198
|
+
#$stderr.puts "#{pred} #{obj} #{type}"
|
199
|
+
typetag = "type"
|
200
|
+
typetag = "datatype" unless type == 'iri'
|
201
|
+
type = "xsd:string" unless type
|
202
|
+
pos << {
|
203
|
+
"predicates" => pred,
|
204
|
+
"objects" => {
|
205
|
+
"value" => obj,
|
206
|
+
typetag => type}
|
207
|
+
}
|
208
|
+
end
|
209
|
+
|
210
|
+
mappingclause = {
|
211
|
+
name => {
|
212
|
+
"sources" => source,
|
213
|
+
"s" => s,
|
214
|
+
"po" => pos
|
215
|
+
}
|
216
|
+
}
|
217
|
+
|
218
|
+
return mappingclause
|
219
|
+
end
|
220
|
+
|
221
|
+
|
222
|
+
def get_root_url(uniq)
|
223
|
+
if uniq
|
224
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})_process"
|
225
|
+
else
|
226
|
+
"this:individual_$(#{@personid_column})_process"
|
227
|
+
end
|
228
|
+
end
|
229
|
+
|
230
|
+
# creates an entity/identifier/role set of clauses
|
231
|
+
#
|
232
|
+
# Parameters passed as a hash
|
233
|
+
#
|
234
|
+
# @param params [Hash] a hash of options
|
235
|
+
# @option params :entityid_column [String] (required) the column header that contains the identifier of the entity
|
236
|
+
# @option params :uniqueid_column [String] (required) the column header that contains unique ID for that row (over ALL datasets! e.g. a hash of a timestamp); defaults to "uniqid"
|
237
|
+
# @option params :identifier_type [String] the URL of the ontological type of that identifier; defaults to 'sio:identifier'
|
238
|
+
# @option params :identifier_type_column [String] the column header for the ontological type of that identifier. Overrides identifier_type.
|
239
|
+
# @option params :entity_type [String] the URL of the ontological type defining a "entity"; defaults to 'sio:specialized-object'
|
240
|
+
# @option params :entity_type_column [String] the column header for the ontological type of the "entity". Overrides entity_type
|
241
|
+
# @option params :entity_label [String] the label for an "entity"; defaults to 'some entity'
|
242
|
+
# @option params :entity_label_column [String] column for the label
|
243
|
+
# @option params :entity_tag [String] a single-word unique tag for the entity within this model (defaults to "thisEntity"). Does not appear in the output RDF
|
244
|
+
# @option params :entity_role_tag [String] a single-word tag for therole (e.g. "patient", "clinician", "drug") the entity plays in this dataset; defaults to "thisRole". This does not appear in the output RDF
|
245
|
+
# @option params :role_type [String] the URL for the ontological type of that role; defaults to "obo:OBI_0000093" ("patient")
|
246
|
+
# @option params :role_type_column [String] the column header that contains the ontological type of that role. Overrides role_type
|
247
|
+
# @option params :role_label [String] the label for that kind of role; defaults to "Some Role"
|
248
|
+
# @option params :role_label_column [String] the column header that has the label for that kind of role (overrides role_label)
|
249
|
+
|
250
|
+
def entity_identifier_role_mappings(params = {})
|
251
|
+
@entityid_column = params.fetch(:entityid_column, 'pid')
|
252
|
+
@uniqueid_column = params.fetch(:uniqueid_column, 'uniqid')
|
253
|
+
|
254
|
+
identifier_type = params.fetch(:identifier_type, SIO["identifier"][self.sio_verbose])
|
255
|
+
identifier_type_column = params.fetch(:identifier_type_column, nil)
|
256
|
+
entity_tag = params.fetch(:entity_tag, 'thisEntity')
|
257
|
+
entity_type = params.fetch(:entity_type, SIO["specialized-object"][self.sio_verbose])
|
258
|
+
entity_type_column = params.fetch(:entity_type_column, nil)
|
259
|
+
entity_label = params.fetch(:entity_label, nil)
|
260
|
+
entity_label_column = params.fetch(:entity_label_column, nil)
|
261
|
+
entity_role_tag = params.fetch(:entity_role_tag, 'thisRole')
|
262
|
+
role_type = params.fetch(:role_type, 'obo:OBI_0000093') # patient
|
263
|
+
role_type_column = params.fetch(:role_type_column, nil) #
|
264
|
+
role_label = params.fetch(:role_label, 'Some Role') # patient
|
265
|
+
role_label_column = params.fetch(:role_label_column, nil) #
|
266
|
+
|
267
|
+
identifier_type = identifier_type_column ? "$(#{identifier_type_column})":identifier_type
|
268
|
+
entity_type = entity_type_column ? "$(#{entity_type_column})":entity_type
|
269
|
+
role_type = role_type_column ? "$(#{role_type_column})":role_type
|
270
|
+
role_label = role_label_column ? "$(#{role_label_column})":role_label
|
271
|
+
entity_label = entity_label_column ? "$(#{entity_label_column})":entity_label
|
272
|
+
|
273
|
+
abort "You MUST have a @entityid_column and a @uniqueid_column to use this library. Sorry!" unless @entityid_column and @uniqueid_column
|
274
|
+
@mappings << mapping_clause(
|
275
|
+
"identifier_has_value_for_#{entity_tag}_#{entity_role_tag}",
|
276
|
+
["#{source_tag}-source"],
|
277
|
+
"this:individual_#{entity_tag}_$(#{@entityid_column})#ID",
|
278
|
+
[[SIO["has-value"][self.sio_verbose], "$(#{@entityid_column})", "xsd:string"]]
|
279
|
+
)
|
280
|
+
|
281
|
+
@mappings << mapping_clause(
|
282
|
+
"identifier_denotes_role_#{entity_role_tag}",
|
283
|
+
["#{source_tag}-source"],
|
284
|
+
"this:individual_#{entity_tag}_$(#{@entityid_column})#ID",
|
285
|
+
[
|
286
|
+
["a", "#{identifier_type}", "iri"],
|
287
|
+
["a", SIO["identifier"][self.sio_verbose], "iri"],
|
288
|
+
[SIO["denotes"][self.sio_verbose], "this:individual_#{entity_tag}_$(#{@entityid_column})_$(#{@uniqueid_column})##{entity_role_tag}", "iri"],
|
289
|
+
]
|
290
|
+
)
|
291
|
+
@mappings << mapping_clause(
|
292
|
+
"entity_has_role_#{entity_role_tag}",
|
293
|
+
["#{source_tag}-source"],
|
294
|
+
"this:individual_#{entity_tag}_$(#{@entityid_column})#Entity",
|
295
|
+
[
|
296
|
+
["a", "#{entity_type}", "iri"],
|
297
|
+
["a", SIO["object"][self.sio_verbose], "iri"],
|
298
|
+
[SIO["has-role"][self.sio_verbose], "this:individual_#{entity_tag}_$(#{@entityid_column})_$(#{@uniqueid_column})##{entity_role_tag}", "iri"],
|
299
|
+
]
|
300
|
+
)
|
301
|
+
|
302
|
+
@mappings << mapping_clause(
|
303
|
+
"#{entity_role_tag}_annotation",
|
304
|
+
["#{source_tag}-source"],
|
305
|
+
"this:individual_#{entity_tag}_$(#{@entityid_column})_$(#{@uniqueid_column})##{entity_role_tag}",
|
306
|
+
[
|
307
|
+
["a", "#{role_type}", "iri"],
|
308
|
+
["a", SIO["role"][self.sio_verbose], "iri"],
|
309
|
+
["rdfs:label", " Role: #{role_label}", "xsd:string"],
|
310
|
+
]
|
311
|
+
)
|
312
|
+
if entity_label
|
313
|
+
@mappings << mapping_clause(
|
314
|
+
"#{entity_role_tag}_entity_label_annotation",
|
315
|
+
["#{source_tag}-source"],
|
316
|
+
"this:individual_#{entity_tag}_$(#{@entityid_column})#Entity",
|
317
|
+
[
|
318
|
+
["rdfs:label", " Role: #{entity_label}", "xsd:string"],
|
319
|
+
]
|
320
|
+
)
|
321
|
+
end
|
322
|
+
|
323
|
+
|
324
|
+
|
325
|
+
end
|
326
|
+
|
327
|
+
# creates the person/identifier/role portion of the CDE
|
328
|
+
#
|
329
|
+
# Parameters passed as a hash. this is a specification of the entity-identifier-role method, with Patient defaults
|
330
|
+
#
|
331
|
+
# @param params [Hash] a hash of options
|
332
|
+
# @option params :personid_column [String] (required) the column header that contains the anonymous identifier of the person; defaults to "pid"
|
333
|
+
# @option params :uniqueid_column [String] (required) the column header that contains unique ID for that row (over ALL datasets! e.g. a hash of a timestamp); defaults to "uniqid"
|
334
|
+
# @option params :identifier_type [String] the URL of the ontological type of that identifier; defaults to 'sio:identifier'
|
335
|
+
# @option params :identifier_type_column [String] the column header for the ontological type of that identifier. Overrides identifier_type.
|
336
|
+
# @option params :person_type [String] the URL of the ontological type defining a "person"; defaults to 'sio:person'
|
337
|
+
# @option params :person_type_column [String] the column header for the ontological type of the "individual". Overrides person_type
|
338
|
+
# @option params :person_role_tag [String] a single-word label for the kind of role (e.g. "patient", "clinician") the person plays in this dataset; defaults to "thisRole"
|
339
|
+
# @option params :role_type [String] the URL for the ontological type of that role; defaults to "obo:OBI_0000093" ("patient")
|
340
|
+
# @option params :person_tag [String] a single-word unique tag for the person within this model (defaults to "thisPerson"). Does not appear in the output RDF
|
341
|
+
# @option params :role_type_column [String] the column header that contains the ontological type of that role. Overrides role_type
|
342
|
+
# @option params :role_label [String] the label for that kind of role; defaults to "Patient"
|
343
|
+
# @option params :role_label_column [String] the column header that has the label for that kind of role (overrides role_label)
|
344
|
+
# @option params :person_label [String] the label for that person (no default)
|
345
|
+
# @option params :person_label_column [String] the column header that has the label for that person (no default)
|
346
|
+
#
|
347
|
+
def person_identifier_role_mappings(params = {})
|
348
|
+
@personid_column = params.fetch(:personid_column, 'pid')
|
349
|
+
uniqueid_column = params.fetch(:uniqueid_column, 'uniqid')
|
350
|
+
|
351
|
+
identifier_type = params.fetch(:identifier_type, SIO["identifier"][self.sio_verbose])
|
352
|
+
identifier_type_column = params.fetch(:identifier_type_column, nil)
|
353
|
+
person_type = params.fetch(:person_type, SIO["person"][self.sio_verbose])
|
354
|
+
person_tag = params.fetch(:person_tag, 'thisPerson')
|
355
|
+
person_type_column = params.fetch(:person_type_column, nil)
|
356
|
+
person_role_tag = params.fetch(:person_role_tag, 'thisRole')
|
357
|
+
role_type = params.fetch(:role_type, 'obo:OBI_0000093') # patient
|
358
|
+
role_type_column = params.fetch(:role_type_column, nil) #
|
359
|
+
role_label = params.fetch(:role_label, 'Patient Role') # patient
|
360
|
+
role_label_column = params.fetch(:role_label_column, nil) #
|
361
|
+
person_label = params.fetch(:person_label, nil) # patient
|
362
|
+
person_label_column = params.fetch(:person_label_column, nil) #
|
363
|
+
|
364
|
+
self.entity_identifier_role_mappings({
|
365
|
+
entityid_column: @personid_column,
|
366
|
+
uniqueid_column: uniqueid_column,
|
367
|
+
identifier_type: identifier_type,
|
368
|
+
identifier_type_column: identifier_type_column,
|
369
|
+
entity_tag: person_tag,
|
370
|
+
entity_type: person_type,
|
371
|
+
entity_type_column: person_type_column,
|
372
|
+
entity_role_tag: person_role_tag,
|
373
|
+
role_type: role_type,
|
374
|
+
role_type_column: role_type_column,
|
375
|
+
role_label: role_label,
|
376
|
+
role_label_column: role_label_column,
|
377
|
+
entity_label: person_label,
|
378
|
+
entity_label_column: person_label_column,
|
379
|
+
})
|
380
|
+
|
381
|
+
end
|
382
|
+
|
383
|
+
|
384
|
+
|
385
|
+
|
386
|
+
|
387
|
+
|
388
|
+
|
389
|
+
# creates the role_in_process portion of the CDE
|
390
|
+
#
|
391
|
+
# Parameters passed as a hash
|
392
|
+
#
|
393
|
+
# @param params [Hash] a hash of options
|
394
|
+
# @option params :person_role_tag [String] the tag of the role that is fulfilled in this process (default 'thisRole') - see person_role_tag above, synchronize these tags!
|
395
|
+
# @option params :entity_role_tag [String] the tag of the role that is fulfilled in this process (default 'thisRole') - see entity_role_tag above, synchronize these tags!
|
396
|
+
# @option params :process_type [String] the URL for the ontological type of the process (defaults to http://semanticscience.org/resource/process)
|
397
|
+
# @option params :process_type_column [String] the column header that contains the URL for the ontological type of the process - overrides process_type
|
398
|
+
# @option params :process_tag [String] some single-word tag for that process; defaults to "thisprocess"
|
399
|
+
# @option params :process_label [String] the label associated with the process type in that row (defaults to "thisprocess")
|
400
|
+
# @option params :process_label_column [String] the column header for the label associated with the process type in that row
|
401
|
+
# @option params :process_start_column [ISO 8601 date (only date)] (optional) the column header for the datestamp when that process started. NOTE: For instantaneous processes, create ONLY the start date column, and an identical end date will be automatically generated
|
402
|
+
# @option params :process_end_column [ISO 8601 date (only date)] (optional) the column header for the datestamp when that process ended
|
403
|
+
# @option params :process_duration_column [xsd:int] (optional) the column header for the duration of the event measured in integer numbers of days
|
404
|
+
# @option params :make_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
405
|
+
def role_in_process(params)
|
406
|
+
person_role_tag = params.fetch(:person_role_tag, 'thisRole')
|
407
|
+
entity_role_tag = params.fetch(:person_role_tag, nil)
|
408
|
+
process_type = params.fetch(:process_type, SIO["process"][self.sio_verbose])
|
409
|
+
process_type_column = params.fetch(:process_type_column, nil)
|
410
|
+
process_tag = params.fetch(:process_tag, 'thisprocess') # some one-word name
|
411
|
+
process_label = params.fetch(:process_label, 'Process')
|
412
|
+
process_label_column = params.fetch(:process_label_column, nil)
|
413
|
+
process_start_column = params.fetch(:process_start_column, nil)
|
414
|
+
process_end_column = params.fetch(:process_end_column, nil)
|
415
|
+
process_duration_column = params.fetch(:process_end_column, nil)
|
416
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
417
|
+
|
418
|
+
process_type = process_type_column ? "$(#{process_type_column})":process_type
|
419
|
+
process_label = process_label_column ? "$(#{process_label_column})":process_label
|
420
|
+
|
421
|
+
person_role_tag = entity_role_tag if entity_role_tag
|
422
|
+
|
423
|
+
root_url = get_root_url(make_unique_process)
|
424
|
+
|
425
|
+
@mappings << mapping_clause(
|
426
|
+
"#{person_role_tag}_realized_#{process_tag}",
|
427
|
+
["#{source_tag}-source"],
|
428
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})##{person_role_tag}",
|
429
|
+
[
|
430
|
+
[SIO["is-realized-in"][self.sio_verbose], root_url + "#process_#{process_tag}","iri"]
|
431
|
+
]
|
432
|
+
)
|
433
|
+
|
434
|
+
@mappings << mapping_clause(
|
435
|
+
"process_#{process_tag}_process_annotation",
|
436
|
+
["#{source_tag}-source"],
|
437
|
+
root_url + "#process_#{process_tag}",
|
438
|
+
[
|
439
|
+
["rdf:type",SIO["process"][self.sio_verbose], "iri"],
|
440
|
+
["rdf:type","#{process_type}", "iri"],
|
441
|
+
["rdfs:label","Process: #{process_label}", "xsd:string"],
|
442
|
+
]
|
443
|
+
)
|
444
|
+
|
445
|
+
|
446
|
+
if process_start_column
|
447
|
+
@mappings << mapping_clause(
|
448
|
+
"process_#{process_tag}_process_annotation_start",
|
449
|
+
["#{source_tag}-source"],
|
450
|
+
root_url + "#process_#{process_tag}",
|
451
|
+
[[SIO["has-start-time"][self.sio_verbose], root_url + "#process_#{process_tag}_startdate_#{process_start_column}", "iri"]]
|
452
|
+
)
|
453
|
+
@mappings << mapping_clause(
|
454
|
+
"process_#{process_tag}_process_annotation_start_value",
|
455
|
+
["#{source_tag}-source"],
|
456
|
+
root_url + "#process_#{process_tag}_startdate_$(#{process_start_column})",
|
457
|
+
[
|
458
|
+
[SIO["has-value"][self.sio_verbose], "$(#{process_start_column})", "xsd:date"],
|
459
|
+
["rdf:type", SIO["start-date"][self.sio_verbose], "iri"],
|
460
|
+
["rdfs:label", "Start Date: $(#{process_start_column})"],
|
461
|
+
]
|
462
|
+
)
|
463
|
+
# now create the MIRROR (!!!!) end time, if one is not provided
|
464
|
+
unless process_end_column
|
465
|
+
@mappings << mapping_clause(
|
466
|
+
"process_#{process_tag}_process_annotation_end",
|
467
|
+
["#{source_tag}-source"],
|
468
|
+
root_url + "#process_#{process_tag}",
|
469
|
+
[[SIO["has-end-time"][self.sio_verbose], root_url + "#process_#{process_tag}_enddate_#{process_start_column}", "iri"]]
|
470
|
+
)
|
471
|
+
@mappings << mapping_clause(
|
472
|
+
"process_#{process_tag}_process_annotation_end_value",
|
473
|
+
["#{source_tag}-source"],
|
474
|
+
root_url + "#process_#{process_tag}_enddate_$(#{process_start_column})",
|
475
|
+
[
|
476
|
+
[SIO["has-value"][self.sio_verbose], "$(#{process_start_column})", "xsd:date"],
|
477
|
+
["rdf:type", SIO["end-date"][self.sio_verbose], "iri"],
|
478
|
+
["rdfs:label", "End Date: $(#{process_start_column})"],
|
479
|
+
]
|
480
|
+
)
|
481
|
+
end
|
482
|
+
|
483
|
+
end
|
484
|
+
|
485
|
+
if process_end_column
|
486
|
+
@mappings << mapping_clause(
|
487
|
+
"process_#{process_tag}_process_annotation_end",
|
488
|
+
["#{source_tag}-source"],
|
489
|
+
root_url + "#process_#{process_tag}",
|
490
|
+
[[SIO["has-end-time"][self.sio_verbose], root_url + "#process_#{process_tag}_enddate_#{process_end_column}", "iri"]]
|
491
|
+
)
|
492
|
+
@mappings << mapping_clause(
|
493
|
+
"process_#{process_tag}_process_annotation_end_value",
|
494
|
+
["#{source_tag}-source"],
|
495
|
+
root_url + "#process_#{process_tag}_enddate_#{process_end_column}",
|
496
|
+
[
|
497
|
+
[SIO["has-value"][self.sio_verbose], "$(#{process_end_column})", "xsd:date"],
|
498
|
+
["rdf:type", SIO["end-date"][self.sio_verbose], "iri"],
|
499
|
+
["rdfs:label", "End Date: $(#{process_end_column})"],
|
500
|
+
]
|
501
|
+
)
|
502
|
+
end
|
503
|
+
|
504
|
+
if process_duration_column
|
505
|
+
@mappings << mapping_clause(
|
506
|
+
"#{process_tag}_process_annotation_duration",
|
507
|
+
["#{source_tag}-source"],
|
508
|
+
root_url + "##{process_tag}",
|
509
|
+
[[SIO["exists-at"][self.sio_verbose], root_url + "##{process_tag}_exists_at_#{process_duration_column}", "iri"]]
|
510
|
+
)
|
511
|
+
@mappings << mapping_clause(
|
512
|
+
"#{process_tag}_process_annotation_duration_value",
|
513
|
+
["#{source_tag}-source"],
|
514
|
+
root_url + "##{process_tag}_exists_at_#{process_duration_column}",
|
515
|
+
[
|
516
|
+
[SIO["has-value"][self.sio_verbose], "$(#{process_duration_column})"],
|
517
|
+
["rdf:type", SIO["day"][self.sio_verbose], "iri"],
|
518
|
+
["rdfs:label", "Duration: $(#{process_duration_column}) days"],
|
519
|
+
]
|
520
|
+
)
|
521
|
+
end
|
522
|
+
|
523
|
+
end
|
524
|
+
|
525
|
+
|
526
|
+
|
527
|
+
# creates the process has annotations portion of the CDE
|
528
|
+
#
|
529
|
+
# Parameters passed as a hash
|
530
|
+
#
|
531
|
+
# @param params [Hash] a hash of options
|
532
|
+
# @option params :process_tag [String] (required) the same process tag that is used in the "role in process"
|
533
|
+
# @option params :process_annotations_columns [Array] ([[predcol, valcol,datatypecol], ...]) (if predol looks like a URI, it will be used as a URI)
|
534
|
+
# @option params :process_annotations [Array] ([[pred, valuecolumn,datatype]...])
|
535
|
+
# @option params :make_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
536
|
+
def process_has_annotations(params)
|
537
|
+
process_tag = params.fetch(:process_tag, "thisprocess")
|
538
|
+
process_annotations_columns = params.fetch(:process_annotations_columns, [])
|
539
|
+
process_annotations = params.fetch(:process_annotations, [])
|
540
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
541
|
+
|
542
|
+
root_url = get_root_url(make_unique_process)
|
543
|
+
|
544
|
+
|
545
|
+
if !process_annotations_columns.empty?
|
546
|
+
process_annotations_columns.each do |predicate, value, datatype|
|
547
|
+
case
|
548
|
+
when datatype =~ /iri/
|
549
|
+
datatype = "iri"
|
550
|
+
when datatype =~ /^xsd\:/
|
551
|
+
datatype = datatype
|
552
|
+
when datatype
|
553
|
+
datatype = "$(#{datatype})" # its a column header
|
554
|
+
else
|
555
|
+
datatype = "xsd:string"
|
556
|
+
end
|
557
|
+
|
558
|
+
|
559
|
+
if predicate =~ /https?\:\/\//
|
560
|
+
predicate = predicate
|
561
|
+
else
|
562
|
+
predicate = "$(#{predicate})" # if the predicate looks like a URI, assume that it is, rather than a colulmn header
|
563
|
+
end
|
564
|
+
|
565
|
+
next unless predicate and value
|
566
|
+
uniqid = get_uniq_id
|
567
|
+
|
568
|
+
@mappings << mapping_clause(
|
569
|
+
"#{uniqid}_process_custom_annotation",
|
570
|
+
["#{source_tag}-source"],
|
571
|
+
root_url + "#process_#{process_tag}",
|
572
|
+
[[predicate, "$(#{value})", datatype]]
|
573
|
+
)
|
574
|
+
|
575
|
+
end
|
576
|
+
elsif !process_annotations.empty?
|
577
|
+
process_annotations.each do |predicate, value, datatype|
|
578
|
+
datatype = "xsd:string" unless datatype # otherwise make it default
|
579
|
+
|
580
|
+
next unless predicate and value
|
581
|
+
uniqid = get_uniq_id
|
582
|
+
|
583
|
+
@mappings << mapping_clause(
|
584
|
+
"#{uniqid}_process_custom_annotation",
|
585
|
+
["#{source_tag}-source"],
|
586
|
+
root_url + "#process_#{process_tag}",
|
587
|
+
[[predicate, value, datatype]]
|
588
|
+
)
|
589
|
+
|
590
|
+
end
|
591
|
+
|
592
|
+
end
|
593
|
+
|
594
|
+
|
595
|
+
end
|
596
|
+
|
597
|
+
|
598
|
+
# creates the process has agent portion of the CDE
|
599
|
+
#
|
600
|
+
# Parameters passed as a hash
|
601
|
+
#
|
602
|
+
# @param params [Hash] a hash of options
|
603
|
+
# @option params :process_tag [String] (required) the same process tag that is used in the "role in process"
|
604
|
+
# @option params :entityid_column [String] (required) default "pid"
|
605
|
+
# @option params :entity_tag [String] (required) default "thisEntity". The entity-tag that you used for the entity in the entity/identifier/role clauses
|
606
|
+
def process_has_agent(params)
|
607
|
+
process_tag = params.fetch(:process_tag, "thisprocess")
|
608
|
+
entityid_column = params.fetch(:entityid_column, "pid")
|
609
|
+
entity_tag = params.fetch(:entity_tag, "thisEntity")
|
610
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
611
|
+
|
612
|
+
root_url = get_root_url(make_unique_process)
|
613
|
+
|
614
|
+
|
615
|
+
@mappings << mapping_clause(
|
616
|
+
"process_has_agent_#{entity_tag}",
|
617
|
+
["#{source_tag}-source"],
|
618
|
+
root_url + "##{process_tag}",
|
619
|
+
[[SIO['has-agent'][self.sio_verbose], "this:individual_#{entity_tag}_$(#{entityid_column})#Entity" , 'iri']]
|
620
|
+
)
|
621
|
+
|
622
|
+
|
623
|
+
end
|
624
|
+
|
625
|
+
|
626
|
+
|
627
|
+
|
628
|
+
# creates the process_has_part portion of the CDE
|
629
|
+
#
|
630
|
+
# Parameters passed as a hash
|
631
|
+
#
|
632
|
+
# @param params [Hash] a hash of options
|
633
|
+
# @option params :parent_process_tag [String] (required) the same process tag that is used in the "role in process" for the parent process
|
634
|
+
# @option params :part_process_tag [String] (required) the same process tag that is used in the "role in process" for the process that is a part of the parent
|
635
|
+
# @option params :part_process_type [String] (optional) the rdf:type of the child process
|
636
|
+
# @option params :part_process_type_column [String] (optional) the rdf:type of the child process
|
637
|
+
# @option params :parent_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
638
|
+
# @option params :part_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
639
|
+
def process_has_part(params)
|
640
|
+
parent_process_tag = params.fetch(:parent_process_tag, nil)
|
641
|
+
part_process_tag = params.fetch(:part_process_tag, nil)
|
642
|
+
part_process_type = params.fetch(:part_process_type, nil)
|
643
|
+
part_process_type_column = params.fetch(:part_process_type_column, nil)
|
644
|
+
parent_unique_process = params.fetch(:parent_unique_process, true)
|
645
|
+
part_unique_process = params.fetch(:part_unique_process, true)
|
646
|
+
|
647
|
+
parent_root_url = get_root_url(parent_unique_process)
|
648
|
+
part_root_url = get_root_url(part_unique_process)
|
649
|
+
|
650
|
+
part_process_type = part_process_type_column ? "$(#{part_process_type_column})":part_process_type
|
651
|
+
|
652
|
+
abort "cannot create part relationship unless both parent and child processes have a tag" unless (parent_process_tag && part_process_tag)
|
653
|
+
|
654
|
+
#uniqid = get_uniq_id
|
655
|
+
|
656
|
+
@mappings << mapping_clause(
|
657
|
+
"process_#{parent_process_tag}_has_part_#{part_process_tag}",
|
658
|
+
["#{source_tag}-source"],
|
659
|
+
parent_root_url + "#process_#{parent_process_tag}",
|
660
|
+
[
|
661
|
+
[SIO["has-part"][self.sio_verbose], part_root_url + "#process_#{part_process_tag}" , "iri"],
|
662
|
+
]
|
663
|
+
)
|
664
|
+
@mappings << mapping_clause(
|
665
|
+
"process_#{part_process_tag}_process_has_type",
|
666
|
+
["#{source_tag}-source"],
|
667
|
+
parent_root_url + "#process_#{part_process_tag}",
|
668
|
+
[
|
669
|
+
["rdf:type", SIO["process"][self.sio_verbose], "iri"],
|
670
|
+
]
|
671
|
+
)
|
672
|
+
if part_process_type
|
673
|
+
@mappings << mapping_clause(
|
674
|
+
"process_#{part_process_tag}_process_has_specific_type",
|
675
|
+
["#{source_tag}-source"],
|
676
|
+
parent_root_url + "#process_#{part_process_tag}",
|
677
|
+
[
|
678
|
+
["rdf:type", part_process_type, "iri"],
|
679
|
+
]
|
680
|
+
)
|
681
|
+
end
|
682
|
+
|
683
|
+
end
|
684
|
+
|
685
|
+
|
686
|
+
|
687
|
+
|
688
|
+
|
689
|
+
# creates the process has target portion of the CDE
|
690
|
+
#
|
691
|
+
# Parameters passed as a hash
|
692
|
+
#
|
693
|
+
# @param params [Hash] a hash of options
|
694
|
+
# @option params :process_with_target_tag [String] (required) the same process tag that is used in the "role in process" for which this is the target
|
695
|
+
# @option params :target_type_tag [String] a tag to differentiate this target from other targets
|
696
|
+
# @option params :target_type [String] the ontological type for the target (e.g. process is targetted at creatinine - http://purl.obolibrary.org/obo/CHEBI_16737)
|
697
|
+
# @option params :target_type_column [String] the column header specifying the ontological type for the target node (overrides target_type).
|
698
|
+
# @option params :target_type_label [String] the label for all targets
|
699
|
+
# @option params :target_type_label_column [String] the label column for each target
|
700
|
+
# @option params :make_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
701
|
+
def process_has_target(params)
|
702
|
+
process_with_target_tag = params.fetch(:process_with_target_tag, "thisprocess") # some one-word name
|
703
|
+
target_type_tag = params.fetch(:target_type_tag, "thisTarget") # some one-word name
|
704
|
+
target_type = params.fetch(:target_type, SIO["information-content-entity"][self.sio_verbose]) # some one-word name
|
705
|
+
target_type_column = params.fetch(:target_type_column, nil) # some one-word name
|
706
|
+
target_type_label = params.fetch(:target_type_label, "information content entity") # some one-word name
|
707
|
+
target_type_label_column = params.fetch(:target_type_label_column, nil) # some one-word name
|
708
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
709
|
+
|
710
|
+
root_url = get_root_url(make_unique_process)
|
711
|
+
|
712
|
+
|
713
|
+
abort "must specify the process_with_target_tag
|
714
|
+
(the identifier of the process that has the input)
|
715
|
+
before you can use the process_has_target function" unless process_with_target_tag
|
716
|
+
|
717
|
+
target_type = target_type_column ? "$(#{target_type_column})":target_type
|
718
|
+
target_label = target_type_label_column ? "$(#{target_type_label_column})":target_type_label
|
719
|
+
|
720
|
+
@mappings << mapping_clause(
|
721
|
+
"process_#{process_with_target_tag}_has_target_#{target_type_tag}",
|
722
|
+
["#{source_tag}-source"],
|
723
|
+
root_url + "#process_#{process_with_target_tag}",
|
724
|
+
[[SIO["has-target"][self.sio_verbose],"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_target_tag}_Target", "iri"]]
|
725
|
+
)
|
726
|
+
|
727
|
+
@mappings << mapping_clause(
|
728
|
+
"process_#{process_with_target_tag}_has_target_#{target_type_tag}_annotation",
|
729
|
+
["#{source_tag}-source"],
|
730
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_target_tag}_Target",
|
731
|
+
[
|
732
|
+
["rdf:type",SIO["information-content-entity"][self.sio_verbose], "iri"],
|
733
|
+
["rdf:type","#{target_type}", "iri"],
|
734
|
+
["rdfs:label","Process Target: #{target_label}", "xsd:string"],
|
735
|
+
]
|
736
|
+
)
|
737
|
+
|
738
|
+
end
|
739
|
+
|
740
|
+
|
741
|
+
|
742
|
+
|
743
|
+
|
744
|
+
|
745
|
+
# creates the process is specified by portion of the CDE
|
746
|
+
#
|
747
|
+
# Parameters passed as a hash
|
748
|
+
#
|
749
|
+
# @param params [Hash] a hash of options
|
750
|
+
# @option params :process_with_protocol_tag [String] (required) the same process tag that is used in the "role in process" for which this is the input
|
751
|
+
# @option params :protocol_type_tag [String] a tag to differentiate this input from other inputs
|
752
|
+
# @option params :process_type [String] ("sio:process" - process) usually you want to be more specific, like "measuring" or "estimating"
|
753
|
+
# @option params :process_type_column [String] ("sio:process" - process)
|
754
|
+
# @option params :process_type_label [String] ("protocol")
|
755
|
+
# @option params :process_type_label_column [String] ("protocol")
|
756
|
+
# @option params :protocol_uri [String] uri of the process protocol for all inputs
|
757
|
+
# @option params :protocol_uri_column [String] column header for the protocol uri column
|
758
|
+
# @option params :protocol_label [String] label of the process protocol for all inputs
|
759
|
+
# @option params :protocol_label_column [String] column header for the label for the protocol uri
|
760
|
+
# @option params :make_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
761
|
+
def process_is_specified_by(params)
|
762
|
+
process_with_protocol_tag = params.fetch(:process_with_protocol_tag, "thisprocess") # some one-word name
|
763
|
+
protocol_type_tag = params.fetch(:protocol_type_tag, "thisProtocoltype") # some one-word name
|
764
|
+
process_type = params.fetch(:processs_type, SIO["process"][self.sio_verbose]) #
|
765
|
+
process_type_column = params.fetch(:protocol_type_column, nil) #
|
766
|
+
process_type_label = params.fetch(:protocol_type_label, "Process")
|
767
|
+
process_type_label_column = params.fetch(:protocol_type_label_column, nil)
|
768
|
+
protocol_uri = params.fetch(:protocol_uri, nil) # Protocol
|
769
|
+
protocol_uri_column = params.fetch(:protocol_uri_column, nil)
|
770
|
+
protocol_label = params.fetch(:protocol_uri, nil) # Protocol
|
771
|
+
protocol_label_column = params.fetch(:protocol_uri_column, nil)
|
772
|
+
protocol_type = params.fetch(:protocol_type, "http://purl.obolibrary.org/obo/NCIT_C42651") # Protocol
|
773
|
+
protocol_type_column = params.fetch(:protocol_type_column, nil)
|
774
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
775
|
+
|
776
|
+
root_url = get_root_url(make_unique_process)
|
777
|
+
|
778
|
+
|
779
|
+
abort "must specify the process_with_target_tag and the protocol type tag
|
780
|
+
(the identifier of the process that has the input)
|
781
|
+
before you can use the process_has_target function" unless (process_with_protocol_tag and protocol_type_tag)
|
782
|
+
|
783
|
+
process_type = process_type_column ? "$(#{process_type_column})":process_type
|
784
|
+
process_type_label = process_type_label_column ? "$(#{process_type_label_column})":process_type_label
|
785
|
+
protocol_uri = protocol_uri_column ? "$(#{protocol_uri_column})":protocol_uri
|
786
|
+
protocol_label = protocol_label_column ? "$(#{protocol_label_column})":protocol_label
|
787
|
+
protocol_type = protocol_type_column ? "$(#{protocol_type_column})":protocol_type
|
788
|
+
|
789
|
+
abort "must specify either a default protocol URI, or a column of protocol URIs" unless protocol_uri
|
790
|
+
|
791
|
+
@mappings << mapping_clause(
|
792
|
+
"#{process_with_protocol_tag}_specified_by_#{protocol_type_tag}_specifictype_annotation",
|
793
|
+
["#{source_tag}-source"],
|
794
|
+
root_url + "##{process_with_protocol_tag}",
|
795
|
+
[
|
796
|
+
["rdf:type","#{process_type}", "iri"],
|
797
|
+
["rdfs:label","Protocol: #{process_type_label}", "xsd:string"],
|
798
|
+
]
|
799
|
+
)
|
800
|
+
|
801
|
+
@mappings << mapping_clause(
|
802
|
+
"#{process_with_protocol_tag}_specified_by_#{protocol_type_tag}",
|
803
|
+
["#{source_tag}-source"],
|
804
|
+
root_url + "##{process_with_protocol_tag}",
|
805
|
+
[[SIO["is-specified-by"][self.sio_verbose], protocol_uri, "iri"]]
|
806
|
+
)
|
807
|
+
|
808
|
+
@mappings << mapping_clause(
|
809
|
+
"#{process_with_protocol_tag}_specified_by_#{protocol_type_tag}_annotation",
|
810
|
+
["#{source_tag}-source"],
|
811
|
+
protocol_uri,
|
812
|
+
[
|
813
|
+
["rdf:type",SIO["information-content-entity"][self.sio_verbose], "iri"],
|
814
|
+
["rdf:type","http://purl.obolibrary.org/obo/NCIT_C42651", "iri"], # Protocol
|
815
|
+
["rdf:type","#{protocol_type}", "iri"],
|
816
|
+
["rdfs:label","Protocol: #{protocol_label}", "xsd:string"],
|
817
|
+
]
|
818
|
+
)
|
819
|
+
|
820
|
+
end
|
821
|
+
|
822
|
+
|
823
|
+
|
824
|
+
|
825
|
+
|
826
|
+
# creates the process caused by
|
827
|
+
#
|
828
|
+
# Parameters passed as a hash. there can be only one cause!
|
829
|
+
#
|
830
|
+
# @param params [Hash] a hash of options
|
831
|
+
# @option params :process_with_cause_tag [String] (required) the same process tag that is used in the "role in process" for which this is the input
|
832
|
+
# @option params :cause_type [URI] an ontological type for the cause (process or event or entity are all fine)
|
833
|
+
# @option params :cause_type_column [string] column header for cause URIs
|
834
|
+
# TODO: Allow any existing node to be a cause...
|
835
|
+
def process_caused_by(params)
|
836
|
+
process_with_cause_tag = params.fetch(:process_with_cause_tag, nil) # some one-word name
|
837
|
+
cause_type = params.fetch(:cause_type, nil)
|
838
|
+
cause_type_column = params.fetch(:cause_type_column, nil)
|
839
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
840
|
+
|
841
|
+
root_url = get_root_url(make_unique_process)
|
842
|
+
|
843
|
+
cause_type = cause_type_column ? "$(#{cause_type_column})":cause_type
|
844
|
+
|
845
|
+
abort "must specify the process_with_cause_tag" unless process_with_cause_tag
|
846
|
+
abort "must specify the cause type" unless (cause_type or cause_type_column)
|
847
|
+
|
848
|
+
@mappings << mapping_clause(
|
849
|
+
"process_#{process_with_cause_tag}_has_cause",
|
850
|
+
["#{source_tag}-source"],
|
851
|
+
root_url + "#process_#{process_with_cause_tag}",
|
852
|
+
[[SIO["is-causally-related-from"][self.sio_verbose], root_url + "#cause_of_process_#{process_with_cause_tag}", "iri"]]
|
853
|
+
)
|
854
|
+
|
855
|
+
@mappings << mapping_clause(
|
856
|
+
"process_#{process_with_cause_tag}_has_cause_annotation",
|
857
|
+
["#{source_tag}-source"],
|
858
|
+
root_url + "#cause_of_process_#{process_with_cause_tag}",
|
859
|
+
[
|
860
|
+
["rdf:type",SIO["entity"][self.sio_verbose], "iri"],
|
861
|
+
["rdf:type",cause_type, "iri"],
|
862
|
+
]
|
863
|
+
)
|
864
|
+
|
865
|
+
end
|
866
|
+
|
867
|
+
|
868
|
+
# creates the process has_attribute
|
869
|
+
#
|
870
|
+
# Parameters passed as a hash. there can be only one cause!
|
871
|
+
#
|
872
|
+
# @param params [Hash] a hash of options
|
873
|
+
# @option params :process_with_attribute_tag [String] (required) the same process tag that is used in the "role in process" for which this is the input
|
874
|
+
# @option params :attribute_tag [string] the tag of the attribute
|
875
|
+
def process_has_attribute(params)
|
876
|
+
process_with_attribute_tag = params.fetch(:process_with_attribute_tag, nil) # some one-word name
|
877
|
+
attribute_tag = params.fetch(:attribute_tag, nil) # some one-word name
|
878
|
+
|
879
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
880
|
+
|
881
|
+
root_url = get_root_url(make_unique_process)
|
882
|
+
|
883
|
+
abort "must specify the process_with_attribute_tag" unless process_with_attribute_tag
|
884
|
+
abort "must specify the attribute_tag" unless (attribute_tag)
|
885
|
+
|
886
|
+
@mappings << mapping_clause(
|
887
|
+
"process_#{process_with_attribute_tag}_has_attribute_#{attribute_tag}",
|
888
|
+
["#{source_tag}-source"],
|
889
|
+
root_url + "#process_#{process_with_attribute_tag}",
|
890
|
+
[[SIO["has-attribute"][self.sio_verbose], root_url + "#attribute_#{attribute_tag}", "iri"]]
|
891
|
+
)
|
892
|
+
end
|
893
|
+
|
894
|
+
|
895
|
+
|
896
|
+
|
897
|
+
# creates the build attribute clauses
|
898
|
+
#
|
899
|
+
# Parameters passed as a hash.
|
900
|
+
#
|
901
|
+
# @param params [Hash] a hash of options
|
902
|
+
# @option params :attribute_tag [String] (required) a unique tag for the attribute
|
903
|
+
# @option params :attribute_type [URI] an ontological type for the attribute
|
904
|
+
# @option params :attribute_type_column [string] column header for attribute URIs
|
905
|
+
# @option params :attribute_value_column [string] column header for attribute URIs
|
906
|
+
# @option params :attribute_label [string] attribute value label
|
907
|
+
# @option params :attribute_label_column [string] column header for attribute value label
|
908
|
+
# @option params :attribute_value_unit_column [string] column header for attribute unit URIs
|
909
|
+
# @option params :attribute_value_unit_label_column [string] column header for attribute unit labels
|
910
|
+
#
|
911
|
+
# TODO: Allow any existing node to be a cause...
|
912
|
+
def build_attribute(params)
|
913
|
+
attribute_tag = params.fetch(:attribute_tag, nil) # some one-word name
|
914
|
+
attribute_type = params.fetch(:attribute_type, nil)
|
915
|
+
attribute_label = params.fetch(:attribute_label, nil)
|
916
|
+
attribute_label_column = params.fetch(:attribute_label_column, nil)
|
917
|
+
attribute_type_column = params.fetch(:attribute_type_column, nil)
|
918
|
+
attribute_value_column = params.fetch(:attribute_value_column, nil)
|
919
|
+
attribute_value_unit_column = params.fetch(:attribute_value_unit_column, nil)
|
920
|
+
attribute_value_unit_label_column = params.fetch(:attribute_value_unit_label_column, nil)
|
921
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
922
|
+
|
923
|
+
root_url = get_root_url(make_unique_process)
|
924
|
+
|
925
|
+
attribute_type = attribute_type_column ? "$(#{attribute_type_column})":attribute_type
|
926
|
+
attribute_label = attribute_label_column ? "$(#{attribute_label_column})":attribute_label
|
927
|
+
attribute_value_unit_column = "$(#{attribute_value_unit_column})" if attribute_value_unit_column
|
928
|
+
attribute_value_unit_label_column = "$(#{attribute_value_unit_label_column})" if attribute_value_unit_label_column
|
929
|
+
|
930
|
+
abort "must specify the attribute_tag" unless attribute_tag
|
931
|
+
abort "must specify the attribute_type" unless (attribute_type or attribute_type_column)
|
932
|
+
abort "must specify both a unit column and a unit label column" if (attribute_value_unit_column and !(attribute_value_unit_label_column))
|
933
|
+
|
934
|
+
@mappings << mapping_clause(
|
935
|
+
"attribute_#{attribute_tag}_annotation",
|
936
|
+
["#{source_tag}-source"],
|
937
|
+
root_url + "#attribute_#{attribute_tag}",
|
938
|
+
[
|
939
|
+
["rdf:type",SIO["attribute"][self.sio_verbose], "iri"],
|
940
|
+
["rdf:type",attribute_type, "iri"],
|
941
|
+
]
|
942
|
+
)
|
943
|
+
|
944
|
+
if attribute_value_column
|
945
|
+
@mappings << mapping_clause(
|
946
|
+
"attribute_#{attribute_tag}_measurement",
|
947
|
+
["#{source_tag}-source"],
|
948
|
+
root_url + "#attribute_#{attribute_tag}",
|
949
|
+
[[SIO["has-measurement-value"][self.sio_verbose], root_url + "#measurement_of_attribute_#{attribute_tag}", "iri"]]
|
950
|
+
)
|
951
|
+
|
952
|
+
|
953
|
+
@mappings << mapping_clause(
|
954
|
+
"attribute_#{attribute_tag}_measurement_value",
|
955
|
+
["#{source_tag}-source"],
|
956
|
+
root_url + "#measurement_of_attribute_#{attribute_tag}",
|
957
|
+
[[SIO["has-measurement-value"][self.sio_verbose], root_url + "#measurementvalue_of_attribute_#{attribute_tag}", "iri"]]
|
958
|
+
)
|
959
|
+
@mappings << mapping_clause(
|
960
|
+
"attribute_#{attribute_tag}_measurement_value_value",
|
961
|
+
["#{source_tag}-source"],
|
962
|
+
root_url + "#measurementvalue_of_attribute_#{attribute_tag}",
|
963
|
+
[
|
964
|
+
[SIO["has-value"][self.sio_verbose], "$(#{attribute_value_column})", "xsd:string"],
|
965
|
+
["rdf:type", SIO["information-content-entity"][self.sio_verbose], "iri"],
|
966
|
+
]
|
967
|
+
)
|
968
|
+
end
|
969
|
+
|
970
|
+
if attribute_label
|
971
|
+
@mappings << mapping_clause(
|
972
|
+
"attribute_#{attribute_tag}_measurement_value_label",
|
973
|
+
["#{source_tag}-source"],
|
974
|
+
root_url + "#measurementvalue_of_attribute_#{attribute_tag}",
|
975
|
+
[["rdfs:label", attribute_label]]
|
976
|
+
)
|
977
|
+
end
|
978
|
+
|
979
|
+
if attribute_value_unit_column
|
980
|
+
@mappings << mapping_clause(
|
981
|
+
"attribute_#{attribute_tag}_measurement_value_unit_node",
|
982
|
+
["#{source_tag}-source"],
|
983
|
+
root_url + "#measurementvalue_of_attribute_#{attribute_tag}",
|
984
|
+
[
|
985
|
+
[SIO["has-unit"][self.sio_verbose], root_url + "#measurementvalue_unit_of_attribute_#{attribute_tag}", "iri"],
|
986
|
+
]
|
987
|
+
)
|
988
|
+
@mappings << mapping_clause(
|
989
|
+
"attribute_#{attribute_tag}_measurement_value_unit_node_type",
|
990
|
+
["#{source_tag}-source"],
|
991
|
+
root_url + "#measurementvalue_unit_of_attribute_#{attribute_tag}",
|
992
|
+
[
|
993
|
+
["rdf:type", "#{attribute_value_unit_column}", "iri"],
|
994
|
+
["rdfs:label", "#{attribute_value_unit_label_column}"],
|
995
|
+
]
|
996
|
+
)
|
997
|
+
end
|
998
|
+
|
999
|
+
|
1000
|
+
end
|
1001
|
+
|
1002
|
+
|
1003
|
+
|
1004
|
+
|
1005
|
+
# creates the process has input portion of the CDE
|
1006
|
+
#
|
1007
|
+
# Parameters passed as a hash
|
1008
|
+
#
|
1009
|
+
# @param params [Hash] a hash of options
|
1010
|
+
# @option params :process_with_input_tag [String] (required) the same process tag that is used in the "role in process" for which this is the input
|
1011
|
+
# @option params :input_is_output_of_process_tag [String] defaults to 'unidentifiedProcess'; if the input is the output of another process, then specify the process tag here (matches the "role in process" which generates taht output
|
1012
|
+
# @option params :input_type [String] the ontological type for the input node (default http://semanticscience.org/resource/information-content-entity). Ignored if using output from another process (specify it there!)
|
1013
|
+
# @option params :input_type_tag [String] a tag to differentiate this input from other inputs
|
1014
|
+
# @option params :input_type_column [String] the column header specifying the ontological type for the input node (overrides input_type). Ignored if using output from another process (specify it there!)
|
1015
|
+
# @option params :input_type_label [String] the label for all inputs
|
1016
|
+
# @option params :input_type_label_column [String] the label column for each input
|
1017
|
+
# @option params :input_has_value [String] the value of the input
|
1018
|
+
# @option params :input_has_value_column [String] the column containing the value of the input
|
1019
|
+
# @option params :input_has_value_datatype [String] datatype of the value (default xsd:string)
|
1020
|
+
# @option params :input_has_value_datatype_column [String] the column containing the datatype of the value of the input )(overrides input_has_value_datatype)
|
1021
|
+
# @option params :make_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
1022
|
+
|
1023
|
+
|
1024
|
+
# NEED AN INPUT REFERS TO HERE>>>>>>
|
1025
|
+
|
1026
|
+
def process_has_input(params)
|
1027
|
+
process_with_input_tag = params.fetch(:process_with_input_tag, "thisprocess") # some one-word name
|
1028
|
+
input_is_output_of_process_tag = params.fetch(:input_is_output_of_process_tag, 'unidentifiedProcess') # some one-word name
|
1029
|
+
input_type = params.fetch(:input_type, SIO["information-content-entity"][self.sio_verbose]) # some one-word name
|
1030
|
+
input_type_tag = params.fetch(:input_type_tag, "thisInput") # some one-word name
|
1031
|
+
input_type_column = params.fetch(:input_type_column, nil) # some one-word name
|
1032
|
+
input_type_label = params.fetch(:input_type_label, "information content entity") # some one-word name
|
1033
|
+
input_type_label_column = params.fetch(:input_type_label_column, nil) # some one-word name
|
1034
|
+
input_has_value = params.fetch(:input_has_value, nil) # some one-word name
|
1035
|
+
input_has_value_column = params.fetch(:input_has_value_column, nil) # some one-word name
|
1036
|
+
input_has_value_datatype = params.fetch(:input_has_value_datatype, "xsd:string") # some one-word name
|
1037
|
+
input_has_value_datatype_column = params.fetch(:input_has_value_datatype_column, nil) # some one-word name
|
1038
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
1039
|
+
|
1040
|
+
root_url = get_root_url(make_unique_process)
|
1041
|
+
|
1042
|
+
|
1043
|
+
abort "must specify the process_with_input_tag (the identifier of the process that receives the input) before you can use the process_has_input function" unless process_with_input_tag
|
1044
|
+
|
1045
|
+
input_type = input_type_column ? "$(#{input_type_column})":input_type
|
1046
|
+
input_label = input_type_label_column ? "$(#{input_type_label_column})":input_type_label
|
1047
|
+
input_value = input_has_value_column ? "$(#{input_has_value_column})":input_has_value
|
1048
|
+
input_value_datatype = input_has_value_datatype_column ? "$(#{input_has_value_datatype_column})":input_has_value_datatype
|
1049
|
+
|
1050
|
+
@mappings << mapping_clause(
|
1051
|
+
"process_#{process_with_input_tag}_has_input_#{input_type_tag}",
|
1052
|
+
["#{source_tag}-source"],
|
1053
|
+
root_url + "#process_#{process_with_input_tag}",
|
1054
|
+
[[SIO["has-input"][self.sio_verbose],"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{input_is_output_of_process_tag}_Output", "iri"]]
|
1055
|
+
)
|
1056
|
+
|
1057
|
+
@mappings << mapping_clause(
|
1058
|
+
"process_#{process_with_input_tag}_has_input_#{input_type_tag}_annotation",
|
1059
|
+
["#{source_tag}-source"],
|
1060
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{input_is_output_of_process_tag}_Output",
|
1061
|
+
[
|
1062
|
+
["rdf:type",SIO["information-content-entity"][self.sio_verbose], "iri"],
|
1063
|
+
["rdf:type","#{input_type}", "iri"],
|
1064
|
+
["rdfs:label","Process Input: #{input_label} - Type: #{input_type_tag}", "xsd:string"],
|
1065
|
+
]
|
1066
|
+
)
|
1067
|
+
|
1068
|
+
|
1069
|
+
if input_value
|
1070
|
+
|
1071
|
+
@mappings << mapping_clause(
|
1072
|
+
"input_#{input_type_tag}_has_value",
|
1073
|
+
["#{source_tag}-source"],
|
1074
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{input_is_output_of_process_tag}_Output",
|
1075
|
+
[[SIO["has-value"][self.sio_verbose],"#{input_value}", "#{input_value_datatype}"]]
|
1076
|
+
)
|
1077
|
+
end
|
1078
|
+
|
1079
|
+
# TODO: need to allow units here too! ...one day...
|
1080
|
+
end
|
1081
|
+
|
1082
|
+
|
1083
|
+
|
1084
|
+
|
1085
|
+
|
1086
|
+
|
1087
|
+
|
1088
|
+
# creates the process_hasoutput_output portion of the CDE
|
1089
|
+
#
|
1090
|
+
# TODO allow multiple outputs
|
1091
|
+
#
|
1092
|
+
# Parameters passed as a hash
|
1093
|
+
#
|
1094
|
+
# @param params [Hash] a hash of options
|
1095
|
+
# @option params :process_with_output_tag [String] Required - the same process tag that is used in the "role in process" for which this is the output
|
1096
|
+
# @option params :output_value [String] the default value of that output (defaults to nil, and the output node is not created in the RDF)
|
1097
|
+
# @option params :output_value_column [String] the column header for the value of that output (e.g. the column that contains "80" for "80 mmHg")
|
1098
|
+
# @option params :output_type [String] the URL associated with the output ontological type (defaults to http://semanticscience.org/resource/realizable-entity)
|
1099
|
+
# @option params :output_type_column [String] the column header for the URL associated with the output ontological type (overrides output_type)
|
1100
|
+
# @option params :output_type_label [String] the the label of that ontological type (defaults to "measurement-value")
|
1101
|
+
# @option params :output_type_label_column [String] the column header for the label of that ontological type (overrides output_type_label)
|
1102
|
+
# @option params :output_value_datatype [xsd:type] the xsd:type for that kind of measurement (defaults to xsd:string)
|
1103
|
+
# @option params :output_value_datatype_column [String] the column header for the xsd:type for that kind of measurement (overrides output_value_datatype)
|
1104
|
+
# @option params :output_comments_column [String] the column header for amy textual comments. text must not contain a comma!! defaults to nil
|
1105
|
+
# @option params :output_start_column [xsd:date] the column header for start date, if the observation is time-constrained (e.g. symptoms from 2020-01-01 to 2020-01-05)
|
1106
|
+
# @option params :output_end_column [xsd:date] the column header for end date, if the observation is time-constrained (e.g. symptoms from symptoms from 2020-01-01 to 2020-01-05)
|
1107
|
+
# @option params :output_measured_at_column [xsd:date] the column header for a time-instant date of the observation
|
1108
|
+
# @option params :output_annotations [Array] Array of Arrays of [[predicate, valuecolumn, datatype]...] that will be applied as annotations to the output of the tagged process. predicate may be a full URI or a column reference; value MUST be a column-reference; datatype is options, default xsd:string
|
1109
|
+
# @option params :make_unique_process [boolean] (true) (optional) if you want the core URI to be globally unique, or based only on the patient ID. this can be used to merge nodes over multiple runs of different yarrrml transforms.
|
1110
|
+
def process_hasoutput_output(params)
|
1111
|
+
process_with_output_tag = params.fetch(:process_with_output_tag, "thisprocess") # some one-word name
|
1112
|
+
output_value = params.fetch(:output_value, nil)
|
1113
|
+
output_value_column = params.fetch(:output_value_column, nil)
|
1114
|
+
output_type = params.fetch(:output_type, SIO["information-content-entity"][self.sio_verbose])
|
1115
|
+
output_type_column = params.fetch(:output_type_column, nil)
|
1116
|
+
output_type_label = params.fetch(:output_type_label, "measurement-value")
|
1117
|
+
output_type_label_column = params.fetch(:output_type_label_column, nil)
|
1118
|
+
output_value_datatype = params.fetch(:output_value_datatype, "xsd:string")
|
1119
|
+
output_value_datatype_column = params.fetch(:output_value_datatype_column, nil)
|
1120
|
+
output_comments_column = params.fetch(:output_comments_column, nil)
|
1121
|
+
output_start_column = params.fetch(:output_start_column, nil)
|
1122
|
+
output_end_column = params.fetch(:output_end_column, nil)
|
1123
|
+
output_timeinstant_column = params.fetch(:output_timeinstant_column, nil)
|
1124
|
+
output_measured_at_column = params.fetch(:output_measured_at_column, nil)
|
1125
|
+
output_annotations = params.fetch(:output_annotations, [])
|
1126
|
+
#output_annotations_columns = params.fetch(:output_annotations_columns, [])
|
1127
|
+
make_unique_process = params.fetch(:make_unique_process, true)
|
1128
|
+
|
1129
|
+
output_value = output_value_column ? "$(#{output_value_column})":output_value
|
1130
|
+
output_type = output_type_column ? "$(#{output_type_column})":output_type
|
1131
|
+
output_type_label = output_type_label_column ? "$(#{output_type_label_column})":output_type_label
|
1132
|
+
output_value_datatype = output_value_datatype_column ? "$(#{output_value_datatype_column})":output_value_datatype
|
1133
|
+
|
1134
|
+
|
1135
|
+
root_url = get_root_url(make_unique_process)
|
1136
|
+
|
1137
|
+
#return unless output_value
|
1138
|
+
|
1139
|
+
@mappings << mapping_clause(
|
1140
|
+
"process_#{process_with_output_tag}_process_has_output",
|
1141
|
+
["#{source_tag}-source"],
|
1142
|
+
root_url + "#process_#{process_with_output_tag}",
|
1143
|
+
[[SIO["has-output"][self.sio_verbose], "this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output", "iri"]]
|
1144
|
+
)
|
1145
|
+
@mappings << mapping_clause(
|
1146
|
+
"process_#{process_with_output_tag}_Output_annotation",
|
1147
|
+
["#{source_tag}-source"],
|
1148
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1149
|
+
[["rdf:type",SIO["information-content-entity"][self.sio_verbose], "iri"]]
|
1150
|
+
)
|
1151
|
+
|
1152
|
+
if output_type
|
1153
|
+
@mappings << mapping_clause(
|
1154
|
+
"process_#{process_with_output_tag}_Output_type_annotation",
|
1155
|
+
["#{source_tag}-source"],
|
1156
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1157
|
+
[["rdf:type",output_type, "iri"]]
|
1158
|
+
)
|
1159
|
+
end
|
1160
|
+
|
1161
|
+
if output_type_label
|
1162
|
+
@mappings << mapping_clause(
|
1163
|
+
"process_#{process_with_output_tag}_Output_type_label_annotation",
|
1164
|
+
["#{source_tag}-source"],
|
1165
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1166
|
+
[["rdfs:label","Output Type: #{output_type_label}", "xsd:string"]]
|
1167
|
+
)
|
1168
|
+
end
|
1169
|
+
|
1170
|
+
if output_value
|
1171
|
+
@mappings << mapping_clause(
|
1172
|
+
"process_#{process_with_output_tag}_Output_value_annotation",
|
1173
|
+
["#{source_tag}-source"],
|
1174
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1175
|
+
[[SIO["has-value"][self.sio_verbose],output_value, output_value_datatype]]
|
1176
|
+
)
|
1177
|
+
end
|
1178
|
+
|
1179
|
+
if output_comments_column
|
1180
|
+
@mappings << mapping_clause(
|
1181
|
+
"process_#{process_with_output_tag}_Output_value_comments",
|
1182
|
+
["#{source_tag}-source"],
|
1183
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1184
|
+
[["rdfs:comment","$(#{output_comments_column})", "xsd:string"]]
|
1185
|
+
)
|
1186
|
+
end
|
1187
|
+
|
1188
|
+
|
1189
|
+
if output_measured_at_column
|
1190
|
+
|
1191
|
+
@mappings << mapping_clause(
|
1192
|
+
"process_#{process_with_output_tag}_output_measured_at_timeinstant",
|
1193
|
+
["#{source_tag}-source"],
|
1194
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1195
|
+
[
|
1196
|
+
[SIO["measured-at"][self.sio_verbose], "this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output_measured_at", "iri"],
|
1197
|
+
]
|
1198
|
+
)
|
1199
|
+
@mappings << mapping_clause(
|
1200
|
+
"process_#{process_with_output_tag}_output_measured_at_timeinstant_value",
|
1201
|
+
["#{source_tag}-source"],
|
1202
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output_measured_at",
|
1203
|
+
[
|
1204
|
+
[SIO["has-value"][self.sio_verbose], "$(#{output_timeinstant_column})", "xsd:date"],
|
1205
|
+
["rdf:type", SIO["time-instant"][self.sio_verbose], "iri"],
|
1206
|
+
]
|
1207
|
+
)
|
1208
|
+
end
|
1209
|
+
|
1210
|
+
|
1211
|
+
if output_start_column # start and end will be attributes of the information object
|
1212
|
+
|
1213
|
+
@mappings << mapping_clause(
|
1214
|
+
"process_#{process_with_output_tag}_output_has_start_atribute",
|
1215
|
+
["#{source_tag}-source"],
|
1216
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1217
|
+
[
|
1218
|
+
# need to add the start column into this URI so that, if it is empty, the attribute will not be created at all by SDMRDFizer
|
1219
|
+
[SIO["has-attribute"][self.sio_verbose], "this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output_start_attribute_$(#{output_start_column})", "iri"],
|
1220
|
+
]
|
1221
|
+
)
|
1222
|
+
@mappings << mapping_clause(
|
1223
|
+
"process_#{process_with_output_tag}_output_has_start_attribute_value",
|
1224
|
+
["#{source_tag}-source"],
|
1225
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output_start_attribute_$(#{output_start_column})",
|
1226
|
+
[
|
1227
|
+
[SIO["has-value"][self.sio_verbose], "$(#{output_start_column})", "xsd:date"],
|
1228
|
+
["rdf:type", SIO["start-date"][self.sio_verbose], "iri"],
|
1229
|
+
]
|
1230
|
+
)
|
1231
|
+
end
|
1232
|
+
|
1233
|
+
|
1234
|
+
if output_end_column # start and end will be attributes of the information object
|
1235
|
+
|
1236
|
+
@mappings << mapping_clause(
|
1237
|
+
"process_#{process_with_output_tag}_output_has_end_atribute",
|
1238
|
+
["#{source_tag}-source"],
|
1239
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1240
|
+
[
|
1241
|
+
# need to add the start column into this URI so that, if it is empty, the attribute will not be created at all by SDMRDFizer
|
1242
|
+
[SIO["has-attribute"][self.sio_verbose], "this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output_end_attribute_$(#{output_end_column})", "iri"],
|
1243
|
+
]
|
1244
|
+
)
|
1245
|
+
@mappings << mapping_clause(
|
1246
|
+
"process_#{process_with_output_tag}_output_has_end_attribute_value",
|
1247
|
+
["#{source_tag}-source"],
|
1248
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output_end_attribute_$(#{output_end_column})",
|
1249
|
+
[
|
1250
|
+
[SIO["has-value"][self.sio_verbose], "$(#{output_end_column})", "xsd:date"],
|
1251
|
+
["rdf:type", SIO["end-date"][self.sio_verbose], "iri"],
|
1252
|
+
]
|
1253
|
+
)
|
1254
|
+
end
|
1255
|
+
|
1256
|
+
output_annotations.each do |pred, value, dtype|
|
1257
|
+
datatype = "xsd:string"
|
1258
|
+
predicate = ""
|
1259
|
+
if dtype and dtype =~ /\S+\:\S+/ # URI or qname
|
1260
|
+
datatype = dtype
|
1261
|
+
elsif dtype
|
1262
|
+
datatype = "$(#{datatype})" # make it the column reference if it exists, but isn't a uri
|
1263
|
+
end
|
1264
|
+
|
1265
|
+
if pred and pred =~ /\S+\:\S+/ # URI or qname
|
1266
|
+
predicate = pred
|
1267
|
+
else
|
1268
|
+
predicate = "$(#{pred})" # make it the column reference if it exists, but isn't a uri
|
1269
|
+
end
|
1270
|
+
|
1271
|
+
next unless predicate and value
|
1272
|
+
uniqid = get_uniq_id
|
1273
|
+
|
1274
|
+
@mappings << mapping_clause(
|
1275
|
+
"#{uniqid}_output_custom_annotation",
|
1276
|
+
["#{source_tag}-source"],
|
1277
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_with_output_tag}_Output",
|
1278
|
+
[["$(#{predicate})", "$(#{value})", datatype]]
|
1279
|
+
)
|
1280
|
+
|
1281
|
+
end
|
1282
|
+
|
1283
|
+
end
|
1284
|
+
|
1285
|
+
|
1286
|
+
# creates the input output refers to portion of the CDE
|
1287
|
+
#
|
1288
|
+
# Parameters passed as a hash
|
1289
|
+
#
|
1290
|
+
#@param params [Hash] a hash of options
|
1291
|
+
#@option params :inout_process_tag [String] ("unidentifiedProcess")
|
1292
|
+
#@option params :refers_to_tag [String] (nil) required unique one-word tag of an attribute
|
1293
|
+
#@option params :inout_refers_to [String] ([]) an ontology URI
|
1294
|
+
#@option params :inout_refers_to_column [String] ([]) column headers for column of ontologyURIs
|
1295
|
+
#@option params :inout_refers_to_label [String] ([]) an ontology term label
|
1296
|
+
#@option params :inout_refers_to_label_column [String] ([]) column header for column of ontology term labels
|
1297
|
+
#@option params :inout_refers_to_uri_column [String] ([]) column header for column containing the URIs of the in/out node (e.g. a specific clinical variant identifier)
|
1298
|
+
#@option params :is_attribute [Boolean] (true) is this output an attribute of a patient/entity?
|
1299
|
+
#@option params :entity_tag [String] (required) then you must tag the entity or person, defaults to "thisPerson"
|
1300
|
+
#@option params :base_types [Array] ([]) an array of ontology terms that will be applied as the rdf:type for all the referred-to quality/attribute
|
1301
|
+
|
1302
|
+
def input_output_refers_to(params)
|
1303
|
+
entityid_column = params.fetch(:entityid_column, 'pid')
|
1304
|
+
inout_process_tag = params.fetch(:inout_process_tag, 'unidentifiedProcess')
|
1305
|
+
refers_to_tag = params.fetch(:refers_to_tag, nil)
|
1306
|
+
inout_refers_to = params.fetch(:inout_refers_to, nil)
|
1307
|
+
inout_refers_to_label = params.fetch(:inout_refers_to_label, nil)
|
1308
|
+
inout_refers_to_column = params.fetch(:inout_refers_to_column, nil)
|
1309
|
+
inout_refers_to_label_column = params.fetch(:inout_refers_to_label_column, nil )
|
1310
|
+
inout_refers_to_uri_column = params.fetch(:inout_refers_to_uri_column, nil )
|
1311
|
+
is_attribute = params.fetch(:is_attribute, true )
|
1312
|
+
entity_tag = params.fetch(:entity_tag, "thisPerson" )
|
1313
|
+
base_types = params.fetch(:base_types, [] )
|
1314
|
+
|
1315
|
+
refers_to = inout_refers_to_column ? "$(#{inout_refers_to_column})":inout_refers_to
|
1316
|
+
refers_to_label = inout_refers_to_label_column ? "$(#{inout_refers_to_label_column})":inout_refers_to_label
|
1317
|
+
|
1318
|
+
abort "must specify in_out_process_tag" unless inout_process_tag
|
1319
|
+
abort "must specify refers_to_tag" unless refers_to_tag
|
1320
|
+
abort "must have an entity tag" unless entity_tag
|
1321
|
+
#$stderr.puts "is an attribute #{is_attribute}"
|
1322
|
+
|
1323
|
+
attribute_node_uri = inout_refers_to_uri_column ? "$(#{inout_refers_to_uri_column})":"this:individual_#{entity_tag}_$(#{entityid_column})_$(#{@uniqueid_column})##{refers_to_tag}_TypedAttributeNode"
|
1324
|
+
|
1325
|
+
types = []
|
1326
|
+
types << ["rdf:type", SIO["attribute"][self.sio_verbose], "iri"] if is_attribute # add base type if its an attribute
|
1327
|
+
types << ["rdf:type", refers_to, "iri"]
|
1328
|
+
base_types.each do |b|
|
1329
|
+
types << ["rdf:type", b, "iri"]
|
1330
|
+
end
|
1331
|
+
|
1332
|
+
@mappings << mapping_clause(
|
1333
|
+
"inout_from_process_#{inout_process_tag}_refers_to_concepts",
|
1334
|
+
["#{source_tag}-source"],
|
1335
|
+
"this:individual_#{entity_tag}_$(#{entityid_column})_$(#{@uniqueid_column})#process_#{inout_process_tag}_Output",
|
1336
|
+
[
|
1337
|
+
[SIO["refers-to"][self.sio_verbose], attribute_node_uri, "iri"]
|
1338
|
+
]
|
1339
|
+
)
|
1340
|
+
|
1341
|
+
if is_attribute
|
1342
|
+
@mappings << mapping_clause(
|
1343
|
+
"has_attribute_of_inout_from_process_#{inout_process_tag}",
|
1344
|
+
["#{source_tag}-source"],
|
1345
|
+
"this:individual_#{entity_tag}_$(#{entityid_column})#Entity",
|
1346
|
+
[
|
1347
|
+
[SIO["has-attribute"][self.sio_verbose], attribute_node_uri, "iri"]
|
1348
|
+
]
|
1349
|
+
)
|
1350
|
+
end
|
1351
|
+
|
1352
|
+
@mappings << mapping_clause(
|
1353
|
+
"inout_from_process_#{inout_process_tag}_refers_to_concept_#{refers_to_tag}_type",
|
1354
|
+
["#{source_tag}-source"],
|
1355
|
+
attribute_node_uri,
|
1356
|
+
|
1357
|
+
types
|
1358
|
+
|
1359
|
+
)
|
1360
|
+
|
1361
|
+
|
1362
|
+
if refers_to_label
|
1363
|
+
@mappings << mapping_clause(
|
1364
|
+
"inout_from_process_#{inout_process_tag}_refers_to_concept_#{refers_to_tag}_label",
|
1365
|
+
["#{source_tag}-source"],
|
1366
|
+
attribute_node_uri,
|
1367
|
+
[
|
1368
|
+
["rdfs:label", "Attribute Type: #{refers_to_label}" ]
|
1369
|
+
]
|
1370
|
+
)
|
1371
|
+
end
|
1372
|
+
|
1373
|
+
|
1374
|
+
end
|
1375
|
+
|
1376
|
+
|
1377
|
+
|
1378
|
+
|
1379
|
+
|
1380
|
+
|
1381
|
+
|
1382
|
+
# creates the output_has_unit portion of the CDE
|
1383
|
+
#
|
1384
|
+
# Parameters passed as a hash
|
1385
|
+
# @option params :inout_process_tag [String] ("unidentifiedProcess")
|
1386
|
+
# @option params :output_unit [URL] the ontological type of that unit (default nil)
|
1387
|
+
# @option params :output_unit_column [String]column containing the ontological type of that unit (overrides output_unit)
|
1388
|
+
# @option params :output_unit_label [string] the string label for that unit (e.g. "centimeters" for the ontological type "cm" ) (default nil)
|
1389
|
+
# @option params :output_unit_label_column [string] column header containing the string label for that unit (e.g. "centimeters" for the ontological type "cm" )
|
1390
|
+
|
1391
|
+
def output_has_unit(params)
|
1392
|
+
process_tag = params.fetch(:inout_process_tag, 'unidentifiedProcess')
|
1393
|
+
|
1394
|
+
output_unit = params.fetch(:output_unit, nil) # URI
|
1395
|
+
output_unit_column = params.fetch(:output_unit_column, nil) # URI
|
1396
|
+
output_unit_label = params.fetch(:output_unit_label, nil)
|
1397
|
+
output_unit_label_column = params.fetch(:output_unit_label_column, nil)
|
1398
|
+
|
1399
|
+
output_unit = output_unit_column ? "$(#{output_unit_column})":output_unit
|
1400
|
+
output_unit_label = output_unit_label_column ? "$(#{output_unit_label_column})":output_unit_label
|
1401
|
+
|
1402
|
+
if output_unit
|
1403
|
+
@mappings << mapping_clause(
|
1404
|
+
"process_#{process_tag}_Output_hasunit_unit",
|
1405
|
+
["#{source_tag}-source"],
|
1406
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_tag}_Output",
|
1407
|
+
[[SIO["has-unit"][self.sio_verbose], "this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_tag}_Output_unit", "iri"]]
|
1408
|
+
)
|
1409
|
+
|
1410
|
+
@mappings << mapping_clause(
|
1411
|
+
"process_#{process_tag}_Output_unit_annotation",
|
1412
|
+
["#{source_tag}-source"],
|
1413
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_tag}_Output_unit",
|
1414
|
+
[["rdf:type",output_unit, "iri"]]
|
1415
|
+
)
|
1416
|
+
|
1417
|
+
end
|
1418
|
+
|
1419
|
+
if output_unit and output_unit_label
|
1420
|
+
|
1421
|
+
@mappings << mapping_clause(
|
1422
|
+
"process_#{process_tag}_Output_unit_label_annotation",
|
1423
|
+
["#{source_tag}-source"],
|
1424
|
+
"this:individual_$(#{@personid_column})_$(#{@uniqueid_column})#process_#{process_tag}_Output_unit",
|
1425
|
+
[["rdfs:label",output_unit_label,"xsd:string"]
|
1426
|
+
]
|
1427
|
+
)
|
1428
|
+
end
|
1429
|
+
|
1430
|
+
|
1431
|
+
end
|
1432
|
+
|
1433
|
+
|
1434
|
+
|
1435
|
+
# creates the entity has component entity portion of the CDE
|
1436
|
+
#
|
1437
|
+
# Parameters passed as a hash
|
1438
|
+
#
|
1439
|
+
# @param params [Hash] a hash of options
|
1440
|
+
# @option params :parent_entityid_column [String] (required) the column that contains the parent entity id
|
1441
|
+
# @option params :parent_entity_tag [String] (required) default "thisPerson" the tag of the parent entity
|
1442
|
+
# @option params :part_entity_tag [String] (required) the tag of the part entity
|
1443
|
+
# @option params :part_type_column [String] (required) the column that contains the parent entity id
|
1444
|
+
# TODO make it possible to explicitly compose entities from other modelled entities (part entity id column)
|
1445
|
+
def entity_has_component(params)
|
1446
|
+
parent_entityid_column = params.fetch(:parent_entityid_column, 'pid')
|
1447
|
+
parent_entity_tag = params.fetch(:part_entity_tag, "thisPerson")
|
1448
|
+
part_entity_tag = params.fetch(:part_entity_tag, nil)
|
1449
|
+
part_type = params.fetch(:part_type, nil)
|
1450
|
+
part_type_column = params.fetch(:part_type_column, nil)
|
1451
|
+
|
1452
|
+
part_type = part_type_column ? "$(#{part_type_column})":part_type
|
1453
|
+
|
1454
|
+
abort "cannot create entity has component without both a part type and part tag" unless (part_type && part_entity_tag)
|
1455
|
+
|
1456
|
+
#uniqid = get_uniq_id
|
1457
|
+
|
1458
|
+
@mappings << mapping_clause(
|
1459
|
+
"parent_entity_has_part_#{part_entity_tag}",
|
1460
|
+
["#{source_tag}-source"],
|
1461
|
+
"this:individual_#{parent_entity_tag}_$(#{parent_entityid_column})#Entity",
|
1462
|
+
[[SIO["has-component-part"][self.sio_verbose], "this:individual_#{part_entity_tag}#componentEntity" , "iri"]]
|
1463
|
+
)
|
1464
|
+
|
1465
|
+
@mappings << mapping_clause(
|
1466
|
+
"parent_entity_has_part_#{part_entity_tag}",
|
1467
|
+
["#{source_tag}-source"],
|
1468
|
+
"this:individual_#{part_entity_tag}#componentEntity",
|
1469
|
+
[['rdf:type', part_type , "iri"]]
|
1470
|
+
)
|
1471
|
+
|
1472
|
+
end
|
1473
|
+
|
1474
|
+
|
1475
|
+
|
1476
|
+
# creates a time-based locally-unique identifier
|
1477
|
+
|
1478
|
+
def get_uniq_id
|
1479
|
+
return Time.now.to_f.to_s.gsub("\.", "")
|
1480
|
+
|
1481
|
+
end
|
1482
|
+
end
|
1483
|
+
|
1484
|
+
|
1485
|
+
|