Skip to content

Commit

Permalink
Add option --require-all-thermistors
Browse files Browse the repository at this point in the history
  • Loading branch information
albireox committed Oct 8, 2024
1 parent c6908bc commit c44d3dc
Show file tree
Hide file tree
Showing 7 changed files with 51 additions and 3 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,10 @@

## Next version

### 🚀 New

* Add option `--require-all-thermistors`. When passed, the thermistors don't close the valve when they become active. Once all thermistors are active, the valves are all closed at the same time. This can potentially prevent overpressures in the last one or two cryostat being filled as the other valves close.

### ✨ Improved

* Improve handling of keyboard interrupt during post-processing.
Expand Down
13 changes: 13 additions & 0 deletions src/lvmcryo/__main__.py
Original file line number Diff line number Diff line change
Expand Up @@ -157,10 +157,22 @@ async def ln2(
bool,
Option(
" /--no-use-thermistors",
envvar="LVMCRYO_USE_THERMISTORS",
help="Use thermistor values to determine purge/fill time.",
rich_help_panel="Purge and fill options",
),
] = True,
require_all_thermistors: Annotated[
bool,
Option(
"--require-all-thermistors",
envvar="LVMCRYO_REQUIRE_ALL_THERMISTORS",
help="If set, waits until all thermistors have activated before closing "
"any of the valves. This prevents overpressures in the cryostats when only"
"some of the valves are open. Ignore if --no-use-thermistors is used. ",
rich_help_panel="Purge and fill options",
),
] = False,
check_pressures: Annotated[
bool,
Option(
Expand Down Expand Up @@ -421,6 +433,7 @@ async def ln2(
email=email,
email_level=email_level,
use_thermistors=use_thermistors,
require_all_thermistors=require_all_thermistors,
check_pressures=check_pressures,
check_temperatures=check_temperatures,
max_pressure=max_pressure,
Expand Down
1 change: 1 addition & 0 deletions src/lvmcryo/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@ class Config(BaseModel):
dry_run: bool = False

use_thermistors: bool = True
require_all_thermistors: bool=False
check_pressures: bool = True
check_temperatures: bool = True
max_pressure: float | None = None
Expand Down
14 changes: 14 additions & 0 deletions src/lvmcryo/handlers/ln2.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@

from lvmopstools.devices.specs import spectrograph_pressures, spectrograph_temperatures
from lvmopstools.devices.thermistors import read_thermistors
from sdsstools.utils import GatheringTaskGroup

from lvmcryo.config import ValveConfig, get_internal_config
from lvmcryo.handlers.thermistor import ThermistorMonitor
Expand Down Expand Up @@ -347,6 +348,7 @@ async def fill(
self,
cameras: list[str] | None = None,
use_thermistors: bool = True,
require_all_thermistors: bool = False,
min_fill_time: float | None = None,
max_fill_time: float | None = None,
prompt: bool | None = None,
Expand All @@ -360,6 +362,9 @@ async def fill(
used to instantiate the `.LN2Handler` instance.
use_thermistors
Whether to use the thermistors to close the valves.
require_all_thermistors
Whether to require all thermistors to be active before closing the
valves. If `False`, valves as closed as their thermistors become active.
min_fill_time
The minimum time to keep the fill valves open. Only relevant if
using the thermistors.
Expand Down Expand Up @@ -391,6 +396,7 @@ async def fill(
min_open_time=min_fill_time or 0.0,
max_open_time=max_fill_time,
use_thermistor=use_thermistors,
close_on_active=not require_all_thermistors,
)
)

Expand All @@ -417,6 +423,14 @@ async def fill(
raise

finally:
if use_thermistors and require_all_thermistors:
# If we are waiting for all thermistors to be active,
# we need to close all valves now.
self.log.info("Closing all valves.")
async with GatheringTaskGroup() as group:
for valve_handler in self.valve_handlers.values():
group.create_task(valve_handler._set_state(False))

self.event_times.fill_complete = get_now()
if prompt:
sshkeyboard.stop_listening()
Expand Down
11 changes: 10 additions & 1 deletion src/lvmcryo/handlers/thermistor.py
Original file line number Diff line number Diff line change
Expand Up @@ -130,6 +130,8 @@ def __post_init__(self):
self.log = self.valve_handler.log

self.thermistor_monitor = ThermistorMonitor(interval=self.monitoring_interval)

self.active: bool = False
self.first_active: datetime | None = None

async def start_monitoring(self):
Expand Down Expand Up @@ -262,10 +264,17 @@ async def start_monitoring(self):
f"Thermistor {self.channel!r} has been active for more than "
f"{elapsed_active:.1f} seconds."
)
self.active = True

if self.close_valve:
self.valve_handler.log.debug(
f"Closing valve {self.valve_handler.valve!r} "
"due to thermistor feedback."
)
await self.valve_handler.finish()
else:
self.valve_handler.log.warning(
f"Thermistor {self.channel!r} is active. Calling "
"ValveHandler.finish() but not closing the valve."
)

await self.valve_handler.finish(close_valve=self.close_valve)
10 changes: 8 additions & 2 deletions src/lvmcryo/handlers/valve.py
Original file line number Diff line number Diff line change
Expand Up @@ -224,6 +224,7 @@ async def start_fill(
min_open_time: float = 0.0,
max_open_time: float | None = None,
use_thermistor: bool = True,
close_on_active: bool = True,
):
"""Starts a fill.
Expand All @@ -238,6 +239,9 @@ async def start_fill(
Whether to use the thermistor to close the valve. If ``True`` and
``fill_time`` is not ``None``, ``fill_time`` become the maximum
open time.
close_on_active
If ``use_thermistor=True``, closes the valve when the thermistor becomes
active. Otherwise just blocks while the thermistor is inactive.
"""

Expand All @@ -260,6 +264,7 @@ async def start_fill(
self.thermistor = ThermistorHandler(
self,
channel=thermistor_channel,
close_valve=close_on_active,
**self.thermistor_info,
)
self.thermistor.min_open_time = min_open_time
Expand Down Expand Up @@ -294,10 +299,11 @@ async def _schedule_timeout(self, timeout: float):
await asyncio.sleep(timeout)
await self.finish(did_timeout=True)

async def finish(self, did_timeout: bool = False):
async def finish(self, close_valve: bool = True, did_timeout: bool = False):
"""Finishes the fill, closing the valve."""

await self._set_state(False, did_timeout=did_timeout)
if close_valve:
await self._set_state(False, did_timeout=did_timeout)

self._monitor_task = await cancel_task(self._monitor_task)
self._timeout_task = await cancel_task(self._timeout_task)
Expand Down
1 change: 1 addition & 0 deletions src/lvmcryo/runner.py
Original file line number Diff line number Diff line change
Expand Up @@ -134,6 +134,7 @@ async def ln2_runner(
max_fill_time = config.fill_time or config.max_fill_time
await handler.fill(
use_thermistors=config.use_thermistors,
require_all_thermistors=config.require_all_thermistors,
min_fill_time=config.min_fill_time,
max_fill_time=max_fill_time,
prompt=not config.no_prompt,
Expand Down

0 comments on commit c44d3dc

Please sign in to comment.