Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
Bliss
bliss
Commits
e23eeae8
Commit
e23eeae8
authored
Jan 02, 2021
by
Matias Guijarro
Browse files
axis: move "pre_move" hook logic to hook.py, generic "execute_pre_hooks" context manager
parent
1ead07a4
Changes
2
Hide whitespace changes
Inline
Side-by-side
bliss/common/axis.py
View file @
e23eeae8
...
...
@@ -11,6 +11,7 @@ Axis related classes (:class:`~bliss.common.axis.Axis`, \
and :class:`~bliss.common.axis.GroupMove`)
"""
from
bliss
import
global_map
from
bliss.common.hook
import
execute_pre_move_hooks
from
bliss.common.protocols
import
Scannable
from
bliss.common.cleanup
import
capture_exceptions
from
bliss.common.motor_config
import
MotorConfig
...
...
@@ -31,6 +32,7 @@ import sys
import
math
import
functools
import
collections
import
itertools
import
numpy
from
unittest
import
mock
import
warnings
...
...
@@ -114,55 +116,11 @@ class GroupMove:
self
.
_stop_motion
=
stop_motion
self
.
_interrupted_move
=
False
hooks
=
collections
.
defaultdict
(
list
)
executed_hooks
=
dict
()
axes
=
set
()
hooked_axes
=
set
()
for
motions
in
motions_dict
.
values
():
for
motion
in
motions
:
axis
=
motion
.
axis
axes
.
add
(
axis
)
# group motion hooks
for
hook
in
axis
.
motion_hooks
:
hooks
[
hook
].
append
(
motion
)
with
capture_exceptions
(
raise_index
=
0
)
as
capture
:
for
hook
,
motions
in
hooks
.
items
():
hooked_axes
.
union
({
m
.
axis
for
m
in
motions
})
with
capture
():
hook
.
_init
()
hook
.
pre_move
(
motions
)
executed_hooks
[
hook
]
=
motions
if
capture
.
failed
:
# something wrong happened with this hook:
# let's call post_move for all executed hooks so far
# (including this one), in reversed order
for
hook
,
motions
in
reversed
(
list
(
executed_hooks
.
items
())):
with
capture
():
hook
.
post_move
(
motions
)
return
# now check if axes are ready ;
# the check happens after pre_move hooks execution,
# some axes can **become** ready thanks to the hook
with
capture_exceptions
(
raise_index
=
0
)
as
capture
:
for
axis
in
axes
:
with
capture
():
axis
.
_check_ready
()
if
capture
.
failed
:
# this axis _check_ready() had a problem:
# need to ensure post_move hook is called,
# if the pre_move was executed
for
hook
in
reversed
(
axis
.
motion_hooks
):
motions
=
executed_hooks
.
get
(
hook
)
if
motions
:
with
capture
():
hook
.
post_move
(
motions
)
return
# motions_dict is { controller: [motion, ...] }
all_motions
=
list
(
itertools
.
chain
(
*
motions_dict
.
values
()))
with
execute_pre_move_hooks
(
all_motions
):
for
axis
in
(
m
.
axis
for
m
in
all_motions
):
axis
.
_check_ready
()
for
controller
,
motions
in
motions_dict
.
items
():
if
prepare_motion
is
not
None
:
...
...
bliss/common/hook.py
View file @
e23eeae8
...
...
@@ -8,14 +8,64 @@
"""Base hook system. Check the doc to find
how to use motion hooks in your system"""
import
sys
import
weakref
import
functools
import
itertools
import
collections
import
contextlib
from
bliss.common.logtools
import
*
from
bliss
import
global_map
__all__
=
[
"MotionHook"
]
def
group_hooks
(
axes
):
hooks
=
collections
.
defaultdict
(
list
)
for
axis
in
axes
:
for
hook
in
axis
.
motion_hooks
:
hooks
[
hook
].
append
(
axis
)
return
hooks
@
contextlib
.
contextmanager
def
execute_pre_hooks
(
hooks_dict
,
pre_method_name
,
post_method_name
):
# hooks_dict is { hook: [item, ...] }
# each hook is executed by calling its "pre" method, with item list as argument ;
# in case of error "post" methods are executed with same arguments
executed_hooks
=
{}
try
:
for
hook
,
arg
in
hooks_dict
.
items
():
try
:
hook
.
_init
()
getattr
(
hook
,
pre_method_name
)(
arg
)
except
BaseException
:
raise
finally
:
executed_hooks
[
hook
]
=
arg
yield
except
BaseException
:
if
post_method_name
:
# let's call post_move for all executed hooks so far
# (including this one), in reversed order
for
hook
,
arg
in
reversed
(
list
(
executed_hooks
.
items
())):
try
:
getattr
(
hook
,
post_method_name
)(
arg
)
except
BaseException
:
sys
.
excepthook
(
*
sys
.
exc_info
())
raise
@
contextlib
.
contextmanager
def
execute_pre_move_hooks
(
motions
):
hooks
=
{
hook
:
[
m
for
m
in
motions
if
m
.
axis
in
hook_axes
]
for
hook
,
hook_axes
in
group_hooks
(
m
.
axis
for
m
in
motions
).
items
()
}
with
execute_pre_hooks
(
hooks
,
"pre_move"
,
"post_move"
):
yield
class
MotionHook
:
"""
Base motion hook. Executed before a motion starts and after motion ends.
...
...
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment