Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Axis Caproto IOC #13

Merged
merged 3 commits into from
May 23, 2024
Merged
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Next Next commit
Implement Axis Caproto IOC
mrakitin committed May 23, 2024

Verified

This commit was created on GitHub.com and signed with GitHub’s verified signature. The key has expired.
commit a2fc5db7ea5e2792143bbf273e92b589aaa56a51
1 change: 1 addition & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
@@ -35,6 +35,7 @@ dependencies = [
"h5py",
"numpy",
"ophyd",
"pillow",
"pyepics", # does not work with 'setuptools' version higher than v66.1.1
"scikit-image[data]",
]
1 change: 1 addition & 0 deletions src/srx_caproto_iocs/axis/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
""""Axis Cameras Caproto IOC code."""
99 changes: 99 additions & 0 deletions src/srx_caproto_iocs/axis/caproto_ioc.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
from __future__ import annotations

import requests
from PIL import Image, ImageFont, ImageDraw
from io import BytesIO

import textwrap
from enum import Enum

from caproto import ChannelType
from caproto.server import pvproperty, run, template_arg_parser

from ..base import CaprotoSaveIOC, check_args
from ..utils import now, save_image

DEFAULT_MAX_LENGTH = 10_000_000


class AxisSaveIOC(CaprotoSaveIOC):
"""Axis caproto save IOC."""

common_kwargs = {"max_length": 255, "string_encoding": "utf-8"}

key1 = pvproperty(
value="",
string_encoding="utf-8",
dtype=ChannelType.CHAR,
doc="key 1 for data 1",
max_length=255,
)
data1 = pvproperty(
value=0,
dtype=ChannelType.DOUBLE,
doc="data 1",
max_length=DEFAULT_MAX_LENGTH,
)

def __init__(self, *args, camera_host=None, **kwargs):
self._camera_host = camera_host
print(f"{camera_host = }")
super().__init__(*args, **kwargs)

async def _get_current_dataset(
self, *args, **kwargs
):
url = f"http://{self._camera_host}/axis-cgi/jpg/image.cgi"
resp = requests.get(url)
img = Image.open(BytesIO(resp.content))

dataset = img
print(f"{now()}:\n{dataset.size}")

return dataset

@staticmethod
def saver(request_queue, response_queue):
"""The saver callback for threading-based queueing."""
while True:
received = request_queue.get()
filename = received["filename"]
data = received["data"]
# 'frame_number' is not used for this exporter.
frame_number = received["frame_number"] # noqa: F841
try:
save_image(fname=filename, data=data, file_format="jpeg", mode="x")
print(f"{now()}: saved data into:\n {filename}")

success = True
error_message = ""
except Exception as exc: # pylint: disable=broad-exception-caught
success = False
error_message = exc
print(
f"Cannot save file {filename!r} due to the following exception:\n{exc}"
)

response = {"success": success, "error_message": error_message}
response_queue.put(response)


if __name__ == "__main__":
parser, split_args = template_arg_parser(
default_prefix="", desc=textwrap.dedent(AxisSaveIOC.__doc__)
)

parser.add_argument(
"-c", "--camera-host",
help="The camera hostname, e.g., 'xf06bm-cam5'",
required=True,
type=str,
)

ioc_options, run_options = check_args(parser, split_args)

print(f"{ioc_options = }")
print(f"{run_options = }")

ioc = AxisSaveIOC(camera_host=parser.parse_args().camera_host, **ioc_options)
run(ioc.pvdb, **run_options)
4 changes: 4 additions & 0 deletions src/srx_caproto_iocs/utils.py
Original file line number Diff line number Diff line change
@@ -15,6 +15,10 @@ def now(as_object=False):
return _now.isoformat()


def save_image(fname, data, file_format="jpeg", mode="x"):
data.save(fname, file_format=file_format)


def save_hdf5_zebra(
fname,
data,