Skip to content

Commit 0e0b273

Browse files
authored
Merge pull request #4 from virtualcell/local-fielddata
generate FV solver input files with local field data
2 parents 08b5207 + c135925 commit 0e0b273

File tree

10 files changed

+773
-24
lines changed

10 files changed

+773
-24
lines changed

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ build-backend = "poetry.core.masonry.api"
44

55
[tool.poetry]
66
name = "libvcell"
7-
version = "0.0.6"
7+
version = "0.0.7"
88
description = "This is a python package which wraps a subset of VCell Java code as a native python package."
99
authors = ["Jim Schaff <[email protected]>", "Ezequiel Valencia <[email protected]>"]
1010
repository = "https://github.com/virtualcell/libvcell"

vcell-native/src/main/java/org/vcell/libvcell/Entrypoints.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ public String toJson() {
5252
documentation = """
5353
Converts VCML file into Finite Volume Input files.
5454
vcml_content: text of VCML XML document
55-
output_dir_path: path to the output directory
55+
output_dir_path: path to the output directory (expected to be subdirectory of the workspace)
5656
Returns a JSON string with success status and message"""
5757
)
5858
public static CCharPointer entrypoint_vcmlToFiniteVolumeInput(
@@ -65,7 +65,9 @@ public static CCharPointer entrypoint_vcmlToFiniteVolumeInput(
6565
String vcmlContentStr = CTypeConversion.toJavaString(vcml_content);
6666
String simulationName = CTypeConversion.toJavaString(simulation_name);
6767
String outputDirPathStr = CTypeConversion.toJavaString(output_dir_path);
68-
vcmlToFiniteVolumeInput(vcmlContentStr, simulationName, new File(outputDirPathStr));
68+
File outputDir = new File(outputDirPathStr);
69+
File parentDir = outputDir.getParentFile();
70+
vcmlToFiniteVolumeInput(vcmlContentStr, simulationName, parentDir, outputDir);
6971
returnValue = new ReturnValue(true, "Success");
7072
}catch (Throwable t) {
7173
logger.error("Error processing spatial model", t);

vcell-native/src/main/java/org/vcell/libvcell/MainRecorder.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ public static void main(String[] args) {
2020
File vcml_file = new File(args[1]);
2121
String vcml_sim_name = args[2];
2222
File output_dir = new File(args[3]);
23+
File parent_dir = output_dir.getParentFile();
2324
logger.info("Logger logging");
2425
PropertyLoader.setProperty(PropertyLoader.vcellServerIDProperty, "none");
2526
PropertyLoader.setProperty(PropertyLoader.mongodbDatabase, "none");
@@ -35,7 +36,7 @@ public static void main(String[] args) {
3536
byte[] data = f_vcml.readAllBytes();
3637
logger.info("Read " + data.length + " bytes from " + vcml_file.getAbsolutePath());
3738
String vcml_str = new String(data);
38-
vcmlToFiniteVolumeInput(vcml_str, vcml_sim_name, output_dir);
39+
vcmlToFiniteVolumeInput(vcml_str, vcml_sim_name, parent_dir, output_dir);
3940
}
4041

4142
// use reflection to load jsbml classes and call their default constructors

vcell-native/src/main/java/org/vcell/libvcell/SolverUtils.java

Lines changed: 57 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2,34 +2,42 @@
22

33
import cbit.util.xml.VCLoggerException;
44
import cbit.vcell.biomodel.BioModel;
5+
import cbit.vcell.field.FieldDataIdentifierSpec;
6+
import cbit.vcell.field.FieldFunctionArguments;
7+
import cbit.vcell.field.FieldUtilities;
58
import cbit.vcell.geometry.GeometrySpec;
69
import cbit.vcell.mapping.MappingException;
710
import cbit.vcell.mapping.SimulationContext;
11+
import cbit.vcell.math.MathException;
12+
import cbit.vcell.messaging.server.SimulationTask;
813
import cbit.vcell.mongodb.VCMongoMessage;
914
import cbit.vcell.parser.ExpressionException;
10-
import cbit.vcell.solver.Simulation;
11-
import cbit.vcell.solver.SolverException;
12-
import cbit.vcell.solver.TimeBounds;
13-
import cbit.vcell.solver.UniformOutputTimeSpec;
15+
import cbit.vcell.solver.*;
1416
import cbit.vcell.xml.XMLSource;
1517
import cbit.vcell.xml.XmlHelper;
1618
import cbit.vcell.xml.XmlParseException;
1719
import org.apache.logging.log4j.LogManager;
1820
import org.apache.logging.log4j.Logger;
21+
import org.vcell.libvcell.solvers.LocalFVSolverStandalone;
1922
import org.vcell.sbml.FiniteVolumeRunUtil;
2023
import org.vcell.sbml.vcell.SBMLExporter;
2124
import org.vcell.sbml.vcell.SBMLImporter;
25+
import org.vcell.util.document.ExternalDataIdentifier;
26+
import org.vcell.util.document.KeyValue;
27+
import org.vcell.util.document.User;
2228

2329
import java.beans.PropertyVetoException;
2430
import java.io.ByteArrayInputStream;
2531
import java.io.File;
2632
import java.io.InputStream;
33+
import java.util.ArrayList;
34+
import java.util.List;
2735

2836

2937
public class SolverUtils {
3038
private static final Logger logger = LogManager.getLogger(Entrypoints.class);
3139

32-
public static void vcmlToFiniteVolumeInput(String vcml_content, String simulation_name, File outputDir) throws XmlParseException, MappingException, SolverException, ExpressionException {
40+
public static void vcmlToFiniteVolumeInput(String vcml_content, String simulation_name, File parentDir, File outputDir) throws XmlParseException, MappingException, SolverException, ExpressionException, MathException {
3341
GeometrySpec.avoidAWTImageCreation = true;
3442
VCMongoMessage.enabled = false;
3543
if (vcml_content.substring(0, 300).contains("<sbml xmlns=\"http://www.sbml.org/sbml")) {
@@ -41,7 +49,50 @@ public static void vcmlToFiniteVolumeInput(String vcml_content, String simulatio
4149
if (sim == null) {
4250
throw new IllegalArgumentException("Simulation not found: " + simulation_name);
4351
}
44-
FiniteVolumeRunUtil.writeInputFilesOnly(outputDir, sim);
52+
FieldDataIdentifierSpec[] fdiSpecs = getFieldDataIdentifierSpecs(sim, parentDir);
53+
54+
TempSimulation tempSimulation = new TempSimulation(sim, false);
55+
tempSimulation.setSimulationOwner(sim.getSimulationOwner());
56+
SimulationJob tempSimulationJob = new SimulationJob(tempSimulation, 0, fdiSpecs);
57+
SimulationTask simTask = new SimulationTask(tempSimulationJob, 0);
58+
LocalFVSolverStandalone solver = new LocalFVSolverStandalone(simTask, outputDir);
59+
solver.initialize();
60+
}
61+
62+
private static FieldDataIdentifierSpec[] getFieldDataIdentifierSpecs(Simulation sim, File parentDir) throws MathException, ExpressionException {
63+
FieldDataIdentifierSpec[] fdiSpecs = null;
64+
FieldFunctionArguments[] fieldFuncArgs = FieldUtilities.getFieldFunctionArguments(sim.getMathDescription());
65+
if (fieldFuncArgs != null) {
66+
List<FieldDataIdentifierSpec> fdiSpecList = new ArrayList<>();
67+
for (FieldFunctionArguments fieldFuncArg : fieldFuncArgs) {
68+
if (fieldFuncArg != null) {
69+
String name = fieldFuncArg.getFieldName();
70+
File fieldDataDir = new File(parentDir, name);
71+
if (!fieldDataDir.exists()) {
72+
throw new IllegalArgumentException("Field data directory does not exist: " + fieldDataDir.getAbsolutePath());
73+
}
74+
// search fieldDataDir for files with name pattern SimID_<key>_* and extract the key
75+
KeyValue key = null;
76+
for (File f: fieldDataDir.listFiles()) {
77+
String[] filename_parts = f.getName().split("_");
78+
if (filename_parts.length < 3) {
79+
continue;
80+
}
81+
if (filename_parts[0].equals("SimID")) {
82+
key = new KeyValue(filename_parts[1]);
83+
break;
84+
}
85+
}
86+
if (key == null) {
87+
throw new IllegalArgumentException("Field data directory does not contain a file with key: " + name);
88+
}
89+
ExternalDataIdentifier extDataId = new ExternalDataIdentifier(key, User.tempUser, name);
90+
fdiSpecList.add(new FieldDataIdentifierSpec(fieldFuncArg, extDataId));
91+
}
92+
}
93+
fdiSpecs = fdiSpecList.toArray(new FieldDataIdentifierSpec[fdiSpecList.size()]);
94+
}
95+
return fdiSpecs;
4596
}
4697

4798

0 commit comments

Comments
 (0)