• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

Open-Sn / opensn / 24923222905

24 Apr 2026 12:38PM UTC coverage: 74.824% (-0.002%) from 74.826%
24923222905

push

github

web-flow
Merge pull request #1031 from andrsd/anon-ns

Enforce the use of anonymous namespace for internal linkage

28 of 29 new or added lines in 3 files covered. (96.55%)

2 existing lines in 2 files now uncovered.

21220 of 28360 relevant lines covered (74.82%)

66140591.16 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

35.23
/python/lib/context.cc
1
// SPDX-FileCopyrightText: 2025 The OpenSn Authors <https://open-sn.github.io/opensn/>
2
// SPDX-License-Identifier: MIT
3

4
#include "python/lib/py_wrappers.h"
5
#include "python/lib/py_env.h"
6
#include "framework/logging/log.h"
7
#include "framework/runtime.h"
8
#include "caliper/cali.h"
9
#include "petscsys.h"
10
#include <pybind11/eval.h>
11
#include <stdexcept>
12

13
namespace opensn
14
{
15

16
namespace
17
{
18

19
// Wrap Finalize
20
void
21
WrapFinalize(py::module& context)
72✔
22
{
23
  // clang-format off
24
  // finalize
25
  context.def(
72✔
26
    "Finalize",
27
    []()
72✔
28
    {
29
      PyEnv::p_default_env.reset();
×
30
    },
×
31
    R"(
32
    Finalize OpenSn context.
33

34
    This function can only be invoked **once at the end of the runtime process**.
35

36
    In standard Python module mode, the context is automatically finalized when the interpreter ends
37
    the lifecycle of variables. However, in environments like IPython within Jupyter, functions
38
    registered with `atexit` may not be executed.
39

40
    In such cases, users must explicitly call this finalize function followed by MPI Finalize to
41
    properly terminate the context; otherwise, an MPI error will occur. This process can be
42
    registered to the ``post_execute`` event of IPython console as follows:
43

44
    .. code-block::
45

46
       from IPython import get_ipython
47

48
       def finalize_env():
49
           Finalize()
50
           MPI.Finalize()
51

52
       ipython_instance = get_ipython()
53
       if ipython_instance is not None:
54
           ipython_instance.events.register("post_execute", finalize_env)
55

56
    This approach allows the module to safely execute the Python script generated by ``nbconvert``.
57
    )"
58
  );
59
  // clang-format on
60
}
72✔
61

62
// Wrap settings
63
void
64
WrapSettings(py::module& context)
72✔
65
{
66
  // clang-format off
67
  // log settings
68
  context.def(
72✔
69
    "SetVerbosityLevel",
70
    [](unsigned int level)
72✔
71
    {
72
      log.SetVerbosity(level);
×
73
    },
74
    "Set verbosity level (0 to 3). Default is 0.",
75
    py::arg("level")
72✔
76
  );
77
  context.def(
72✔
78
    "UseColor",
79
    [](bool cfg)
72✔
80
    {
81
      suppress_color = (!cfg);
39✔
82
    },
83
    "Enable/disable color output. Default is True.",
84
    py::arg("config") = true
72✔
85
  );
86
  // PETSc error handler
87
  context.def(
72✔
88
    "EnablePETScErrorHandler",
89
    []()
72✔
90
    {
91
      ::PetscOptionsSetValue(nullptr, "-no_signal_handler", "false");
×
92
    },
93
    "Allow PETSc error handler."
94
  );
95
  // Caliper reporting
96
  context.def(
72✔
97
    "SetCaliperConfig",
98
    [](const std::string& config)
72✔
99
    {
100
      if (use_caliper)
×
101
      {
102
        throw std::runtime_error("This function can only be called before enabling Cailper.");
×
103
      }
104
      cali_config = config;
×
105
    },
×
106
    R"(
107
    Set configuration to the Caliper manager.
108

109
    This function can only be called before using :py:func:`pyopensn.context.EnableCaliper`. Note
110
    that this function does not start the Caliper manager immediately.
111

112
    Parameters
113
    ----------
114
    config: str, default='runtime-report(calc.inclusive=true),max_column_width=80'
115
        Configuration.
116
    )",
117
    py::arg("config") = "runtime-report(calc.inclusive=true),max_column_width=80"
72✔
118
  );
119
  context.def(
72✔
120
    "EnableCaliper",
121
    []()
72✔
122
    {
123
      // check if caliper is already initialized
124
      if (use_caliper)
×
125
      {
126
        throw std::runtime_error("Caliper is already set.");
×
127
      }
128
      use_caliper = true;
×
129
      // initialize Caliper
130
      cali_mgr.add(cali_config.c_str());
×
131
      cali_set_global_string_byname("opensn.version", GetVersionStr().c_str());
×
132
      cali_set_global_string_byname("opensn.input", input_path.c_str());
×
133
      cali_mgr.start();
×
134
    },
×
135
    R"(
136
    Start the Caliper manager and mark the program begin.
137
    )"
138
  );
