Coverage for src/backend/InvenTree/plugin/samples/integration/transition.py: 0%

38 statements  

« prev     ^ index     » next       coverage.py v7.15.2, created at 2026-10-07 17:47 +0000

1"""Sample implementation of state transition implementation.""" 

2 

3import warnings 

4 

5from django.core.exceptions import ValidationError 

6 

7from common.notifications import trigger_notification 

8from generic.states import TransitionMethod 

9from order.models import ReturnOrder 

10from order.status_codes import ReturnOrderStatus 

11from plugin import InvenTreePlugin 

12from plugin.mixins import SettingsMixin, TransitionMixin 

13 

14 

15class SampleTransitionPlugin(TransitionMixin, InvenTreePlugin): 

16 """A sample plugin which shows how state transitions might be implemented.""" 

17 

18 NAME = 'SampleTransitionPlugin' 

19 SLUG = 'sample-transition' 

20 

21 class ReturnChangeHandler(TransitionMethod): 

22 """Transition method for ReturnOrder objects.""" 

23 

24 def transition( 

25 self, current_state, target_state, instance, default_action, **kwargs 

26 ) -> bool: 

27 """Example override function for state transition.""" 

28 # Only act on ReturnOrders that should be completed 

29 if ( 

30 not isinstance(instance, ReturnOrder) 

31 or target_state != ReturnOrderStatus.COMPLETE.value 

32 ): 

33 return False 

34 

35 # Only allow proceeding if the return order has a responsible user assigned 

36 if not instance.responsible: 

37 msg = 'Return order without responsible owner can not be completed!' 

38 

39 # Trigger whoever created the return order 

40 instance.created_by 

41 trigger_notification( 

42 instance, 

43 'sampel_123_456', 

44 targets=[instance.created_by], 

45 context={'message': msg}, 

46 ) 

47 

48 raise ValidationError(msg) 

49 

50 return False # Do not act 

51 

52 TRANSITION_HANDLERS = [ReturnChangeHandler()] 

53 

54 

55class BrokenTransitionPlugin(SettingsMixin, TransitionMixin, InvenTreePlugin): 

56 """An intentionally broken plugin to test error handling.""" 

57 

58 NAME = 'BrokenTransitionPlugin' 

59 SLUG = 'sample-broken-transition' 

60 

61 SETTINGS = { 

62 'BROKEN_GET_METHOD': { 

63 'name': 'Broken Get Method', 

64 'description': 'If set, the get_transition_handlers method will raise an error.', 

65 'validator': bool, 

66 'default': False, 

67 }, 

68 'WRONG_RETURN_TYPE': { 

69 'name': 'Wrong Return Type', 

70 'description': 'If set, the get_transition_handlers method will return an incorrect type.', 

71 'validator': bool, 

72 'default': False, 

73 }, 

74 'WRONG_RETURN_VALUE': { 

75 'name': 'Wrong Return Value', 

76 'description': 'If set, the get_transition_handlers method will return an incorrect value.', 

77 'validator': bool, 

78 'default': False, 

79 }, 

80 } 

81 

82 @property 

83 def has_transition_handlers(self) -> bool: 

84 """Ensure that this plugin always has handlers.""" 

85 return True 

86 

87 def get_transition_handlers(self) -> list[TransitionMethod]: 

88 """Return transition handlers for the given instance.""" 

89 warnings.warn( 

90 'get_transition_handlers is intentionally broken in this plugin', 

91 stacklevel=2, 

92 ) 

93 

94 if self.get_setting('BROKEN_GET_METHOD', backup_value=False, cache=False): 

95 raise ValueError('This is a broken transition plugin!') 

96 

97 if self.get_setting('WRONG_RETURN_TYPE', backup_value=False, cache=False): 

98 return 'This is not a list of handlers!' 

99 

100 if self.get_setting('WRONG_RETURN_VALUE', backup_value=False, cache=False): 

101 return [1, 2, 3] 

102 

103 # Return a valid handler list (empty) 

104 return []