Skip to content

Commit

Permalink
use hpp
Browse files Browse the repository at this point in the history
  • Loading branch information
haohanyang committed Nov 6, 2024
1 parent cb70092 commit cc7ed7f
Show file tree
Hide file tree
Showing 3 changed files with 116 additions and 21 deletions.
44 changes: 44 additions & 0 deletions phreeqc-stubs/__init__.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
from typing import List


class Phreeqc:
def __init__(self) -> None:
"""
Create a Phreeqc instance.
"""
...

def get_selected_output_string(self) -> str: ...

def load_database(self, path: str) -> None:
"""
Load the specified database file into phreeqc.
:param path: The path of the phreeqc database to load. The full path (or relative path \
with respect to the working directory) will be required if the file is not in the current working directory
"""
...

def run_file(self, path: str) -> None:
"""
Runs the specified phreeqc input file.
:param path: The path of the phreeqc input file to run.
"""
...

def run_string(self, input: str) -> None:
"""
Runs the specified string as input to phreeqc.
:param input: String containing phreeqc input.
"""
...

def get_selected_output(self) -> List[List]:
"""
Get the selected output.
:return: A 2d-array consisting of each row from the selected output
"""
...
24 changes: 16 additions & 8 deletions setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,8 @@ def build_extension(self, ext: CMakeExtension) -> None:
# Using this requires trailing slash for auto-detection & inclusion of
# auxiliary "native" libs

debug = int(os.environ.get("DEBUG", 0)) if self.debug is None else self.debug
debug = int(os.environ.get("DEBUG", 0)
) if self.debug is None else self.debug
cfg = "Debug" if debug else "Release"

# CMake lets you override the generator - we need to check this.
Expand All @@ -55,10 +56,12 @@ def build_extension(self, ext: CMakeExtension) -> None:
# Adding CMake arguments set as environment variable
# (needed e.g. to build for ARM OSx on conda-forge)
if "CMAKE_ARGS" in os.environ:
cmake_args += [item for item in os.environ["CMAKE_ARGS"].split(" ") if item]
cmake_args += [
item for item in os.environ["CMAKE_ARGS"].split(" ") if item]

# In this example, we pass in the version to C++. You might not need to.
cmake_args += [f"-DEXAMPLE_VERSION_INFO={self.distribution.get_version()}"]
cmake_args += [f"-DEXAMPLE_VERSION_INFO={
self.distribution.get_version()}"]

if self.compiler.compiler_type != "msvc":
# Using Ninja-build since it a) is available as a wheel and b)
Expand All @@ -73,14 +76,16 @@ def build_extension(self, ext: CMakeExtension) -> None:
ninja_executable_path = Path(ninja.BIN_DIR) / "ninja"
cmake_args += [
"-GNinja",
f"-DCMAKE_MAKE_PROGRAM:FILEPATH={ninja_executable_path}",
f"-DCMAKE_MAKE_PROGRAM:FILEPATH={
ninja_executable_path}",
]
except ImportError:
pass

else:
# Single config generators are handled "normally"
single_config = any(x in cmake_generator for x in {"NMake", "Ninja"})
single_config = any(
x in cmake_generator for x in {"NMake", "Ninja"})

# CMake allows an arch-in-generator style for backward compatibility
contains_arch = any(x in cmake_generator for x in {"ARM", "Win64"})
Expand All @@ -102,7 +107,8 @@ def build_extension(self, ext: CMakeExtension) -> None:
# Cross-compile support for macOS - respect ARCHFLAGS if set
archs = re.findall(r"-arch (\S+)", os.environ.get("ARCHFLAGS", ""))
if archs:
cmake_args += ["-DCMAKE_OSX_ARCHITECTURES={}".format(";".join(archs))]
cmake_args += [
"-DCMAKE_OSX_ARCHITECTURES={}".format(";".join(archs))]

# Set CMAKE_BUILD_PARALLEL_LEVEL to control the parallel build level
# across all generators.
Expand Down Expand Up @@ -132,10 +138,12 @@ def build_extension(self, ext: CMakeExtension) -> None:
version="0.0.1",
author="Haohan Yang",
description="Python bindings for PHREEQC Version 3",
long_description="",
long_description="Python bindings for PHREEQC Version 3",
packages=["phreeqc-stubs"],
package_data={"phreeqc-stubs": ["*.pyi"]},
ext_modules=[CMakeExtension("phreeqc")],
cmdclass={"build_ext": CMakeBuild},
zip_safe=False,
extras_require={"test": ["pytest>=6.0"]},
python_requires=">=3.7",
)
)
69 changes: 56 additions & 13 deletions src/main.cpp
Original file line number Diff line number Diff line change
@@ -1,25 +1,27 @@
#include <exception>
#include <pybind11/pybind11.h>
#include "IPhreeqc.h"
#include "IPhreeqc.hpp"

namespace py = pybind11;

struct Phreeqc
{
Phreeqc()
{
int res = CreateIPhreeqc();
if (res < 0)
instance = new IPhreeqc();
}

~Phreeqc()
{
if (instance != nullptr)
{
throw std::runtime_error("Failed to create an IPhreeqc instance");
delete instance;
}

id = res;
}

void loadDatabase(const char *path)
{
int errors = LoadDatabase(id, path);
int errors = instance->LoadDatabase(path);
if (errors > 0)
{
throw std::runtime_error("Failed to load database");
Expand All @@ -28,7 +30,7 @@ struct Phreeqc

void runString(const char *input)
{
int errors = RunString(id, input);
int errors = instance->RunString(input);
if (errors > 0)
{
throw std::runtime_error("Failed to run string");
Expand All @@ -37,19 +39,60 @@ struct Phreeqc

void runFile(const char *path)
{
int errors = RunFile(id, path);
int errors = instance->RunFile(path);
if (errors > 0)
{
throw std::runtime_error("Failed to run path");
}
}

const char *getSelectedOutputString()
const py::list getSelectedOutput()
{
return GetSelectedOutputString(id);
py::list output;

VAR var;
VarInit(&var);

const int colCount = instance->GetSelectedOutputColumnCount();
const int rowCount = instance->GetSelectedOutputRowCount();

for (int row = 0; row < rowCount; row++)
{
py::list rowData;
for (int col = 0; col < colCount; col++)
{
if (instance->GetSelectedOutputValue(row, col, &var) != VR_OK)
{
rowData.append(py::str("error"));
}
else
{
if (var.type == TT_LONG)
{
rowData.append(py::int_(var.lVal));
}
else if (var.type == TT_DOUBLE)
{
rowData.append(py::float_(var.dVal));
}
else if (var.type == TT_STRING)
{
rowData.append(py::str(var.sVal));
}
else
{
rowData.append(py::none());
}
}
}

output.append(rowData);
}

return output;
}

int id;
IPhreeqc *instance;
};

PYBIND11_MODULE(phreeqc, m)
Expand All @@ -60,5 +103,5 @@ PYBIND11_MODULE(phreeqc, m)
.def("load_database", &Phreeqc::loadDatabase)
.def("run_string", &Phreeqc::runString)
.def("run_file", &Phreeqc::runFile)
.def("get_selected_output_string", &Phreeqc::getSelectedOutputString);
.def("get_selected_output", &Phreeqc::getSelectedOutput);
}

0 comments on commit cc7ed7f

Please sign in to comment.