139
  // clang-format on
140
}
72✔
141

142
// Wrap sys.argv translator
143
void
144
WrapSysArgv(py::module& context)
72✔
145
{
146
  // clang-format off
147
  context.def(
144✔
148
    "InitializeWithArgv",
149
    [](py::list sys_argv)
72✔
150
    {
151
      // looping over each argument of the list
152
      for (int i_arg = 0; i_arg < sys_argv.size(); ++i_arg)
×
153
      {
154
        // skip for the first argument (Python script name)
155
        if (i_arg == 0)
×
156
        {
157
          continue;
×
158
        }
159
        // cast argument to string
160
        auto arg = sys_argv[i_arg].cast<std::string>();
×
161
        // color
162
        if (arg == "-c" || arg == "--suppress-color")
×
163
        {
164
          suppress_color = true;
×
165
          continue;
×
166
        }
167
        // verbosity
168
        if (arg == "-v" || arg == "--verbose")
×
169
        {
170
          auto next_arg = sys_argv[++i_arg].cast<std::string>();
×
171
          log.SetVerbosity(std::atoi(next_arg.c_str()));
×
172
          continue;
×
173
        }
×
174
        // caliper
175
        if (arg == "--caliper")
×
176
        {
177
          auto next_arg = sys_argv[++i_arg].cast<std::string>();
×
178
          use_caliper = true;
×
179
          cali_config = next_arg;
×
180
          cali_mgr.add(cali_config.c_str());
×
181
          cali_set_global_string_byname("opensn.version", GetVersionStr().c_str());
×
182
          cali_set_global_string_byname("opensn.input", input_path.c_str());
×
183
          cali_mgr.start();
×
184
          continue;
×
UNCOV
185
        }
×
186
        // PETSc handler
187
        if (arg == "--allow-petsc-error-handler")
×
188
        {
189
          ::PetscOptionsSetValue(nullptr, "-no_signal_handler", "false");
×
190
          continue;
×
191
        }
192
        // execute Python statement
193
        if (arg == "--py")
×
194
        {
195
          auto next_arg = sys_argv[++i_arg].cast<std::string>();
×
196
          try
×
197
          {
198
            py::exec(next_arg);
×
199
          }
200
          catch (py::error_already_set& e)
×
201
          {
202
            py::object exc_type = e.type();
×
203
            std::string type_name = py::str(exc_type.attr("__name__"));
×
204
            log.LogAllError() << "Caught an exception of type: [" << type_name
×
205
              << "] when executing code of the sys.argv.\nException message: " << e.what() << "\n";
×
206
            e.restore();
×
207
          }
×
208
          continue;
×
209
        }
×
210
        // throw error for invalid argument
211
        throw std::runtime_error("Invalid argument: " + arg + "\n");
×
212
      }
×
213
    },
×
214
    R"(
215
    Overwrite OpenSn settings using ``sys.argv``.
216

217
    This is a temporary solution for dealing with command line argument mode of the console. Once
218
    the console is gone, this functionality will also be killed.
219

220
    Parameters
221
    ----------
222
    sys_argv: List[str], default=sys.argv
223
        Argument vector to be used. Default to ``sys.argv``.
224
    )",
225
    py::arg_v("sys_argv", py::module::import("sys").attr("argv").cast<py::list>(), "sys.argv")
216✔
226
  );
227
  // clang-format on
228
}
72✔
229

230
} // namespace
231

232
// Wrap the context components of OpenSn
233
void
234
py_context(py::module& pyopensn)
72✔
235
{
236
  py::module context = pyopensn.def_submodule("context", "Context manager module.");
72✔
237
  WrapFinalize(context);
72✔
238
  WrapSettings(context);
72✔
239
  WrapSysArgv(context);
72✔
240
}
72✔
241

242
} // namespace opensn
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc