1 26
import logging
2 26
import os
3 26
from enum import Enum
4 26
from sys import platform
5

6 26
logger = logging.getLogger(__name__)
7

8

9 26
class Simulation(object):
10
    """
11
    Base class for a Molecular Dynamics simulation wrapper.
12
    """
13

14 26
    class Ensemble(Enum):
15
        """
16
        An enumeration of the different thermodynamic ensembles.
17
        """
18

19 26
        NVE = "NVE"
20 26
        NVT = "NVT"
21 26
        NPT = "NPT"
22

23 26
    @property
24
    def path(self):
25
        """os.PathLike: The path for the creation and execution of files for this protocol."""
26 26
        return self._path
27

28 26
    @path.setter
29
    def path(self, value):
30 26
        self._path = value
31

32 26
    @property
33
    def executable(self):
34
        """str: The Molecular Dynamics executable that will be used.
35

36
        .. note::
37
            This could be made safer by making an ``ENUM`` of ``sander``, ``pmemd`` and ``pmemd.cuda``.
38
        """
39 26
        return self._executable
40

41 26
    @executable.setter
42
    def executable(self, value):
43 26
        self._executable = value
44

45 26
    @property
46 26
    def n_threads(self) -> int:
47
        """int: Number of threads to use for the simulation."""
48 0
        return self._n_threads
49

50 26
    @n_threads.setter
51 26
    def n_threads(self, value: int):
52 0
        self._n_threads = value
53

54 26
    @property
55
    def gpu_devices(self):
56
        """int or str: A wrapper around the environmental variable ``CUDA_VISIBLE_DEVICES``."""
57 26
        return self._gpu_devices
58

59 26
    @gpu_devices.setter
60
    def gpu_devices(self, value):
61 0
        self._gpu_devices = value
62

63 26
    @property
64 26
    def plumed_file(self) -> str:
65
        """os.PathLike: The name of the Plumed-style restraints file.
66

67
        .. note::
68
            When running simulations with a MD engine that supports Plumed and other restraint module(s),
69
            you can only use one or the other. If both are specified, an ``Exception`` will be thrown.
70
        """
71 26
        return self._plumed_file
72

73 26
    @plumed_file.setter
74 26
    def plumed_file(self, value: str):
75 0
        self._plumed_file = value
76

77 26
    @property
78 26
    def plumed_kernel_library(self) -> str:
79
        """os.PathLike: The file path of the Plumed kernel library if it is different from the default. The default
80
        name is ``libplumedKernel`` with its extension determined automatically depending on the operating system and is
81
        located in ``os.environ['CONDA_PREFIX']/lib``. This variable is useful for users who did not install or want to
82
        use Plumed from the conda repository."""
83 0
        return self._plumed_kernel_library
84

85 26
    @plumed_kernel_library.setter
86 26
    def plumed_kernel_library(self, value: str):
87 0
        self._plumed_kernel_library = value
88

89 26
    @property
90 26
    def topology(self) -> str:
91
        """os.PathLike: The topology file to simulate."""
92 26
        return self._topology
93

94 26
    @topology.setter
95 26
    def topology(self, value: os.PathLike):
96 26
        self._topology = value
97

98 26
    @property
99 26
    def coordinates(self) -> str:
100
        """os.PathLike: The coordinates of the MD system."""
101 26
        return self._coordinates
102

103 26
    @coordinates.setter
104 26
    def coordinates(self, value: str):
105 26
        self._coordinates = value
106

107 26
    @property
108 26
    def prefix(self) -> str:
109
        """
110
        The prefix for file names generated from this simulation.
111
        """
112 0
        return self._prefix
113

114 26
    @prefix.setter
115 26
    def prefix(self, new_prefix: str):
116 0
        self._prefix = new_prefix
117

118 26
    @property
119 26
    def phase(self) -> str:
120
        """str: Which ``phase`` of the calculation to simulate.
121

122
        .. note ::
123
            This could probably be combined with the ``window`` attribute for simplicity.
124
        """
125 0
        return self._phase
126

127 26
    @phase.setter
128 26
    def phase(self, value: str):
129 0
        self._phase = value
130

131 26
    @property
132 26
    def window(self) -> str:
133
        """str: Which ``window`` of the calculation to simulate."""
134 0
        return self._window
135

136 26
    @window.setter
137 26
    def window(self, value: str):
138 0
        self._window = value
139

140 26
    @property
141 26
    def converged(self) -> bool:
