-
Notifications
You must be signed in to change notification settings - Fork 849
/
Copy pathraising-exceptions.sql
207 lines (182 loc) · 5.15 KB
/
raising-exceptions.sql
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
/*
An exploration into RAISE and RAISE_APPLICATION_ERROR
*/
-- Explicit Raise of System Exception
CREATE OR REPLACE PROCEDURE use_salary (salary_in IN NUMBER)
IS
BEGIN
IF salary_in < 0
THEN
RAISE VALUE_ERROR;
END IF;
END;
/
BEGIN
use_salary (salary_in => -1);
END;
/
-- Raise a User-Defined Exception
-- Which in this case simply "mimics" the pre-defined VALUE_ERROR exception and doesn't really add value.
CREATE OR REPLACE PROCEDURE use_salary (salary_in IN NUMBER)
IS
negative_salary EXCEPTION;
PRAGMA EXCEPTION_INIT (negative_salary, -6502);
BEGIN
IF salary_in < 0
THEN
RAISE negative_salary;
END IF;
END;
/
BEGIN
use_salary (salary_in => -1);
END;
/
-- Different Code for Different Error Conditions
-- All the exception handling logic "front loaded" into the executable section, making it harder to focus on the "positive" side of things: when nothing went wrong. Not a great way to write maintainable code.
CREATE OR REPLACE PROCEDURE use_salary (salary_in IN NUMBER)
IS
PROCEDURE notify_support (string_in IN VARCHAR2)
IS
BEGIN
-- Just a placeholder to make a point!
DBMS_OUTPUT.PUT_LINE ('Hey support, deal with THIS: ' || string_in);
END;
PROCEDURE notify_hr (string_in IN VARCHAR2)
IS
BEGIN
-- Just a placeholder to make a point!
DBMS_OUTPUT.PUT_LINE ('Hey HR, deal with THIS: ' || string_in);
END;
BEGIN
CASE
WHEN salary_in < 0
THEN
notify_support (
'Negative salary submitted ' || salary_in);
RAISE VALUE_ERROR;
WHEN salary_in > 10000
THEN
notify_support (
'Too large salary submitted ' || salary_in);
RAISE VALUE_ERROR;
WHEN salary_in < 100
THEN
notify_hr (
'No one should be treated so shabbily! ' || salary_in);
RAISE VALUE_ERROR;
ELSE
/* No problems, proceed with normal execution*/
NULL;
END CASE;
/* Rest of procedure */
END;
/
BEGIN
use_salary (salary_in => -1);
END;
/
-- Move Exception Handling Logic to Exception Section
-- Cleaner and easier to understand, debug and maintain.
CREATE OR REPLACE PROCEDURE use_salary (salary_in IN NUMBER)
IS
negative_salary EXCEPTION;
too_large_salary EXCEPTION;
too_small_salary EXCEPTION;
PROCEDURE notify_support (string_in IN VARCHAR2)
IS
BEGIN
-- Just a placeholder to make a point!
DBMS_OUTPUT.PUT_LINE ('Hey support, deal with THIS: ' || string_in);
END;
PROCEDURE notify_hr (string_in IN VARCHAR2)
IS
BEGIN
-- Just a placeholder to make a point!
DBMS_OUTPUT.PUT_LINE ('Hey HR, deal with THIS: ' || string_in);
END;
BEGIN
CASE
WHEN salary_in < 0 THEN RAISE negative_salary;
WHEN salary_in > 10000 THEN RAISE too_large_salary;
WHEN salary_in < 100 THEN RAISE too_small_salary;
ELSE NULL;
END CASE;
/* Rest of procedure */
EXCEPTION
WHEN negative_salary
THEN
notify_support (
'Negative salary submitted ' || salary_in);
RAISE VALUE_ERROR;
WHEN too_large_salary
THEN
notify_support (
'Too large salary submitted ' || salary_in);
RAISE VALUE_ERROR;
WHEN too_small_salary
THEN
notify_hr (
'No one should be treated so shabbily! ' || salary_in);
RAISE VALUE_ERROR;
END;
/
BEGIN
use_salary (salary_in => -1);
END;
/
-- Use RAISE_APPLICATION_ERROR for App-Specific Error Message
BEGIN
RAISE_APPLICATION_ERROR (-20000, 'Say whatever you want');
END;
/
CREATE OR REPLACE PROCEDURE use_salary (salary_in IN NUMBER)
IS
negative_salary EXCEPTION;
too_large_salary EXCEPTION;
too_small_salary EXCEPTION;
PROCEDURE notify_support (string_in IN VARCHAR2)
IS
BEGIN
-- Just a placeholder to make a point!
DBMS_OUTPUT.PUT_LINE ('Hey support, deal with THIS: ' || string_in);
END;
PROCEDURE notify_hr (string_in IN VARCHAR2)
IS
BEGIN
-- Just a placeholder to make a point!
DBMS_OUTPUT.PUT_LINE ('Hey HR, deal with THIS: ' || string_in);
END;
BEGIN
CASE
WHEN salary_in < 0 THEN RAISE negative_salary;
WHEN salary_in > 10000 THEN RAISE too_large_salary;
WHEN salary_in < 100 THEN RAISE too_small_salary;
ELSE NULL;
END CASE;
/* Rest of procedure */
EXCEPTION
WHEN negative_salary
THEN
notify_support (
'Negative salary submitted ' || salary_in);
RAISE_APPLICATION_ERROR (-20001,
'Negative salaries are not allowed. Please re-enter.');
WHEN too_large_salary
THEN
notify_support (
'Too large salary submitted ' || salary_in);
RAISE_APPLICATION_ERROR (-20001,
'We are not nearly that generous. Please re-enter.');
WHEN too_small_salary
THEN
notify_hr (
'No one should be treated so shabbily! ' || salary_in);
RAISE_APPLICATION_ERROR (-20001,
'C''mon, a person''s gotta eat! Please re-enter.');
END;
/
BEGIN
use_salary (salary_in => -1);
END;
/