https://mooseframework.inl.gov
Loading...
Searching...
No Matches
GeochemicalDatabaseValidator.C
Go to the documentation of this file.
1//* This file is part of the MOOSE framework
2//* https://mooseframework.inl.gov
3//*
4//* All rights reserved, see COPYRIGHT for full restrictions
5//* https://github.com/idaholab/moose/blob/master/COPYRIGHT
6//*
7//* Licensed under LGPL 2.1, please see LICENSE for details
8//* https://www.gnu.org/licenses/lgpl-2.1.html
9
11
12#include "Conversion.h"
13#include "MooseUtils.h"
14#include "string"
15
17 const nlohmann::json & db)
18 : _filename(filename), _root(db)
19{
20}
21
22void
24{
25 // Check that the database has a Header key (required)
26 if (!_root.contains("Header"))
27 mooseError("The MOOSE database ", _filename, " does not have a required \"Header\" field");
28
29 // Check that temperatures are present
30 checkHeaderField("temperatures");
31
32 // The size of the temperature array is used to check all other arrays, which must
33 // have the same number of elements
34 _temperature_size = _root["Header"]["temperatures"].size();
35
36 // Now check that the values are all Real
37 checkHeaderArray("temperatures");
38
39 // Check the pressure values are present and are Reals
40 checkHeaderField("pressures");
41 checkHeaderArray("pressures");
42
43 // Check activity model coefficients
44 checkHeaderField("activity model");
45
46 // If the activity model is Debye-Huckel, test the coefficients are also present
47 // and are Reals
48 if (_root["Header"]["activity model"] == "debye-huckel")
49 {
50 checkHeaderField("adh");
51 checkHeaderArray("adh");
52
53 checkHeaderField("bdh");
54 checkHeaderArray("bdh");
55
56 checkHeaderField("bdot");
57 checkHeaderArray("bdot");
58 }
59
60 // Check fugacity model is specified
61 checkHeaderField("fugacity model");
62
63 // If there are neutral species, check their arrays of coefficients
64 if (_root["Header"].contains("neutral species"))
65 for (auto & ns : _root["Header"]["neutral species"].items())
66 for (auto & coeffs : ns.value().items())
67 {
68 if (coeffs.key() == "note")
69 continue;
70
71 // Check that there are a correct number of values and that they are real numbers
72 auto values = coeffs.value();
73 checkArraySize(values, "Header:neutral species:" + ns.key() + ":" + coeffs.key());
74 checkArrayValues(values, "Header:neutral species:" + ns.key() + ":" + coeffs.key());
75 }
76
77 // Check the element data
78 for (auto & el : _root["elements"].items())
79 checkElements(el.key());
80
81 // Check the basis species data
82 for (auto & species : _root["basis species"].items())
83 checkBasisSpecies(species.key());
84
85 // Check the secondary species data
86 if (_root.contains("secondary species"))
87 for (auto & species : _root["secondary species"].items())
88 checkSecondarySpecies(species.key());
89
90 // Check the mineral species data
91 if (_root.contains("mineral species"))
92 for (auto & species : _root["mineral species"].items())
93 checkMineralSpecies(species.key());
94
95 // Check the sorbing mineral species data
96 if (_root.contains("sorbing minerals"))
97 for (auto & species : _root["sorbing minerals"].items())
98 checkSorbingMineralSpecies(species.key());
99
100 // Check the gas species data
101 if (_root.contains("gas species"))
102 for (auto & species : _root["gas species"].items())
103 checkGasSpecies(species.key());
104
105 // Check the redox couple data
106 if (_root.contains("redox couples"))
107 for (auto & species : _root["redox couples"].items())
108 checkRedoxSpecies(species.key());
109
110 // Check the oxide species data
111 if (_root.contains("oxides"))
112 for (auto & species : _root["oxides"].items())
113 checkOxideSpecies(species.key());
114
115 // Check the surface species data
116 if (_root.contains("surface species"))
117 for (auto & species : _root["surface species"].items())
118 checkSurfaceSpecies(species.key());
119}
120
121bool
122GeochemicalDatabaseValidator::isValueReal(const nlohmann::json & value) const
123{
124 if (value.is_number())
125 return true;
126 try
127 {
128 MooseUtils::convert<Real>(value, true);
129 }
130 catch (const std::invalid_argument & err)
131 {
132 return false;
133 }
134
135 return true;
136}
137
138void
140 const std::string field) const
141{
142 // Check each value in the array can be successfully converted to a Real
143 for (auto & item : array.items())
144 if (!isValueReal(item.value()))
145 mooseError("Array value ",
146 nlohmann::to_string(item.value()),
147 " in the ",
148 field,
149 " field of ",
150 _filename,
151 " cannot be converted to Real");
152}
153
154void
156 const std::string species,
157 const std::string field) const
158{
159 // Check each value in the array can be successfully converted to a Real
160 for (auto & item : _root[type][species][field].items())
161 if (!isValueReal(item.value()))
162 mooseError("Array value ",
163 nlohmann::to_string(item.value()),
164 " in the ",
165 field,
166 " field of ",
167 type,
168 " ",
169 species,
170 " in ",
171 _filename,
172 " cannot be converted to Real");
173}
174
175void
177 const std::string field) const
178{
179 if (array.size() != _temperature_size)
180 mooseError("The number of values in the ",
181 field,
182 " field of ",
183 _filename,
184 " is not equal to the number of temperature values");
185}
186
187void
189 const std::string species,
190 const std::string field) const
191{
192 if (_root[type][species][field].size() != _temperature_size)
193 mooseError("The number of values in the ",
194 field,
195 " field of ",
196 type,
197 " ",
198 species,
199 " in ",
200 _filename,
201 " is not equal to the number of temperature values");
202}
203
204void
206{
207 if (!_root["Header"].contains(field))
209 "The MOOSE database ", _filename, " does not have a required \"Header:", field, "\" field");
210}
211
212void
214{
215 // Check that all values are real numbers and of size equal to the temperature
216 checkArraySize(_root["Header"][field], "Header:" + field);
217 checkArrayValues(_root["Header"][field], "Header:" + field);
218}
219
220void
222 const std::string species,
223 const std::string field) const
224{
225 if (!_root[type].contains(species) || !_root[type][species].contains(field))
226 mooseError("The ", type, " ", species, " in ", _filename, " does not have a ", field);
227
228 // The field value should be a real number
229 if (!isValueReal(_root[type][species][field]))
230 mooseError(field,
231 " value ",
232 nlohmann::to_string(_root[type][species][field]),
233 " of the ",
234 type,
235 " ",
236 species,
237 " in ",
238 _filename,
239 " cannot be converted to Real");
240}
241
242void
244 const std::string species,
245 const std::string field) const
246{
247 if (!_root[type].contains(species) || !_root[type][species].contains(field))
248 mooseError("The ", type, " ", species, " in ", _filename, " does not have a ", field);
249
250 // Each weight value for each constituent should be a real number
251 for (auto & item : _root[type][species][field].items())
252 if (!isValueReal(item.value()))
253 mooseError("Weight value ",
254 nlohmann::to_string(item.value()),
255 " of constituent ",
256 item.key(),
257 " of the ",
258 type,
259 " ",
260 species,
261 " in ",
262 _filename,
263 " cannot be converted to Real");
264}
265
266void
267GeochemicalDatabaseValidator::checkElements(const std::string element) const
268{
269 // Check molecular weight can be converted to a Real
270 checkSpeciesValue("elements", element, "molecular weight");
271}
272
273void
275{
276 // Check molecular weight can be converted to a Real
277 checkSpeciesValue("basis species", species, "molecular weight");
278
279 // Check charge can be converted to a Real
280 checkSpeciesValue("basis species", species, "charge");
281
282 // Check ionic radius can be converted to a Real
283 checkSpeciesValue("basis species", species, "radius");
284
285 // Check element weights can be converted to a Real
286 checkSpeciesWeightValue("basis species", species, "elements");
287}
288
289void
291{
292 // Check molecular weight can be converted to a Real
293 checkSpeciesValue("secondary species", species, "molecular weight");
294
295 // Check charge can be converted to a Real
296 checkSpeciesValue("secondary species", species, "charge");
297
298 // Check ionic radius can be converted to a Real
299 checkSpeciesValue("secondary species", species, "radius");
300
301 // Check basis species weights can be converted to a Real
302 checkSpeciesWeightValue("secondary species", species, "species");
303
304 // Check the number of logk values and whether they can be converted to a Real
305 checkArraySize("secondary species", species, "logk");
306 checkArrayValues("secondary species", species, "logk");
307}
308
309void
311{
312 // Check molecular weight can be converted to a Real
313 checkSpeciesValue("mineral species", species, "molecular weight");
314
315 // Check molar volume can be converted to a Real
316 checkSpeciesValue("mineral species", species, "molar volume");
317
318 // Check basis species weights can be converted to a Real
319 checkSpeciesWeightValue("mineral species", species, "species");
320
321 // Check the number of logk values and whether they can be converted to a Real
322 checkArraySize("mineral species", species, "logk");
323 checkArrayValues("mineral species", species, "logk");
324}
325
326void
328{
329 // Check surface area can be converted to a Real
330 checkSpeciesValue("sorbing minerals", species, "surface area");
331
332 // Check sorbing site weights can be converted to a Real
333 checkSpeciesWeightValue("sorbing minerals", species, "sorbing sites");
334}
335
336void
337GeochemicalDatabaseValidator::checkGasSpecies(const std::string species) const
338{
339 // Check molecular weight can be converted to a Real
340 checkSpeciesValue("gas species", species, "molecular weight");
341
342 // Check basis species weights can be converted to a Real
343 checkSpeciesWeightValue("gas species", species, "species");
344
345 // Check the number of logk values and whether they can be converted to a Real
346 checkArraySize("gas species", species, "logk");
347 checkArrayValues("gas species", species, "logk");
348
349 // Check optional fugacity coefficients
350 if (_root["gas species"][species].contains("chi"))
351 checkArrayValues("gas species", species, "chi");
352
353 if (_root["gas species"][species].contains("Pcrit"))
354 checkSpeciesValue("gas species", species, "Pcrit");
355
356 if (_root["gas species"][species].contains("Tcrit"))
357 checkSpeciesValue("gas species", species, "Tcrit");
358
359 if (_root["gas species"][species].contains("omega"))
360 checkSpeciesValue("gas species", species, "omega");
361}
362
363void
365{
366 // Check molecular weight can be converted to a Real
367 checkSpeciesValue("redox couples", species, "molecular weight");
368
369 // Check charge can be converted to a Real
370 checkSpeciesValue("redox couples", species, "charge");
371
372 // Check ionic radius can be converted to a Real
373 checkSpeciesValue("redox couples", species, "radius");
374
375 // Check basis species weights can be converted to a Real
376 checkSpeciesWeightValue("redox couples", species, "species");
377
378 // Check the number of logk values and whether they can be converted to a Real
379 checkArraySize("redox couples", species, "logk");
380 checkArrayValues("redox couples", species, "logk");
381}
382
383void
385{
386 // Check molecular weight can be converted to a Real
387 checkSpeciesValue("oxides", species, "molecular weight");
388
389 // Check basis species weights can be converted to a Real
390 checkSpeciesWeightValue("oxides", species, "species");
391}
392
393void
395{
396 // Check molecular weight can be converted to a Real
397 checkSpeciesValue("surface species", species, "molecular weight");
398
399 // Check charge can be converted to a Real
400 checkSpeciesValue("surface species", species, "charge");
401
402 // Check basis species weights can be converted to a Real
403 checkSpeciesWeightValue("surface species", species, "species");
404
405 // Check equilibrium constants can be converted to a Real
406 checkSpeciesValue("surface species", species, "log K");
407 checkSpeciesValue("surface species", species, "dlogK/dT");
408}
const GeochemicalDatabaseReader db("database/moose_testdb.json", true, true, false)
void mooseError(Args &&... args)
std::array< Real, 2 > values
const nlohmann::json & _root
JSON database.
void checkOxideSpecies(const std::string species) const
Check oxide species in the database Each oxide species should have a real number as their molecular w...
void checkBasisSpecies(const std::string species) const
Check basis species in the database Each basis species should have a real number as their molecular w...
void checkRedoxSpecies(const std::string species) const
Check redox couple species in the database Each redox couple species should have a real number as the...
void checkMineralSpecies(const std::string species) const
Check mineral species in the database Each mineral species should have a real number as their molecul...
void checkSpeciesValue(const std::string type, const std::string species, const std::string field) const
Check given species field value can be converted to a Real.
void checkGasSpecies(const std::string species) const
Check gas species in the database Each gas species should have a real number as their molecular weigh...
void validate()
Validate the thermodynamic database.
void checkElements(const std::string element) const
Check elements in the database Each elemenent should have a real number as their molecular weights.
void checkSorbingMineralSpecies(const std::string species) const
Check sorbing mineral species in the database Each sorbing mineral species should have a real number ...
void checkArrayValues(const nlohmann::json &array, const std::string field) const
Check Json::Value array is comprised of Reals.
GeochemicalDatabaseValidator(const FileName filename, const nlohmann::json &db)
void checkSecondarySpecies(const std::string species) const
Check secondary species in the database Each secondary species should have a real number as their mol...
void checkArraySize(const nlohmann::json &array, const std::string field) const
Check Json::Value array is the correct size.
bool isValueReal(const nlohmann::json &value) const
Check Json::Value can be converted to a Real.
void checkSpeciesWeightValue(const std::string type, const std::string species, const std::string field) const
Check given species stoichiometric weigth values can be converted to a Real.
unsigned int _temperature_size
Number of temperature points.
void checkSurfaceSpecies(const std::string species) const
Check surface species in the database Each surface species should have a real number as their molecul...
const FileName _filename
Database filename.
void checkHeaderField(const std::string field) const
Check fields are present in the Header section.
void checkHeaderArray(const std::string field) const
Check arrays in field can be converted to Reals.