142
        """bool: Whether the simulation is converged.
143

144
        .. warning ::
145
            This is just a placeholder and is not implemented yet.
146
        """
147 0
        return self._converged
148

149 26
    @converged.setter
150 26
    def converged(self, value: bool):
151 26
        self._converged = value
152

153 26
    @property
154 26
    def temperature(self) -> float:
155
        """float: Desired temperature of the system (Kelvin). Default is 298.15 K."""
156 26
        return self._temperature
157

158 26
    @temperature.setter
159 26
    def temperature(self, value: float):
160 0
        self._temperature = value
161

162 26
    @property
163 26
    def pressure(self) -> float:
164
        """float: Desired pressure of the system (bar). Default is 1.01325 bar."""
165 26
        return self._pressure
166

167 26
    @pressure.setter
168 26
    def pressure(self, value: float):
169 0
        self._pressure = value
170

171 26
    @property
172 26
    def thermostat(self) -> dict:
173
        """dict: Dictionary for the thermostat options."""
174 26
        return self._thermostat
175

176 26
    @thermostat.setter
177 26
    def thermostat(self, value: dict):
178 0
        self._thermostat = value
179

180 26
    @property
181 26
    def barostat(self) -> dict:
182
        """dict: Dictionary for the barostat options."""
183 26
        return self._barostat
184

185 26
    @barostat.setter
186 26
    def barostat(self, value: dict):
187 0
        self._barostat = value
188

189 26
    def __init__(self):
190 26
        self.title = "PBC MD Simulation"
191 26
        self._path = "."
192 26
        self._executable = "sander"
193 26
        self._n_threads = 1
194 26
        self._gpu_devices = None
195 26
        self._plumed_file = None
196 26
        self._plumed_kernel_library = None
197 26
        self._topology = "prmtop"
198 26
        self._coordinates = "rst7"
199 26
        self._prefix = "md"
200 26
        self._phase = None
201 26
        self._window = None
202 26
        self.converged = False
203

204 26
        self._temperature = 298.15
205 26
        self._pressure = 1.01325
206 26
        self._thermostat = {}
207 26
        self._barostat = {}
208

209 26
    def _set_plumed_kernel(self):
210
        # Set the Plumed kernel library path
211 0
        if self.plumed_kernel_library is None:
212
            # using "startswith" as recommended from https://docs.python.org/3/library/sys.html#sys.platform
213 0
            if platform.startswith("linux"):
214 0
                self.plumed_kernel_library = os.path.join(
215
                    os.environ["CONDA_PREFIX"], "lib", "libplumedKernel.so"
216
                )
217 0
            elif platform.startswith("darwin"):
218 0
                self.plumed_kernel_library = os.path.join(
219
                    os.environ["CONDA_PREFIX"], "lib", "libplumedKernel.dylib"
220
                )
221
            else:
222 0
                logger.warning(
223
                    f"Plumed is not supported with the '{platform}' platform."
224
                )
225

226
        # Add Plumed kernel library to env dict
227 0
        if os.path.isfile(self.plumed_kernel_library):
228 0
            os.environ = dict(os.environ, PLUMED_KERNEL=self.plumed_kernel_library)
229
        else:
230 0
            logger.warning(
231
                f"Plumed kernel library {self.plumed_kernel_library} does not exist, "
232
                "PLUMED_KERNEL environment variable is not set."
233
            )
234

235 26
    def _config_min(self):
236
        """Place holder function."""
237 0
        raise NotImplementedError()
238

239 26
    def _config_md(self):
240
        """Place holder function."""
241 0
        raise NotImplementedError()
242

243 26
    def config_gb_min(self):
244
        """Place holder function."""
245 0
        raise NotImplementedError()
246

247 26
    def config_gb_md(self):
248
        """Place holder function."""
249 0
        raise NotImplementedError()
250

251 26
    def config_pbc_min(self):
252
        """Place holder function."""
253 0
        raise NotImplementedError()
254

255 26
    def config_pbc_md(self):
256
        """Place holder function."""
257 0
        raise NotImplementedError()
258

259 26
    def _write_input_file(self):
260
        """Place holder function."""
261 0
        raise NotImplementedError()
262

263 26
    def run(self):
264
        """Place holder function."""
265 0
        raise NotImplementedError()
266

267 26
    def check_complete(self):
268
        """Place holder function."""
269 0
        raise NotImplementedError()
270

271 26
    def check_converged(self):
272
        """Place holder function"""
273 0
        raise NotImplementedError()

Read our documentation on viewing source code .

Loading