summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHarald Demel <tuempl@gmail.com>2011-06-08 18:59:01 +0200
committerHarald Demel <tuempl@gmail.com>2011-06-08 18:59:01 +0200
commit0ece986c986c731fbbfc1ce920bd22f974537150 (patch)
treeb6c3925db7402377c4bfe7ec1df2dceaf7e7eec2
parent74d3a2b11e37f12085dadf40ecc91deb539bcf3b (diff)
parentcf31e1f2788869624a9a363f7579838ddae369a2 (diff)
downloadfoop-0ece986c986c731fbbfc1ce920bd22f974537150.tar.gz
foop-0ece986c986c731fbbfc1ce920bd22f974537150.tar.bz2
foop-0ece986c986c731fbbfc1ce920bd22f974537150.zip
Merge branch 'master' of git.manuel.mausz.at:/foop
-rw-r--r--.gitignore1
-rw-r--r--bank-eiffel/account.e134
-rw-r--r--bank-eiffel/application.e24
-rw-r--r--bank-eiffel/bank.e1120
-rw-r--r--bank-eiffel/bank.ecf16
-rw-r--r--bank-eiffel/bank_store.e48
-rw-r--r--bank-eiffel/person.e16
-rw-r--r--bank-eiffel/retiree.e9
-rw-r--r--bank-eiffel/retireeaccount.e37
-rw-r--r--bank-eiffel/student.e9
-rw-r--r--bank-eiffel/studentaccount.e37
-rw-r--r--bank-eiffel/tests/test_account.e249
-rw-r--r--bank-eiffel/tests/test_person.e79
13 files changed, 1581 insertions, 198 deletions
diff --git a/.gitignore b/.gitignore
index b1bee25..0df8baa 100644
--- a/.gitignore
+++ b/.gitignore
@@ -12,3 +12,4 @@ pacman-c++/*.pb.cc
12*-build-desktop 12*-build-desktop
13.*.swp 13.*.swp
14bank-eiffel/EIFGENs 14bank-eiffel/EIFGENs
15bank-eiffel/bank.data
diff --git a/bank-eiffel/account.e b/bank-eiffel/account.e
index 3ef7a8b..a6e30ef 100644
--- a/bank-eiffel/account.e
+++ b/bank-eiffel/account.e
@@ -1,31 +1,13 @@
1note
2 description: "Summary description for {ACCOUNT}."
3 author: ""
4 date: "$Date$"
5 revision: "$Revision$"
6
7class 1class
8 ACCOUNT 2 ACCOUNT
9 3
10create 4create
11 make 5 make
12 6
13-- TODO
14-- interest should defined by bank (via make?)
15-- add more checks to invariant (like balance >= creditline) ?
16-- check if balance is a getter and not a setter (doesn't has an assign)
17-- + check if authorized_signers is a getter and not a setter (it doesn't has an assign)
18-- -> if not: add a getter (via Result or so..) and move them to {NONE}
19-- much other stuff to test like: lower creditline so that balance will be invalid
20
21feature -- Access 7feature -- Access
22 8
23 transfer_minamount: REAL_64 assign set_transfer_minamount 9 balance: REAL_64
24 -- Mindestbetrag für jede Einzahlung, Auszahlung und Überweisung 10 -- Kontostand
25
26 authorized_signers: ARRAYED_SET [PERSON]
27 -- Zeichnungsberechtigte
28 attribute Result := ({like authorized_signers}).default end --| Remove line when Void Safety is properly set
29 11
30 creditline: REAL_64 assign set_creditline 12 creditline: REAL_64 assign set_creditline
31 -- Kreditrahmen 13 -- Kreditrahmen
@@ -36,25 +18,57 @@ feature -- Access
36 interest_debit: REAL_64 assign set_interest_debit 18 interest_debit: REAL_64 assign set_interest_debit
37 -- Sollverzinsung 19 -- Sollverzinsung
38 20
39 balance: REAL_64 21 transfer_minamount: REAL_64 assign set_transfer_minamount
40 -- Kontostand 22 -- Mindestbetrag fuer jede Einzahlung, Auszahlung und Ueberweisung
23
24feature {NONE} -- Implementation
25
26 range: detachable TUPLE [min: REAL_64; max: REAL_64]
27
28 creditline_range: attached like range
29 -- min/max for creditline
30
31 interest_deposit_range: attached like range
32 -- min/max for interest_deposit
33
34 interest_debit_range: attached like range
35 -- min/max for interest_debit
36
37 authorized_signers: ARRAYED_SET [PERSON]
38 -- Zeichnungsberechtigte
41 39
42feature {NONE} -- Initialization 40feature {NONE} -- Initialization
43 41
44 make (an_authorized_signer: PERSON) 42 make (an_authorized_signer: PERSON;
43 an_interest_deposit: like interest_deposit;
44 an_interest_debit: like interest_debit;
45 a_credit_line: like creditline;
46 an_interest_deposit_range: like interest_deposit_range;
47 an_interest_debit_range: like interest_debit_range;
48 a_credit_line_range: like creditline_range)
49 require
50 a_credit_line_range.min < a_credit_line_range.max
51 an_interest_debit_range.min < an_interest_debit_range.max
52 an_interest_deposit_range.min < an_interest_deposit_range.max
45 do 53 do
46 create authorized_signers.make(1) 54 create authorized_signers.make(1)
47 add_authorized_signer (an_authorized_signer) 55 add_authorized_signer (an_authorized_signer)
48 transfer_minamount := 2 56 creditline := a_credit_line
49 balance := 0 57 interest_debit := an_interest_debit
58 interest_deposit := an_interest_deposit
59 interest_deposit_range := an_interest_deposit_range
60 interest_debit_range := an_interest_debit_range
61 creditline_range := a_credit_line_range
62
63 set_default_transfer_minamount
64 balance := 0.0
50 end 65 end
51 66
52feature -- Basic operations 67feature -- Basic operations
53 68
54 deposit (an_amount: like transfer_minamount; an_authorized_signer: PERSON) 69 deposit (an_amount: like transfer_minamount; an_authorized_signer: PERSON)
55 require 70 require
56 an_authorized_signer_authorized: authorized_signers.has (an_authorized_signer) 71 an_authorized_signer_authorized: get_authorized_signers.has (an_authorized_signer)
57 an_amount_positive: an_amount > 0.0
58 transfer_minamount_ok: an_amount >= transfer_minamount 72 transfer_minamount_ok: an_amount >= transfer_minamount
59 do 73 do
60 balance := balance + an_amount 74 balance := balance + an_amount
@@ -65,50 +79,64 @@ feature -- Basic operations
65 79
66 withdraw (an_amount: like transfer_minamount; an_authorized_signer: PERSON) 80 withdraw (an_amount: like transfer_minamount; an_authorized_signer: PERSON)
67 require 81 require
68 an_authorized_signer_authorized: authorized_signers.has (an_authorized_signer) 82 an_authorized_signer_authorized: get_authorized_signers.has (an_authorized_signer)
69 an_amount_positive: an_amount > 0.0
70 transfer_minamount_ok: an_amount >= transfer_minamount 83 transfer_minamount_ok: an_amount >= transfer_minamount
84 balance_beneath_creditline: balance - an_amount >= creditline
71 do 85 do
72 balance := balance - an_amount 86 balance := balance - an_amount
73 ensure 87 ensure
88 balance_beneath_creditline: balance >= creditline
74 balance_decreased: balance < old balance 89 balance_decreased: balance < old balance
75 withdrawed: balance = old balance - an_amount 90 withdrawed: balance = old balance - an_amount
76 creditline_ok: balance >= creditline
77 end 91 end
78 92
79 transfer(an_amount: like transfer_minamount; an_authorized_signer: PERSON; an_account: like Current; another_authorized_signer: PERSON;) 93 transfer(an_amount: like transfer_minamount; an_authorized_signer: PERSON;
94 an_account: like Current; another_authorized_signer: PERSON)
80 require 95 require
81 an_account_attached: an_account /= Void 96 recipient_account_not_same: Current /= an_account
82 do 97 do
83 withdraw (an_amount, an_authorized_signer) 98 withdraw (an_amount, an_authorized_signer)
84 an_account.deposit (an_amount, another_authorized_signer) 99 an_account.deposit (an_amount, another_authorized_signer)
85 end 100 end
86 101
87 add_authorized_signer (an_authorized_signer: PERSON) 102 add_authorized_signer (an_authorized_signer: PERSON)
88 require
89 an_authorized_signer_attached: an_authorized_signer /= Void
90 an_authorized_signer_notinlist: not authorized_signers.has (an_authorized_signer)
91 do 103 do
92 authorized_signers.put (an_authorized_signer) 104 if not authorized_signers.has (an_authorized_signer) then
105 authorized_signers.put (an_authorized_signer)
106 end
93 ensure 107 ensure
94 authorized_signers_assigned: authorized_signers.has (an_authorized_signer) 108 authorized_signers_assigned: authorized_signers.has (an_authorized_signer)
95 end 109 end
96 110
97 remove_authorized_signer (an_authorized_signer: PERSON) 111 remove_authorized_signer (an_authorized_signer: PERSON)
98 require 112 require
99 an_authorized_signer_attached: an_authorized_signer /= Void 113 authorized_signer_exists: (get_authorized_signers.has (an_authorized_signer))
100 an_authorized_signer_inlist: authorized_signers.has (an_authorized_signer) 114 authorized_signers_not_empty: get_authorized_signers.count >= 2
101 authorized_signers_never_empty: authorized_signers.count >= 2
102 do 115 do
103 authorized_signers.prune (an_authorized_signer) 116 authorized_signers.prune (an_authorized_signer)
104 ensure 117 ensure
105 authorized_signers_assigned: not authorized_signers.has (an_authorized_signer) 118 authorized_signers_assigned: not authorized_signers.has (an_authorized_signer)
106 end 119 end
107 120
121 get_authorized_signers: FINITE [PERSON]
122 do
123 Result := authorized_signers
124 end
125
126 advance
127 do
128 if balance < 0.0 then
129 -- debit
130 balance := balance + (balance * interest_debit)
131 else
132 -- deposit
133 balance := balance + (balance * interest_deposit)
134 end
135 end
136
108feature {NONE} -- Implementation 137feature {NONE} -- Implementation
109 138
110 set_transfer_minamount (a_transfer_minamount: like transfer_minamount) 139 set_transfer_minamount (a_transfer_minamount: like transfer_minamount)
111 -- Assign `transfer_minamount' with `a_transfer_minamount'.
112 require 140 require
113 a_transfer_minamount_positive: a_transfer_minamount > 0.0 141 a_transfer_minamount_positive: a_transfer_minamount > 0.0
114 do 142 do
@@ -117,8 +145,15 @@ feature {NONE} -- Implementation
117 transfer_minamount_assigned: transfer_minamount = a_transfer_minamount 145 transfer_minamount_assigned: transfer_minamount = a_transfer_minamount
118 end 146 end
119 147
148 set_default_transfer_minamount
149 do
150 set_transfer_minamount (2.0)
151 end
152
120 set_creditline (a_creditline: like creditline) 153 set_creditline (a_creditline: like creditline)
121 -- Assign `creditline' with `a_creditline'. 154 require
155 a_creditline_within_bounds: a_creditline >= creditline_range.min
156 and a_creditline <= creditline_range.max
122 do 157 do
123 creditline := a_creditline 158 creditline := a_creditline
124 ensure 159 ensure
@@ -126,9 +161,9 @@ feature {NONE} -- Implementation
126 end 161 end
127 162
128 set_interest_deposit (an_interest_deposit: like interest_deposit) 163 set_interest_deposit (an_interest_deposit: like interest_deposit)
129 -- Assign `interest_deposit' with `an_interest_deposit'.
130 require 164 require
131 an_interest_deposit_within_bounds: an_interest_deposit >= 0.0 and an_interest_deposit <= 1.0 165 an_interest_deposit_within_bounds: interest_deposit >= interest_deposit_range.min
166 and interest_deposit <= interest_deposit_range.max
132 do 167 do
133 interest_deposit := an_interest_deposit 168 interest_deposit := an_interest_deposit
134 ensure 169 ensure
@@ -136,9 +171,9 @@ feature {NONE} -- Implementation
136 end 171 end
137 172
138 set_interest_debit (an_interest_debit: like interest_debit) 173 set_interest_debit (an_interest_debit: like interest_debit)
139 -- Assign `interest_debit' with `an_interest_debit'.
140 require 174 require
141 an_interest_debit_within_bounds: an_interest_debit >= 0.0 and an_interest_debit <= 1.0 175 an_interest_deposit_within_bounds: interest_debit >= interest_debit_range.min
176 and interest_debit <= interest_debit_range.max
142 do 177 do
143 interest_debit := an_interest_debit 178 interest_debit := an_interest_debit
144 ensure 179 ensure
@@ -146,9 +181,12 @@ feature {NONE} -- Implementation
146 end 181 end
147 182
148invariant 183invariant
149 interest_debit_within_bounds: interest_debit >= 0.0 and interest_debit <= 1.0
150 interest_deposit_within_bounds: interest_deposit >= 0.0 and interest_deposit <= 1.0
151 authorized_signers_attached: authorized_signers /= Void
152 authorized_signers_not_empty: authorized_signers.count > 0 184 authorized_signers_not_empty: authorized_signers.count > 0
153 transfer_minamount_positive: transfer_minamount > 0.0 185 transfer_minamount_positive: transfer_minamount > 0.0
186 creditline_within_bounds: creditline >= creditline_range.min
187 and creditline <= creditline_range.max
188 interest_debit_within_bounds: interest_debit >= interest_debit_range.min
189 and interest_debit <= interest_debit_range.max
190 interest_deposit_within_bounds: interest_deposit >= interest_deposit_range.min
191 and interest_deposit <= interest_deposit_range.max
154end 192end
diff --git a/bank-eiffel/application.e b/bank-eiffel/application.e
deleted file mode 100644
index c880bf9..0000000
--- a/bank-eiffel/application.e
+++ /dev/null
@@ -1,24 +0,0 @@
1note
2 description : "bank application root class"
3 date : "$Date$"
4 revision : "$Revision$"
5
6class
7 APPLICATION
8
9inherit
10 ARGUMENTS
11
12create
13 make
14
15feature {NONE} -- Initialization
16
17 make
18 -- Run application.
19 do
20 --| Add your code here
21 print ("Hello Eiffel World!%N")
22 end
23
24end
diff --git a/bank-eiffel/bank.e b/bank-eiffel/bank.e
index 32d10ff..223f60f 100644
--- a/bank-eiffel/bank.e
+++ b/bank-eiffel/bank.e
@@ -1,20 +1,1124 @@
1note
2 description: "Summary description for {BANK}."
3 author: ""
4 date: "$Date$"
5 revision: "$Revision$"
6
7class 1class
8 BANK 2 BANK
9 3
10create 4create
11 make 5 run
6
7feature {NONE} -- Implementation
8
9 store: BANK_STORE
10
11 over: BOOLEAN
12
13 last_error: STRING
14
15 data_file: RAW_FILE
16
17 data_filename: STRING = "bank.data"
18
19 fd: FORMAT_DOUBLE
12 20
13feature {NONE} -- Initialization 21feature {NONE} -- Initialization
14 22
15 make 23 run
24 do
25 create fd.make(2, 2)
26 create store.make(100)
27 store.ranges.account.interest_deposit := [0.01, 0.04]
28 store.ranges.account.interest_debit := [0.02, 0.1]
29 store.ranges.account.creditline := [-1000.0, 0.0]
30 store.ranges.studentaccount.interest_deposit := [0.02, 0.03]
31 store.ranges.studentaccount.interest_debit := [0.03, 0.06]
32 store.ranges.studentaccount.creditline := [-300.0, 0.0]
33 store.ranges.retireeaccount.interest_deposit := [0.02, 0.03]
34 store.ranges.retireeaccount.interest_debit := [0.03, 0.06]
35 store.ranges.retireeaccount.creditline := [-300.0, 0.0]
36 create last_error.make_empty
37
38 create data_file.make (data_filename)
39 if data_file.exists then
40 data_file.open_read
41 store ?= store.retrieved (data_file)
42 data_file.close
43 end
44
45 session
46
47 if data_file.is_creatable then
48 data_file.open_write
49 store.independent_store (data_file)
50 data_file.close
51 end
52 end
53
54feature -- Basic operations
55
56 session
57 do
58 from
59 until
60 over
61 loop
62 main_screen
63 end
64 end
65
66 print_last_error
67 do
68 if not last_error.is_empty then
69 print (last_error + "%N%N")
70 last_error := ""
71 end
72 end
73
74 print_header
75 do
76 clear_screen
77 print ("**************************************%N")
78 print ("********* BANK of FOOP *********%N")
79 print ("**************************************%N")
80 end
81
82 clear_screen
83 do
84 io.put_character ((0x1B).to_character_8)
85 io.put_string ("[2J")
86 io.put_character ((0x1B).to_character_8)
87 io.put_string ("[H")
88 end
89
90 main_screen
91 do
92 print_header
93 print ("Operations:%N")
94 print (" r ...list/edit global ranges%N")
95 print (" p ...list/create/edit/delete persons%N")
96 print (" a ...list/create/edit/delete accounts%N")
97 print (" q ...quit%N")
98 print ("%N")
99 print_last_error
100 print ("Enter a command, followed by <return>: ")
101 io.read_character
102 io.next_line
103
104 inspect io.last_character.lower
105 when 'r' then
106 ranges_screen
107 when 'p' then
108 persons_screen
109 when 'a' then
110 accounts_screen
111 when 'q' then
112 over := True
113 else
114 last_error := "Error: Unknown command '" + io.last_character.out + "'"
115 end
116 print ("%N%N")
117 end
118
119 ranges_screen
120 local
121 back: BOOLEAN
122 do
123 from
124 until
125 back
126 loop
127 print_header
128 print ("Global Ranges:%N")
129 print (" Account:%N")
130 print_ranges(store.ranges.account)
131 print (" Student account:%N")
132 print_ranges(store.ranges.studentaccount)
133 print (" Retiree account:%N")
134 print_ranges(store.ranges.retireeaccount)
135 print ("%N")
136 print ("Operations:%N")
137 print (" a ...edit account ranges%N")
138 print (" s ...edit student account ranges%N")
139 print (" r ...edit retiree account ranges%N")
140 print (" b ...back%N")
141 print ("%N")
142 print_last_error
143 print ("Enter a command, followed by <return>: ")
144 io.read_character
145 io.next_line
146
147 inspect io.last_character.lower
148 when 'a' then
149 edit_ranges("account", store.ranges.account)
150 when 's' then
151 edit_ranges("student account", store.ranges.studentaccount)
152 when 'r' then
153 edit_ranges("retiree account", store.ranges.retireeaccount)
154 when 'b' then
155 back := True
156 else
157 last_error := "Error: Unknown command '" + io.last_character.out + "'"
158 end
159 print ("%N%N")
160 end
161 end
162
163 print_ranges(range: like {BANK_STORE}.account_range)
164 do
165 print (" - Interest deposit: " + print_range(range.interest_deposit) + "%N")
166 print (" - Interest debit: " + print_range(range.interest_debit) + "%N")
167 print (" - Creditline: " + print_range(range.creditline) + "%N")
168 end
169
170 print_range(range: like {BANK_STORE}.range): STRING_8
171 do
172 Result := "[" + fd.formatted(range.min) + ", " + fd.formatted(range.max) + "]"
173 end
174
175 edit_ranges(type: STRING_8; range: like {BANK_STORE}.account_range)
176 do
177 print ("%N")
178 print ("Edit " + type + " range:%N")
179 edit_range("interest depost", range.interest_deposit)
180 edit_range("interest debit", range.interest_debit)
181 edit_range("creditline", range.creditline)
182 end
183
184 edit_range(type: STRING_8; range: like {BANK_STORE}.range)
185 local
186 back: BOOLEAN
187 do
188 from
189 back := False
190 until
191 back
192 loop
193 print ("Enter " + type + " minimum [" + fd.formatted(range.min) + "]: ")
194 io.readline
195 if io.last_string.is_double then
196 range.min := io.last_string.to_double
197 back := True
198 elseif io.last_string.is_empty then
199 back := True
200 else
201 print ("Invalid value%N")
202 end
203 end
204
205 from
206 back := False
207 until
208 back
209 loop
210 print ("Enter " + type + " maximum [" + fd.formatted(range.max) + "]: ")
211 io.readline
212 if io.last_string.is_double then
213 range.max := io.last_string.to_double
214 back := True
215 elseif io.last_string.is_empty then
216 back := True
217 else
218 print ("Invalid value%N")
219 end
220 end
221 end
222
223 persons_screen
224 local
225 back: BOOLEAN
226 do
227 from
228 until
229 back
230 loop
231 print_header
232 print ("Operations:%N")
233 print (" l ...list persons%N")
234 print (" c ...create person%N")
235 print (" e ...edit person%N")
236 print (" d ...delete person%N")
237 print (" b ...back%N")
238 print ("%N")
239 print_last_error
240 print ("Enter a command, followed by <return>: ")
241 io.read_character
242 io.next_line
243
244 inspect io.last_character.lower
245 when 'l' then
246 list_persons
247 print ("Press <return> to go back")
248 io.read_line
249 when 'c' then
250 create_persons
251 when 'e' then
252 edit_person
253 when 'd' then
254 delete_person
255 when 'b' then
256 back := True
257 else
258 last_error := "Error: Unknown command '" + io.last_character.out + "'"
259 end
260 print ("%N%N")
261 end
262 end
263
264 list_persons
265 do
266 print ("%N")
267 print ("Persons: " + store.persons.count.out + "%N")
268 from
269 store.persons.start
270 until
271 store.persons.off
272 loop
273 print ("#" + store.persons.index.out + " " + store.persons.item.surname + ", " + store.persons.item.firstname)
274 if attached {RETIREE} store.persons.item then
275 print (" (RETIREE)")
276 elseif attached {STUDENT} store.persons.item then
277 print (" (STUDENT)")
278 end
279 print ("%N")
280 store.persons.forth
281 end
282 print ("%N")
283 end
284
285 create_persons
286 local
287 back: BOOLEAN
288 firstname: STRING
289 surname: STRING
290 do
291 from
292 until
293 back
294 loop
295 print_header
296 print ("Operations:%N")
297 print (" p ...create person%N")
298 print (" s ...create student%N")
299 print (" r ...create retiree%N")
300 print (" b ...back%N")
301 print ("%N")
302 print_last_error
303 print ("Enter a command, followed by <return>: ")
304 io.read_character
305 io.next_line
306
307 inspect io.last_character.lower
308 when 'p', 's', 'r' then
309 print ("Enter surname: ")
310 io.readline
311 surname := io.last_string.twin
312
313 print ("Enter firstname: ")
314 io.readline
315 firstname := io.last_string.twin
316
317 inspect io.last_character.lower
318 when 'p' then
319 store.persons.put(create {PERSON}.make(surname, firstname))
320 when 's' then
321 store.persons.put(create {STUDENT}.make(surname, firstname))
322 when 'r' then
323 store.persons.put(create {RETIREE}.make(surname, firstname))
324 else
325 end
326 last_error := "Person (#" + store.persons.count.out + ") created successfully"
327 back := True
328 when 'b' then
329 back := True
330 else
331 last_error := "Error: Unknown command '" + io.last_character.out + "'"
332 end
333 print ("%N%N")
334 end
335 rescue
336 if not (create {EXCEPTIONS}).is_signal then
337 last_error := "Exception: " + (create {EXCEPTIONS}).tag_name
338 retry
339 end
340 end
341
342 edit_person
343 local
344 back: BOOLEAN
345 num: INTEGER
346 do
347 list_persons
348 from
349 until
350 back
351 loop
352 print_last_error
353 print ("Enter person id (b ...back): ")
354 io.readline
355 io.last_string.to_lower
356 if io.last_string.is_integer then
357 num := io.last_string.to_integer
358 if store.persons.valid_index (num) then
359 store.persons.go_i_th (num)
360
361 print ("Enter surname [" + store.persons.item.surname + "]: ")
362 io.readline
363 if not io.last_string.is_empty then
364 store.persons.item.surname := io.last_string.twin
365 end
366
367 print ("Enter firstname [" + store.persons.item.firstname + "]: ")
368 io.readline
369 if not io.last_string.is_empty then
370 store.persons.item.firstname := io.last_string.twin
371 end
372 last_error := "Person (#" + num.out + ") edited successfully"
373 back := True
374 else
375 last_error := "Error: Invalid person id"
376 end
377 elseif io.last_string.is_equal ("b") then
378 back := True
379 else
380 last_error := "Error: Not a number"
381 end
382 end
383 end
384
385 delete_person
386 local
387 back: BOOLEAN
388 do
389 list_persons
390 from
391 until
392 back
393 loop
394 print_last_error
395 print ("Enter person id (b ...back): ")
396 io.readline
397 io.last_string.to_lower
398 if io.last_string.is_integer then
399 if store.persons.valid_index (io.last_string.to_integer) then
400 store.persons.go_i_th (io.last_string.to_integer)
401 store.persons.remove
402 last_error := "Person (#" + io.last_string + ") removed successfully"
403 back := True
404 else
405 last_error := "Error: Invalid person id"
406 end
407 elseif io.last_string.is_equal ("b") then
408 back := True
409 else
410 last_error := "Error: Not a number"
411 end
412 end
413 end
414
415 accounts_screen
416 local
417 back: BOOLEAN
418 done: BOOLEAN
419 do
420 from
421 until
422 back
423 loop
424 print_header
425 print ("Operations:%N")
426 print (" l ...list accounts%N")
427 print (" c ...create account%N")
428 print (" e ...edit account%N")
429 print (" d ...delete account%N")
430 print (" b ...back%N")
431 print ("%N")
432 print_last_error
433 print ("Enter a command, followed by <return>: ")
434 io.read_character
435 io.next_line
436
437 inspect io.last_character.lower
438 when 'l' then
439 list_accounts
440
441 from
442 done := False
443 until
444 back or done
445 loop
446 print ("Enter account id for details (b ...back): ")
447 io.readline
448 io.last_string.to_lower
449 if io.last_string.is_integer then
450 if store.accounts.valid_index (io.last_string.to_integer) then
451 store.accounts.go_i_th (io.last_string.to_integer)
452 print ("%N")
453 print ("Account #" + store.accounts.index.out + ":%N")
454 list_account_details(store.accounts.item)
455 print ("Press <return> to go back")
456 io.read_line
457 done := True
458 else
459 print ("Error: Invalid account id%N%N")
460 end
461 elseif io.last_string.is_equal("b") then
462 done := True
463 else
464 print ("Error: Not a number%N%N")
465 end
466 end
467 when 'c' then
468 create_accounts
469 when 'e' then
470 edit_accounts
471 when 'd' then
472 delete_account
473 when 'b' then
474 back := True
475 else
476 last_error := "Error: Unknown command '" + io.last_character.out + "'"
477 end
478 print ("%N%N")
479 end
480 end
481
482 list_accounts
483 local
484 account: ACCOUNT
485 person: PERSON
486 do
487 print ("%N")
488 print ("Accounts: " + store.accounts.count.out + "%N")
489 from
490 store.accounts.start
491 until
492 store.accounts.off
493 loop
494 account := store.accounts.item
495 account.get_authorized_signers.linear_representation.start
496 person := account.get_authorized_signers.linear_representation.item
497
498 print ("#" + store.accounts.index.out + " " + person.surname + ", " + person.firstname)
499 if attached {RETIREEACCOUNT} account then
500 print (" (RETIREE ACCOUNT)")
501 elseif attached {STUDENTACCOUNT} account then
502 print (" (STUDENT ACCOUNT)")
503 end
504 print ("%N")
505
506 store.accounts.forth
507 end
508 print ("%N")
509 end
510
511 list_account_details(account: ACCOUNT)
512 local
513 person: PERSON
514 range: like {BANK_STORE}.account_range
515 do
516 range := store.ranges.account
517 if attached {RETIREEACCOUNT} account then
518 range := store.ranges.retireeaccount
519 elseif attached {STUDENTACCOUNT} account then
520 range := store.ranges.studentaccount
521 end
522
523 print (" - Balance: " + fd.formatted(account.balance) + "%N")
524 print (" - Interest deposit: " + fd.formatted(account.interest_deposit) + " " + print_range(range.interest_deposit) + "%N")
525 print (" - Interest debit: " + fd.formatted(account.interest_debit) + " " + print_range(range.interest_debit) +"%N")
526 print (" - Creditline: " + fd.formatted(account.creditline) + " " + print_range(range.creditline) +"%N")
527 print (" - Minimum transfer amount: " + fd.formatted(account.transfer_minamount) +"%N")
528 print (" - Authorized signers:%N")
529 from
530 account.get_authorized_signers.linear_representation.start
531 until
532 account.get_authorized_signers.linear_representation.off
533 loop
534 person := account.get_authorized_signers.linear_representation.item
535 print (" - #" + account.get_authorized_signers.linear_representation.index.out + " " + person.surname + ", " + person.firstname)
536 if attached {RETIREE} person then
537 print (" (RETIREE)")
538 elseif attached {STUDENT} person then
539 print (" (STUDENT)")
540 end
541 print ("%N")
542 account.get_authorized_signers.linear_representation.forth
543 end
544
545 print (" - Type: ")
546 if attached {RETIREEACCOUNT} account then
547 print ("Retiree account")
548 elseif attached {STUDENTACCOUNT} account then
549 print ("Student account")
550 else
551 print ("Account")
552 end
553 print ("%N%N")
554 end
555
556 create_accounts
557 local
558 back: BOOLEAN
559 do
560 from
561 until
562 back
563 loop
564 print_header
565 print ("Operations:%N")
566 print (" a ...create account%N")
567 print (" s ...create student account%N")
568 print (" r ...create retiree account%N")
569 print (" b ...back%N")
570 print ("%N")
571 print_last_error
572 print ("Enter a command, followed by <return>: ")
573 io.read_character
574 io.next_line
575
576 inspect io.last_character.lower
577 when 'a' then
578 back := create_account('a', store.ranges.account)
579 when 's' then
580 back := create_account('s', store.ranges.studentaccount)
581 when 'r' then
582 back := create_account('r', store.ranges.retireeaccount)
583 when 'b' then
584 back := True
585 else
586 last_error := "Error: Unknown command '" + io.last_character.out + "'"
587 end
588 print ("%N%N")
589 end
590 rescue
591 if not (create {EXCEPTIONS}).is_signal then
592 last_error := "Exception: " + (create {EXCEPTIONS}).tag_name
593 retry
594 end
595 end
596
597 create_account(type: CHARACTER; range: like {BANK_STORE}.account_range): BOOLEAN
598 local
599 back: BOOLEAN
600 next: BOOLEAN
601 interest_deposit: like {ACCOUNT}.interest_deposit
602 interest_debit: like {ACCOUNT}.interest_debit
603 creditline: like {ACCOUNT}.creditline
604 do
605 Result := false
606 interest_deposit := (range.interest_deposit.min + range.interest_deposit.max) / 2
607 interest_debit := (range.interest_debit.min + range.interest_debit.max) / 2
608 creditline := (range.creditline.min + range.creditline.max) / 2
609
610 print_last_error
611 from
612 next := False
613 list_persons
614 until
615 back or next
616 loop
617 print ("Enter person (authorized signer) id (b ...back): ")
618 io.readline
619 io.last_string.to_lower
620 if io.last_string.is_integer then
621 if store.persons.valid_index (io.last_string.to_integer) then
622 store.persons.go_i_th (io.last_string.to_integer)
623 next := True
624 else
625 print ("Error: Invalid person id%N%N")
626 end
627 elseif io.last_string.is_equal ("b") then
628 back := True
629 else
630 print ("Error: Not a number%N%N")
631 end
632 end
633
634 from
635 next := False
636 until
637 back or next
638 loop
639 print ("Enter interest deposit " + print_range(range.interest_deposit) + " [" + fd.formatted(interest_deposit) + "] (b ...back): ")
640 io.readline
641 io.last_string.to_lower
642 if io.last_string.is_empty then
643 next := True
644 elseif io.last_string.is_double then
645 interest_deposit := io.last_string.to_double
646 next := True
647 elseif io.last_string.is_equal ("b") then
648 back := True
649 else
650 print ("Error: Invalid interest deposit number%N%N")
651 end
652 end
653
654 from
655 next := False
656 until
657 back or next
658 loop
659 print ("Enter interest debit " + print_range(range.interest_debit) + " [" + fd.formatted(interest_debit) + "] (b ...back):")
660 io.readline
661 io.last_string.to_lower
662 if io.last_string.is_empty then
663 next := True
664 elseif io.last_string.is_double then
665 interest_debit := io.last_string.to_double
666 next := True
667 elseif io.last_string.is_equal ("b") then
668 back := True
669 else
670 print ("Error: Invalid interest debit number%N%N")
671 end
672 end
673
674 from
675 next := False
676 until
677 back or next
678 loop
679 print ("Enter creditline " + print_range(range.creditline) + " [" + fd.formatted(creditline) + "] (b ...back): ")
680 io.readline
681 io.last_string.to_lower
682 if io.last_string.is_empty then
683 next := True
684 elseif io.last_string.is_double then
685 creditline := io.last_string.to_double
686 next := True
687 elseif io.last_string.is_equal ("b") then
688 back := True
689 else
690 print ("Error: Invalid creditline number%N%N")
691 end
692 end
693
694 if not back then
695 inspect type
696 when 'a' then
697 store.accounts.put(create {ACCOUNT}.make(store.persons.item,
698 interest_deposit, interest_debit, creditline,
699 range.interest_deposit, range.interest_debit, range.creditline))
700 when 's' then
701 store.accounts.put(create {STUDENTACCOUNT}.make(store.persons.item,
702 interest_deposit, interest_debit, creditline,
703 range.interest_deposit, range.interest_debit, range.creditline))
704 when 'r' then
705 store.accounts.put(create {RETIREEACCOUNT}.make(store.persons.item,
706 interest_deposit, interest_debit, creditline,
707 range.interest_deposit, range.interest_debit, range.creditline))
708 else
709 end
710 last_error := "Account (#" + store.accounts.count.out + ") created successfully"
711 Result := true
712 back := True
713 end
714 end
715
716 edit_accounts
717 local
718 back: BOOLEAN
16 do 719 do
720 list_accounts
721 from
722 until
723 back
724 loop
725 print_last_error
726 print ("Enter account id (b ...back): ")
727 io.readline
728 io.last_string.to_lower
729 if io.last_string.is_integer then
730 if store.accounts.valid_index (io.last_string.to_integer) then
731 store.accounts.go_i_th (io.last_string.to_integer)
732 edit_account(store.accounts.index, store.accounts.item)
733 back := True
734 else
735 last_error := "Error: Invalid account id"
736 end
737 elseif io.last_string.is_equal ("b") then
738 back := True
739 else
740 last_error := "Error: Not a number"
741 end
742 end
743 end
744
745 edit_account(index: INTEGER; account: ACCOUNT)
746 local
747 back: BOOLEAN
748 do
749 from
750 until
751 back
752 loop
753 print_header
754 print ("Edit account #" + index.out + ":%N")
755 list_account_details (account)
756
757 print ("Operations:%N")
758 print (" 1 ...edit interest deposit%N")
759 print (" 2 ...edit interest debit%N")
760 print (" 3 ...edit creditline%N")
761 print (" 4 ...edit minimum transfer amount%N")
762 print (" 5 ...add authorized signer%N")
763 print (" 6 ...remove authorized signer%N")
764 print (" 7 ...deposit%N")
765 print (" 8 ...withdraw%N")
766 print (" 9 ...transfer%N")
767 print (" 0 ...advance%N")
768 print (" b ...back%N")
769 print ("%N")
770 print_last_error
771 print ("Enter a command, followed by <return>: ")
772 io.read_character
773 io.next_line
774
775 inspect io.last_character.lower
776 when '1' then
777 account.interest_deposit := edit_account_detail_double("interest deposit", account.interest_deposit)
778 last_error := "Interest deposit changed successfully"
779 when '2' then
780 account.interest_debit := edit_account_detail_double("interest debit", account.interest_debit)
781 last_error := "Interest debit changed successfully"
782 when '3' then
783 account.creditline := edit_account_detail_double("creditline", account.creditline)
784 last_error := "Creditline changed successfully"
785 when '4' then
786 account.transfer_minamount := edit_account_detail_double("transfer miniumum amount", account.transfer_minamount)
787 last_error := "Transfer minimum amount changed successfully"
788 when '5' then
789 if edit_account_add_asigner (account) then
790 last_error := "Authorized signer added successfully"
791 end
792 when '6' then
793 if edit_account_remove_asigner (account) then
794 last_error := "Authorized signer removed successfully"
795 end
796 when '7' then
797 if edit_account_deposit (account) then
798 last_error := "Deposit successfully"
799 end
800 when '8' then
801 if edit_account_withdraw (account) then
802 last_error := "Widthdraw successfully"
803 end
804 when '9' then
805 if edit_account_transfer (account) then
806 last_error := "Transfer successfully"
807 end
808 when '0' then
809 account.advance
810 last_error := "Account advanced successfully"
811 when 'b' then
812 back := True
813 else
814 last_error := "Error: Unknown command '" + io.last_character.out + "'"
815 end
816 print ("%N%N")
817 end
818 rescue
819 if not (create {EXCEPTIONS}).is_signal then
820 last_error := "Exception: " + (create {EXCEPTIONS}).tag_name
821 retry
822 end
823 end
824
825 edit_account_detail_double(type: STRING_8; val: REAL_64): REAL_64
826 local
827 back: BOOLEAN
828 do
829 Result := val
830 from
831 until
832 back
833 loop
834 print ("Enter " + type + " [" + fd.formatted(val) + "]: ")
835 io.readline
836 if io.last_string.is_double then
837 Result := io.last_string.to_double
838 back := True
839 elseif io.last_string.is_empty then
840 back := True
841 else
842 print ("Error: Invalid value%N")
843 end
844 end
845 end
846
847 edit_account_add_asigner(account: ACCOUNT): BOOLEAN
848 local
849 back: BOOLEAN
850 do
851 Result := False
852 from
853 list_persons
854 until
855 back
856 loop
857 print_last_error
858 print ("Enter person (authorized signer) id (b ...back): ")
859 io.readline
860 io.last_string.to_lower
861 if io.last_string.is_integer then
862 if store.persons.valid_index (io.last_string.to_integer) then
863 store.persons.go_i_th(io.last_string.to_integer)
864 account.add_authorized_signer (store.persons.item)
865 Result := True
866 back := True
867 else
868 last_error := "Error: Invalid person id"
869 end
870 elseif io.last_string.is_equal ("b") then
871 back := True
872 else
873 last_error := "Error: Not a number"
874 end
875 end
876 end
877
878 edit_account_remove_asigner(account: ACCOUNT): BOOLEAN
879 local
880 back: BOOLEAN
881 do
882 Result := False
883 from
884 list_persons
885 until
886 back
887 loop
888 print_last_error
889 print ("Enter person (authorized signer) id (b ...back): ")
890 io.readline
891 io.last_string.to_lower
892 if io.last_string.is_integer then
893 if store.persons.valid_index (io.last_string.to_integer) then
894 store.persons.go_i_th(io.last_string.to_integer)
895 account.remove_authorized_signer (store.persons.item)
896 Result := True
897 back := True
898 else
899 last_error := "Error: Invalid person id"
900 end
901 elseif io.last_string.is_equal ("b") then
902 back := True
903 else
904 last_error := "Error: Not a number"
905 end
906 end
907 end
908
909 edit_account_deposit(account: ACCOUNT): BOOLEAN
910 local
911 back: BOOLEAN
912 amount: like {ACCOUNT}.balance
913 do
914 Result := False
915 from
916 until
917 back
918 loop
919 print_last_error
920
921 if amount = 0.0 and last_error.is_empty and not back then
922 print ("Enter deposit amount (b ...back): ")
923 io.readline
924 io.last_string.to_lower
925 if io.last_string.is_double and io.last_string.to_double > 0.0 then
926 amount := io.last_string.to_double
927 elseif io.last_string.is_equal("b") then
928 back := True
929 else
930 last_error := "Error: Invalid value"
931 end
932 end
933
934 if last_error.is_empty and not back then
935 list_persons
936 print ("Enter person (authorized signer) id (b ...back): ")
937 io.readline
938 io.last_string.to_lower
939 if io.last_string.is_integer then
940 if store.persons.valid_index (io.last_string.to_integer) then
941 store.persons.go_i_th(io.last_string.to_integer)
942 account.deposit (amount, store.persons.item)
943 Result := True
944 back := True
945 else
946 last_error := "Error: Invalid person id"
947 end
948 elseif io.last_string.is_equal ("b") then
949 back := True
950 else
951 last_error := "Error: Not a number"
952 end
953 end
954 end
955 end
956
957 edit_account_withdraw(account: ACCOUNT): BOOLEAN
958 local
959 back: BOOLEAN
960 amount: like {ACCOUNT}.balance
961 do
962 Result := False
963 from
964 until
965 back
966 loop
967 print_last_error
968
969 if amount = 0.0 and last_error.is_empty and not back then
970 print ("Enter withdraw amount (b ...back): ")
971 io.readline
972 io.last_string.to_lower
973 if io.last_string.is_double and io.last_string.to_double > 0.0 then
974 amount := io.last_string.to_double
975 elseif io.last_string.is_equal("b") then
976 back := True
977 else
978 last_error := "Error: Invalid value"
979 end
980 end
981
982 if last_error.is_empty and not back then
983 list_persons
984 print ("Enter person (authorized signer) id (b ...back): ")
985 io.readline
986 io.last_string.to_lower
987 if io.last_string.is_integer then
988 if store.persons.valid_index (io.last_string.to_integer) then
989 store.persons.go_i_th(io.last_string.to_integer)
990 account.withdraw (amount, store.persons.item)
991 Result := True
992 back := True
993 else
994 last_error := "Error: Invalid person id"
995 end
996 elseif io.last_string.is_equal ("b") then
997 back := True
998 else
999 last_error := "Error: Not a number"
1000 end
1001 end
1002 end
1003 end
1004
1005 edit_account_transfer(account: ACCOUNT): BOOLEAN
1006 local
1007 back: BOOLEAN
1008 amount: like {ACCOUNT}.balance
1009 signer: PERSON
1010 recipient: ACCOUNT
1011 do
1012 Result := False
1013 from
1014 until
1015 back
1016 loop
1017 print_last_error
1018
1019 if amount = 0.0 and last_error.is_empty and not back then
1020 print ("Enter transfer amount (b ...back): ")
1021 io.readline
1022 io.last_string.to_lower
1023 if io.last_string.is_double and io.last_string.to_double > 0.0 then
1024 amount := io.last_string.to_double
1025 elseif io.last_string.is_equal("b") then
1026 back := True
1027 else
1028 last_error := "Error: Invalid value"
1029 end
1030 end
17 1031
1032 print (signer)
1033 if signer = Void and last_error.is_empty and not back then
1034 list_persons
1035 print ("Enter person (authorized signer) id (b ...back): ")
1036 io.readline
1037 io.last_string.to_lower
1038 if io.last_string.is_integer then
1039 if store.persons.valid_index (io.last_string.to_integer) then
1040 store.persons.go_i_th(io.last_string.to_integer)
1041 signer := store.persons.item
1042 else
1043 last_error := "Error: Invalid person id"
1044 end
1045 elseif io.last_string.is_equal ("b") then
1046 back := True
1047 else
1048 last_error := "Error: Not a number"
1049 end
1050 end
1051
1052 print (recipient)
1053 if recipient = Void and last_error.is_empty and not back then
1054 list_accounts
1055 print ("Enter recipient account id (b ...back): ")
1056 io.readline
1057 io.last_string.to_lower
1058 if io.last_string.is_integer then
1059 if store.accounts.valid_index (io.last_string.to_integer) then
1060 store.accounts.go_i_th(io.last_string.to_integer)
1061 recipient := store.accounts.item
1062 else
1063 last_error := "Error: Invalid account id"
1064 end
1065 elseif io.last_string.is_equal ("b") then
1066 back := True
1067 else
1068 last_error := "Error: Not a number"
1069 end
1070 end
1071
1072 if last_error.is_empty and not back then
1073 list_persons
1074 print ("Enter person (authorized signer) id (b ...back): ")
1075 io.readline
1076 io.last_string.to_lower
1077 if io.last_string.is_integer then
1078 if store.persons.valid_index (io.last_string.to_integer) then
1079 store.persons.go_i_th(io.last_string.to_integer)
1080 account.transfer (amount, signer, recipient, store.persons.item)
1081 Result := True
1082 back := True
1083 else
1084 last_error := "Error: Invalid person id"
1085 end
1086 elseif io.last_string.is_equal ("b") then
1087 back := True
1088 else
1089 last_error := "Error: Not a number"
1090 end
1091 end
1092 end
18 end 1093 end
19 1094
1095 delete_account
1096 local
1097 back: BOOLEAN
1098 do
1099 list_accounts
1100 from
1101 until
1102 back
1103 loop
1104 print_last_error
1105 print ("Enter account id (b ...back): ")
1106 io.readline
1107 io.last_string.to_lower
1108 if io.last_string.is_integer then
1109 if store.accounts.valid_index (io.last_string.to_integer) then
1110 store.accounts.go_i_th (io.last_string.to_integer)
1111 store.accounts.remove
1112 last_error := "Account (#" + io.last_string + ") removed successfully"
1113 back := True
1114 else
1115 last_error := "Error: Invalid account id"
1116 end
1117 elseif io.last_string.is_equal ("b") then
1118 back := True
1119 else
1120 last_error := "Error: Not a number"
1121 end
1122 end
1123 end
20end 1124end
diff --git a/bank-eiffel/bank.ecf b/bank-eiffel/bank.ecf
index b3bf92c..404ab84 100644
--- a/bank-eiffel/bank.ecf
+++ b/bank-eiffel/bank.ecf
@@ -1,26 +1,24 @@
1<?xml version="1.0" encoding="ISO-8859-1"?> 1<?xml version="1.0" encoding="ISO-8859-1"?>
2<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-7-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-7-0 http://www.eiffel.com/developers/xml/configuration-1-7-0.xsd" name="bank" uuid="ABD750A4-A528-4FEE-A7EA-37791A0D0F37"> 2<system xmlns="http://www.eiffel.com/developers/xml/configuration-1-7-0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.eiffel.com/developers/xml/configuration-1-7-0 http://www.eiffel.com/developers/xml/configuration-1-7-0.xsd" name="bank" uuid="ABD750A4-A528-4FEE-A7EA-37791A0D0F37">
3 <target name="bank"> 3 <target name="bank">
4 <description>FOOP Exercise #3</description> 4 <description>Bank of FOOP</description>
5 <root class="APPLICATION" feature="make"/> 5 <root class="BANK" feature="run"/>
6 <version major="0" minor="1" release="0" build="0" product="bank"/> 6 <version major="0" minor="1" release="0" build="0" product="bank"/>
7 <option warning="true" void_safety="none"> 7 <option warning="true" is_attached_by_default="true" void_safety="all">
8 <assertions precondition="true" postcondition="true" check="true" invariant="true" loop="true" supplier_precondition="true"/> 8 <assertions precondition="true" postcondition="true" check="true" invariant="true" loop="true" supplier_precondition="true"/>
9 </option> 9 </option>
10 <setting name="executable_name" value="bank"/> 10 <setting name="console_application" value="true"/>
11 <precompile name="base_pre" location="$ISE_PRECOMP\base.ecf"/> 11 <precompile name="precompile" location="$ISE_PRECOMP\base.ecf"/>
12 <library name="base" location="$ISE_LIBRARY\library\base\base.ecf"/> 12 <library name="base" location="$ISE_LIBRARY\library\base\base.ecf"/>
13 <library name="testing" location="$ISE_LIBRARY\library\testing\testing.ecf"/> 13 <library name="testing" location="$ISE_LIBRARY\library\testing\testing.ecf"/>
14 <cluster name="bank" location=".\" recursive="true"> 14 <cluster name="bank" location=".\" recursive="true">
15 <class_option class="BANK" void_safety="none">
16 </class_option>
15 <file_rule> 17 <file_rule>
16 <exclude>/EIFGENs$</exclude> 18 <exclude>/EIFGENs$</exclude>
17 <exclude>/CVS$</exclude> 19 <exclude>/CVS$</exclude>
18 <exclude>/.svn$</exclude> 20 <exclude>/.svn$</exclude>
19 </file_rule> 21 </file_rule>
20 <tests name="tests" location="\home\manuel\uni\foop\bank-eiffel\tests\"/>
21 </cluster> 22 </cluster>
22 </target> 23 </target>
23 <target name="bank_dotnet" extends="bank">
24 <setting name="msil_generation" value="true"/>
25 </target>
26</system> 24</system>
diff --git a/bank-eiffel/bank_store.e b/bank-eiffel/bank_store.e
new file mode 100644
index 0000000..acc6f3a
--- /dev/null
+++ b/bank-eiffel/bank_store.e
@@ -0,0 +1,48 @@
1class
2 BANK_STORE
3
4inherit
5 STORABLE
6
7create
8 make
9
10feature
11
12 persons: ARRAYED_SET [PERSON]
13
14 accounts: ARRAYED_SET [ACCOUNT]
15
16 ranges: TUPLE [
17 account: attached like account_range;
18 studentaccount: attached like account_range;
19 retireeaccount: attached like account_range
20 ]
21
22feature {NONE} -- Implementation
23
24 account_range: detachable TUPLE [
25 creditline: attached like range;
26 interest_deposit: attached like range;
27 interest_debit: attached like range
28 ]
29
30 range: detachable like {ACCOUNT}.range
31
32feature {NONE} -- Initialization
33
34 make(cap: INTEGER)
35 do
36 create persons.make(cap)
37 create accounts.make(cap)
38 create ranges
39 ranges.account := new_range
40 ranges.studentaccount := new_range
41 ranges.retireeaccount := new_range
42 end
43
44 new_range: attached like account_range
45 do
46 create Result
47 end
48end
diff --git a/bank-eiffel/person.e b/bank-eiffel/person.e
index 54e1a45..ffaab72 100644
--- a/bank-eiffel/person.e
+++ b/bank-eiffel/person.e
@@ -1,9 +1,3 @@
1note
2 description: "Summary description for {PERSON}."
3 author: ""
4 date: "$Date$"
5 revision: "$Revision$"
6
7class 1class
8 PERSON 2 PERSON
9 3
@@ -14,11 +8,9 @@ feature -- Access
14 8
15 surname: STRING_8 assign set_surname 9 surname: STRING_8 assign set_surname
16 -- Nachname 10 -- Nachname
17 attribute Result := ({like surname}).default end --| Remove line when Void Safety is properly set
18 11
19 firstname: STRING_8 assign set_firstname 12 firstname: STRING_8 assign set_firstname
20 -- Vorname 13 -- Vorname
21 attribute Result := ({like firstname}).default end --| Remove line when Void Safety is properly set
22 14
23feature {NONE} -- Initialization 15feature {NONE} -- Initialization
24 16
@@ -33,7 +25,7 @@ feature {NONE} -- Implementation
33 set_surname (a_surname: like surname) 25 set_surname (a_surname: like surname)
34 -- Assign `surname' with `a_surname'. 26 -- Assign `surname' with `a_surname'.
35 require 27 require
36 a_surname_not_empty: a_surname /= Void and then not a_surname.is_empty 28 a_surname_not_empty: not a_surname.is_empty
37 do 29 do
38 surname := a_surname 30 surname := a_surname
39 ensure 31 ensure
@@ -43,7 +35,7 @@ feature {NONE} -- Implementation
43 set_firstname (a_firstname: like firstname) 35 set_firstname (a_firstname: like firstname)
44 -- Assign `firstname' with `a_firstname'. 36 -- Assign `firstname' with `a_firstname'.
45 require 37 require
46 a_firstname_not_empty: a_firstname /= Void and then not a_firstname.is_empty 38 a_firstname_not_empty: not a_firstname.is_empty
47 do 39 do
48 firstname := a_firstname 40 firstname := a_firstname
49 ensure 41 ensure
@@ -51,6 +43,6 @@ feature {NONE} -- Implementation
51 end 43 end
52 44
53invariant 45invariant
54 firstname_not_empty: firstname /= Void and then not firstname.is_empty 46 firstname_not_empty: not firstname.is_empty
55 surname_not_empty: surname /= Void and then not surname.is_empty 47 surname_not_empty: not surname.is_empty
56end 48end
diff --git a/bank-eiffel/retiree.e b/bank-eiffel/retiree.e
index 57e5d05..e8a2edd 100644
--- a/bank-eiffel/retiree.e
+++ b/bank-eiffel/retiree.e
@@ -1,13 +1,10 @@
1note
2 description: "Summary description for {RETIREE}."
3 author: ""
4 date: "$Date$"
5 revision: "$Revision$"
6
7class 1class
8 RETIREE 2 RETIREE
9 3
10inherit 4inherit
11 PERSON 5 PERSON
12 6
7create
8 make
9
13end 10end
diff --git a/bank-eiffel/retireeaccount.e b/bank-eiffel/retireeaccount.e
index 3f56fd4..24ae004 100644
--- a/bank-eiffel/retireeaccount.e
+++ b/bank-eiffel/retireeaccount.e
@@ -1,15 +1,40 @@
1note
2 description: "Summary description for {RETIREEACCOUNT}."
3 author: ""
4 date: "$Date$"
5 revision: "$Revision$"
6
7class 1class
8 RETIREEACCOUNT 2 RETIREEACCOUNT
9 3
10inherit 4inherit
11 ACCOUNT 5 ACCOUNT
6 redefine
7 add_authorized_signer,
8 set_default_transfer_minamount
9 end
10
11create
12 make
13
14feature -- Basic operations
15
16 add_authorized_signer (an_authorized_signer: PERSON)
17 do
18 check
19 authorized_signers_only_one: get_authorized_signers.count = 0
20 end
21 Precursor (an_authorized_signer)
22 end
23
24feature {NONE} -- Implementation
25
26 set_default_transfer_minamount
27 do
28 set_transfer_minamount (1.0)
29 end
12 30
13invariant 31invariant
14 authorized_signers_only_one: authorized_signers.count = 1 32 authorized_signers_only_one: authorized_signers.count = 1
33 authorized_signers_attached: authorized_signers.linear_representation /= Void
34 authorized_signers_only_retirees:
35 (attached authorized_signers.linear_representation as signers) implies signers.for_all(
36 agent (person: PERSON): BOOLEAN
37 do
38 Result := attached {RETIREE} person
39 end)
15end 40end
diff --git a/bank-eiffel/student.e b/bank-eiffel/student.e
index 2b5afd4..0c3863a 100644
--- a/bank-eiffel/student.e
+++ b/bank-eiffel/student.e
@@ -1,13 +1,10 @@
1note
2 description: "Summary description for {STUDENT}."
3 author: ""
4 date: "$Date$"
5 revision: "$Revision$"
6
7class 1class
8 STUDENT 2 STUDENT
9 3
10inherit 4inherit
11 PERSON 5 PERSON
12 6
7create
8 make
9
13end 10end
diff --git a/bank-eiffel/studentaccount.e b/bank-eiffel/studentaccount.e
index a80d4bb..abbb070 100644
--- a/bank-eiffel/studentaccount.e
+++ b/bank-eiffel/studentaccount.e
@@ -1,15 +1,40 @@
1note
2 description: "Summary description for {STUDENTACCOUNT}."
3 author: ""
4 date: "$Date$"
5 revision: "$Revision$"
6
7class 1class
8 STUDENTACCOUNT 2 STUDENTACCOUNT
9 3
10inherit 4inherit
11 ACCOUNT 5 ACCOUNT
6 redefine
7 set_default_transfer_minamount,
8 add_authorized_signer
9 end
10
11create
12 make
13
14feature -- Basic operations
15
16 add_authorized_signer (an_authorized_signer: PERSON)
17 do
18 check
19 authorized_signers_only_one: get_authorized_signers.count = 0
20 end
21 Precursor (an_authorized_signer)
22 end
23
24feature {NONE} -- Implementation
25
26 set_default_transfer_minamount
27 do
28 set_transfer_minamount (1.0)
29 end
12 30
13invariant 31invariant
14 authorized_signers_only_one: authorized_signers.count = 1 32 authorized_signers_only_one: authorized_signers.count = 1
33 authorized_signers_attached: authorized_signers.linear_representation /= Void
34 authorized_signers_only_students:
35 (attached authorized_signers.linear_representation as signers) implies signers.for_all(
36 agent (person: PERSON): BOOLEAN
37 do
38 Result := attached {STUDENT} person
39 end)
15end 40end
diff --git a/bank-eiffel/tests/test_account.e b/bank-eiffel/tests/test_account.e
index a460023..0b6ac46 100644
--- a/bank-eiffel/tests/test_account.e
+++ b/bank-eiffel/tests/test_account.e
@@ -1,12 +1,3 @@
1note
2 description: "[
3 Eiffel tests that can be executed by testing tool.
4 ]"
5 author: "EiffelStudio test wizard"
6 date: "$Date$"
7 revision: "$Revision$"
8 testing: "type/manual"
9
10class 1class
11 TEST_ACCOUNT 2 TEST_ACCOUNT
12 3
@@ -19,15 +10,243 @@ feature -- Test routines
19 local 10 local
20 person1: PERSON 11 person1: PERSON
21 person2: PERSON 12 person2: PERSON
13 person3: PERSON
14 account1: ACCOUNT
15 account2: ACCOUNT
16 do
17 create person1.make ("PERSON1", "PERSON1")
18 create person2.make ("PERSON2", "PERSON2")
19 create person3.make ("PERSON3", "PERSON3")
20
21 create account1.make (person1, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
22 assert("CREATE_EDIT_ACCOUNT_MINAMOUNT", account1.transfer_minamount = 2.0)
23
24 assert("CREATE_EDIT_ACCOUNT_SIGNER_1", account1.get_authorized_signers.count = 1)
25 account1.add_authorized_signer (person2)
26 account1.add_authorized_signer (person2)
27 account1.add_authorized_signer (person3)
28 account1.remove_authorized_signer (person3)
29 assert("CREATE_EDIT_ACCOUNT_SIGNER_2", account1.get_authorized_signers.count = 2)
30
31 assert("CREATE_EDIT_ACCOUNT_BALANCE_1", account1.balance = 0.0)
32 account1.deposit (50.0, person1)
33 account1.deposit (50.0, person2)
34 -- balance = 100.0
35 account1.advance
36 -- balance = 100.0 + 1% deposit
37 account1.withdraw (100.0 + 100.0 * 0.01 + 50.0, person1)
38 -- balance = -50.0
39 account1.creditline := -100.0
40 account1.withdraw (50.0, person1)
41 -- balance = -100.0
42 account1.advance
43 -- balance = -100.0 + 2% debit
44 assert("CREATE_EDIT_ACCOUNT_BALANCE_2", account1.balance = -102.0)
45
46 create account2.make(person3, 0.01, 0.02, -50, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
47 account2.deposit (102.0, person3)
48 account2.transfer (102.0, person3, account1, person1)
49 assert("CREATE_EDIT_ACCOUNT_BALANCE_3", account1.balance = 0.0 and account2.balance = 0.0)
50
51 account1.interest_deposit := 0.01
52 account1.interest_deposit := 0.022
53 account1.interest_debit := 0.01
54 account1.interest_debit := 0.02
55 account1.creditline := -100.0
56 account1.creditline := -50.0
57 account1.transfer_minamount := 10.0
58 end
59
60 ACCOUNT_CHECK_RANGES
61 local
62 person: PERSON
22 account: ACCOUNT 63 account: ACCOUNT
64 retry_count: INTEGER
23 do 65 do
24 create person1.make ("SOME_SURNAME_1", "SOME_FIRSTNAME_1") 66 create person.make("PERSON", "PERSON")
25 create person2.make ("SOME_SURNAME_2", "SOME_FIRSTNAME_2") 67 create account.make(person, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
26 create account.make (person1) 68
27 account.add_authorized_signer (person2) 69 inspect retry_count
28 --assert ("not_implemented", False) 70 when 0 then
71 account.interest_deposit := 0.0
72 assert("ACCOUNT_CHECK_RANGES_INTEREST_DEPOSIT_MIN", False)
73 when 1 then
74 account.interest_deposit := 0.023
75 assert("ACCOUNT_CHECK_RANGES_INTEREST_DEPOSIT_MAX", False)
76 when 2 then
77 account.interest_debit := 0.0
78 assert("ACCOUNT_CHECK_RANGES_INTEREST_DEBIT_MIN", False)
79 when 3 then
80 account.interest_debit := 0.03
81 assert("ACCOUNT_CHECK_RANGES_INTEREST_DEBIT_MAX", False)
82 when 4 then
83 account.creditline := -101.0
84 assert("ACCOUNT_CHECK_RANGES_CREDITLINE_MIN", False)
85 when 5 then
86 account.creditline := -49.0
87 assert("ACCOUNT_CHECK_RANGES_CREDITLINE_MAX", False)
88 when 6 then
89 account.transfer_minamount := -1.0
90 assert("ACCOUNT_CHECK_RANGES_TRANSFER_MINAMOUNT_POSITIVE", False)
91 else
92 end
93 rescue
94 if not (create {EXCEPTIONS}).is_developer_exception then
95 retry_count := retry_count + 1
96 retry
97 end
29 end 98 end
30 99
31end 100 ACCOUNT_CHECK_OPERATIONS
101 local
102 person1: PERSON
103 account1: ACCOUNT
104 person2: PERSON
105 account2: ACCOUNT
106 retry_count: INTEGER
107 do
108 create person1.make("PERSON1", "PERSON1")
109 create person2.make("PERSON2", "PERSON2")
110 create account1.make(person1, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
111 create account2.make(person2, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
112
113 inspect retry_count
114 when 0 then
115 account1.deposit (10.0, person2)
116 assert("ACCOUNT_CHECK_OPERATIONS_DEPOSIT_OTHER", False)
117 when 1 then
118 account1.withdraw (10.0, person2)
119 assert("ACCOUNT_CHECK_OPERATIONS_WITHDRAW_OTHER", False)
120 when 2 then
121 account1.transfer (10.0, person2, account2, person2)
122 assert("ACCOUNT_CHECK_OPERATIONS_TRANSFER_OTHER_1", False)
123 when 3 then
124 account1.transfer (10.0, person1, account2, person1)
125 assert("ACCOUNT_CHECK_OPERATIONS_TRANSFER_OTHER_2", False)
126 when 4 then
127 account1.withdraw (51.0, person1)
128 assert("ACCOUNT_CHECK_OPERATIONS_WITHDRAW_OVER_CREDIT", False)
129 when 5 then
130 account1.deposit (1.0, person1)
131 assert("ACCOUNT_CHECK_OPERATIONS_DEPOSIT_BELOW_MINAMOUNT", False)
132 when 6 then
133 account1.withdraw (1.0, person1)
134 assert("ACCOUNT_CHECK_OPERATIONS_WITHDRAW_BELOW_MINAMOUNT", False)
135 when 7 then
136 account1.transfer (1.0, person1, account2, person2)
137 assert("ACCOUNT_CHECK_OPERATIONS_TRANSFER_BELOW_MINAMOUNT", False)
138 when 8 then
139 account1.remove_authorized_signer (person1)
140 assert("ACCOUNT_CHECK_OPERATIONS_REMOVE_AUTHORIZED_SIGNER_EMPTY", False)
141 else
142 end
143 rescue
144 if retry_count /= 9 and not (create {EXCEPTIONS}).is_developer_exception then
145 retry_count := retry_count + 1
146 retry
147 end
148 end
32 149
150 CREATE_STUDENTACCOUNT
151 local
152 student: STUDENT
153 account: STUDENTACCOUNT
154 do
155 create student.make("STUDENT", "STUDENT")
156 create account.make(student, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
157 assert("CREATE_STUDENTACCOUNT", attached {ACCOUNT} account)
158 assert("CREATE_STUDENTACCOUNT_MINAMOUNT", account.transfer_minamount = 1.0)
159 end
160
161 STUDENTACCOUNT_ONLY_STUDENTS
162 local
163 account: STUDENTACCOUNT
164 student: STUDENT
165 person: PERSON
166 retiree: RETIREE
167 retry_count: INTEGER
168 do
169 create student.make("STUDENT", "STUDENT")
170 create person.make("PERSON", "PERSON")
171 create retiree.make("RETIREE", "RETIREE")
172
173 inspect retry_count
174 when 0 then
175 create account.make(person, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
176 assert("STUDENTACCOUNT_ONLY_STUDENTS_1", False)
177 when 1 then
178 create account.make(retiree, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
179 assert("STUDENTACCOUNT_ONLY_STUDENTS_2", False)
180 when 2 then
181 create account.make(student, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
182 account.add_authorized_signer (create {STUDENT}.make("STUDENT2", "STUDENT2"))
183 assert("STUDENTACCOUNT_ONE_STUDENT_ONLY_1", False)
184 when 3 then
185 create account.make(student, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
186 account.add_authorized_signer (person)
187 assert("STUDENTACCOUNT_ONE_STUDENT_ONLY_2", False)
188 when 4 then
189 create account.make(student, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
190 account.add_authorized_signer (retiree)
191 assert("STUDENTACCOUNT_ONE_STUDENT_ONLY_3", False)
192 else
193 end
194 rescue
195 if not (create {EXCEPTIONS}).is_developer_exception then
196 retry_count := retry_count + 1
197 retry
198 end
199 end
200
201 CREATE_RETIREEACCOUNT
202 local
203 retiree: RETIREE
204 account: RETIREEACCOUNT
205 do
206 create retiree.make("RETIREE", "RETIREE")
207 create account.make(retiree, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
208 assert("CREATE_RETIREEACCOUNT", attached {ACCOUNT} account)
209 assert("CREATE_RETIREEACCOUNT_MINAMOUNT", account.transfer_minamount = 1.0)
210 end
33 211
212
213 RETIREEACCOUNT_ONLY_RETIREES
214 local
215 account: RETIREEACCOUNT
216 retiree: RETIREE
217 person: PERSON
218 student: STUDENT
219 retry_count: INTEGER
220 do
221 create retiree.make("RETIREE", "RETIREE")
222 create person.make("PERSON", "PERSON")
223 create student.make("STUDENT", "STUDENT")
224
225 inspect retry_count
226 when 0 then
227 create account.make(person, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
228 assert("RETIREEACCOUNT_ONLY_RETIREES_1", False)
229 when 1 then
230 create account.make(student, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
231 assert("RETIREEACCOUNT_ONLY_RETIREES_2", False)
232 when 2 then
233 create account.make(retiree, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
234 account.add_authorized_signer (create {RETIREE}.make("RETIREE2", "RETIREE2"))
235 assert("RETIREEACCOUNT_ONE_RETIREE_ONLY_1", False)
236 when 3 then
237 create account.make(retiree, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
238 account.add_authorized_signer (person)
239 assert("RETIREEACCOUNT_ONE_RETIREE_ONLY_2", False)
240 when 4 then
241 create account.make(retiree, 0.01, 0.02, -50.0, [0.01, 0.022], [0.01, 0.02], [-100.0, -50.0])
242 account.add_authorized_signer (student)
243 assert("RETIREEACCOUNT_ONE_RETIREE_ONLY_3", False)
244 else
245 end
246 rescue
247 if not (create {EXCEPTIONS}).is_developer_exception then
248 retry_count := retry_count + 1
249 retry
250 end
251 end
252end
diff --git a/bank-eiffel/tests/test_person.e b/bank-eiffel/tests/test_person.e
index a501deb..01e9a50 100644
--- a/bank-eiffel/tests/test_person.e
+++ b/bank-eiffel/tests/test_person.e
@@ -1,12 +1,3 @@
1note
2 description: "[
3 Eiffel tests that can be executed by testing tool.
4 ]"
5 author: "EiffelStudio test wizard"
6 date: "$Date$"
7 revision: "$Revision$"
8 testing: "type/manual"
9
10class 1class
11 TEST_PERSON 2 TEST_PERSON
12 3
@@ -14,10 +5,11 @@ inherit
14 EQA_TEST_SET 5 EQA_TEST_SET
15 6
16feature -- Test routines 7feature -- Test routines
17
18 CREATE_EDIT_PERSON 8 CREATE_EDIT_PERSON
19 local 9 local
20 person: PERSON 10 person: PERSON
11 student: STUDENT
12 retiree: RETIREE
21 do 13 do
22 create person.make("SOME_SURNAME_1", "SOME_FIRSTNAME_1") 14 create person.make("SOME_SURNAME_1", "SOME_FIRSTNAME_1")
23 assert("CREATE_EDIT_PERSON_FIRSTNAME_1", person.firstname.is_equal("SOME_FIRSTNAME_1")) 15 assert("CREATE_EDIT_PERSON_FIRSTNAME_1", person.firstname.is_equal("SOME_FIRSTNAME_1"))
@@ -27,81 +19,52 @@ feature -- Test routines
27 assert("CREATE_EDIT_PERSON_FIRSTNAME_2", person.firstname.is_equal("SOME_FIRSTNAME_2")) 19 assert("CREATE_EDIT_PERSON_FIRSTNAME_2", person.firstname.is_equal("SOME_FIRSTNAME_2"))
28 person.surname := "SOME_SURNAME_2" 20 person.surname := "SOME_SURNAME_2"
29 assert("CREATE_EDIT_PERSON_SURNAME_2", person.surname.is_equal("SOME_SURNAME_2")) 21 assert("CREATE_EDIT_PERSON_SURNAME_2", person.surname.is_equal("SOME_SURNAME_2"))
22
23 create student.make ("STUDENT_SURNAME", "STUDENT_FIRSTNAME")
24 assert("CREATE_EDIT_PERSON_STUDENT", attached {PERSON} student)
25 create retiree.make ("RETIREE_SURNAME", "RETIREE_FIRSTNAME")
26 assert("CREATE_EDIT_PERSON_RETIREE", attached {PERSON} student)
30 end 27 end
31 28
32 CREATE_EDIT_PERSON_EMPTY_SURNAME 29 PERSON_EMPTY_SURNAME
33 local 30 local
34 person: PERSON 31 person: PERSON
35 retry_count: INTEGER 32 retry_count: INTEGER
36 doretry: BOOLEAN
37 do 33 do
38 if retry_count = 0 then 34 inspect retry_count
39 doretry := True 35 when 0 then
40 create person.make("", "SOME_FIRSTNAME") 36 create person.make("", "SOME_FIRSTNAME")
41 doretry := False 37 assert("PERSON_EMPTY_SURNAME_1", False)
42 assert("CREATE_EDIT_PERSON_EMPTY_SURNAME_1", False) 38 when 1 then
43 elseif retry_count = 1 then
44 create person.make(void, "SOME_FIRSTNAME")
45 doretry := False
46 assert("CREATE_EDIT_PERSON_EMPTY_SURNAME_2", False)
47 elseif retry_count = 2 then
48 doretry := False
49 create person.make("SOME_SURNAME", "SOME_FIRSTNAME") 39 create person.make("SOME_SURNAME", "SOME_FIRSTNAME")
50 doretry := True
51 person.surname := "" 40 person.surname := ""
52 doretry := False 41 assert("PERSON_EMPTY_SURNAME_3", False)
53 assert("CREATE_EDIT_PERSON_EMPTY_SURNAME_3", False)
54 elseif retry_count = 3 then
55 doretry := False
56 create person.make("SOME_SURNAME", "SOME_FIRSTNAME")
57 doretry := True
58 person.surname := void
59 doretry := False
60 assert("CREATE_EDIT_PERSON_EMPTY_SURNAME_4", False)
61 else 42 else
62 doretry := False
63 end 43 end
64 rescue 44 rescue
65 if doretry then 45 if not (create {EXCEPTIONS}).is_developer_exception then
66 retry_count := retry_count + 1 46 retry_count := retry_count + 1
67 retry 47 retry
68 end 48 end
69 end 49 end
70 50
71 CREATE_EDIT_PERSON_EMPTY_FIRSTNAME 51 PERSON_EMPTY_FIRSTNAME
72 local 52 local
73 person: PERSON 53 person: PERSON
74 retry_count: INTEGER 54 retry_count: INTEGER
75 doretry: BOOLEAN
76 do 55 do
77 if retry_count = 0 then 56 inspect retry_count
78 doretry := True 57 when 0 then
79 create person.make("SOME_SURNAME", "") 58 create person.make("SOME_SURNAME", "")
80 doretry := False 59 assert("PERSON_EMPTY_FIRSTNAME_1", False)
81 assert("CREATE_EDIT_PERSON_EMPTY_FIRSTNAME_1", False) 60 when 1 then
82 elseif retry_count = 1 then
83 create person.make("SOME_SURNAME", void)
84 doretry := False
85 assert("CREATE_EDIT_PERSON_EMPTY_FIRSTNAME_2", False)
86 elseif retry_count = 2 then
87 doretry := False
88 create person.make("SOME_SURNAME", "SOME_FIRSTNAME") 61 create person.make("SOME_SURNAME", "SOME_FIRSTNAME")
89 doretry := True
90 person.firstname := "" 62 person.firstname := ""
91 doretry := False 63 assert("PERSON_EMPTY_FIRSTNAME_3", False)
92 assert("CREATE_EDIT_PERSON_EMPTY_FIRSTNAME_3", False)
93 elseif retry_count = 3 then
94 doretry := False
95 create person.make("SOME_SURNAME", "SOME_FIRSTNAME")
96 doretry := True
97 person.firstname := void
98 doretry := False
99 assert("CREATE_EDIT_PERSON_EMPTY_FIRSTNAME_4", False)
100 else 64 else
101 doretry := False
102 end 65 end
103 rescue 66 rescue
104 if doretry then 67 if not (create {EXCEPTIONS}).is_developer_exception then
105 retry_count := retry_count + 1 68 retry_count := retry_count + 1
106 retry 69 retry
107 end 70 end