Codebase list hibiscus / 6358a62
Update upstream source from tag 'upstream/2.8.4+dfsg' Update to upstream version '2.8.4+dfsg' with Debian dir 8fb9f8368bb2d94e45ee33225380506f471e2f5d Jochen Sprickerhof 5 years ago
133 changed file(s) with 4302 addition(s) and 1344 deletion(s). Raw diff Collapse all Expand all
22 <classpathentry kind="src" path="src"/>
33 <classpathentry kind="src" output="test-bin" path="test"/>
44 <classpathentry including="*.java" kind="src" output="updates" path="updates"/>
5 <classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
5 <classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.7"/>
66 <classpathentry exported="true" kind="src" path="/jameica"/>
77 <classpathentry kind="lib" path="lib/super-csv-2.4.0.jar"/>
88 <classpathentry kind="lib" path="lib/swtchart/org.swtchart_0.10.0.v20160212.jar"/>
1010 <classpathentry kind="lib" path="lib/itextpdf-5.3.3.jar"/>
1111 <classpathentry kind="con" path="org.eclipse.jdt.junit.JUNIT_CONTAINER/4"/>
1212 <classpathentry exported="true" kind="lib" path="lib/obantoo-bin-2.1.12.jar"/>
13 <classpathentry exported="true" kind="lib" path="lib/hbci4j-core-3.0.18-SNAPSHOT.jar"/>
13 <classpathentry exported="true" kind="lib" path="lib/hbci4j-core-3.0.21-SNAPSHOT.jar" sourcepath="/hbci4j-core/src/main/java"/>
1414 <classpathentry kind="output" path="bin"/>
1515 </classpath>
66 org.eclipse.jdt.core.compiler.annotation.nullanalysis=disabled
77 org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
88 org.eclipse.jdt.core.compiler.codegen.methodParameters=do not generate
9 org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.6
9 org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.7
1010 org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
11 org.eclipse.jdt.core.compiler.compliance=1.6
11 org.eclipse.jdt.core.compiler.compliance=1.7
1212 org.eclipse.jdt.core.compiler.debug.lineNumber=generate
1313 org.eclipse.jdt.core.compiler.debug.localVariable=generate
1414 org.eclipse.jdt.core.compiler.debug.sourceFile=generate
109109 org.eclipse.jdt.core.compiler.problem.unusedTypeParameter=ignore
110110 org.eclipse.jdt.core.compiler.problem.unusedWarningToken=warning
111111 org.eclipse.jdt.core.compiler.problem.varargsArgumentNeedCast=warning
112 org.eclipse.jdt.core.compiler.source=1.6
112 org.eclipse.jdt.core.compiler.release=disabled
113 org.eclipse.jdt.core.compiler.source=1.7
113114 org.eclipse.jdt.core.compiler.taskCaseSensitive=enabled
114115 org.eclipse.jdt.core.compiler.taskPriorities=NORMAL,HIGH,NORMAL,LOW,LOW
115116 org.eclipse.jdt.core.compiler.taskTags=TODO,FIXME,XXX,BUGZILLA,TICKET
129130 org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer=16
130131 org.eclipse.jdt.core.formatter.alignment_for_expressions_in_for_loop_header=0
131132 org.eclipse.jdt.core.formatter.alignment_for_method_declaration=0
133 org.eclipse.jdt.core.formatter.alignment_for_module_statements=16
132134 org.eclipse.jdt.core.formatter.alignment_for_multiple_fields=16
133135 org.eclipse.jdt.core.formatter.alignment_for_parameterized_type_references=0
134136 org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration=16
166168 org.eclipse.jdt.core.formatter.brace_position_for_method_declaration=next_line
167169 org.eclipse.jdt.core.formatter.brace_position_for_switch=next_line
168170 org.eclipse.jdt.core.formatter.brace_position_for_type_declaration=next_line
171 org.eclipse.jdt.core.formatter.comment.align_tags_descriptions_grouped=false
172 org.eclipse.jdt.core.formatter.comment.align_tags_names_descriptions=false
169173 org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment=false
170174 org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment=false
175 org.eclipse.jdt.core.formatter.comment.count_line_length_from_starting_position=false
171176 org.eclipse.jdt.core.formatter.comment.format_block_comments=true
172177 org.eclipse.jdt.core.formatter.comment.format_header=false
173178 org.eclipse.jdt.core.formatter.comment.format_html=true
178183 org.eclipse.jdt.core.formatter.comment.indent_root_tags=true
179184 org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags=insert
180185 org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter=insert
181 org.eclipse.jdt.core.formatter.comment.line_length=80
186 org.eclipse.jdt.core.formatter.comment.line_length=160
182187 org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries=true
183188 org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries=true
184189 org.eclipse.jdt.core.formatter.comment.preserve_white_space_between_code_and_line_comments=false
390395 org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line=false
391396 org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line=false
392397 org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line=false
393 org.eclipse.jdt.core.formatter.lineSplit=80
398 org.eclipse.jdt.core.formatter.lineSplit=160
394399 org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column=false
395400 org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column=false
396401 org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body=0
11 eclipse.preferences.version=1
22 editor_save_participant_org.eclipse.jdt.ui.postsavelistener.cleanup=true
33 formatter_profile=_meins
4 formatter_settings_version=12
5 org.eclipse.jdt.ui.text.custom_code_templates=<?xml version\="1.0" encoding\="UTF-8"?><templates/>
4 formatter_settings_version=14
65 sp_cleanup.add_default_serial_version_id=true
76 sp_cleanup.add_generated_serial_version_id=false
87 sp_cleanup.add_missing_annotations=true
00 #Build Number for ANT. Do not edit!
1 #Tue Jun 05 11:12:48 CEST 2018
2 build.number=364
1 #Wed Jun 27 18:39:48 CEST 2018
2 build.number=367
0 2018-09-26 Version 2.8.4
1
2 * NEW: 0700 Beim Empfang neuer UPD gleich die BPD mit aktualisieren
3 * NEW: 0699 Neue HBCI4Java-Version mit Server-Adressen für IsBank - https://github.com/hbci4j/hbci4java/commit/649179cd52cc57bc540ce224cc8ef6ebaf0a806e
4 * NEW: 0698 Scrollbalken in Einstellungsdialog für elektr. Kontoauszug für kleine Displays anzeigen, Fenstergröße speichern
5 * NEW: 0697 BUGZILLA 1495 - automatisches Entfernen nicht unterstüzter Zeichen beim Einfügen des Verwendungszweck per Zwischenablage
6 * NEW: 0696 Neue HBCI4Java-Version mit aktualisierter Server-Adresse der Sparda-Bank Berlin - https://github.com/hbci4j/hbci4java/commit/c91f6ed2c5b6b5ddc8d29c4ec6cb66428af6f15e
7 * NEW: 0695 Support für dedizierte EndToEnd-ID in Umsätzen
8 * BUG: 0694 NPE beim Parsen von CAMT-Dateien - https://github.com/hbci4j/hbci4java/commit/b2b607ad8b72012978badab5f8cc39a8f8dfccaa
9 * CHG: 0693 Nachtrag zu Bugzilla 1864 - Kontofilter in der Liste der Konten auf der Startseite ausblenden, dort ist der Platz dafuer zu knapp
10 * NEW: 0692 BUGZILLA 1864 - Filterkriterien in der Liste der Konten (u.a. deaktivierte Konten ausblenden)
11 * NEW: 0691 Suchbegriff "flicker" in die Liste der TAN-Verfahren aufgenommen, für die chipTAN USB in Frage kommt
12 * NEW: 0690 Sonderbehandlung fuer Fehlerfall https://homebanking-hilfe.de/forum/topic.php?p=139423#real139423 (Fehler beim Update der H2-Datenbank durch fehlerhaften H2-Treiber)
13 * NEW: 0689 BUGZILLA 1861 - Unterstützung für benutzerspezifische CSV-Import-Profile
14 * NEW: 0688 Neue obantoo-Version mit aktualisierter BLZ-Datei gültig ab 03.09.2018
15 * NEW: 0687 Nur jene Synchronizisierungsoptionen anzeigen, die das Backend unterstützt
16 * NEW: 0686 Manueller Import von Umsätzen im CAMT-Format
17 * BUG: 0685 BUGZILLA 1860 - Kein Scrollbalken bei Anzeige einer überlangen Banknachricht
18 * NEW: 0684 BUGZILLA 1621 - Support für Umsatz-Abruf im CAMT-Format
19 * BUG: 0683 Neuer PIN/TAN-Bankzugang liess sich nicht mehr anlegen, da die ChipTAN-USB-Checkbox zu dem Zeitpunkt nicht korrekt berücksichtigt wurde
20 * NEW: 0682 Neue HBCI4Java-Version mit CAMT-Bugfix - https://github.com/hbci4j/hbci4java/commit/3dc9ebf080810acc2636aef0c9413e0d40672dbb
21 * NEW: 0681 Neue HBCI4Java-Version mit Unterstützung für CAMT - https://github.com/hbci4j/hbci4java/commit/ecca11320308b1fa1dc40bb37e6571d629064471
22 * BUG: 0680 BUGZILLA 1858 - Hibiscus sucht auch bei deaktivierter chipTAN-USB-Option weiter nach Kartenlesern
23 * NEW: 0679 Support für HKKAZ/HKKAN in Segment-Version 7 - https://github.com/hbci4j/hbci4java/commit/e3372a339bd5b9f0c2cea80155199f475dd46ed4
24 * DEL: 0678 Option "Dauerhafte Internetverbindung, Aufforderung zum Verbinden nicht erforderlich" aus den Einstellungen entfernt, braucht keiner mehr
25 * NEW: 0677 Option "Alle Daten des Verwendungszwecks anzeigen" auch in Liste der Umsätze konfigurierbar (per Config-Button oben rechts)
26 * NEW: 0676 In der Auswertung "Umsätze nach Kategorien -> Im Verlauf" können durch Rechtsklick in die Grafik auch andere Intervalle (Jahr, Monat, Woche) ausgewählt werden.
27 * BUG: 0675 In Kontoliste in der Spalte "verfügbarer Saldo" das Währungskennzeichen des konkreten Kontos verwenden und nicht des ersten gefundenen
28 * NEW: 0674 Wenn eine Bank im Verwendungszweck zwar das "SVWZ"-Tag liefert, es aber keinen Wert enthält, wird ebenfalls ein Fallback auf die Anzeige des kompletten Verwendungszweck gemacht
29 * NEW: 0673 Beim MT940-Export in Feld :25: das Währungskennzeichen weglassen und die Auszugsnummer in Feld ":28C:" mit dem Pseudowert "1" ausgeben - SAP benötigt das für den Import
30 * NEW: 0672 Fehler beim Ermitteln der Kartenleser-Features tolerieren (der tanJACK USB scheint das nicht zu unterstützen) - https://github.com/hbci4j/hbci4java/commit/22b702505bc9aef54bdb7b6663c948ce4b0b91cf
31 * BUG: 0671 Export-Optionen "Saldo ausblenden" und "Summenzeile anzeigen" funktionierten nur, wenn die Checkboxen beim Export betätigt wurden - https://homebanking-hilfe.de/forum/topic.php?p=138415
32
033 2018-06-27 Version 2.8.3
134
235 * NEW: 0670 chipTAN USB auch dann anbieten, wenn zwar chipTAN optisch ausgewählt aber ein Kartenleser gefunden wurde
Binary diff not shown
0 <?xml version="1.0" encoding="UTF-8" standalone="no"?>
1 <!-- Created with Inkscape (http://www.inkscape.org/) -->
2
3 <svg
4 xmlns:dc="http://purl.org/dc/elements/1.1/"
5 xmlns:cc="http://creativecommons.org/ns#"
6 xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
7 xmlns:svg="http://www.w3.org/2000/svg"
8 xmlns="http://www.w3.org/2000/svg"
9 xmlns:xlink="http://www.w3.org/1999/xlink"
10 xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
11 xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
12 width="210mm"
13 height="297mm"
14 viewBox="0 0 210 297"
15 version="1.1"
16 id="svg8"
17 inkscape:version="0.92.3 (2405546, 2018-03-11)"
18 sodipodi:docname="camtsetup.svg"
19 inkscape:export-filename="/work/willuhn/git/hibiscus/src/img/300/camtsetup.png"
20 inkscape:export-xdpi="84.57"
21 inkscape:export-ydpi="84.57">
22 <defs
23 id="defs2"><marker
24 inkscape:stockid="Arrow1Mend"
25 orient="auto"
26 refY="0.0"
27 refX="0.0"
28 id="Arrow1Mend"
29 style="overflow:visible;"
30 inkscape:isstock="true">
31 <path
32 id="path1469"
33 d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
34 style="fill-rule:evenodd;stroke:#6f6f6f;stroke-width:1pt;stroke-opacity:1;fill:#6f6f6f;fill-opacity:1"
35 transform="scale(0.4) rotate(180) translate(10,0)" />
36 </marker>
37 <marker
38 inkscape:stockid="Arrow1Lstart"
39 orient="auto"
40 refY="0.0"
41 refX="0.0"
42 id="Arrow1Lstart"
43 style="overflow:visible"
44 inkscape:isstock="true">
45 <path
46 id="path1460"
47 d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
48 style="fill-rule:evenodd;stroke:#6f6f6f;stroke-width:1pt;stroke-opacity:1;fill:#6f6f6f;fill-opacity:1"
49 transform="scale(0.8) translate(12.5,0)" />
50 </marker>
51 <marker
52 inkscape:stockid="Arrow2Send"
53 orient="auto"
54 refY="0.0"
55 refX="0.0"
56 id="Arrow2Send"
57 style="overflow:visible;"
58 inkscape:isstock="true">
59 <path
60 id="path1493"
61 style="fill-rule:evenodd;stroke-width:0.625;stroke-linejoin:round;stroke:#6f6f6f;stroke-opacity:1;fill:#6f6f6f;fill-opacity:1"
62 d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
63 transform="scale(0.3) rotate(180) translate(-2.3,0)" />
64 </marker>
65 <marker
66 inkscape:stockid="Arrow2Mend"
67 orient="auto"
68 refY="0.0"
69 refX="0.0"
70 id="Arrow2Mend"
71 style="overflow:visible;"
72 inkscape:isstock="true">
73 <path
74 id="path1487"
75 style="fill-rule:evenodd;stroke-width:0.625;stroke-linejoin:round;stroke:#6f6f6f;stroke-opacity:1;fill:#6f6f6f;fill-opacity:1"
76 d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
77 transform="scale(0.6) rotate(180) translate(0,0)" />
78 </marker>
79 <marker
80 inkscape:stockid="Arrow2Lend"
81 orient="auto"
82 refY="0.0"
83 refX="0.0"
84 id="Arrow2Lend"
85 style="overflow:visible;"
86 inkscape:isstock="true">
87 <path
88 id="path1481"
89 style="fill-rule:evenodd;stroke-width:0.625;stroke-linejoin:round;stroke:#6f6f6f;stroke-opacity:1;fill:#6f6f6f;fill-opacity:1"
90 d="M 8.7185878,4.0337352 L -2.2072895,0.016013256 L 8.7185884,-4.0017078 C 6.9730900,-1.6296469 6.9831476,1.6157441 8.7185878,4.0337352 z "
91 transform="scale(1.1) rotate(180) translate(1,0)" />
92 </marker>
93 <marker
94 inkscape:stockid="Arrow1Lend"
95 orient="auto"
96 refY="0.0"
97 refX="0.0"
98 id="Arrow1Lend"
99 style="overflow:visible;"
100 inkscape:isstock="true">
101 <path
102 id="path1463"
103 d="M 0.0,0.0 L 5.0,-5.0 L -12.5,0.0 L 5.0,5.0 L 0.0,0.0 z "
104 style="fill-rule:evenodd;stroke:#6f6f6f;stroke-width:1pt;stroke-opacity:1;fill:#6f6f6f;fill-opacity:1"
105 transform="scale(0.8) rotate(180) translate(12.5,0)" />
106 </marker>
107 <linearGradient
108 inkscape:collect="always"
109 id="linearGradient1421">
110 <stop
111 style="stop-color:#bdbdbd;stop-opacity:1"
112 offset="0"
113 id="stop1417" />
114 <stop
115 id="stop1425"
116 offset="0.40976068"
117 style="stop-color:#fafafa;stop-opacity:0.83137256" />
118 <stop
119 style="stop-color:#fefefe;stop-opacity:0.74509805"
120 offset="0.46878463"
121 id="stop1427" />
122 <stop
123 style="stop-color:#a0a0a0;stop-opacity:0.66274512"
124 offset="1"
125 id="stop1419" />
126 </linearGradient>
127 <filter
128 inkscape:collect="always"
129 style="color-interpolation-filters:sRGB"
130 id="filter1029"
131 x="-0.18230396"
132 width="1.3646079"
133 y="-0.22848846"
134 height="1.4569769">
135 <feGaussianBlur
136 inkscape:collect="always"
137 stdDeviation="1.3494205"
138 id="feGaussianBlur1031" />
139 </filter>
140 <filter
141 inkscape:collect="always"
142 style="color-interpolation-filters:sRGB"
143 id="filter1121"
144 x="-0.11554185"
145 width="1.2310837"
146 y="-0.082112184"
147 height="1.1642244">
148 <feGaussianBlur
149 inkscape:collect="always"
150 stdDeviation="2.0961503"
151 id="feGaussianBlur1123" />
152 </filter>
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 <linearGradient
186 inkscape:collect="always"
187 xlink:href="#linearGradient1421"
188 id="linearGradient1423"
189 x1="161.86833"
190 y1="63.457966"
191 x2="201.7448"
192 y2="63.457966"
193 gradientUnits="userSpaceOnUse" />
194 <filter
195 inkscape:collect="always"
196 style="color-interpolation-filters:sRGB"
197 id="filter2723"
198 x="-0.25683135"
199 width="1.5136627"
200 y="-0.2960247"
201 height="1.5920494">
202 <feGaussianBlur
203 inkscape:collect="always"
204 stdDeviation="1.3345558"
205 id="feGaussianBlur2725" />
206 </filter>
207 <filter
208 inkscape:collect="always"
209 style="color-interpolation-filters:sRGB"
210 id="filter2727"
211 x="-0.27834261"
212 width="1.5566852"
213 y="-0.0898687"
214 height="1.1797374">
215 <feGaussianBlur
216 inkscape:collect="always"
217 stdDeviation="1.3345558"
218 id="feGaussianBlur2729" />
219 </filter>
220 </defs>
221 <sodipodi:namedview
222 id="base"
223 pagecolor="#ffffff"
224 bordercolor="#666666"
225 borderopacity="1.0"
226 inkscape:pageopacity="0.0"
227 inkscape:pageshadow="2"
228 inkscape:zoom="1.979899"
229 inkscape:cx="549.26181"
230 inkscape:cy="401.53886"
231 inkscape:document-units="mm"
232 inkscape:current-layer="layer1"
233 showgrid="false"
234 inkscape:snap-global="false" />
235 <metadata
236 id="metadata5">
237 <rdf:RDF>
238 <cc:Work
239 rdf:about="">
240 <dc:format>image/svg+xml</dc:format>
241 <dc:type
242 rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
243 <dc:title></dc:title>
244 </cc:Work>
245 </rdf:RDF>
246 </metadata>
247 <g
248 inkscape:label="Layer 1"
249 inkscape:groupmode="layer"
250 id="layer1">
251 <path
252 sodipodi:nodetypes="sccssssss"
253 inkscape:connector-curvature="0"
254 id="path1043"
255 d="m 110.38811,173.8337 h 23.06949 l 17.98406,14.22678 v 44.20244 c 0,1.57208 -1.10922,2.8377 -2.48704,2.8377 h -38.56651 c -1.37782,0 -2.48704,-1.26562 -2.48704,-2.8377 V 176.6714 c 0,-1.57209 1.10922,-2.8377 2.48704,-2.8377 z"
256 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:0.553;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#060606;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:3.4313364;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;filter:url(#filter1121);color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
257 <path
258 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke:#3d76a4;stroke-width:5.73099995;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate"
259 d="m 106.89183,169.77046 h 23.06949 l 17.98407,14.22678 v 44.20244 c 0,1.57208 -1.10922,2.8377 -2.48704,2.8377 h -38.56652 c -1.37782,0 -2.48704,-1.26562 -2.48704,-2.8377 v -55.59152 c 0,-1.57209 1.10922,-2.8377 2.48704,-2.8377 z"
260 id="rect819"
261 inkscape:connector-curvature="0"
262 sodipodi:nodetypes="sccssssss" />
263 <text
264 xml:space="preserve"
265 style="font-style:normal;font-weight:normal;font-size:12.34722233px;line-height:17.22174644px;font-family:Sans;letter-spacing:0px;word-spacing:0px;fill:#3d76a4;fill-opacity:1;stroke:none;stroke-width:1.32474971px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
266 x="126.15907"
267 y="228.31453"
268 id="text817"><tspan
269 sodipodi:role="line"
270 x="126.15907"
271 y="228.31453"
272 style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-family:Sans;-inkscape-font-specification:'Sans Bold';text-align:center;text-anchor:middle;fill:#3d76a4;fill-opacity:1;stroke-width:1.32474971px"
273 id="tspan1041">CAMT</tspan></text>
274 <path
275 style="opacity:0.38399999;fill:#000000;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:1.36500001;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;filter:url(#filter1029)"
276 d="m 130.60573,171.09885 c 2.01587,6.00037 0.96068,11.10305 1.27566,14.31585 1.73239,-0.29923 16.22149,-0.45673 17.15069,-0.0473 z"
277 id="path851"
278 inkscape:connector-curvature="0"
279 sodipodi:nodetypes="cccc" />
280 <path
281 sodipodi:nodetypes="cccc"
282 inkscape:connector-curvature="0"
283 id="path849"
284 d="m 129.50409,168.58259 c 4.0475,3.82701 3.46478,10.29985 3.02381,13.27641 6.78782,-0.53546 13.6229,0.20474 16.58371,2.69309 z"
285 style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:1.36500001;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
286 <path
287 style="fill:none;fill-rule:evenodd;stroke:#3d76a4;stroke-width:2.66499996;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
288 d="m 129.50409,168.58259 c 4.0475,3.82701 3.46478,10.29985 3.02381,13.27641 6.78782,-0.53546 13.6229,0.20474 16.58371,2.69309"
289 id="path847"
290 inkscape:connector-curvature="0"
291 sodipodi:nodetypes="ccc" />
292 <path
293 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:0.553;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#060606;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:3.4313364;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;filter:url(#filter1121);color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate"
294 d="m 78.827098,93.135783 h 23.069492 l 17.98406,14.226777 V 151.565 c 0,1.57208 -1.10922,2.8377 -2.48704,2.8377 H 78.827098 c -1.37782,0 -2.48704,-1.26562 -2.48704,-2.8377 V 95.973483 c 0,-1.57209 1.10922,-2.8377 2.48704,-2.8377 z"
295 id="path1125"
296 inkscape:connector-curvature="0"
297 sodipodi:nodetypes="sccssssss" />
298 <path
299 sodipodi:nodetypes="sccssssss"
300 inkscape:connector-curvature="0"
301 id="path1127"
302 d="m 75.330818,89.072543 h 23.06949 l 17.984072,14.226777 v 44.20244 c 0,1.57208 -1.10922,2.8377 -2.48704,2.8377 H 75.330818 c -1.37782,0 -2.48704,-1.26562 -2.48704,-2.8377 V 91.910243 c 0,-1.57209 1.10922,-2.8377 2.48704,-2.8377 z"
303 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke:#666666;stroke-width:5.73099995;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
304 <text
305 id="text1133"
306 y="147.84215"
307 x="94.35128"
308 style="font-style:normal;font-weight:normal;font-size:12.34722233px;line-height:13.82831383px;font-family:Sans;letter-spacing:0px;word-spacing:0px;fill:#666666;fill-opacity:1;stroke:none;stroke-width:1.06371641px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;"
309 xml:space="preserve"><tspan
310 style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-family:Sans;-inkscape-font-specification:'Sans Bold';text-align:center;text-anchor:middle;fill:#666666;fill-opacity:1;stroke-width:1.06371641px;"
311 y="147.84215"
312 x="94.35128"
313 sodipodi:role="line"
314 id="tspan1433">MT940</tspan></text>
315 <path
316 sodipodi:nodetypes="cccc"
317 inkscape:connector-curvature="0"
318 id="path1135"
319 d="m 99.044718,90.400933 c 2.015872,6.00037 0.960682,11.103047 1.275662,14.315847 1.73239,-0.29923 16.22149,-0.45673 17.15069,-0.0473 z"
320 style="opacity:0.38399999;fill:#000000;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:1.36500001;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;filter:url(#filter1029)" />
321 <path
322 style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:1.36500001;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
323 d="m 97.943078,87.884673 c 4.047502,3.82701 3.464782,10.29985 3.023812,13.276407 6.78782,-0.53546 13.6229,0.20474 16.58371,2.69309 z"
324 id="path1137"
325 inkscape:connector-curvature="0"
326 sodipodi:nodetypes="cccc" />
327 <path
328 sodipodi:nodetypes="ccc"
329 inkscape:connector-curvature="0"
330 id="path1139"
331 d="m 97.943078,87.884673 c 4.047502,3.82701 3.464782,10.29985 3.023812,13.276407 6.78782,-0.53546 13.6229,0.20474 16.58371,2.69309"
332 style="fill:none;fill-rule:evenodd;stroke:#666666;stroke-width:2.66499996;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
333 <g
334 id="g1446"
335 transform="matrix(0.3091787,0,0,0.3091787,35.176442,93.214905)">
336 <path
337 sodipodi:nodetypes="cccccc"
338 inkscape:connector-curvature="0"
339 id="rect1404"
340 d="m 151.47395,53.29985 h 67.94122 l 6.89807,5.811382 v 68.744418 h -74.83929 z"
341 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#999999;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:2.66499996;stroke-linecap:square;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
342 <rect
343 y="93.176338"
344 x="162.15178"
345 height="33.923363"
346 width="53.294643"
347 id="rect1407"
348 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:3.48955512;stroke-linecap:square;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
349 <rect
350 y="53.29985"
351 x="161.30135"
352 height="25.985863"
353 width="40.443455"
354 id="rect1415"
355 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:url(#linearGradient1423);fill-opacity:1;fill-rule:evenodd;stroke:none;stroke-width:2.16499996;stroke-linecap:square;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
356 <path
357 sodipodi:nodetypes="ccsssssssscccccccccccccssssccccsssscccc"
358 inkscape:connector-curvature="0"
359 style="fill:#000000;fill-opacity:0.98387098;stroke-width:0.15967564"
360 d="m 227.45195,58.428605 -7.3069,-6.739932 c -0.29939,-0.299392 -0.70561,-0.46769 -1.12907,-0.46769 h -67.74065 c -0.88189,0 -1.59676,0.714868 -1.59676,1.596756 v 75.047551 c 0,0.88173 0.71487,1.59676 1.59676,1.59676 h 75.04755 c 0.88189,0 1.59676,-0.71503 1.59676,-1.59676 V 59.557671 c 0,-0.42346 -0.1683,-0.829515 -0.46769,-1.129066 z m -64.99933,-4.014109 h 38.32216 V 78.365843 H 162.45262 Z M 163.251,126.26854 V 94.6788 h 51.09621 v 31.58974 z m 61.47513,0 h -7.18541 V 92.73665 c 0,-0.88189 -0.71487,-1.596755 -1.59676,-1.596755 h -54.28972 c -0.88188,0 -1.59675,0.714865 -1.59675,1.596755 v 33.53189 h -7.18541 V 54.414496 h 6.38703 V 79.9626 c 0,0.881889 0.71487,1.596756 1.59676,1.596756 h 41.51566 c 0.88189,0 1.59676,-0.714867 1.59676,-1.596756 V 54.414496 h 14.38632 l 6.37152,5.804711 z"
361 id="path1259" />
362 <rect
363 x="219.23196"
364 y="121.34135"
365 style="fill:#231f20;stroke-width:0.15967564"
366 width="3.1935129"
367 height="3.1935129"
368 id="rect1261" />
369 <path
370 inkscape:connector-curvature="0"
371 id="path1409"
372 d="m 166.40401,102.24777 h 44.41221"
373 style="fill:none;fill-rule:evenodd;stroke:#a9a9a9;stroke-width:2.19798326;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
374 <path
375 style="fill:none;fill-rule:evenodd;stroke:#a9a9a9;stroke-width:2.19798326;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
376 d="m 166.40401,109.99628 h 44.41221"
377 id="path1411"
378 inkscape:connector-curvature="0" />
379 <path
380 inkscape:connector-curvature="0"
381 id="path1413"
382 d="m 166.40401,117.5558 h 44.41221"
383 style="fill:none;fill-rule:evenodd;stroke:#a9a9a9;stroke-width:2.19798326;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1" />
384 <rect
385 y="53.205357"
386 x="186.53125"
387 height="20.221727"
388 width="8.4099703"
389 id="rect1429"
390 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#000000;fill-opacity:0.97849462;fill-rule:evenodd;stroke:none;stroke-width:2.16499996;stroke-linecap:square;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
391 </g>
392 <text
393 id="text1456"
394 y="209.45544"
395 x="125.61912"
396 style="font-style:normal;font-weight:normal;font-size:16.7424984px;line-height:23.35221863px;font-family:Sans;letter-spacing:0px;word-spacing:0px;fill:#5e5e5e;fill-opacity:1;stroke:none;stroke-width:1.79632437px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;"
397 xml:space="preserve"><tspan
398 id="tspan1454"
399 style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-family:Sans;-inkscape-font-specification:'Sans Bold';text-align:center;text-anchor:middle;fill:#5e5e5e;fill-opacity:1;stroke-width:1.79632437px;"
400 y="209.45544"
401 x="125.61912"
402 sodipodi:role="line">&lt;/&gt;</tspan></text>
403 <path
404 sodipodi:nodetypes="cc"
405 inkscape:connector-curvature="0"
406 id="path2585"
407 d="m 84.769881,163.26256 c -5.988006,24.47914 -2.874726,29.48428 8.522642,35.64015"
408 style="opacity:0.68199989;fill:none;fill-rule:evenodd;stroke:#6f6f6f;stroke-width:2.59508085;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1;filter:url(#filter2727)" />
409 <path
410 inkscape:transform-center-x="0.73614057"
411 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:0.68199989;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#6f6f6f;fill-opacity:1;fill-rule:evenodd;stroke:#6f6f6f;stroke-width:1.66467774;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;filter:url(#filter2723);color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate"
412 inkscape:transform-center-y="-0.97010407"
413 d="M 96.854902,201.57525 84.38394,198.445 l 5.524401,-7.68957 z"
414 id="path2587"
415 inkscape:connector-curvature="0"
416 sodipodi:nodetypes="cccc" />
417 <path
418 style="fill:none;fill-rule:evenodd;stroke:#509c6b;stroke-width:2.59508085;stroke-linecap:round;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-opacity:1"
419 d="m 83.534743,161.20662 c -5.988006,24.47914 -2.874726,29.48428 8.522642,35.64015"
420 id="path1458"
421 inkscape:connector-curvature="0"
422 sodipodi:nodetypes="cc" />
423 <path
424 sodipodi:nodetypes="cccc"
425 inkscape:connector-curvature="0"
426 id="path2583"
427 d="m 95.619764,199.51931 -12.470962,-3.13025 5.524401,-7.68957 z"
428 inkscape:transform-center-y="-0.97010407"
429 style="color:#000000;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#509c6b;fill-opacity:1;fill-rule:evenodd;stroke:#509c6b;stroke-width:1.66467774;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;paint-order:markers stroke fill;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate"
430 inkscape:transform-center-x="0.73614057" />
431 </g>
432 </svg>
22 <plugin xmlns="http://www.willuhn.de/schema/jameica-plugin"
33 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
44 xsi:schemaLocation="http://www.willuhn.de/schema/jameica-plugin http://www.willuhn.de/schema/jameica-plugin-1.2.xsd"
5 name="hibiscus" version="2.8.3" class="de.willuhn.jameica.hbci.HBCI">
5 name="hibiscus" version="2.8.4" class="de.willuhn.jameica.hbci.HBCI">
66
77 <description>HBCI-Onlinebanking-Plugin für Jameica</description>
8 <url>https://www.willuhn.de/products/hibiscus/releases/2.8/hibiscus-2.8.3.zip</url>
8 <url>https://www.willuhn.de/products/hibiscus/releases/2.8/hibiscus-2.8.4.zip</url>
99 <homepage>http://www.willuhn.de/products/hibiscus</homepage>
1010 <license>GPL - http://www.gnu.org/copyleft/gpl.html</license>
1111 <icon>hibiscus-large.png</icon>
5454
5555 <navigation>
5656 <item id="hibiscus.navi" name="Hibiscus" icon-close="folder.png" icon-open="folder-open.png">
57 <item id="hibiscus.navi.passports" name="Bank-Zugänge" icon-close="user-info.png" action="de.willuhn.jameica.hbci.gui.action.PassportList" />
57 <item id="hibiscus.navi.passports" name="Bank-Zugänge" icon-close="system-users.png" action="de.willuhn.jameica.hbci.gui.action.PassportList" />
5858 <item id="hibiscus.navi.accounts" name="Konten" icon-close="system-file-manager.png" action="de.willuhn.jameica.hbci.gui.action.KontoList" />
5959 <item id="hibiscus.navi.umsatz" name="Umsätze" icon-close="emblem-documents.png" action="de.willuhn.jameica.hbci.gui.action.KontoauszugList" />
6060 <item id="hibiscus.navi.kontoauszug" name="Elektr. Kontoauszüge" icon-close="application-pdf.png" action="de.willuhn.jameica.hbci.gui.action.KontoauszugPdfList" />
176176 empfaenger_blz varchar(15),
177177 empfaenger_name varchar(255),
178178 betrag double NOT NULL,
179 zweck varchar(35),
179 zweck varchar(255),
180180 zweck2 varchar(35),
181181 zweck3 varchar(1000),
182182 datum date NOT NULL,
191191 flags int(1) NULL,
192192 gvcode varchar(3) NULL,
193193 addkey varchar(3) NULL,
194 txid varchar(100),
195 purposecode varchar(10),
196 endtoendid varchar(100),
194197 UNIQUE (id),
195198 PRIMARY KEY (id)
196199 );
442445 CREATE INDEX idx_umsatz_valuta ON umsatz(valuta);
443446 CREATE INDEX idx_umsatz_flags ON umsatz(flags);
444447
445 INSERT INTO version (name,version) values ('db',62);
448 INSERT INTO version (name,version) values ('db',64);
446449
447450 COMMIT;
285285 , empfaenger_blz VARCHAR(15)
286286 , empfaenger_name VARCHAR(255)
287287 , betrag DOUBLE NOT NULL
288 , zweck VARCHAR(35)
288 , zweck VARCHAR(255)
289289 , zweck2 VARCHAR(35)
290290 , zweck3 TEXT
291291 , datum DATE NOT NULL
300300 , flags int(1)
301301 , gvcode varchar(3)
302302 , addkey varchar(3)
303 , txid varchar(100)
304 , purposecode varchar(10)
305 , endtoendid varchar(100)
303306 , UNIQUE (id)
304307 , PRIMARY KEY (id)
305308 ) ENGINE=InnoDB;
469472 ALTER TABLE ueberweisung ADD INDEX (termin);
470473 ALTER TABLE lastschrift ADD INDEX (termin);
471474
472 INSERT INTO version (name,version) values ('db',62);
475 INSERT INTO version (name,version) values ('db',64);
156156 empfaenger_blz varchar(15),
157157 empfaenger_name varchar(255),
158158 betrag float NOT NULL,
159 zweck varchar(35),
159 zweck varchar(255),
160160 zweck2 varchar(35),
161161 zweck3 varchar(1000),
162162 datum date NOT NULL,
170170 umsatztyp_id integer NULL,
171171 flags integer NULL,
172172 gvcode varchar(3) NULL,
173 addkey varchar(3) NULL
173 addkey varchar(3) NULL,
174 txid varchar(100),
175 purposecode varchar(10),
176 endtoendid varchar(100)
174177 );
175178
176179 CREATE TABLE umsatztyp (
388391 CREATE INDEX idx_umsatz_valuta ON umsatz(valuta);
389392 CREATE INDEX idx_umsatz_flags ON umsatz(flags);
390393
391 INSERT INTO version (name,version) values ('db',62);
394 INSERT INTO version (name,version) values ('db',63);
4545 */
4646 protected void updateUPD(HBCIPassport passport)
4747 {
48 BPDUtil.updateCache(passport,Prefix.UPD);
48 if (BPDUtil.updateCache(passport,Prefix.UPD))
49 {
50 // Wenn wir neue UPD haben, aktualisieren wir gleich auch nochmal die BPD
51 // Denn wenn wir die UPD haben, sind auch die Konten vorhanden. Und damit
52 // koennen wir die BPD ebenfalls korrekt fuer alle verfuegbaren Kundenkennungen speichern
53 BPDUtil.expireCache(passport,Prefix.BPD);
54 BPDUtil.updateCache(passport,Prefix.BPD);
55 }
4956 }
5057
5158 /**
134134 public final static int HBCI_TRANSFER_BZU_LENGTH = settings.getInt("hbci.transfer.bzu.length",13);
135135
136136 /**
137 * Maximale Text-Laenge einer Verwendungszweck-Zeile fuer Auslandsueberweisungen.
138 */
139 public final static int HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH = settings.getInt("hbci.foreigntransfer.usage.maxlength",140);
137 * Maximale Text-Laenge einer Verwendungszweck-Zeile bei SEPA-Auftraegen.
138 */
139 public final static int HBCI_SEPATRANSFER_USAGE_MAXLENGTH = settings.getInt("hbci.foreigntransfer.usage.maxlength",140);
140140
141141 /**
142142 * Maximale Anzahl von Verwendungszwecken.
9595 * Template fuer den Dateinamen.
9696 */
9797 KONTOAUSZUG_TEMPLATE_NAME("kontoauszug.template.name","Vorlage für Dateinamen","${jahr}-${nummer}"),
98
99 /**
100 * Legt fest, ob CAMT fuer den Umsatz-Abruf verwendet werden soll.
101 */
102 UMSATZ_CAMT("umsatz.camt","CAMT-Format für Umsatz-Abruf verwenden",null);
98103
99104 ;
100105
1111 import de.willuhn.jameica.gui.Action;
1212 import de.willuhn.jameica.hbci.HBCI;
1313 import de.willuhn.jameica.hbci.gui.dialogs.ExportDialog;
14 import de.willuhn.jameica.hbci.server.EinnahmeAusgabe;
14 import de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum;
1515 import de.willuhn.jameica.messaging.StatusBarMessage;
1616 import de.willuhn.jameica.system.Application;
1717 import de.willuhn.jameica.system.OperationCanceledException;
3232 */
3333 public void handleAction(Object context) throws ApplicationException
3434 {
35 if (context == null || !(context instanceof EinnahmeAusgabe[]))
35 if (context == null || !(context instanceof EinnahmeAusgabeZeitraum[]))
3636 throw new ApplicationException(i18n.tr("Bitte wählen Sie die zu exportierenden Daten aus"));
3737
3838 try
3939 {
40 ExportDialog d = new ExportDialog((EinnahmeAusgabe[]) context,EinnahmeAusgabe.class);
40 ExportDialog d = new ExportDialog((EinnahmeAusgabeZeitraum[])context,EinnahmeAusgabeZeitraum.class);
4141 d.open();
4242 }
4343 catch (OperationCanceledException oce)
5555 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Fehler bei der Erstellung der Liste"),StatusBarMessage.TYPE_ERROR));
5656 }
5757 }
58
5958 }
60
61 /*******************************************************************************
62 * $Log: EinnahmeAusgabeExport.java,v $
63 * Revision 1.5 2011/05/11 10:20:28 willuhn
64 * @N OCE fangen
65 *
66 * Revision 1.4 2010-08-24 17:38:04 willuhn
67 * @N BUGZILLA 896
68 *
69 * Revision 1.3 2009/04/05 21:16:22 willuhn
70 * @B BUGZILLA 716
71 ******************************************************************************/
1111 import de.willuhn.jameica.gui.Action;
1212 import de.willuhn.jameica.gui.GUI;
1313 import de.willuhn.jameica.hbci.HBCI;
14 import de.willuhn.jameica.hbci.PassportRegistry;
1415 import de.willuhn.jameica.hbci.gui.views.KontoList;
1516 import de.willuhn.jameica.hbci.passport.Passport;
17 import de.willuhn.jameica.hbci.rmi.Konto;
1618 import de.willuhn.jameica.system.Application;
1719 import de.willuhn.jameica.system.OperationCanceledException;
1820 import de.willuhn.logging.Logger;
3234 */
3335 public void handleAction(Object context) throws ApplicationException
3436 {
35 if (context == null || !(context instanceof Passport))
36 throw new ApplicationException(i18n.tr("Kein Sicherheitsmedium ausgewählt oder keines verfügbar"));
37 if (context == null)
38 throw new ApplicationException(i18n.tr("Bitte wählen Sie ein Konto oder einen Bankzugang aus"));
3739
38 final Passport p = (Passport) context;
40 Passport passport = null;
41
42 if (context instanceof Konto)
43 {
44 try
45 {
46 Konto k = (Konto) context;
47 passport = PassportRegistry.findByClass(k.getPassportClass());
48 }
49 catch (ApplicationException ae)
50 {
51 throw ae;
52 }
53 catch (Exception e)
54 {
55 Logger.error("error while reading passport from select box",e);
56 throw new ApplicationException(i18n.tr("Fehler beim Auslesen der Konto-Informationen"));
57 }
58 }
59 else if (context instanceof Passport)
60 {
61 passport = (Passport) context;
62 }
63
64 final Passport p = passport;
3965
4066 GUI.startSync(new Runnable()
4167 {
0 /**********************************************************************
1 *
2 * Copyright (c) 2004 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.gui.action;
11
12 import de.willuhn.jameica.gui.Action;
13 import de.willuhn.jameica.hbci.HBCI;
14 import de.willuhn.jameica.hbci.gui.dialogs.KontoauszugSettingsDialog;
15 import de.willuhn.jameica.system.Application;
16 import de.willuhn.jameica.system.OperationCanceledException;
17 import de.willuhn.util.ApplicationException;
18 import de.willuhn.util.I18N;
19
20 /**
21 * Action fuer die Einstellungen des Kontoauszugsabrufes.
22 */
23 public class KontoauszugSettings implements Action
24 {
25 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
26
27 /**
28 * @see de.willuhn.jameica.gui.Action#handleAction(java.lang.Object)
29 */
30 @Override
31 public void handleAction(Object context) throws ApplicationException
32 {
33 try
34 {
35 KontoauszugSettingsDialog d = new KontoauszugSettingsDialog();
36 d.open();
37 }
38 catch (ApplicationException ae)
39 {
40 throw ae;
41 }
42 catch (OperationCanceledException oce)
43 {
44 throw oce;
45 }
46 catch (Exception e)
47 {
48 throw new ApplicationException(i18n.tr("Fehler beim Speichern der Einstellungen"),e);
49 }
50 }
51
52 }
53
54
2727 */
2828 public class UmsatzDetailEdit implements Action
2929 {
30
31 private boolean createReverse=false;
32 private Konto toBookTo=null;
30 private boolean createReverse = false;
31 private Konto toBookTo = null;
3332
3433 /**
3534 * setzt ein flag, dass die Gegenbuchung des Kontext-Objects erstellt werden soll
3635 * @param toBookTo Offline-Konto, auf das die Gegenbuchung erstellt werden soll
3736 * @return das (modifizierte) Objekt selbst
3837 * */
39 public UmsatzDetailEdit asReverse(Konto toBookTo){
40 this.createReverse=true;
41 this.toBookTo=toBookTo;
38 public UmsatzDetailEdit asReverse(Konto toBookTo)
39 {
40 this.createReverse = true;
41 this.toBookTo = toBookTo;
4242 return this;
4343 }
4444
7171 throw new ApplicationException(i18n.tr("Fehler beim Anlegen des Umsatzes: {0}",re.getMessage()));
7272 }
7373 }
74 else if (!(context instanceof Umsatz)){
74 else if (!(context instanceof Umsatz))
75 {
7576 return;
76 }else if(createReverse){
77 }
78 else if (createReverse)
79 {
7780 try
7881 {
7982 Umsatz orig=(Umsatz)context;
8689 u.setGegenkontoNummer(konto.getKontonummer());
8790 u.setUmsatzTyp(null);
8891 context = u;
89 } catch (RemoteException e)
92 }
93 catch (RemoteException e)
9094 {
9195 throw new ApplicationException(e);
9296 }
136136 }
137137
138138 ButtonArea buttons = new ButtonArea();
139 buttons.addButton(i18n.tr("Bank-Zugang einrichten"),new PassportDetail(),null,true,"user-info.png");
139 buttons.addButton(i18n.tr("Bank-Zugang einrichten"),new PassportDetail(),null,true,"system-users.png");
140140 buttons.addButton(i18n.tr("Konten-Übersicht"),new KontoList(),null,false,"wallet-open.png");
141141 buttons.paint(comp);
142142 }
1919 import de.willuhn.jameica.hbci.Settings;
2020 import de.willuhn.jameica.hbci.gui.action.KontoNew;
2121 import de.willuhn.jameica.hbci.gui.parts.KontoList;
22 import de.willuhn.jameica.hbci.server.KontoUtil;
2223 import de.willuhn.jameica.system.Application;
2324 import de.willuhn.util.I18N;
2425
6667 */
6768 public void paint(Composite parent) throws RemoteException
6869 {
69 KontoList l = new KontoList(new KontoNew());
70 KontoList l = new KontoList(KontoUtil.getKonten(null),new KontoNew());
71 l.setShowFilter(false);
7072 l.paint(parent);
7173 }
7274
7981 }
8082
8183 }
82
83
84 /*********************************************************************
85 * $Log: Konten.java,v $
86 * Revision 1.9 2010/08/12 17:12:32 willuhn
87 * @N Saldo-Chart komplett ueberarbeitet (Daten wurden vorher mehrmals geladen, Summen-Funktion, Anzeige mehrerer Konten, Durchschnitt ueber mehrere Konten, Bugfixing, echte "Homogenisierung" der Salden via SaldoFinder)
88 *
89 * Revision 1.8 2010-07-29 21:43:22 willuhn
90 * @N BUGZILLA 886
91 *
92 * Revision 1.7 2010/06/17 12:16:52 willuhn
93 * @N BUGZILLA 530
94 *
95 * Revision 1.6 2008/01/04 16:39:31 willuhn
96 * @N Weitere Hoehen-Angaben von Komponenten
97 *
98 * Revision 1.5 2007/12/18 17:10:22 willuhn
99 * @N Neues ExpandPart
100 * @N Boxen auf der Startseite koennen jetzt zusammengeklappt werden
101 *
102 * Revision 1.4 2007/08/29 10:04:42 willuhn
103 * @N Bug 476
104 *
105 * Revision 1.3 2006/06/29 23:10:33 willuhn
106 * @R Box-System aus Hibiscus in Jameica-Source verschoben
107 * @C keine eigene Startseite mehr, jetzt alles ueber Jameica-Boxsystem geregelt
108 *
109 * Revision 1.2 2006/03/27 21:34:16 willuhn
110 * *** empty log message ***
111 *
112 * Revision 1.1 2006/03/20 00:35:54 willuhn
113 * @N new box "Konten-Übersicht"
114 *
115 **********************************************************************/
7474 * Liefert das eigentliche SWT-Chart-Objekt.
7575 * @return das eigentliche SWT-Chart-Objekt.
7676 */
77 protected org.swtchart.Chart getChart()
77 public org.swtchart.Chart getChart()
7878 {
7979 return this.chart;
8080 }
3131 import de.willuhn.jameica.hbci.gui.input.BICInput;
3232 import de.willuhn.jameica.hbci.gui.input.IBANInput;
3333 import de.willuhn.jameica.hbci.gui.input.PurposeCodeInput;
34 import de.willuhn.jameica.hbci.gui.input.ZweckInput;
3435 import de.willuhn.jameica.hbci.rmi.Address;
3536 import de.willuhn.jameica.hbci.rmi.HibiscusAddress;
3637 import de.willuhn.jameica.hbci.rmi.SepaSammelTransfer;
5253
5354 // Eingabe-Felder
5455 private Input betrag = null;
55 private TextInput zweck = null;
56 private ZweckInput zweck = null;
5657
5758 private AddressInput empfName = null;
5859 private TextInput empfkto = null;
186187
187188 SepaSammelTransferBuchung s = this.getBuchung();
188189
189 zweck = new TextInput(s.getZweck(),HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
190 zweck.setValidChars(HBCIProperties.HBCI_SEPA_VALIDCHARS);
190 zweck = new ZweckInput(s.getZweck());
191191 zweck.setEnabled(!s.getSammelTransfer().ausgefuehrt());
192192 return zweck;
193193 }
4141 import de.willuhn.jameica.hbci.gui.input.PurposeCodeInput;
4242 import de.willuhn.jameica.hbci.gui.input.ReminderIntervalInput;
4343 import de.willuhn.jameica.hbci.gui.input.TerminInput;
44 import de.willuhn.jameica.hbci.gui.input.ZweckInput;
4445 import de.willuhn.jameica.hbci.gui.parts.AuslandsUeberweisungList;
4546 import de.willuhn.jameica.hbci.reminder.ReminderUtil;
4647 import de.willuhn.jameica.hbci.rmi.Address;
7273 // Eingabe-Felder
7374 private KontoInput kontoAuswahl = null;
7475 private Input betrag = null;
75 private TextInput zweck = null;
76 private ZweckInput zweck = null;
7677
7778 private AddressInput empfName = null;
7879 private TextInput empfkto = null;
270271 {
271272 if (zweck != null)
272273 return zweck;
273 zweck = new TextInput(getTransfer().getZweck(),HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
274 zweck.setValidChars(HBCIProperties.HBCI_SEPA_VALIDCHARS);
274 zweck = new ZweckInput(getTransfer().getZweck());
275275 zweck.setEnabled(!getTransfer().ausgefuehrt());
276276 return zweck;
277277 }
1010
1111 import java.rmi.RemoteException;
1212 import java.util.ArrayList;
13 import java.util.Calendar;
1314 import java.util.Date;
1415 import java.util.List;
1516
16 import org.eclipse.swt.widgets.TableItem;
17 import org.eclipse.swt.widgets.TreeItem;
1718
1819 import de.willuhn.datasource.rmi.DBIterator;
1920 import de.willuhn.jameica.gui.AbstractControl;
2021 import de.willuhn.jameica.gui.AbstractView;
2122 import de.willuhn.jameica.gui.GUI;
2223 import de.willuhn.jameica.gui.formatter.CurrencyFormatter;
23 import de.willuhn.jameica.gui.formatter.TableFormatter;
24 import de.willuhn.jameica.gui.formatter.TreeFormatter;
2425 import de.willuhn.jameica.gui.input.DateInput;
2526 import de.willuhn.jameica.gui.input.Input;
26 import de.willuhn.jameica.gui.parts.TablePart;
27 import de.willuhn.jameica.gui.input.SelectInput;
28 import de.willuhn.jameica.gui.parts.TreePart;
2729 import de.willuhn.jameica.gui.util.Color;
2830 import de.willuhn.jameica.gui.util.Font;
2931 import de.willuhn.jameica.hbci.HBCI;
3638 import de.willuhn.jameica.hbci.gui.input.RangeInput;
3739 import de.willuhn.jameica.hbci.rmi.Konto;
3840 import de.willuhn.jameica.hbci.server.EinnahmeAusgabe;
41 import de.willuhn.jameica.hbci.server.EinnahmeAusgabeTreeNode;
3942 import de.willuhn.jameica.messaging.StatusBarMessage;
4043 import de.willuhn.jameica.system.Application;
4144 import de.willuhn.jameica.util.DateUtil;
4952 {
5053 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
5154
52 private KontoInput kontoAuswahl = null;
53 private DateInput start = null;
54 private DateInput end = null;
55 private RangeInput range = null;
56
57 private TablePart table = null;
55 private KontoInput kontoAuswahl = null;
56 private DateInput start = null;
57 private DateInput end = null;
58 private RangeInput range = null;
59 private SelectInput interval = null;
60
61 private TreePart tree = null;
62
63 /**
64 * Gruppierung der Einnahmen/Ausgaben nach Zeitraum.
65 */
66 private enum Interval
67 {
68 ALL(-1, -1, i18n.tr("Gesamtzeitraum")),
69 YEAR(Calendar.DAY_OF_YEAR, Calendar.YEAR,i18n.tr("Jahr")),
70 MONTH(Calendar.DAY_OF_MONTH, Calendar.MONDAY, i18n.tr("Monat")),
71
72 ;
73
74 private String name;
75 private int type;
76 private int size;
77
78 /**
79 * ct.
80 * @param type
81 * @param size
82 * @param name
83 */
84 private Interval(int type, int size, String name)
85 {
86 this.name = name;
87 this.type = type;
88 this.size = size;
89 }
90
91 /**
92 * @see java.lang.Enum#toString()
93 */
94 @Override
95 public String toString()
96 {
97 return this.name;
98 }
99 }
58100
59101 /**
60102 * ct.
128170 }
129171
130172 /**
173 * Liefert ein Auswahl-Feld für die zeitliche Gruppierung.
174 * @return Auswahl-Feld
175 * */
176 public SelectInput getInterval()
177 {
178 if(this.interval !=null)
179 return this.interval;
180
181 this.interval = new SelectInput(Interval.values(), null);
182 this.interval.setName(i18n.tr("Gruppierung nach"));
183 return this.interval;
184 }
185
186 /**
131187 * Liefert eine Tabelle mit den Einnahmen/Ausgaben und Salden
132188 * @return Tabelle mit den Einnahmen/Ausgaben und Salden
133189 * @throws RemoteException
134190 */
135 public TablePart getTable() throws RemoteException
136 {
137 if (this.table != null)
138 return this.table;
139
140 table = new TablePart(getWerte(), null);
141 table.addColumn(i18n.tr("Konto"), "text");
142 table.addColumn(i18n.tr("Anfangssaldo"), "anfangssaldo",new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
143 table.addColumn(i18n.tr("Einnahmen"), "einnahmen", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
144 table.addColumn(i18n.tr("Ausgaben"), "ausgaben", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
145 table.addColumn(i18n.tr("Endsaldo"), "endsaldo", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
146 table.addColumn(i18n.tr("Plus/Minus"), "plusminus", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
147 table.addColumn(i18n.tr("Differenz"), "differenz", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
148
149 table.setFormatter(new TableFormatter()
191 public TreePart getTree() throws RemoteException
192 {
193 if (this.tree != null)
194 return this.tree;
195
196 tree = new TreePart(getWerte(), null);
197 tree.addColumn(i18n.tr("Konto"), "text");
198 tree.addColumn(i18n.tr("Anfangssaldo"), "anfangssaldo",new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
199 tree.addColumn(i18n.tr("Einnahmen"), "einnahmen", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
200 tree.addColumn(i18n.tr("Ausgaben"), "ausgaben", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
201 tree.addColumn(i18n.tr("Endsaldo"), "endsaldo", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
202 tree.addColumn(i18n.tr("Plus/Minus"), "plusminus", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
203 tree.addColumn(i18n.tr("Differenz"), "differenz", new CurrencyFormatter(HBCIProperties.CURRENCY_DEFAULT_DE, HBCI.DECIMALFORMAT));
204
205 tree.setFormatter(new TreeFormatter()
150206 {
151207 /**
152208 * @see de.willuhn.jameica.gui.formatter.TableFormatter#format(org.eclipse.swt.widgets.TableItem)
153209 */
154 public void format(TableItem item)
210 public void format(TreeItem item)
155211 {
156 if (item == null)
212 if (item == null || item.getData() instanceof EinnahmeAusgabeTreeNode)
157213 return;
158214
159215 EinnahmeAusgabe ea = (EinnahmeAusgabe) item.getData();
179235 }
180236 });
181237
182 table.setRememberColWidths(true);
183 table.setSummary(false);
184 return table;
185 }
186
187 /**
188 * Ermittelt die Liste der Zeilen fuer die Tabelle.
238 tree.setRememberColWidths(true);
239 return tree;
240 }
241
242 /**
243 * Ermittelt die Liste der Knoten für den Baum. Wenn keine Aufschlüsselung gewünscht ist,
244 * werden die Zeilen ohne Elternknoten angezeigt.
189245 * @return Liste mit den Werten.
190246 * @throws RemoteException
191247 */
192 private List<EinnahmeAusgabe> getWerte() throws RemoteException
193 {
194 List<EinnahmeAusgabe> list = new ArrayList<EinnahmeAusgabe>();
195
248 private List<Object> getWerte() throws RemoteException
249 {
196250 Date start = (Date) this.getStart().getValue();
197251 Date end = (Date) this.getEnd().getValue();
198 Object o = getKontoAuswahl().getValue();
252
253 Interval interval = (Interval) getInterval().getValue();
254 List<Object> result=new ArrayList<Object>();
255
256 // Sonderfall "alle". Es findet keine zeitliche Gruppierung statt
257 if(Interval.ALL.equals(interval))
258 {
259 result.addAll(this.getWerte(start, end));
260 return result;
261 }
262
263 EinnahmeAusgabeTreeNode node;
264 Calendar calendar = Calendar.getInstance();
265 calendar.setTime(DateUtil.startOfDay(start));
266 while (calendar.getTime().before(end))
267 {
268 calendar.set(interval.type, 1);
269 Date nodeFrom = calendar.getTime();
270
271 // ermittle den Zeipunkt unmittelbar vor dem nächsten Zeitraumstart
272 calendar.add(interval.size,1);
273 calendar.setTimeInMillis(calendar.getTime().getTime()-1);
274 Date nodeTo = DateUtil.startOfDay(calendar.getTime());
275
276 List<EinnahmeAusgabe> werte = this.getWerte(nodeFrom, nodeTo);
277 node = new EinnahmeAusgabeTreeNode(nodeFrom, nodeTo, werte);
278 result.add(node);
279
280 // ermittle den Start des nächsten Zeitraums
281 calendar.setTime(nodeFrom);
282 calendar.add(interval.size, 1);
283 }
284 return result;
285 }
286
287 /**
288 * Liefert die Werte fuer den angegebenen Zeitraum.
289 * @param start Startdatum.
290 * @param end Enddatum.
291 * @return die Liste der Werte.
292 * @throws RemoteException
293 */
294 private List<EinnahmeAusgabe> getWerte(Date start, Date end) throws RemoteException
295 {
296 List<EinnahmeAusgabe> list = new ArrayList<EinnahmeAusgabe>();
297
298 Object o = getKontoAuswahl().getValue();
199299
200300 // Uhrzeit zuruecksetzen, falls vorhanden
201301 if (start != null) start = DateUtil.startOfDay(start);
239339 summen.setAusgaben(summeAusgaben);
240340 summen.setEinnahmen(summeEinnahmen);
241341 summen.setEndsaldo(summeEndsaldo);
242 summen.setEnddatum((Date) this.getStart().getValue());
243 summen.setStartdatum((Date) this.getEnd().getValue());
342 summen.setEnddatum(start);
343 summen.setStartdatum(end);
244344 list.add(summen);
245345
246346 return list;
253353 {
254354 try
255355 {
256 TablePart table = this.getTable();
257 table.removeAll();
356 TreePart tree = this.getTree();
357 tree.removeAll();
258358
259359 Date tStart = (Date) getStart().getValue();
260360 Date tEnd = (Date) getEnd().getValue();
263363 GUI.getView().setErrorText(i18n.tr("Das Anfangsdatum muss vor dem Enddatum liegen"));
264364 return;
265365 }
266
267 List<EinnahmeAusgabe> list = this.getWerte();
268 for (EinnahmeAusgabe ea:list)
269 table.addItem(ea);
366 if (tStart == null || tEnd == null)
367 {
368 // bei einem offenen Intervall ist keine Aufschlüsselung möglich
369 getInterval().setValue(Interval.ALL);
370 }
371
372 tree.setList(this.getWerte());
270373 }
271374 catch (RemoteException re)
272375 {
414414 Address a = getAddress();
415415 if (a instanceof HibiscusAddress)
416416 s = ((HibiscusAddress)a).getBank();
417 this.bank = new TextInput(s, HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
417 this.bank = new TextInput(s, HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
418418 this.bank.setEnabled(isHibiscusAdresse());
419419 }
420420 return this.bank;
4040 import de.willuhn.jameica.hbci.HBCIProperties;
4141 import de.willuhn.jameica.hbci.Settings;
4242 import de.willuhn.jameica.hbci.gui.action.KontoDelete;
43 import de.willuhn.jameica.hbci.gui.action.KontoFetchFromPassport;
4443 import de.willuhn.jameica.hbci.gui.action.KontoNew;
4544 import de.willuhn.jameica.hbci.gui.action.UmsatzDetail;
46 import de.willuhn.jameica.hbci.gui.dialogs.PassportAuswahlDialog;
4745 import de.willuhn.jameica.hbci.gui.dialogs.SynchronizeOptionsDialog;
4846 import de.willuhn.jameica.hbci.gui.input.BICInput;
4947 import de.willuhn.jameica.hbci.gui.input.BLZInput;
671669 if (kontoList != null)
672670 return kontoList;
673671
674 kontoList = new de.willuhn.jameica.hbci.gui.parts.KontoList(new KontoNew());
672 kontoList = new de.willuhn.jameica.hbci.gui.parts.KontoList(null,new KontoNew());
675673 // BUGZILLA 81 http://www.willuhn.de/bugzilla/show_bug.cgi?id=81
676674 kontoList.addColumn(i18n.tr("Umsätze"),"numumsaetze");
677675 return kontoList;
827825 getKonto().setFlags(flags ^ Konto.FLAG_OFFLINE);
828826 }
829827
830 /**
831 * Liest alle ueber das Sicherheitsmedium verfuegbaren Konten
832 * aus und speichert sie (insofern Konten mit identischer kto-Nummer/BLZ nicht schon existieren).
833 */
834 public synchronized void handleReadFromPassport()
835 {
836
837 try
838 {
839 // Checken, ob wir ein Konto ausgewaehlt haben
840 Object selection = getKontoListe().getSelection();
841 Konto k = null;
842 if (selection != null && (selection instanceof Konto))
843 k = (Konto) selection;
844 PassportAuswahlDialog d = new PassportAuswahlDialog(k,PassportAuswahlDialog.POSITION_CENTER);
845 Passport p = (Passport) d.open();
846
847 new KontoFetchFromPassport().handleAction(p);
848 }
849 catch (OperationCanceledException oce)
850 {
851 Logger.info("operation cancelled");
852 }
853 catch (ApplicationException ae)
854 {
855 GUI.getStatusBar().setErrorText(ae.getMessage());
856 }
857 catch (Exception e)
858 {
859 Logger.error("error while reading passport from select box",e);
860 GUI.getStatusBar().setErrorText(i18n.tr("Fehler beim Auslesen der Konto-Informationen"));
861 }
862 }
863
864828 /**
865829 * Laedt die Tabelle mit den Umsaetzen neu.
866830 */
3939 import de.willuhn.jameica.hbci.gui.input.IBANInput;
4040 import de.willuhn.jameica.hbci.gui.input.KontoInput;
4141 import de.willuhn.jameica.hbci.gui.input.PurposeCodeInput;
42 import de.willuhn.jameica.hbci.gui.input.ZweckInput;
4243 import de.willuhn.jameica.hbci.gui.parts.SepaDauerauftragList;
4344 import de.willuhn.jameica.hbci.rmi.Address;
4445 import de.willuhn.jameica.hbci.rmi.HibiscusAddress;
7374
7475 private KontoInput kontoAuswahl = null;
7576 private DecimalInput betrag = null;
76 private TextInput zweck = null;
77 private ZweckInput zweck = null;
7778 private AddressInput empfName = null;
7879 private TextInput empfkto = null;
7980 private TextInput bic = null;
442443 * @return Eingabe-Feld.
443444 * @throws RemoteException
444445 */
445 public TextInput getZweck() throws RemoteException
446 public ZweckInput getZweck() throws RemoteException
446447 {
447448 if (zweck != null)
448449 return zweck;
449450
450451 SepaDauerauftrag t = getTransfer();
451 zweck = new TextInput(getTransfer().getZweck(),HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
452 zweck.setValidChars(HBCIProperties.HBCI_SEPA_VALIDCHARS);
452 zweck = new ZweckInput(getTransfer().getZweck());
453453 zweck.setMandatory(true);
454454 if (t.isActive())
455455 zweck.setEnabled(getBPD().getBoolean("usageeditable",true));
4242 import de.willuhn.jameica.hbci.gui.input.KontoInput;
4343 import de.willuhn.jameica.hbci.gui.input.ReminderIntervalInput;
4444 import de.willuhn.jameica.hbci.gui.input.TerminInput;
45 import de.willuhn.jameica.hbci.gui.input.ZweckInput;
4546 import de.willuhn.jameica.hbci.gui.parts.SepaLastschriftList;
4647 import de.willuhn.jameica.hbci.reminder.ReminderUtil;
4748 import de.willuhn.jameica.hbci.rmi.Address;
7677 // Eingabe-Felder
7778 private KontoInput kontoAuswahl = null;
7879 private Input betrag = null;
79 private TextInput zweck = null;
80 private ZweckInput zweck = null;
8081
8182 private AddressInput empfName = null;
8283 private TextInput empfkto = null;
391392 {
392393 if (zweck != null)
393394 return zweck;
394 zweck = new TextInput(getTransfer().getZweck(),HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
395 zweck.setValidChars(HBCIProperties.HBCI_SEPA_VALIDCHARS);
395 zweck = new ZweckInput(getTransfer().getZweck());
396396 zweck.setEnabled(!getTransfer().ausgefuehrt());
397397 return zweck;
398398 }
4343 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
4444
4545 // Eingabe-Felder
46 private CheckboxInput onlineMode = null;
4746 private CheckboxInput cachePin = null;
4847 private CheckboxInput storePin = null;
4948 private CheckboxInput decimalGrouping = null;
7675 umsatzTypTree = new UmsatzTypTree(new UmsatzTypNew());
7776 return umsatzTypTree;
7877 }
79
80 /**
81 * Checkbox zur Auswahl des Online-Mode.
82 * @return Checkbox.
83 */
84 public CheckboxInput getOnlineMode()
85 {
86 if (onlineMode == null)
87 onlineMode = new CheckboxInput(Settings.getOnlineMode());
88 return onlineMode;
89 }
9078
9179 /**
9280 * Checkbox zur Auswahl von Dezimal-Trennzeichen in Betraegen.
257245 Settings.setBuchungHabenForeground(hf.getRGB());
258246 Settings.setBuchungSollForeground(sf.getRGB());
259247
260 Settings.setOnlineMode(((Boolean)getOnlineMode().getValue()).booleanValue());
261248 Settings.setDecimalGrouping(((Boolean)getDecimalGrouping().getValue()).booleanValue());
262249 Settings.setKontoCheck(((Boolean)getKontoCheck().getValue()).booleanValue());
263250 Settings.setKontoCheckExcludeAddressbook(((Boolean)getKontoCheckExcludeAddressbook().getValue()).booleanValue());
1515 import org.eclipse.swt.widgets.Event;
1616 import org.eclipse.swt.widgets.Listener;
1717
18 import de.willuhn.datasource.BeanUtil;
1918 import de.willuhn.jameica.gui.AbstractControl;
2019 import de.willuhn.jameica.gui.AbstractView;
2120 import de.willuhn.jameica.gui.input.CheckboxInput;
7574 private Input primanota = null;
7675 private Input art = null;
7776 private Input customerRef = null;
77 private TextInput endToEndId = null;
7878 private TextInput gvcode = null;
7979
8080 private Input kommentar = null;
366366 }
367367 return this.customerRef;
368368 }
369
369
370 /**
371 * Liefert ein Eingabe-Feld mit der EndToEnd-ID.
372 * @return Eingabe-Feld.
373 * @throws RemoteException
374 */
375 public Input getEndToEndId() throws RemoteException
376 {
377 if (this.endToEndId == null)
378 {
379 String eref = StringUtils.trimToNull(getUmsatz().getEndToEndId());
380
381 // Fuer die Abwaertskompatibilitaet
382 if (eref == null)
383 eref = VerwendungszweckUtil.getTag(getUmsatz(),Tag.EREF);
384
385 this.endToEndId = new TextInput(eref,HBCIProperties.HBCI_SEPA_ENDTOENDID_MAXLENGTH);
386 this.endToEndId.setValidChars(HBCIProperties.HBCI_SEPA_VALIDCHARS);
387 this.endToEndId.setName(i18n.tr("End-to-End ID"));
388 this.endToEndId.setEnabled(false);
389
390 }
391 return this.endToEndId;
392 }
393
370394 /**
371395 * Liefert ein Eingabe-Feld fuer den GV-Code.
372396 * @return Eingabe-Feld.
455479 if (showAll)
456480 return VerwendungszweckUtil.toString(u);
457481
458 return (String) BeanUtil.get(u,Tag.SVWZ.name());
482 return (String) u.getAttribute(Tag.SVWZ.name());
459483 }
460484 catch (RemoteException re)
461485 {
263263 input.setEnabled(true);
264264 return input;
265265 }
266
267 /**
268 * @see de.willuhn.jameica.hbci.gui.controller.UmsatzDetailControl#getEndToEndId()
269 */
270 @Override
271 public Input getEndToEndId() throws RemoteException
272 {
273 Input input = super.getEndToEndId();
274 if (!input.isEnabled())
275 input.setEnabled(true);
276 return input;
277 }
266278
267279 /**
268280 * @see de.willuhn.jameica.hbci.gui.controller.UmsatzDetailControl#getGvCode()
357369
358370 u.setCustomerRef((String)getCustomerRef().getValue());
359371 u.setPrimanota((String)getPrimanota().getValue());
372 u.setEndToEndId((String)getEndToEndId().getValue());
360373
361374 Date valuta = (Date) getValuta().getValue();
362375 Date datum = (Date) getDatum().getValue();
99
1010 package de.willuhn.jameica.hbci.gui.dialogs;
1111
12 import java.beans.ExceptionListener;
13 import java.beans.XMLDecoder;
14 import java.beans.XMLEncoder;
15 import java.io.BufferedInputStream;
16 import java.io.BufferedOutputStream;
1712 import java.io.ByteArrayInputStream;
18 import java.io.File;
19 import java.io.FileInputStream;
20 import java.io.FileOutputStream;
2113 import java.io.IOException;
2214 import java.io.InputStreamReader;
15 import java.nio.charset.Charset;
16 import java.nio.charset.UnsupportedCharsetException;
2317 import java.util.ArrayList;
2418 import java.util.List;
2519
2721 import org.eclipse.swt.layout.GridData;
2822 import org.eclipse.swt.layout.GridLayout;
2923 import org.eclipse.swt.widgets.Composite;
24 import org.eclipse.swt.widgets.Event;
25 import org.eclipse.swt.widgets.Listener;
3026 import org.supercsv.io.CsvListReader;
3127 import org.supercsv.io.ICsvListReader;
3228 import org.supercsv.prefs.CsvPreference;
3834 import de.willuhn.jameica.gui.input.SelectInput;
3935 import de.willuhn.jameica.gui.input.SpinnerInput;
4036 import de.willuhn.jameica.gui.input.TextInput;
37 import de.willuhn.jameica.gui.internal.buttons.Cancel;
4138 import de.willuhn.jameica.gui.parts.ButtonArea;
4239 import de.willuhn.jameica.gui.util.Color;
4340 import de.willuhn.jameica.gui.util.Container;
4845 import de.willuhn.jameica.hbci.io.csv.Column;
4946 import de.willuhn.jameica.hbci.io.csv.Format;
5047 import de.willuhn.jameica.hbci.io.csv.Profile;
48 import de.willuhn.jameica.hbci.io.csv.ProfileUtil;
5149 import de.willuhn.jameica.system.Application;
5250 import de.willuhn.jameica.system.OperationCanceledException;
5351 import de.willuhn.logging.Logger;
6260 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
6361 private final static String[] CHARSETS = new String[]{"UTF-8","ISO-8859-15","ISO-8859-1"};
6462
63 private SelectInput profiles = null;
64 private Profile result = null;
6565 private Format format = null;
66 private Profile profile = null;
6766 private byte[] data = null;
6867
6968 private TextInput sepChar = null;
9392 this.data = data;
9493
9594 this.setTitle(i18n.tr("Zuordnung der Spalten"));
96 this.setSize(680,500);
95 this.setSize(680,700);
9796
9897 }
9998
104103 {
105104 // BUGZILLA 281
106105 Container options = new SimpleContainer(parent);
106 options.addInput(this.getProfiles());
107
108 ButtonArea b = new ButtonArea();
109 b.addButton(i18n.tr("CSV-Datei neu laden"), new Action()
110 {
111 public void handleAction(Object context) throws ApplicationException
112 {
113 reload();
114 }
115 },null,false,"view-refresh.png");
116 b.addButton(i18n.tr("Profil speichern..."), new Action() {
117
118 @Override
119 public void handleAction(Object context) throws ApplicationException
120 {
121 // Wir erzeugen erstmal ein neues Profil
122 // Der User entscheidet dann im CSVProfileStoreDialog, ob er ueberschreibt oder nicht
123 Profile p = new Profile();
124 p.setColumns(getColumns());
125 p.setName(getProfile().getName());
126 p.setSystem(false);
127 p.setFileEncoding((String)getFileEncoding().getValue());
128 p.setQuotingChar((String)getQuoteChar().getValue());
129 p.setSeparatorChar((String)getSeparatorChar().getValue());
130 p.setSkipLines(((Integer)getSkipLines().getValue()).intValue());
131
132 Profile pNew = ProfileUtil.add(format,p);
133 if (pNew != null)
134 {
135 // Liste in der Auswahlbox neu laden und das neue Profil selektieren
136 getProfiles().setList(ProfileUtil.read(format));
137 getProfiles().setPreselected(pNew);
138 }
139 }
140 },null,false,"document-save.png");
141 b.addButton(i18n.tr("Profil löschen..."), new Action() {
142
143 @Override
144 public void handleAction(Object context) throws ApplicationException
145 {
146 try
147 {
148 if (!Application.getCallback().askUser(i18n.tr("Soll das Profil wirklich gelöscht werden?"),false))
149 return;
150 }
151 catch (ApplicationException ae)
152 {
153 throw ae;
154 }
155 catch (OperationCanceledException oce)
156 {
157 throw oce;
158 }
159 catch (Exception e)
160 {
161 Logger.error("unable to delete profile",e);
162 getError().setValue(i18n.tr("Fehler beim Löschen: {0}",e.getMessage()));
163 return;
164 }
165 if (ProfileUtil.delete(format,getProfile()))
166 {
167 // Liste aktualisieren
168 getProfiles().setList(ProfileUtil.read(format));
169
170 // Nach dem Loeschen die Auswahl zurueck auf das Default-Profil setzen
171 getProfiles().setValue(getProfiles().getList().get(0));
172 }
173
174 // Einstellungen des ausgewaehlten Profils uebernehmen
175 update();
176
177 // Datei damit neu laden
178 reload();
179 }
180 },null,false,"user-trash-full.png");
181 options.addButtonArea(b);
182
183 options.addText("",false);
107184 options.addHeadline(i18n.tr("Optionen"));
108185 options.addInput(this.getFileEncoding());
109186 options.addInput(this.getSeparatorChar());
110187 options.addInput(this.getQuoteChar());
111188 options.addInput(this.getSkipLines());
112189
190 options.addText("",false);
113191 // BUGZILLA 412
114192 options.addHeadline(i18n.tr("Zuordnung der Spalten"));
115193 options.addText(i18n.tr("In der linken Spalte sehen Sie die erste Zeile Ihrer CSV-Datei.\n" +
123201 SimpleContainer c = new SimpleContainer(parent);
124202 c.addInput(this.getError());
125203
126 ButtonArea b = new ButtonArea();
127 b.addButton(i18n.tr("Übernehmen"), new Action()
204 ButtonArea b2 = new ButtonArea();
205 b2.addButton(i18n.tr("Import starten"), new Action()
128206 {
129207 public void handleAction(Object context) throws ApplicationException
130208 {
131 Profile p = getProfile();
132 p.setFileEncoding((String)getFileEncoding().getValue());
133 p.setQuotingChar((String)getQuoteChar().getValue());
134 p.setSeparatorChar((String)getSeparatorChar().getValue());
135 p.setSkipLines(((Integer)getSkipLines().getValue()).intValue());
136
137 // Spalten noch zuordnen
138 List<Column> columns = new ArrayList<Column>();
139 for (int i=0;i<selects.size();++i)
140 {
141 SelectInput input = selects.get(i);
142 Column c = (Column) input.getValue();
143 if (c == null)
144 continue; // Spalte nicht zugeordnet
145
146 // Spalten konnen mehrfach zugeordnet werden.
147 // Daher verwenden wir einen Clone. Andernfalls wuerden
148 // wir nur die letzte Zuordnung speichern
149 try
150 {
151 c = (Column) c.clone();
152 }
153 catch (CloneNotSupportedException e) {/*dann halt nicht */}
154
155 // Spaltennummer speichern
156 c.setColumn(i);
157 columns.add(c);
158 }
159 p.setColumns(columns);
160
161 storeProfile(p);
209 result = getProfile();
210 result.setFileEncoding((String)getFileEncoding().getValue());
211 result.setQuotingChar((String)getQuoteChar().getValue());
212 result.setSeparatorChar((String)getSeparatorChar().getValue());
213 result.setSkipLines(((Integer)getSkipLines().getValue()).intValue());
214 result.setColumns(getColumns());
162215 close();
163216 }
164217 },null,false,"ok.png");
165 b.addButton(i18n.tr("Datei neu laden"), new Action()
166 {
167 public void handleAction(Object context) throws ApplicationException
168 {
169 Profile p = getProfile();
170 p.setFileEncoding((String)getFileEncoding().getValue());
171 p.setQuotingChar((String)getQuoteChar().getValue());
172 p.setSeparatorChar((String)getSeparatorChar().getValue());
173 p.setSkipLines(((Integer)getSkipLines().getValue()).intValue());
174 reload();
175 }
176 },null,false,"view-refresh.png");
177 b.addButton(i18n.tr("Abbrechen"), new Action()
178 {
179 public void handleAction(Object context) throws ApplicationException
180 {
181 throw new OperationCanceledException();
182 }
183 },null,false,"process-stop.png");
184
185 c.addButtonArea(b);
218 b2.addButton(new Cancel());
219 c.addButtonArea(b2);
220 }
221
222 /**
223 * Liefert die aktuelle Spalten-Zuordnung.
224 * @return die aktuelle Spalten-Zuordnung.
225 */
226 private List<Column> getColumns()
227 {
228 // Spalten noch zuordnen
229 List<Column> columns = new ArrayList<Column>();
230 for (int i=0;i<selects.size();++i)
231 {
232 SelectInput input = selects.get(i);
233 Column c = (Column) input.getValue();
234 if (c == null)
235 continue; // Spalte nicht zugeordnet
236
237 // Spalten konnen mehrfach zugeordnet werden.
238 // Daher verwenden wir einen Clone. Andernfalls wuerden
239 // wir nur die letzte Zuordnung speichern
240 try
241 {
242 c = (Column) c.clone();
243 }
244 catch (CloneNotSupportedException e) {/*dann halt nicht */}
245
246 // Spaltennummer speichern
247 c.setColumn(i);
248 columns.add(c);
249 }
250 return columns;
186251 }
187252
188253 /**
199264
200265 this.selects.clear();
201266
202 Profile p = this.getProfile();
267 Profile p = getProfile();
203268 List<List<String>> lines = new ArrayList<List<String>>(); // Liste mit Zeilen mit Listen von Spalten %-)
204269 int cols = 0;
205270
206271 ////////////////////////////////////////////////////////////////////////////
207272 // CSV-Datei einlesen
208273 CsvPreference prefs = p.createCsvPreference();
209 csv = new CsvListReader(new InputStreamReader(new ByteArrayInputStream(this.data),p.getFileEncoding()),prefs);
274
275 Charset charset = null;
276
277 try
278 {
279 charset = Charset.forName(p.getFileEncoding());
280 }
281 catch (UnsupportedCharsetException e)
282 {
283 getError().setValue(i18n.tr("Encoding {0} ignoriert, wird nicht unterstützt",p.getFileEncoding()));
284 }
285 csv = new CsvListReader(new InputStreamReader(new ByteArrayInputStream(this.data),charset != null ? charset : Charset.defaultCharset()),prefs);
210286 List<String> line = null;
211287 while ((line = csv.read()) != null)
212288 {
219295 lines.add(l);
220296
221297 // Wir verwenden als Basis die Zeile mit den meisten Spalten
222 if (l.size() > cols)
223 cols = l.size();
298 cols = Math.max(l.size(),cols);
224299 }
225300
226301 if (cols == 0)
244319 //
245320 ////////////////////////////////////////////////////////////////////////////
246321
247 List<Column> columns = p.getColumns();
322 List<Column> all = format.getDefaultProfile().getColumns(); // Als Auswahlmoeglichkeit immer die aus dem Default
323 List<Column> columns = p.getColumns(); // Die, die im Template tatsaechlich zugeordnet sind.
248324 List<String> current = lines.get(p.getSkipLines()); // Die erste anzuzeigende Zeile
249325
250326 ScrolledContainer container = new ScrolledContainer(this.parent);
259335 value = value.substring(0,30) + "...";
260336 } catch (Exception e) {} // Spalte gibts in der Zeile nicht
261337
262 final SelectInput s = new SelectInput(columns,getColumn(columns,i));
338 final SelectInput s = new SelectInput(all,getColumn(columns,i));
263339 s.setName((i+1) + ". " + (value != null ? value : "<" + i18n.tr("leer") + ">"));
264340 s.setPleaseChoose("<" + i18n.tr("Nicht zugeordnet") + ">");
265341 selects.add(s);
297373 }
298374 return null;
299375 }
300
301
302 /**
303 * Prueft, ob ein serialisiertes, vom User abgespeichertes Profil existiert
304 * und laedt dieses. Andernfalls wird das Default-Profil des Formats verwendet.
305 * @return das Profil. Nie NULL sondern hoechstens das Default-Profil.
306 */
307 private Profile getProfile()
308 {
309 if (this.profile != null)
310 return this.profile;
311
312 Profile defaultProfile = this.format.getDefaultProfile();
313
314 // 1. Wir nehmen erstmal das Default-Profil
315 this.profile = defaultProfile;
316
317 // 2. Mal schauen, ob wir ein gespeichertes Profil fuer das Format haben
318 File dir = new File(Application.getPluginLoader().getPlugin(HBCI.class).getResources().getWorkPath(),"csv");
319 if (!dir.exists())
320 {
321 // Wir erstellen das Verzeichnis - dann muss es der User nicht selbst anlegen
322 Logger.info("creating " + dir);
323 dir.mkdirs();
324 return this.profile; // Wenn das Verzeichnis noch nicht existierte, gibts auch kein Benutzer-Profil
325 }
326
327 File file = new File(dir,this.format.getClass().getName() + ".xml");
328 if (!file.exists() || !file.canRead())
329 return this.profile; // XML-Datei gibts nicht oder nicht lesbar - also Default-Profil
330
331 Logger.info("reading csv profile " + file);
332 XMLDecoder decoder = null;
333 try
334 {
335 decoder = new XMLDecoder(new BufferedInputStream(new FileInputStream(file)));
336 decoder.setExceptionListener(new ExceptionListener()
337 {
338 public void exceptionThrown(Exception e)
339 {
340 throw new RuntimeException(e);
341 }
342 });
343 Profile p = (Profile) decoder.readObject();
344
345 // Versionsnummer pruefen
346 if (defaultProfile.getVersion() > p.getVersion())
347 {
348 Logger.info("default profile has changed, new version number " + defaultProfile.getVersion() + ". skipping serialized profile");
349 return this.profile;
350 }
351
352
353 this.profile = p;
354
355 // Der User hat beim letzten Mal eventuell nicht alle Spalten zugeordnet.
356 // Die wuerden jetzt hier in dem Objekt fehlen. Daher nehmen wir
357 // noch die Spalten aus dem Default-Profil und haengen die fehlenden noch an.
358 List<Column> currentColumns = this.profile.getColumns();
359 List<Column> defaultColumns = defaultProfile.getColumns();
360 for (Column cd:defaultColumns)
361 {
362 String n1 = cd.getProperty();
363 if (n1 == null)
364 continue; // Sollte es eigentlich nicht geben
365
366 cd.setColumn(-1); // gilt als nicht zugeordnet
367
368 // Checken, ob im serialisierten Profil enthalten
369 boolean found = false;
370 for (Column cc:currentColumns)
371 {
372 String n2 = cc.getProperty();
373 if (n2 == null)
374 continue;
375 if (n1.equals(n2))
376 {
377 found = true;
378 break;
379 }
380 }
381
382 // Wenn wir die Spalte im serialisierten Profil nicht gefunden
383 // haben, haengen wir sie als nicht zugeordnet hinten dran
384 if (!found)
385 currentColumns.add(cd);
386 }
387 }
388 catch (Exception e)
389 {
390 Logger.error("unable to read profile " + file,e);
391 }
392 finally
393 {
394 if (decoder != null) {
395 try {
396 decoder.close();
397 }
398 catch (Exception e) { /* useless */}
399 }
400 }
401
402 return this.profile;
403 }
404
405
406 /**
407 * Serialisiert das Profil.
408 * @param profile das zu serialisierende Profil.
409 */
410 private void storeProfile(Profile profile)
411 {
412 // 2. Mal schauen, ob wir ein gespeichertes Profil fuer das Format haben
413 File dir = new File(Application.getPluginLoader().getPlugin(HBCI.class).getResources().getWorkPath(),"csv");
414 File file = new File(dir,this.format.getClass().getName() + ".xml");
415
416 Logger.info("writing csv profile " + file);
417 XMLEncoder encoder = null;
418 try
419 {
420 encoder = new XMLEncoder(new BufferedOutputStream(new FileOutputStream(file)));
421 encoder.setExceptionListener(new ExceptionListener()
422 {
423 public void exceptionThrown(Exception e)
424 {
425 throw new RuntimeException(e);
426 }
427 });
428 encoder.writeObject(profile);
429 }
430 catch (Exception e)
431 {
432 Logger.error("unable to store profile " + file,e);
433 }
434 finally
435 {
436 if (encoder != null) {
437 try {
438 encoder.close();
439 }
440 catch (Exception e) { /* useless */}
441 }
442 }
443 }
444
376
445377 /**
446378 * Liefert das angepasste Mapping zurueck.
447379 * @see de.willuhn.jameica.gui.dialogs.AbstractDialog#getData()
448380 */
449381 protected Object getData() throws Exception
450382 {
451 return this.getProfile();
383 return this.result;
452384 }
453385
454386
458390 */
459391 private TextInput getSeparatorChar()
460392 {
461 if (this.sepChar == null)
462 {
463 this.sepChar = new TextInput(this.getProfile().getSeparatorChar(),1);
464 this.sepChar.setName(i18n.tr("Trennzeichen"));
465 this.sepChar.setComment(i18n.tr("Zeichen, mit dem die Spalten getrennt sind"));
466 this.sepChar.setMandatory(true);
467 }
393 if (this.sepChar != null)
394 return this.sepChar;
395
396 this.sepChar = new TextInput(getProfile().getSeparatorChar(),1);
397 this.sepChar.setName(i18n.tr("Trennzeichen"));
398 this.sepChar.setComment(i18n.tr("Zeichen, mit dem die Spalten getrennt sind"));
399 this.sepChar.setMandatory(true);
468400 return this.sepChar;
469401 }
470402
474406 */
475407 private LabelInput getError()
476408 {
477 if (this.error == null)
478 {
479 this.error = new LabelInput("");
480 this.error.setName("");
481 this.error.setColor(Color.ERROR);
482 }
409 if (this.error != null)
410 return this.error;
411
412 this.error = new LabelInput("");
413 this.error.setName("");
414 this.error.setColor(Color.ERROR);
483415 return this.error;
484416 }
485417
489421 */
490422 private TextInput getQuoteChar()
491423 {
492 if (this.quoteChar == null)
493 {
494 this.quoteChar = new TextInput(this.getProfile().getQuotingChar(),1);
495 this.quoteChar.setName(i18n.tr("Anführungszeichen"));
496 this.quoteChar.setComment(i18n.tr("Zeichen, mit dem die Spalten umschlossen sind"));
497 this.quoteChar.setMandatory(false);
498 }
424 if (this.quoteChar != null)
425 return this.quoteChar;
426
427 this.quoteChar = new TextInput(this.getProfile().getQuotingChar(),1);
428 this.quoteChar.setName(i18n.tr("Anführungszeichen"));
429 this.quoteChar.setComment(i18n.tr("Zeichen, mit dem die Spalten umschlossen sind"));
430 this.quoteChar.setMandatory(false);
499431 return this.quoteChar;
500432 }
501433
505437 */
506438 private SelectInput getFileEncoding()
507439 {
508 if (this.encoding == null)
509 {
510 this.encoding = new SelectInput(CHARSETS,this.getProfile().getFileEncoding());
511 this.encoding.setName(i18n.tr("Zeichensatz"));
512 this.encoding.setComment(i18n.tr("Zeichensatz der CSV-Datei"));
513 this.encoding.setMandatory(true);
514 this.encoding.setEditable(true);
515 }
440 if (this.encoding != null)
441 return this.encoding;
442
443 this.encoding = new SelectInput(CHARSETS,this.getProfile().getFileEncoding());
444 this.encoding.setName(i18n.tr("Zeichensatz"));
445 this.encoding.setComment(i18n.tr("Zeichensatz der CSV-Datei"));
446 this.encoding.setMandatory(true);
447 this.encoding.setEditable(true);
516448 return this.encoding;
517449 }
518450
523455 */
524456 private SpinnerInput getSkipLines()
525457 {
526 if (this.skipLines == null)
527 {
528 this.skipLines = new SpinnerInput(0,10,this.getProfile().getSkipLines());
529 this.skipLines.setName(i18n.tr("Zeilen überspringen"));
530 this.skipLines.setComment(i18n.tr("Zu überspringende Zeilen am Datei-Anfang"));
531 this.skipLines.setMandatory(false);
532 }
458 if (this.skipLines != null)
459 return this.skipLines;
460
461 this.skipLines = new SpinnerInput(0,10,this.getProfile().getSkipLines());
462 this.skipLines.setName(i18n.tr("Zeilen überspringen"));
463 this.skipLines.setComment(i18n.tr("Zu überspringende Zeilen am Datei-Anfang"));
464 this.skipLines.setMandatory(false);
533465 return this.skipLines;
534466 }
467
468 /**
469 * Liefert das aktuelle Profil.
470 * @return das aktuelle Profil.
471 */
472 private Profile getProfile()
473 {
474 return (Profile) this.getProfiles().getValue();
475 }
476
477 /**
478 * Liefert eine Auswahlbox mit den verfuegbaren Profilen.
479 * @return eine Auswahlbox mit den verfuegbaren Profilen.
480 * @throws ApplicationException
481 */
482 private SelectInput getProfiles()
483 {
484 if (this.profiles != null)
485 return this.profiles;
486
487 this.profiles = new SelectInput(ProfileUtil.read(this.format),null);
488 this.profiles.setAttribute("name");
489 this.profiles.setName(i18n.tr("Profil"));
490 this.profiles.addListener(new Listener() {
491 @Override
492 public void handleEvent(Event event)
493 {
494 if (event != null && event.type == SWT.Selection)
495 {
496 update();
497 reload();
498 }
499 }
500 });
501 return this.profiles;
502 }
503
504 /**
505 * Aktualisiert die Auswahl- und Eingabefelder nach Wechsel des Profils.
506 */
507 private void update()
508 {
509 Profile p = getProfile();
510 Logger.info("chaning profile to: " + p);
511
512 // Einstellungen in die Eingabefelder uebernehmen
513 this.getFileEncoding().setValue(p.getFileEncoding());
514 this.getQuoteChar().setValue(p.getQuotingChar());
515 this.getSeparatorChar().setValue(p.getSeparatorChar());
516 this.getSkipLines().setValue(Integer.valueOf(p.getSkipLines()));
517
518 // Datei mit den neuen Einstellungen laden
519 reload();
520 }
535521 }
0 /**********************************************************************
1 *
2 * Copyright (c) 2004 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9 package de.willuhn.jameica.hbci.gui.dialogs;
10
11 import java.util.List;
12
13 import org.apache.commons.lang.StringUtils;
14 import org.eclipse.swt.SWT;
15 import org.eclipse.swt.events.KeyAdapter;
16 import org.eclipse.swt.events.KeyEvent;
17 import org.eclipse.swt.widgets.Composite;
18
19 import de.willuhn.jameica.gui.Action;
20 import de.willuhn.jameica.gui.dialogs.AbstractDialog;
21 import de.willuhn.jameica.gui.input.Input;
22 import de.willuhn.jameica.gui.input.LabelInput;
23 import de.willuhn.jameica.gui.input.TextInput;
24 import de.willuhn.jameica.gui.internal.buttons.Cancel;
25 import de.willuhn.jameica.gui.parts.Button;
26 import de.willuhn.jameica.gui.parts.ButtonArea;
27 import de.willuhn.jameica.gui.util.Color;
28 import de.willuhn.jameica.gui.util.Container;
29 import de.willuhn.jameica.gui.util.SWTUtil;
30 import de.willuhn.jameica.gui.util.SimpleContainer;
31 import de.willuhn.jameica.hbci.HBCI;
32 import de.willuhn.jameica.hbci.io.csv.Format;
33 import de.willuhn.jameica.hbci.io.csv.Profile;
34 import de.willuhn.jameica.hbci.io.csv.ProfileUtil;
35 import de.willuhn.jameica.system.Application;
36 import de.willuhn.util.ApplicationException;
37 import de.willuhn.util.I18N;
38
39 /**
40 * Dialog zum Speichern eines CSV-Profils.
41 */
42 public class CSVProfileStoreDialog extends AbstractDialog
43 {
44 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
45 private final static int WINDOW_WIDTH = 500;
46
47 private Format format = null;
48 private Profile profile = null;
49 private Button apply = null;
50 private TextInput name = null;
51 private LabelInput hint = null;
52
53 private List<Profile> profiles = null;
54
55 /**
56 * Erzeugt einen neuen Text-Dialog.
57 * @param format das Format.
58 * @param profile das Profil.
59 * @see AbstractDialog#POSITION_MOUSE
60 * @see AbstractDialog#POSITION_CENTER
61 */
62 public CSVProfileStoreDialog(Format format, Profile profile)
63 {
64 super(CSVProfileStoreDialog.POSITION_CENTER);
65 this.setSize(WINDOW_WIDTH,SWT.DEFAULT);
66 this.setTitle(i18n.tr("Name des Profils"));
67 this.setSideImage(SWTUtil.getImage("dialog-question-large.png"));
68
69 this.profile = profile;
70
71 // Wir machen neue Profile generell zu Nicht-System-Profilen
72 this.profile.setSystem(false);
73
74 this.format = format;
75 this.profiles = ProfileUtil.read(format);
76 }
77
78 /**
79 * Liefert das Eingabefeld fuer den Namen.
80 * @return das Eingabefeld fuer den Namen.
81 */
82 private TextInput getName()
83 {
84 if (this.name != null)
85 return this.name;
86
87 this.name = new TextInput(this.suggestName());
88 this.name.setName("");
89 this.name.setMandatory(true);
90 return this.name;
91 }
92
93 /**
94 * Liefert einen Namensvorschlag fuer das Profil.
95 * @return Namensvorschlag fuer das Profil.
96 */
97 private String suggestName()
98 {
99 // Wir versuchen einen Namensvorschlag für das Profil zu ermitteln
100 // Hierzu checken wir, ob es mit einer Zahl endet. Wenn ja, erhoehen
101 // wir sie um 1. Wenn nicht, haengen wir "2" hinten dran.
102 String template = this.profile.getName();
103 int space = template.lastIndexOf(" ");
104
105 // Checken, ob wir schon eine Nummer im Namen haben
106 if (space > 0)
107 {
108 String s1 = StringUtils.trimToNull(template.substring(0,space));
109 String s2 = StringUtils.trimToNull(template.substring(space));
110 if (s1 != null && s2 != null && s2.matches("[0-9]{1,4}"))
111 template = s1;
112 }
113
114 // Erste freie Nummer suchen
115 for (int i=2;i<100;++i)
116 {
117 boolean found = false;
118 String name = template + " " + i;
119 for (Profile p:this.profiles)
120 {
121 if (name.equals(p.getName()))
122 {
123 found = true;
124 break;
125 }
126 }
127
128 // wir haben einen passenden Namen gefunden
129 if (!found)
130 return name;
131 }
132
133 // Ne, dann muss der User selbst einen neuen Namen vergeben
134 return template;
135 }
136
137 /**
138 * Zeigt einen Hinweis-Text an.
139 * @return Hinweis-Text.
140 */
141 private LabelInput getHint()
142 {
143 if (this.hint != null)
144 return this.hint;
145
146 this.hint = new LabelInput("");
147 this.hint.setName("");
148 this.hint.setColor(Color.ERROR);
149 return this.hint;
150 }
151
152 /**
153 * Liefert den Apply-Button.
154 * @return der Apply-Button.
155 */
156 private Button getApply()
157 {
158 if (this.apply != null)
159 return this.apply;
160
161 this.apply = new Button(i18n.tr("Übernehmen"),new Action() {
162 public void handleAction(Object context) throws ApplicationException
163 {
164 // Name uebernehmen
165 profile.setName((String) getName().getValue());
166
167 // Wir koennen das Profil zur Liste hinzufuegen.
168 // Checken, ob eines ueberschrieben werden soll.
169 boolean found = false;
170 for (Profile p:profiles)
171 {
172 if (p.isSystem())
173 continue;
174
175 if (p.getName().equals(profile.getName()))
176 {
177 profiles.set(profiles.indexOf(p),profile);
178 found = true;
179 break;
180 }
181 }
182
183 if (!found)
184 profiles.add(profile);
185
186 ProfileUtil.store(format,profiles);
187 close();
188 }
189 },null,true,"ok.png");
190
191 return this.apply;
192 }
193
194 /**
195 * @see de.willuhn.jameica.gui.dialogs.AbstractDialog#paint(org.eclipse.swt.widgets.Composite)
196 */
197 protected void paint(Composite parent) throws Exception
198 {
199 Container c = new SimpleContainer(parent);
200 c.addText(i18n.tr("Bitte geben Sie einen Namen für das Profil an.\n\n" +
201 "Verwenden Sie einen noch nicht benutzten Namen, um ein neues Profil hinzuzufügen. " +
202 "Vergeben Sie alternativ einen bereits verwendeten Namen, um dieses Profil zu überschreiben."),true);
203
204 final Input name = this.getName();
205 c.addInput(name);
206
207 name.getControl().addKeyListener(new KeyAdapter() {
208 /**
209 * @see org.eclipse.swt.events.KeyAdapter#keyReleased(org.eclipse.swt.events.KeyEvent)
210 */
211 @Override
212 public void keyReleased(KeyEvent e)
213 {
214 updateUI();
215 }
216 });
217
218 c.addInput(getHint());
219
220 ButtonArea buttons = new ButtonArea();
221 buttons.addButton(this.getApply());
222 buttons.addButton(new Cancel());
223
224 c.addButtonArea(buttons);
225 getShell().setMinimumSize(getShell().computeSize(WINDOW_WIDTH,SWT.DEFAULT));
226
227 // UI initialisieren
228 updateUI();
229 }
230
231 /**
232 * Aktualisiert die UI nach Zeicheneingabe
233 */
234 private void updateUI()
235 {
236 // Apply-Button deaktivieren, wenn nichts drin steht.
237 final String text = StringUtils.trimToNull((String) name.getValue());
238 getApply().setEnabled(text != null);
239
240 // Hier brauchen wir nichts weiter checken
241 if (text == null)
242 return;
243
244 getHint().setValue("");
245
246 boolean found = false;
247 boolean system = false;
248
249 // Jetzt noch checken, ob wir ein existierendes Profil ueberschreiben und einen Warnhinweis anzeigen
250 // Ausserdem einen Hinweis, wenn der User versucht, das System-Profil zu ueberschreiben
251 for (Profile p:this.profiles)
252 {
253 if (p.getName().equals(text))
254 {
255 found = true;
256 system = p.isSystem();
257 }
258 }
259
260 if (!found)
261 {
262 getHint().setColor(Color.SUCCESS);
263 getHint().setValue(i18n.tr("Ein neues Profil wird angelegt."));
264 }
265
266 if (found && !system)
267 {
268 getHint().setColor(Color.LINK);
269 getHint().setValue(i18n.tr("Existierendes Profil wird überschrieben."));
270 }
271
272 if (system)
273 {
274 getHint().setColor(Color.ERROR);
275 getHint().setValue(i18n.tr("Das Default-Profil darf nicht überschrieben werden."));
276 getApply().setEnabled(false);
277 }
278 }
279
280 /**
281 * @see de.willuhn.jameica.gui.dialogs.AbstractDialog#getData()
282 */
283 protected Object getData() throws Exception
284 {
285 return this.profile;
286 }
287 }
0 /**********************************************************************
1 *
2 * Copyright (c) 2004 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.gui.dialogs;
11
12 import java.util.Arrays;
13 import java.util.List;
14
15 import org.eclipse.swt.SWT;
16 import org.eclipse.swt.widgets.Composite;
17
18 import de.willuhn.jameica.gui.Action;
19 import de.willuhn.jameica.gui.dialogs.AbstractDialog;
20 import de.willuhn.jameica.gui.input.CheckboxInput;
21 import de.willuhn.jameica.gui.parts.Button;
22 import de.willuhn.jameica.gui.parts.ButtonArea;
23 import de.willuhn.jameica.gui.util.Container;
24 import de.willuhn.jameica.gui.util.SWTUtil;
25 import de.willuhn.jameica.gui.util.SimpleContainer;
26 import de.willuhn.jameica.hbci.HBCI;
27 import de.willuhn.jameica.hbci.MetaKey;
28 import de.willuhn.jameica.hbci.gui.filter.KontoFilter;
29 import de.willuhn.jameica.hbci.rmi.Konto;
30 import de.willuhn.jameica.hbci.server.KontoUtil;
31 import de.willuhn.jameica.messaging.StatusBarMessage;
32 import de.willuhn.jameica.system.Application;
33 import de.willuhn.logging.Logger;
34 import de.willuhn.util.ApplicationException;
35 import de.willuhn.util.I18N;
36
37 /**
38 * Dialog, mit dem der Abruf der Umsaetze initial auf CAMT umgestellt werden kann.
39 * Der Dialog liefert true oder false zurueck.
40 */
41 public class CamtSetupDialog extends AbstractDialog
42 {
43 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
44
45 private final static int WINDOW_WIDTH = 780;
46
47 private Konto konto = null;
48 private CheckboxInput switchAll = null;
49 private Boolean value = null;
50
51 /**
52 * ct.
53 * @param k das Konto.
54 */
55 public CamtSetupDialog(Konto k)
56 {
57 super(POSITION_CENTER);
58
59 this.konto = k;
60 this.setTitle(i18n.tr("Umsätze im SEPA CAMT-Format abrufen"));
61 this.setSize(WINDOW_WIDTH,SWT.DEFAULT);
62 this.setSideImage(SWTUtil.getImage("camtsetup.png"));
63
64 }
65
66 /**
67 * @see de.willuhn.jameica.gui.dialogs.AbstractDialog#paint(org.eclipse.swt.widgets.Composite)
68 */
69 @Override
70 protected void paint(Composite parent) throws Exception
71 {
72 final Container c = new SimpleContainer(parent);
73 String text = "Hibiscus unterstützt beim Abruf der Konto-Umsätze jetzt auch das neue moderne XML-basierte CAMT-Format, welches " +
74 "für den SEPA-Zahlungsverkehr besser geeignet ist als das bisherige MT940-Format.\n\n" +
75 "Das Konto \"{0}\" kann jetzt auf CAMT umgestellt werden. Sie können diese Umstellung später in den Synchronisierungsoptionen " +
76 "des Kontos jederzeit wieder rückgängig machen.";
77 c.addText(i18n.tr(text,this.konto.getLongName()),true);
78
79 c.addHeadline(i18n.tr("Hinweis"));
80 text = "Da sich die Datenformate von CAMT und MT940 grundlegend unterscheiden, kann es nach der Umstellung dazu kommen, dass " +
81 "Umsatzbuchungen ggf. doppelt angezeigt werden. Sie können diese Duplikate einfach löschen. In der Regel sollte das jedoch " +
82 "nur am Tag der Umstellung selbst auftreten.";
83 c.addText(text,true);
84
85 c.addInput(this.getSwitchAll());
86
87 ButtonArea buttons = new ButtonArea();
88
89 final Button yes = new Button(i18n.tr("Ja, auf CAMT umstellen"),new Action() {
90
91 @Override
92 public void handleAction(Object context) throws ApplicationException
93 {
94 apply(true);
95 }
96 },null,true,"ok.png");
97 buttons.addButton(yes);
98
99 final Button no = new Button(i18n.tr("Nein, nicht umstellen"),new Action() {
100
101 @Override
102 public void handleAction(Object context) throws ApplicationException
103 {
104 apply(false);
105 }
106 },null,true,"window-close.png");
107 buttons.addButton(no);
108
109 final Button later = new Button(i18n.tr("Beim nächsten Mal erinnern"),new Action() {
110
111 @Override
112 public void handleAction(Object context) throws ApplicationException
113 {
114 close();
115 }
116 },null,true,"preferences-system-time.png");
117 buttons.addButton(later);
118
119 c.addButtonArea(buttons);
120
121 getShell().setMinimumSize(getShell().computeSize(WINDOW_WIDTH,SWT.DEFAULT));
122 }
123
124 /**
125 * Liefert eine Checkbox, mit der eingestellt werden kann, ob die Umstellung fuer alle Konten erfolgen soll.
126 * @return Checkbox.
127 */
128 private CheckboxInput getSwitchAll()
129 {
130 if (this.switchAll != null)
131 return this.switchAll;
132
133 this.switchAll = new CheckboxInput(false);
134 this.switchAll.setName(i18n.tr("Auch auf alle anderen Konten anwenden"));
135 return this.switchAll;
136 }
137
138 /**
139 * Uebernimmt die Einstellungen und schliesst den Dialog.
140 * @param enabled true, wenn CAMT aktiviert werden soll.
141 */
142 private void apply(boolean enabled)
143 {
144 try
145 {
146 this.value = enabled;
147 final String s = Boolean.toString(enabled);
148 final Boolean all = (Boolean) this.getSwitchAll().getValue();
149
150 List<Konto> konten = all.booleanValue() ? KontoUtil.getKonten(KontoFilter.ONLINE) : Arrays.asList(this.konto);
151 for (Konto k:konten)
152 {
153 MetaKey.UMSATZ_CAMT.set(k,s);
154 }
155 }
156 catch (Exception e)
157 {
158 Logger.error("unable to save changes",e);
159 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Übernehmen der Einstellungen fehlgeschlagen: {0}",e.getMessage()),StatusBarMessage.TYPE_ERROR));
160 }
161 finally
162 {
163 close();
164 }
165 }
166
167 /**
168 * @see de.willuhn.jameica.gui.dialogs.AbstractDialog#getData()
169 */
170 @Override
171 protected Object getData() throws Exception
172 {
173 return this.value;
174 }
175 }
176
1414
1515 import org.apache.commons.lang.StringUtils;
1616 import org.eclipse.swt.SWT;
17 import org.eclipse.swt.events.DisposeEvent;
18 import org.eclipse.swt.events.DisposeListener;
19 import org.eclipse.swt.graphics.Point;
1720 import org.eclipse.swt.widgets.Composite;
1821 import org.eclipse.swt.widgets.Event;
1922 import org.eclipse.swt.widgets.Listener;
23 import org.eclipse.swt.widgets.Shell;
2024 import org.kapott.hbci.GV_Result.GVRKontoauszug.Format;
2125
2226 import de.willuhn.jameica.gui.Action;
3135 import de.willuhn.jameica.gui.parts.ButtonArea;
3236 import de.willuhn.jameica.gui.util.Color;
3337 import de.willuhn.jameica.gui.util.Container;
38 import de.willuhn.jameica.gui.util.ScrolledContainer;
3439 import de.willuhn.jameica.gui.util.SimpleContainer;
3540 import de.willuhn.jameica.hbci.HBCI;
3641 import de.willuhn.jameica.hbci.MetaKey;
4651 import de.willuhn.jameica.hbci.server.KontoauszugPdfUtil;
4752 import de.willuhn.jameica.messaging.StatusBarMessage;
4853 import de.willuhn.jameica.system.Application;
54 import de.willuhn.jameica.system.Settings;
4955 import de.willuhn.logging.Logger;
5056 import de.willuhn.util.ApplicationException;
5157 import de.willuhn.util.I18N;
5662 public class KontoauszugPdfSettingsDialog extends AbstractDialog
5763 {
5864 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
59
60 private final static int WINDOW_WIDTH = 600;
65 private final static Settings settings = new Settings(KontoauszugPdfSettingsDialog.class);
66
67 private final static int WINDOW_WIDTH = 700;
68 private final static int WINDOW_HEIGHT = 500;
6169
6270 private Konto konto = null;
6371
92100 super(POSITION_CENTER);
93101 this.konto = konto;
94102 this.setTitle(i18n.tr("Einstellungen für den elektronischen Kontoauszug"));
95 setSize(WINDOW_WIDTH,SWT.DEFAULT);
103 setSize(settings.getInt("window.width",WINDOW_WIDTH),settings.getInt("window.height",WINDOW_HEIGHT));
96104 }
97105
98106 /**
101109 @Override
102110 protected void paint(Composite parent) throws Exception
103111 {
104 Container c = new SimpleContainer(parent);
112 Container scroll = new ScrolledContainer(parent,1)
113 {
114 /**
115 * @see de.willuhn.jameica.gui.util.ScrolledContainer#update()
116 */
117 @Override
118 public void update()
119 {
120 Composite comp = this.getComposite();
121 if (comp == null || comp.isDisposed())
122 return;
123 comp.setSize(comp.computeSize(settings.getInt("window.width",WINDOW_WIDTH), SWT.DEFAULT));
124 comp.layout();
125 }
126 };
127 Container c = new SimpleContainer(scroll.getComposite());
105128
106129 c.addText(i18n.tr("Wählen Sie das Konto aus, für das Sie den Abruf der elektronischen Kontoauszüge konfigurieren möchten.\nFür weitere Informationen klicken Sie auf die Schaltfläche \"Hilfe\".") + "\n",true);
107130 c.addInput(this.getKontoAuswahl());
134157 c.addInput(this.getFolder());
135158 c.addInput(this.getName());
136159
137 Container c2 = new SimpleContainer(parent);
160 Container c2 = new SimpleContainer(scroll.getComposite());
138161 c2.addInput(this.getExampleText());
139162 c2.addInput(this.getExample());
163 c2.addInput(new LabelInput("")); // Unten noch etwas Platzhalter
140164
141165 Container c3 = new SimpleContainer(parent);
142166 ButtonArea buttons = new ButtonArea();
151175 },null,false,"window-close.png");
152176 c3.addButtonArea(buttons);
153177
154 getShell().setMinimumSize(getShell().computeSize(WINDOW_WIDTH,SWT.DEFAULT));
155
178 // Unabhaengig von dem, was der User als Groesse eingestellt hat, bleibt das die Minimalgroesse.
179 getShell().setMinimumSize(WINDOW_WIDTH,WINDOW_HEIGHT);
180
181 getShell().addDisposeListener(new DisposeListener() {
182
183 @Override
184 public void widgetDisposed(DisposeEvent e)
185 {
186 Shell shell = getShell();
187 if (shell == null || shell.isDisposed())
188 return;
189
190 Point size = shell.getSize();
191 Logger.debug("saving window size: " + size.x + "x" + size.y);
192 settings.setAttribute("window.width",size.x);
193 settings.setAttribute("window.height",size.y);
194 }
195 });
156196 }
157197
158198 /**
298338 return this.nextFetch;
299339
300340 this.nextFetch = new LabelInput("");
301 this.nextFetch.setName(i18n.tr("Nächste Abruf"));
341 this.nextFetch.setName(i18n.tr("Nächster Abruf"));
302342 this.nextFetch.setComment("");
303343 return this.nextFetch;
304344 }
0 /**********************************************************************
1 *
2 * Copyright (c) 2004 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.gui.dialogs;
11
12 import org.eclipse.swt.SWT;
13 import org.eclipse.swt.widgets.Composite;
14
15 import de.willuhn.jameica.gui.Action;
16 import de.willuhn.jameica.gui.dialogs.AbstractDialog;
17 import de.willuhn.jameica.gui.input.CheckboxInput;
18 import de.willuhn.jameica.gui.internal.buttons.Cancel;
19 import de.willuhn.jameica.gui.parts.Button;
20 import de.willuhn.jameica.gui.parts.ButtonArea;
21 import de.willuhn.jameica.gui.util.Container;
22 import de.willuhn.jameica.gui.util.SimpleContainer;
23 import de.willuhn.jameica.hbci.HBCI;
24 import de.willuhn.jameica.system.Application;
25 import de.willuhn.jameica.system.Settings;
26 import de.willuhn.util.ApplicationException;
27 import de.willuhn.util.I18N;
28
29 /**
30 * Dialog zum Konfigurieren der Anzeigeeinstellungen fuer die Umsaetze.
31 */
32 public class KontoauszugSettingsDialog extends AbstractDialog
33 {
34 private final static Settings settings = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getSettings();
35 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
36
37 private final static int WINDOW_WIDTH = 500;
38
39 private CheckboxInput displayAll = null;
40
41 /**
42 * ct.
43 */
44 public KontoauszugSettingsDialog()
45 {
46 super(POSITION_CENTER);
47 this.setTitle(i18n.tr("Anzeige-Einstellungen"));
48 setSize(WINDOW_WIDTH,SWT.DEFAULT);
49 }
50
51 /**
52 * @see de.willuhn.jameica.gui.dialogs.AbstractDialog#paint(org.eclipse.swt.widgets.Composite)
53 */
54 @Override
55 protected void paint(Composite parent) throws Exception
56 {
57 final Container c = new SimpleContainer(parent);
58 c.addInput(this.getDisplayAll());
59
60 final Button apply = new Button(i18n.tr("Übernehmen"),new Action() {
61
62 @Override
63 public void handleAction(Object context) throws ApplicationException
64 {
65 settings.setAttribute("usage.list.all",((Boolean) getDisplayAll().getValue()).booleanValue());
66 close();
67 }
68 },null,true,"ok.png");
69
70 ButtonArea buttons = new ButtonArea();
71 buttons.addButton(apply);
72 buttons.addButton(new Cancel());
73 c.addButtonArea(buttons);
74
75 getShell().setMinimumSize(getShell().computeSize(WINDOW_WIDTH,SWT.DEFAULT));
76 }
77
78 /**
79 * @see de.willuhn.jameica.gui.dialogs.AbstractDialog#getData()
80 */
81 @Override
82 protected Object getData() throws Exception
83 {
84 return null;
85 }
86
87 /**
88 * Liefert die Checkbox, mit der eingestellt werden kann, ob alle Daten des Verwendungszwecks angezeigt werden sollen.
89 * @return Checkbox.
90 */
91 private CheckboxInput getDisplayAll()
92 {
93 if (this.displayAll != null)
94 return this.displayAll;
95
96 this.displayAll = new CheckboxInput(settings.getBoolean("usage.list.all",false));
97 this.displayAll.setName(i18n.tr("Alle Daten des Verwendungszwecks anzeigen"));
98 return this.displayAll;
99 }
100
101 }
102
103
1515 import org.eclipse.swt.widgets.Composite;
1616 import org.eclipse.swt.widgets.Event;
1717 import org.eclipse.swt.widgets.Listener;
18 import org.kapott.hbci.sepa.PainVersion;
19 import org.kapott.hbci.sepa.PainVersion.Type;
18 import org.kapott.hbci.sepa.SepaVersion;
19 import org.kapott.hbci.sepa.SepaVersion.Type;
2020
2121 import de.willuhn.jameica.gui.Action;
2222 import de.willuhn.jameica.gui.dialogs.AbstractDialog;
4343 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
4444
4545 private Type type = null;
46 private PainVersion painVersion = null;
46 private SepaVersion painVersion = null;
4747 private Button ok = null;
4848
4949 /**
7777 {
7878 public void handleAction(Object context) throws ApplicationException
7979 {
80 painVersion = (PainVersion) version.getValue();
80 painVersion = (SepaVersion) version.getValue();
8181 if (painVersion == null)
8282 {
8383 msg.setValue(i18n.tr("Bitte wählen Sie eine SEPA XML-Version aus."));
106106 */
107107 private SelectInput getPainVersionInput()
108108 {
109 List<PainVersion> list = PainVersion.getKnownVersions(type);
110 final SelectInput select = new SelectInput(list,PainVersion.findGreatest(list));
109 List<SepaVersion> list = SepaVersion.getKnownVersions(type);
110 final SelectInput select = new SelectInput(list,SepaVersion.findGreatest(list));
111111 select.setAttribute("file");
112112 select.setName(i18n.tr("Schema-Version der SEPA XML-Datei"));
113113 select.addListener(new Listener() {
2121 import org.eclipse.swt.widgets.Event;
2222 import org.eclipse.swt.widgets.FileDialog;
2323 import org.eclipse.swt.widgets.Listener;
24 import org.kapott.hbci.sepa.PainVersion;
25 import org.kapott.hbci.sepa.PainVersion.Type;
24 import org.kapott.hbci.sepa.SepaVersion;
25 import org.kapott.hbci.sepa.SepaVersion.Type;
2626
2727 import de.willuhn.jameica.gui.Action;
2828 import de.willuhn.jameica.gui.dialogs.AbstractDialog;
5353 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
5454
5555 private Type type = null;
56 private PainVersion painVersion = null;
56 private SepaVersion painVersion = null;
5757 private File file = null;
5858 private Button ok = null;
5959
100100 {
101101 public void handleAction(Object context) throws ApplicationException
102102 {
103 painVersion = (PainVersion) version.getValue();
103 painVersion = (SepaVersion) version.getValue();
104104 if (painVersion == null)
105105 {
106106 msg.setValue(i18n.tr("Bitte wählen Sie eine Schema-Version aus."));
155155 */
156156 private SelectInput getPainVersionInput()
157157 {
158 List<PainVersion> list = PainVersion.getKnownVersions(type);
159 final SelectInput select = new SelectInput(list,PainVersion.findGreatest(list));
158 List<SepaVersion> list = SepaVersion.getKnownVersions(type);
159 final SelectInput select = new SelectInput(list,SepaVersion.findGreatest(list));
160160 select.setAttribute("file");
161161 select.setName(i18n.tr("Schema-Version der SEPA-Datei"));
162162 select.addListener(new Listener() {
238238 * Liefert die ausgewaehlte PAIN-Version.
239239 * @return die ausgewaehlte PAIN-Version.
240240 */
241 public PainVersion getPainVersion()
241 public SepaVersion getPainVersion()
242242 {
243243 return this.painVersion;
244244 }
1111
1212 import java.rmi.RemoteException;
1313 import java.util.ArrayList;
14 import java.util.HashMap;
1415 import java.util.List;
16 import java.util.Map;
17 import java.util.Map.Entry;
1518
1619 import org.eclipse.swt.SWT;
1720 import org.eclipse.swt.widgets.Composite;
3134 import de.willuhn.jameica.gui.util.Container;
3235 import de.willuhn.jameica.gui.util.SimpleContainer;
3336 import de.willuhn.jameica.hbci.HBCI;
37 import de.willuhn.jameica.hbci.MetaKey;
3438 import de.willuhn.jameica.hbci.SynchronizeOptions;
3539 import de.willuhn.jameica.hbci.rmi.Konto;
40 import de.willuhn.jameica.hbci.server.BPDUtil;
41 import de.willuhn.jameica.hbci.server.BPDUtil.Query;
42 import de.willuhn.jameica.hbci.server.BPDUtil.Support;
43 import de.willuhn.jameica.hbci.server.KontoUtil;
3644 import de.willuhn.jameica.hbci.server.KontoauszugPdfUtil;
3745 import de.willuhn.jameica.hbci.synchronize.SynchronizeBackend;
3846 import de.willuhn.jameica.hbci.synchronize.SynchronizeEngine;
3947 import de.willuhn.jameica.hbci.synchronize.jobs.SynchronizeJobKontoauszug;
48 import de.willuhn.jameica.hbci.synchronize.jobs.SynchronizeJobKontoauszugPdf;
49 import de.willuhn.jameica.hbci.synchronize.jobs.SynchronizeJobSepaDauerauftragList;
50 import de.willuhn.jameica.hbci.synchronize.jobs.SynchronizeJobSepaLastschrift;
51 import de.willuhn.jameica.hbci.synchronize.jobs.SynchronizeJobSepaUeberweisung;
4052 import de.willuhn.jameica.messaging.StatusBarMessage;
4153 import de.willuhn.jameica.services.BeanService;
4254 import de.willuhn.jameica.system.Application;
5163 {
5264 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
5365
54 private final static int WINDOW_WIDTH = 400;
66 private final static int WINDOW_WIDTH = 500;
5567
5668 private Konto konto = null;
5769 private boolean offline = false;
6577 private CheckboxInput syncSepaLast = null;
6678 private CheckboxInput syncSepaDauer = null;
6779 private CheckboxInput syncMessages = null;
80 private CheckboxInput useCamt = null;
6881 private LabelInput error = null;
6982 private Button apply = null;
7083
71 private List<Input> properties = new ArrayList<Input>();
84 private Map<SynchronizeBackend,List<Input>> properties = new HashMap<SynchronizeBackend,List<Input>>();
7285
7386 /**
7487 * ct.
98111 List<String> names = backend.getPropertyNames(konto);
99112 if (names != null && names.size() > 0)
100113 {
114 List<Input> props = new ArrayList<Input>();
115 this.properties.put(backend,props);
101116 for (String name:names)
102117 {
103 this.createCustomProperty(name);
118 props.add(this.createCustomProperty(name));
104119 }
105120 }
106121 }
114129 /**
115130 * Erzeugt ein Custom-Property-Input fuer den angegebenen Property-Namen.
116131 * @param name der Name des Custom-Property.
132 * @return das erzeugte Eingabefeld.
117133 * @throws RemoteException
118134 */
119 private void createCustomProperty(String name) throws RemoteException
135 private Input createCustomProperty(String name) throws RemoteException
120136 {
121137 Input t = null;
122138 if (name.endsWith("(true/false)"))
137153 t = new TextInput(konto.getMeta(name,null));
138154 t.setName(name);
139155 }
140 this.properties.add(t);
156 return t;
141157 }
142158
143159 /**
146162 protected void paint(Composite parent) throws Exception
147163 {
148164 Container group = new SimpleContainer(parent);
165
166 group.addHeadline(this.konto.getLongName());
149167
150168 group.addText(i18n.tr("Bitte wählen Sie aus, welche Geschäftsvorfälle bei der " +
151169 "Synchronisierung des Kontos ausgeführt werden sollen."),true);
152170
153 group.addHeadline(this.konto.getLongName());
154
155171 this.apply = new Button(i18n.tr("Übernehmen"),new Action() {
156172 public void handleAction(Object context) throws ApplicationException
157173 {
160176 {
161177 options.setSyncSaldo(((Boolean)getSyncSaldo().getValue()).booleanValue());
162178 options.setSyncKontoauszuege(((Boolean)getSyncUmsatz().getValue()).booleanValue());
179
180 Support support = BPDUtil.getSupport(konto,Query.UmsatzCamt);
181 if (support != null && support.isSupported())
182 {
183 try
184 {
185 Boolean value = (Boolean) getUseCamt().getValue();
186 MetaKey.UMSATZ_CAMT.set(konto,value.toString());
187 }
188 catch (RemoteException re)
189 {
190 Logger.error("unable to save changes",re);
191 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Übernehmen der Einstellungen fehlgeschlagen: {0}",re.getMessage()),StatusBarMessage.TYPE_ERROR));
192 }
193 }
163194 }
164195
165196 if (offline)
177208
178209 try
179210 {
180 for (Input prop:properties)
211 for (List<Input> l:properties.values())
181212 {
182 Object value = prop.getValue();
183 konto.setMeta(prop.getName(),value != null ? value.toString() : null);
213 for (Input prop:l)
214 {
215 Object value = prop.getValue();
216 konto.setMeta(prop.getName(),value != null ? value.toString() : null);
217 }
184218 }
185219 }
186220 catch (Exception e)
192226 }
193227 },null,true,"ok.png");
194228
195 Input i1 = this.getSyncSaldo();
196 Input i2 = this.getSyncUmsatz();
197 Input i3 = this.getSyncOffline();
198 Input i4 = this.getSyncAueb();
199 Input i5 = this.getSyncSepaLast();
200 Input i6 = this.getSyncSepaDauer();
201 Input i7 = this.getSyncMessages();
202 Input i8 = this.getSyncKontoauszug();
203
229 Input i1 = this.getSyncSaldo();
230 Input i2 = this.getSyncUmsatz();
231 Input i3 = this.getSyncOffline();
232 Input i4 = this.getSyncAueb();
233 Input i5 = this.getSyncSepaLast();
234 Input i6 = this.getSyncSepaDauer();
235 Input i7 = this.getSyncMessages();
236 Input i8 = this.getSyncKontoauszug();
237
238 Input camt = null;
239
204240 if (!offline || syncAvail)
205241 {
242 // Wir stellen die Option nur zur Verfuegung, wenn das Konto es prinzipiell unterstuetzt
243 Support support = BPDUtil.getSupport(this.konto,Query.UmsatzCamt);
244
245 // Wichtig: Das Input muss erzeugt werden, bevor getSyncUmsatz gezeichnet wird. Sonst wird der Listener nicht mehr registriert
246 if (!offline && support != null && support.isSupported())
247 camt = this.getUseCamt();
248
206249 group.addInput(i1);
207250 group.addInput(i2);
208251 }
213256 }
214257 else
215258 {
216 group.addInput(i8);
217 group.addInput(i4);
218 group.addInput(i5);
219 group.addInput(i6);
259 BeanService service = Application.getBootLoader().getBootable(BeanService.class);
260 SynchronizeEngine engine = service.get(SynchronizeEngine.class);
261
262 if (engine.supports(SynchronizeJobKontoauszugPdf.class,this.konto)) group.addInput(i8);
263 if (engine.supports(SynchronizeJobSepaUeberweisung.class,this.konto)) group.addInput(i4);
264 if (engine.supports(SynchronizeJobSepaLastschrift.class,this.konto)) group.addInput(i5);
265 if (engine.supports(SynchronizeJobSepaDauerauftragList.class,this.konto)) group.addInput(i6);
266
267 // Abrufen der Nachrichten lassen wir immer zu.
220268 group.addInput(i7);
221269 }
222
270
271 if (camt != null && (!offline || syncAvail))
272 {
273 group.addHeadline(i18n.tr("Erweiterte Einstellungen: FinTS"));
274 group.addInput(camt);
275 }
276
223277 if (this.properties.size() > 0)
224278 {
225 group.addHeadline(i18n.tr("Erweiterte Einstellungen"));
226 for (Input prop:this.properties)
227 {
228 group.addInput(prop);
279 for (Entry<SynchronizeBackend,List<Input>> e:this.properties.entrySet())
280 {
281 group.addHeadline(i18n.tr("Erweiterte Einstellungen: {0}",e.getKey().getName()));
282 for (Input prop:e.getValue())
283 {
284 group.addInput(prop);
285 }
229286 }
230287 }
231288
272329 this.syncUmsatz.addListener(new OfflineListener());
273330 }
274331 return this.syncUmsatz;
332 }
333
334 /**
335 * Liefert eine Checkbox fuer die Aktivierung/Deaktivierung des CAMT-Formats.
336 * @return Checkbox.
337 */
338 private CheckboxInput getUseCamt()
339 {
340 if (this.useCamt == null)
341 {
342 this.useCamt = new CheckboxInput(KontoUtil.useCamt(this.konto,false));
343 this.useCamt.setName(i18n.tr("Umsätze im neuen SEPA CAMT-Format abrufen"));
344
345 final CheckboxInput syncUms = this.getSyncUmsatz();
346
347 final Listener l = new Listener() {
348
349 @Override
350 public void handleEvent(Event event)
351 {
352 // Option nur freischalten, wenn Umsatz-Abruf aktiviert ist
353 useCamt.setEnabled((Boolean)syncUms.getValue());
354 }
355 };
356
357 syncUms.addListener(l);
358 l.handleEvent(null);
359 }
360
361 return this.useCamt;
275362 }
276363
277364 /**
5252 Class type = e.getType();
5353 if (!type.isAssignableFrom(Umsatz.class))
5454 return;
55
56 boolean initial = ExportDialog.SETTINGS.getBoolean(KEY_SUMROW_ADD,false);
57 Exporter.SESSION.put(KEY_SUMROW_ADD,initial);
5558
56 // Erstmal per Default nicht ausblenden
57 Exporter.SESSION.put(KEY_SUMROW_ADD,false);
58
59 final CheckboxInput check = new CheckboxInput(ExportDialog.SETTINGS.getBoolean(KEY_SUMROW_ADD,false));
59 final CheckboxInput check = new CheckboxInput(initial);
6060 check.setName(i18n.tr("Summe-Zeile am Ende der Datei anfügen"));
6161 check.addListener(new Listener() {
6262 public void handleEvent(Event event)
5454 return;
5555
5656 // Erstmal per Default nicht ausblenden
57 Exporter.SESSION.put(KEY_SALDO_HIDE,false);
57 boolean initial = ExportDialog.SETTINGS.getBoolean(KEY_SALDO_HIDE,false);
58 Exporter.SESSION.put(KEY_SALDO_HIDE,initial);
5859
59 final CheckboxInput check = new CheckboxInput(ExportDialog.SETTINGS.getBoolean(KEY_SALDO_HIDE,false));
60 final CheckboxInput check = new CheckboxInput(initial);
6061 check.setName(i18n.tr("Spalte \"Saldo\" in Export ausblenden"));
6162 check.addListener(new Listener() {
6263 public void handleEvent(Event event)
1010 package de.willuhn.jameica.hbci.gui.filter;
1111
1212 import java.rmi.RemoteException;
13
14 import org.apache.commons.lang.StringUtils;
1315
1416 import de.willuhn.jameica.hbci.HBCIProperties;
1517 import de.willuhn.jameica.hbci.rmi.Konto;
149151 SynchronizeEngine engine = service.get(SynchronizeEngine.class);
150152 return engine.supports(SynchronizeJobKontoauszug.class,konto);
151153 }
152 };
154 };
155
156 /**
157 * Liefert einen Kontofilter zur Suche nach Konten mit bestimmten Kriterien.
158 * @param text Suchbegriff.
159 * @param ignoreFlags optionale Flags. Kann NULL bleiben, wenn keine Flags als Filter dienen sollen. Konten mit diesen Flags werden ignoriert.
160 * @param accountType optionale Angabe der Kontoart.
161 * @return der Kontofilter.
162 */
163 public final static KontoFilter SEARCH(final String text, final Integer ignoreFlags, final Integer accountType)
164 {
165 return new KontoFilter() {
166 @Override
167 public boolean accept(Konto konto) throws RemoteException
168 {
169 if (konto == null)
170 return false;
171
172 if (ignoreFlags != null)
173 {
174 int f = ignoreFlags.intValue();
175
176 for (int flag:new int[]{Konto.FLAG_DISABLED,Konto.FLAG_OFFLINE})
177 {
178 // Ist das Flag in der Suche enthalten?
179 if ((f & flag) == flag)
180 {
181 // Dann darf es im Konto nicht enthalten sein
182 if (konto.hasFlag(flag))
183 return false;
184 }
185 }
186 }
187
188 if (accountType != null && (konto.getAccountType() == null || !konto.getAccountType().equals(accountType)))
189 return false;
190
191 String s = StringUtils.trimToNull(text);
192 if (s == null)
193 return true;
194 s = s.toLowerCase();
195
196 String s1 = StringUtils.trimToEmpty(konto.getBezeichnung()).toLowerCase();
197 String s2 = StringUtils.trimToEmpty(konto.getBic()).toLowerCase();
198 String s3 = StringUtils.trimToEmpty(konto.getBLZ()).toLowerCase();
199 String s4 = StringUtils.trimToEmpty(konto.getIban()).toLowerCase();
200 String s5 = StringUtils.trimToEmpty(konto.getKategorie()).toLowerCase();
201 String s6 = StringUtils.trimToEmpty(konto.getKommentar()).toLowerCase();
202 String s7 = StringUtils.trimToEmpty(konto.getKontonummer()).toLowerCase();
203 String s8 = StringUtils.trimToEmpty(konto.getKundennummer()).toLowerCase();
204 String s9 = StringUtils.trimToEmpty(konto.getName()).toLowerCase();
205
206 return s1.contains(s) ||
207 s2.contains(s) ||
208 s3.contains(s) ||
209 s4.contains(s) ||
210 s5.contains(s) ||
211 s6.contains(s) ||
212 s7.contains(s) ||
213 s8.contains(s) ||
214 s9.contains(s);
215 }
216 };
217 }
153218
154219 /**
155220 * Erzeugt einen Konto-Filter basierend auf {@link KontoFilter#FOREIGN}, welcher jedoch nur jene Konten
99
1010 package de.willuhn.jameica.hbci.gui.input;
1111
12 import java.util.Date;
13
1214 import org.eclipse.swt.widgets.Event;
1315 import org.eclipse.swt.widgets.Listener;
1416
17 import de.willuhn.jameica.gui.GUI;
1518 import de.willuhn.jameica.gui.input.Input;
1619 import de.willuhn.jameica.gui.input.SelectInput;
20 import de.willuhn.jameica.gui.parts.NotificationPanel;
1721 import de.willuhn.jameica.hbci.HBCI;
1822 import de.willuhn.jameica.hbci.server.Range;
23 import de.willuhn.jameica.messaging.StatusBarMessage;
1924 import de.willuhn.jameica.system.Application;
2025 import de.willuhn.jameica.system.Settings;
2126 import de.willuhn.util.I18N;
8186
8287 setValue(null);
8388 settings.setAttribute(param,(String)null);
89 checkRange();
8490 }
8591 };
8692
102108 }
103109 });
104110 }
105
111
112 /**
113 * Prueft den vom User eingegebenen Zeitraum auf Plausibilitaet.
114 */
115 private void checkRange()
116 {
117 if (this.from == null || this.to ==null)
118 return;
119
120 Object oFrom = this.from.getValue();
121 Object oTo = this.to.getValue();
122
123 if (!(oFrom instanceof Date) || !(oTo instanceof Date))
124 return;
125
126 Date dFrom = (Date) oFrom;
127 Date dTo = (Date) oTo;
128
129 if (dTo.before(dFrom))
130 {
131 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Bitte prüfen Sie den Zeitraum. Das Bis-Datum sollte nicht vor dem Von-Datum liegen."), StatusBarMessage.TYPE_INFO));
132 return;
133 }
134
135 // Hier weitere Checks bei Bedarf
136
137
138 // Ansonsten Fehlermeldung loeschen
139 NotificationPanel panel = GUI.getView().getNotificationPanel();
140 if (panel != null)
141 panel.reset();
142
143 }
144
106145 /**
107146 * Wendet den Range auf die Von- und Bis-Felder an.
108147 * @param range der Range. Kann null sein.
0 /**********************************************************************
1 *
2 * Copyright (c) 2018 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.gui.input;
11
12 import org.eclipse.swt.SWT;
13 import org.eclipse.swt.widgets.Control;
14 import org.eclipse.swt.widgets.Event;
15 import org.eclipse.swt.widgets.Listener;
16
17 import de.willuhn.jameica.gui.input.TextInput;
18 import de.willuhn.jameica.hbci.HBCI;
19 import de.willuhn.jameica.hbci.HBCIProperties;
20 import de.willuhn.jameica.messaging.StatusBarMessage;
21 import de.willuhn.jameica.system.Application;
22 import de.willuhn.util.I18N;
23
24 /**
25 * Vorkonfiguriertes Eingabefeld fuer den Verwendungszweck.
26 */
27 public class ZweckInput extends TextInput
28 {
29 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
30 private final static String VALID = HBCIProperties.HBCI_SEPA_VALIDCHARS;
31
32 private Control control = null;
33
34 /**
35 * ct.
36 * @param value der Verwendungszweck.
37 */
38 public ZweckInput(String value)
39 {
40 super(value,HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
41 this.setValidChars(VALID);
42 this.setName(i18n.tr("Verwendungszweck"));
43 }
44
45 /**
46 * Ueberschrieben, um die in SEPA-Verwendungszwecken erlaubten Zeichen automatisch zu entfernen.
47 * Dann kann der User per Zwischenablage auch unerlaubte Zeichen einfuegen. Hibiscus schneidet die
48 * dann automatisch raus.
49 * @see de.willuhn.jameica.gui.input.TextInput#getControl()
50 */
51 @Override
52 public Control getControl()
53 {
54 if (this.control != null)
55 return this.control;
56
57 this.control = super.getControl();
58
59 // BUGZILLA 1495 - nicht erlaubte Zeichen automatisch rausschneiden
60 this.control.addListener(SWT.Verify, new Listener()
61 {
62 public void handleEvent(Event e)
63 {
64 if (e.text == null || e.text.length() == 0)
65 return;
66
67 String backup = e.text;
68 e.text = HBCIProperties.clean(e.text,VALID);
69
70 int diff = backup.length() - e.text.length();
71 if (diff > 0)
72 {
73 String msg = diff > 1 ? i18n.tr("Es wurden {0} nicht unterstützte Zeichen entfernt",Integer.toString(diff)) : i18n.tr("Es wurde ein nicht unterstütztes Zeichen entfernt");
74 Application.getMessagingFactory().sendMessage(new StatusBarMessage(msg,StatusBarMessage.TYPE_INFO));
75 }
76 }
77 });
78
79 return this.control;
80
81 }
82
83 }
1212
1313 import de.willuhn.jameica.gui.Action;
1414 import de.willuhn.jameica.gui.extension.Extendable;
15 import de.willuhn.jameica.gui.extension.ExtensionRegistry;
1516 import de.willuhn.jameica.gui.parts.CheckedContextMenuItem;
1617 import de.willuhn.jameica.gui.parts.CheckedSingleContextMenuItem;
1718 import de.willuhn.jameica.gui.parts.ContextMenu;
4748 public class KontoList extends ContextMenu implements Extendable
4849 {
4950
50 private I18N i18n;
51 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
5152
5253 /**
5354 * Erzeugt ein Kontext-Menu fuer eine Liste von Konten.
5455 */
5556 public KontoList()
5657 {
57 i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
58
5958 addItem(new CheckedSingleContextMenuItem(i18n.tr("Öffnen"), new KontoNew(),"document-open.png"));
6059 addItem(new ContextMenuItem(i18n.tr("Neues Konto..."), new KNeu(),"list-add.png"));
6160 addItem(new CheckedSingleContextMenuItem(i18n.tr("Löschen..."), new KontoDelete(),"user-trash-full.png"));
7574 addItem(new ContextMenuItem(i18n.tr("Umsätze importieren..."),new UmsatzImport(),"document-open.png"));
7675 addItem(ContextMenuItem.SEPARATOR);
7776 addMenu(new ExtendedMenu());
77
78 // Wir geben das Context-Menu jetzt noch zur Erweiterung frei.
79 ExtensionRegistry.extend(this);
7880 }
7981
8082 /**
3232 import de.willuhn.jameica.gui.formatter.TableFormatter;
3333 import de.willuhn.jameica.gui.input.SelectInput;
3434 import de.willuhn.jameica.gui.input.TextInput;
35 import de.willuhn.jameica.gui.parts.ButtonArea;
3536 import de.willuhn.jameica.gui.parts.TablePart;
3637 import de.willuhn.jameica.gui.util.Color;
3738 import de.willuhn.jameica.gui.util.DelayedListener;
3839 import de.willuhn.jameica.gui.util.TabGroup;
3940 import de.willuhn.jameica.hbci.HBCI;
4041 import de.willuhn.jameica.hbci.HBCIProperties;
42 import de.willuhn.jameica.hbci.gui.action.EmpfaengerNew;
4143 import de.willuhn.jameica.hbci.gui.filter.AddressFilter;
4244 import de.willuhn.jameica.hbci.gui.formatter.IbanFormatter;
4345 import de.willuhn.jameica.hbci.messaging.ImportMessage;
6062 */
6163 public class EmpfaengerList extends TablePart implements Part
6264 {
65 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
66
6367 private Addressbook book = null;
6468 private TextInput search = null;
65 private I18N i18n = null;
6669 private KeyAdapter listener = null;
6770 private AddressFilter filter = null;
6871
9295 super(action);
9396
9497 this.filter = filter;
95
96 this.i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
9798 this.listener = new DelayedAdapter();
9899
99100 addColumn(i18n.tr("Name"),"name");
231232 tab.addLabelPair(i18n.tr("Suchbegriff"), this.search);
232233 this.search.getControl().addKeyListener(this.listener);
233234
235 ButtonArea buttons = new ButtonArea();
236 buttons.addButton(i18n.tr("Neue Adresse"),new EmpfaengerNew(),null,true,"contact-new.png");
237 buttons.paint(parent);
234238
235239 // Damit wir den MessageConsumer beim Schliessen wieder entfernen
236240 parent.addDisposeListener(new DisposeListener() {
1313 import java.util.Arrays;
1414 import java.util.List;
1515
16 import org.eclipse.swt.SWT;
1617 import org.eclipse.swt.events.DisposeEvent;
1718 import org.eclipse.swt.events.DisposeListener;
19 import org.eclipse.swt.events.KeyAdapter;
20 import org.eclipse.swt.events.KeyEvent;
21 import org.eclipse.swt.events.KeyListener;
22 import org.eclipse.swt.layout.GridData;
1823 import org.eclipse.swt.widgets.Composite;
1924 import org.eclipse.swt.widgets.Event;
2025 import org.eclipse.swt.widgets.Listener;
26 import org.eclipse.swt.widgets.TabFolder;
2127 import org.eclipse.swt.widgets.TableItem;
2228
23 import de.willuhn.datasource.GenericIterator;
2429 import de.willuhn.datasource.GenericObject;
25 import de.willuhn.datasource.rmi.DBIterator;
2630 import de.willuhn.jameica.gui.Action;
2731 import de.willuhn.jameica.gui.GUI;
2832 import de.willuhn.jameica.gui.Part;
29 import de.willuhn.jameica.gui.formatter.CurrencyFormatter;
3033 import de.willuhn.jameica.gui.formatter.DateFormatter;
3134 import de.willuhn.jameica.gui.formatter.Formatter;
3235 import de.willuhn.jameica.gui.formatter.TableFormatter;
36 import de.willuhn.jameica.gui.input.CheckboxInput;
37 import de.willuhn.jameica.gui.input.SelectInput;
38 import de.willuhn.jameica.gui.input.TextInput;
39 import de.willuhn.jameica.gui.parts.ButtonArea;
3340 import de.willuhn.jameica.gui.parts.Column;
3441 import de.willuhn.jameica.gui.parts.TablePart;
42 import de.willuhn.jameica.gui.parts.table.Feature;
43 import de.willuhn.jameica.gui.parts.table.Feature.Context;
44 import de.willuhn.jameica.gui.parts.table.FeatureSummary;
3545 import de.willuhn.jameica.gui.util.Color;
46 import de.willuhn.jameica.gui.util.ColumnLayout;
47 import de.willuhn.jameica.gui.util.Container;
48 import de.willuhn.jameica.gui.util.DelayedListener;
49 import de.willuhn.jameica.gui.util.SimpleContainer;
50 import de.willuhn.jameica.gui.util.TabGroup;
3651 import de.willuhn.jameica.hbci.HBCI;
3752 import de.willuhn.jameica.hbci.HBCIProperties;
3853 import de.willuhn.jameica.hbci.PassportRegistry;
39 import de.willuhn.jameica.hbci.Settings;
4054 import de.willuhn.jameica.hbci.gui.ColorUtil;
55 import de.willuhn.jameica.hbci.gui.action.KontoFetchFromPassport;
56 import de.willuhn.jameica.hbci.gui.action.KontoNew;
57 import de.willuhn.jameica.hbci.gui.filter.KontoFilter;
58 import de.willuhn.jameica.hbci.gui.input.KontoartInput;
4159 import de.willuhn.jameica.hbci.messaging.ObjectChangedMessage;
4260 import de.willuhn.jameica.hbci.messaging.ObjectMessage;
4361 import de.willuhn.jameica.hbci.messaging.SaldoMessage;
4462 import de.willuhn.jameica.hbci.passport.Passport;
4563 import de.willuhn.jameica.hbci.rmi.Konto;
64 import de.willuhn.jameica.hbci.server.KontoUtil;
4665 import de.willuhn.jameica.messaging.Message;
4766 import de.willuhn.jameica.messaging.MessageConsumer;
67 import de.willuhn.jameica.messaging.StatusBarMessage;
4868 import de.willuhn.jameica.system.Application;
4969 import de.willuhn.logging.Logger;
70 import de.willuhn.util.ApplicationException;
5071 import de.willuhn.util.I18N;
5172
5273 /**
5475 */
5576 public class KontoList extends TablePart implements Part
5677 {
57
58 // BUGZILLA 476
78 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
79 private final static de.willuhn.jameica.system.Settings settings = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getSettings();
80
81 private TextInput search = null;
82 private CheckboxInput onlyActive = null;
83 private SelectInput accountType = null;
84
5985 private MessageConsumer mc = null;
60
61 private I18N i18n;
62
63 /**
64 * @param action
65 * @throws RemoteException
66 */
67 public KontoList(Action action) throws RemoteException
68 {
69 this(init(), action);
70 }
86 private boolean showFilter = true;
87
88 private Listener listener = new MyListener();
89 private KeyListener delayed = new MyDelayedListener();
7190
7291 /**
7392 * ct.
7493 * @param konten
7594 * @param action
7695 */
77 public KontoList(GenericIterator konten, Action action)
96 public KontoList(List<Konto> konten, Action action)
7897 {
7998 super(konten,action);
80
81 this.i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
99 this.addFeature(new FeatureSummary());
82100
83101 addColumn(i18n.tr("Kontonummer"),"kontonummer",null,false,Column.ALIGN_RIGHT);
84102 addColumn(i18n.tr("Bankleitzahl"),"blz", new Formatter() {
123141 }
124142 });
125143 addColumn(i18n.tr("Saldo"),"saldo",null,false,Column.ALIGN_RIGHT);
126 addSaldoAvailable(konten);
144 addColumn(i18n.tr("Verfügbar"),"saldo_available",null,false,Column.ALIGN_RIGHT);
127145 // BUGZILLA 108 http://www.willuhn.de/bugzilla/show_bug.cgi?id=108
128146 addColumn(i18n.tr("Saldo aktualisiert am"),"saldo_datum", new DateFormatter(HBCI.LONGDATEFORMAT));
129147 setFormatter(new TableFormatter()
137155 if ((saldo == 0 && k.getSaldoDatum() == null) || Double.isNaN(saldo))
138156 item.setText(saldocolumn,"");
139157 else
140 item.setText(saldocolumn,HBCI.DECIMALFORMAT.format(k.getSaldo()) + " " + k.getWaehrung());
158 item.setText(saldocolumn,HBCI.DECIMALFORMAT.format(saldo) + " " + k.getWaehrung());
159
160 double avail = k.getSaldoAvailable();
161 if ((avail == 0 && k.getSaldoDatum() == null) || Double.isNaN(avail))
162 item.setText(saldocolumn+1,"");
163 else
164 item.setText(saldocolumn+1,HBCI.DECIMALFORMAT.format(avail) + " " + k.getWaehrung());
165
166 item.setForeground(saldocolumn+1,ColorUtil.getForeground(k.getSaldoAvailable()));
141167
142168 // Checken, ob Konto deaktiviert ist
143169 int flags = k.getFlags();
180206 {
181207 public void handleEvent(Event event)
182208 {
183 refreshSummary();
209 featureEvent(Feature.Event.REFRESH,null);
184210 }
185211 });
186212 }
187
188 /**
189 * Fuegt die Spalte "verfuegbarer Betrag" hinzu, wenn wenigstens ein Konto
190 * aus der Liste einen solchen besitzt.
191 * @param konten Liste der zu checkenden Konten.
192 */
193 private void addSaldoAvailable(GenericIterator konten)
194 {
195 try
196 {
197 while (konten.hasNext())
198 {
199 Konto k = (Konto) konten.next();
200 if ((k.getFlags() & Konto.FLAG_OFFLINE) == Konto.FLAG_OFFLINE)
201 continue; // ignorieren
202 double d = k.getSaldoAvailable();
203 if (!Double.isNaN(d))
204 {
205 // Wir haben tatsaechlich eines, wo was drin steht
206 Column col = new Column("saldo_available",i18n.tr("Verfügbar"),new CurrencyFormatter(k.getWaehrung(),HBCI.DECIMALFORMAT),false,Column.ALIGN_RIGHT);
207 addColumn(col);
208 return;
209 }
210 }
211 }
212 catch (RemoteException re)
213 {
214 Logger.error("unable to check if at least one account has an available value",re);
215 }
216 finally
217 {
218 try
219 {
220 konten.begin();
221 }
222 catch (Exception e)
223 {
224 Logger.error("unable to reset iterator",e);
225 }
226 }
213
214 /**
215 * Legt fest, ob die Filtermoeglichkeiten angezeigt werden sollen.
216 * @param b true, wenn die Filtermoeglichkeiten angezeigt werden sollen.
217 */
218 public void setShowFilter(boolean b)
219 {
220 this.showFilter = b;
227221 }
228222
229223 /**
231225 */
232226 public synchronized void paint(Composite parent) throws RemoteException
233227 {
228 if (this.showFilter)
229 {
230 // Daten initial laden
231 reload();
232
233 final TabFolder folder = new TabFolder(parent, SWT.NONE);
234 folder.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
235 TabGroup tab = new TabGroup(folder,i18n.tr("Anzeige einschränken"));
236
237 ColumnLayout cols = new ColumnLayout(tab.getComposite(),2);
238
239 {
240 Container c = new SimpleContainer(cols.getComposite());
241 TextInput search = this.getText();
242 c.addInput(search);
243 search.getControl().addKeyListener(this.delayed);
244
245 c.addInput(this.getActiveOnly());
246 }
247
248 {
249 Container c = new SimpleContainer(cols.getComposite());
250 c.addInput(this.getAccountType());
251 }
252
253 ButtonArea buttons = new ButtonArea();
254 buttons.addButton(i18n.tr("Konten über den Bank-Zugang importieren..."), new Action() {
255 public void handleAction(Object context) throws ApplicationException
256 {
257 new KontoFetchFromPassport().handleAction(getSelection());
258 }
259 },null,false,"mail-send-receive.png");
260 buttons.addButton(i18n.tr("Konto manuell anlegen"),new KontoNew(),null,false,"list-add.png");
261 buttons.paint(parent);
262 }
263
234264 parent.addDisposeListener(new DisposeListener() {
235265 public void widgetDisposed(DisposeEvent e)
236266 {
239269 });
240270 super.paint(parent);
241271 }
242
243 /**
244 * Initialisiert die Konten-Liste.
245 * @return Liste der Konten.
272
273 /**
274 * Liefert das Eingabefeld mit dem Suchbegriff.
275 * @return das Eingabefeld mit dem Suchbegriff.
276 */
277 private TextInput getText()
278 {
279 if (this.search != null)
280 return this.search;
281
282 this.search = new TextInput(settings.getString("kontolist.filter.text",null),255);
283 this.search.setName(i18n.tr("Suchbegriff"));
284 return this.search;
285 }
286
287 /**
288 * Liefert die Checkbox, mit der eingestellt werden kann, ob nur aktive Konten angezeigt werden sollen.
289 * @return Checkbox.
290 */
291 private CheckboxInput getActiveOnly()
292 {
293 if (this.onlyActive != null)
294 return this.onlyActive;
295
296 this.onlyActive = new CheckboxInput(settings.getBoolean("kontolist.filter.active",false));
297 this.onlyActive.setName(i18n.tr("Nur aktive Konten"));
298 this.onlyActive.addListener(this.listener);
299 return this.onlyActive;
300 }
301
302 /**
303 * Liefert eine Auswahlbox mit der Kontoart.
304 * @return eine Auswahlbox mit der Kontoart.
305 */
306 private SelectInput getAccountType()
307 {
308 if (this.accountType != null)
309 return this.accountType;
310
311 this.accountType = new KontoartInput(settings.getInt("kontolist.filter.type",-1));
312 this.accountType.addListener(this.listener);
313 return this.accountType;
314 }
315
316 /**
317 * Laedt die Liste der Konten neu.
318 */
319 private void reload()
320 {
321 GUI.startSync(new Runnable() {
322
323 @Override
324 public void run()
325 {
326 try
327 {
328 removeAll();
329
330 // Liste neu laden
331 List<Konto> konten = getList();
332 if (konten == null)
333 return;
334
335 for (Konto k:konten)
336 addItem(k);
337
338 // Sortierung wiederherstellen
339 sort();
340 }
341 catch (Exception e)
342 {
343 Logger.error("error while reloading table",e);
344 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Fehler beim Aktualisieren der Tabelle"), StatusBarMessage.TYPE_ERROR));
345 }
346 }
347 });
348 }
349
350 /**
351 * Liefert die Liste der gefundenen Konten.
352 * @return die Liste der Konten.
246353 * @throws RemoteException
247354 */
248 private static DBIterator init() throws RemoteException
249 {
250 DBIterator i = Settings.getDBService().createList(Konto.class);
251 i.setOrder("ORDER BY LOWER(kategorie), blz, kontonummer, bezeichnung");
252 return i;
253 }
254
255 /**
256 * @see de.willuhn.jameica.gui.parts.TablePart#getSummary()
257 */
258 protected String getSummary()
355 private List<Konto> getList() throws RemoteException
356 {
357 final String text = (String) this.getText().getValue();
358 final boolean activeOnly = ((Boolean)this.getActiveOnly().getValue()).booleanValue();
359 final Integer type = (Integer) getAccountType().getValue();
360
361 Integer flags = activeOnly ? Konto.FLAG_DISABLED : null;
362 List<Konto> list = KontoUtil.getKonten(KontoFilter.SEARCH(text,flags,type));
363
364 // Speichern der Werte aus den Filter-Feldern.
365 settings.setAttribute("kontolist.filter.text",text);
366 settings.setAttribute("kontolist.filter.active",activeOnly);
367 settings.setAttribute("kontolist.filter.type",type != null ? type.intValue() : -1);
368
369 return list;
370 }
371
372 /**
373 * @see de.willuhn.jameica.gui.parts.TablePart#createFeatureEventContext(de.willuhn.jameica.gui.parts.table.Feature.Event, java.lang.Object)
374 */
375 @Override
376 protected Context createFeatureEventContext(de.willuhn.jameica.gui.parts.table.Feature.Event e, Object data)
377 {
378 Context ctx = super.createFeatureEventContext(e, data);
379 if (this.hasEvent(FeatureSummary.class,e))
380 ctx.addon.put(FeatureSummary.CTX_KEY_TEXT,this.getSummaryText());
381 return ctx;
382 }
383
384 /**
385 * Liefert die Summenzeile.
386 * @return die Summenzeile.
387 */
388 private String getSummaryText()
259389 {
260390 try
261391 {
280410
281411 if (selected)
282412 return i18n.tr("{0} Konten markiert, Gesamt-Saldo: {1} {2}",new String[]{Integer.toString(items.size()),HBCI.DECIMALFORMAT.format(sum),HBCIProperties.CURRENCY_DEFAULT_DE});
283
413
284414 return i18n.tr("Gesamt-Saldo: {0} {1}",new String[]{HBCI.DECIMALFORMAT.format(sum),HBCIProperties.CURRENCY_DEFAULT_DE});
285415 }
286 catch (Exception e)
287 {
288 Logger.error("error while updating summary",e);
289 }
290 return super.getSummary();
416 catch (Exception ex)
417 {
418 Logger.error("error while updating summary",ex);
419 }
420
421 return null;
291422 }
292423
293424 /**
345476 select(o);
346477
347478 // Summen-Zeile aktualisieren
348 refreshSummary();
479 featureEvent(Feature.Event.REFRESH,null);
349480 }
350481 catch (Exception e)
351482 {
363494 return false;
364495 }
365496 }
497
498 /**
499 * Listener zum Neuladen der Daten.
500 */
501 private class MyListener implements Listener
502 {
503 /**
504 * @see org.eclipse.swt.widgets.Listener#handleEvent(org.eclipse.swt.widgets.Event)
505 */
506 @Override
507 public void handleEvent(Event event)
508 {
509 reload();
510 }
511 }
512
513 /**
514 * Listener fuer das verzoegerte Reload.
515 */
516 private class MyDelayedListener extends KeyAdapter
517 {
518 private Listener forward = new DelayedListener(700,listener);
519
520 /**
521 * @see org.eclipse.swt.events.KeyAdapter#keyReleased(org.eclipse.swt.events.KeyEvent)
522 */
523 public void keyReleased(KeyEvent e)
524 {
525 forward.handleEvent(null);
526 }
527 }
366528 }
198198 }
199199
200200 ButtonArea buttons = new ButtonArea();
201 buttons.addButton(i18n.tr("Kontoauszüge abrufen..."), new KontoAction(new KontoFetchKontoauszug(),this.getKontoAuswahl()),null,false,"mail-send-receive.png");
202 buttons.addButton(i18n.tr("Einstellungen"),new KontoAction(new KontoauszugPdfSettings(),this.getKontoAuswahl()),null,false,"document-properties.png");
201 buttons.addButton(i18n.tr("Kontoauszüge abrufen..."), new KontoAction(new KontoFetchKontoauszug()),null,false,"mail-send-receive.png");
202 buttons.addButton(i18n.tr("Einstellungen"),new KontoAction(new KontoauszugPdfSettings()),null,false,"document-properties.png");
203203 buttons.addButton(i18n.tr("Aktualisieren"), new Action()
204204 {
205205 public void handleAction(Object context) throws ApplicationException
460460 return false;
461461 }
462462 }
463
464 /**
465 * Oeffnet die Einstellungen.
466 * @throws ApplicationException
467 */
468 public void handleSettings() throws ApplicationException
469 {
470 new KontoAction(new KontoauszugPdfSettings()).handleAction(null);
471 }
463472
464473 /**
465474 * Uebernimmt automatisch das ausgewaehlte Konto in die Action.
467476 private class KontoAction implements Action
468477 {
469478 private Action redirect = null;
470 private KontoInput input = null;
471479
472480 /**
473481 * ct.
474482 * @param redirect
475483 */
476 private KontoAction(Action redirect, KontoInput input)
484 private KontoAction(Action redirect)
477485 {
478486 this.redirect = redirect;
479 this.input = input;
480487 }
481488
482489 /**
490497 Konto k = null;
491498 try
492499 {
493 Object o = input.getValue();
500 Object o = getKontoAuswahl().getValue();
494501 if (o != null && (o instanceof Konto))
495502 k = (Konto) o;
496503 }
7272 {
7373 Object data = item.getData();
7474 if (data instanceof ConfigObject)
75 item.setImage(SWTUtil.getImage("user-info.png"));
75 {
76 ConfigObject o = (ConfigObject) data;
77 Passport p = o.passport;
78 String icon = "system-users.png";
79 if (p instanceof de.willuhn.jameica.hbci.passports.pintan.rmi.Passport)
80 icon = "hbci-pintan.png";
81 else if (p instanceof de.willuhn.jameica.hbci.passports.rdh.rmi.Passport)
82 icon = "dialog-password.png";
83 else if (p instanceof de.willuhn.jameica.hbci.passports.ddv.rmi.Passport)
84 icon = "gcr-smart-card.png";
85
86 item.setImage(SWTUtil.getImage(icon));
87 }
7688 }
7789 });
7890 this.setMulti(false);
2222 import org.eclipse.swt.widgets.Listener;
2323 import org.eclipse.swt.widgets.TreeItem;
2424
25 import de.willuhn.datasource.BeanUtil;
2625 import de.willuhn.datasource.GenericIterator;
2726 import de.willuhn.datasource.GenericObject;
2827 import de.willuhn.datasource.pseudo.PseudoIterator;
3433 import de.willuhn.jameica.gui.parts.table.Feature;
3534 import de.willuhn.jameica.gui.parts.table.Feature.Context;
3635 import de.willuhn.jameica.gui.parts.table.Feature.Event;
36 import de.willuhn.jameica.gui.parts.table.FeatureShortcut;
3737 import de.willuhn.jameica.gui.parts.table.FeatureSummary;
3838 import de.willuhn.jameica.gui.util.Font;
3939 import de.willuhn.jameica.hbci.HBCI;
5959 private final static de.willuhn.jameica.system.Settings settings = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getSettings();
6060 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
6161 private static Hashtable<String,Color> colorCache = new Hashtable<String,Color>();
62 private boolean summary = false;
6362
6463 /**
6564 * ct.
6968 public UmsatzTree(GenericIterator list) throws RemoteException
7069 {
7170 super(list, new UmsatzDetail());
72
73 try
74 {
75 BeanUtil.invoke(this,"addFeature",new Object[]{"de.willuhn.jameica.gui.parts.table.FeatureShortcut"});
76 }
77 catch (Exception e)
78 {
79 Logger.warn("Shortcut feature not available in this jameica version");
80 }
81 try
82 {
83 BeanUtil.invoke(this,"addFeature",new Object[]{"de.willuhn.jameica.gui.parts.table.FeatureSummary"});
84 this.summary = true;
85 }
86 catch (Exception e)
87 {
88 Logger.warn("Summary feature not available in this jameica version");
89 }
71 this.addFeature(new FeatureShortcut());
72 this.addFeature(new FeatureSummary());
9073
9174 this.setRememberColWidths(true);
9275 this.setRememberOrder(true);
164147
165148 this.setContextMenu(new UmsatzList());
166149
167 if (this.summary)
168 {
169 this.addSelectionListener(new Listener() {
170 @Override
171 public void handleEvent(org.eclipse.swt.widgets.Event event)
172 {
173 featureEvent(Feature.Event.REFRESH,null);
174 }
175 });
176 }
150 this.addSelectionListener(new Listener() {
151 @Override
152 public void handleEvent(org.eclipse.swt.widgets.Event event)
153 {
154 featureEvent(Feature.Event.REFRESH,null);
155 }
156 });
177157 }
178158
179159
1212 import java.rmi.RemoteException;
1313 import java.util.ArrayList;
1414 import java.util.Calendar;
15 import java.util.Collections;
1516 import java.util.Date;
1617 import java.util.HashMap;
1718 import java.util.List;
18
19 import java.util.Set;
20
21 import org.eclipse.swt.SWT;
22 import org.eclipse.swt.events.SelectionAdapter;
23 import org.eclipse.swt.events.SelectionEvent;
24 import org.eclipse.swt.events.SelectionListener;
1925 import org.eclipse.swt.widgets.Composite;
26 import org.eclipse.swt.widgets.Menu;
27 import org.eclipse.swt.widgets.MenuItem;
2028
2129 import de.willuhn.datasource.GenericObject;
2230 import de.willuhn.jameica.gui.Part;
3947 {
4048 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
4149
42 private List data = null;
43 private Date start = null;
44 private Date stop = null;
45 private LineChart chart = null;
50 private List data = null;
51 private Date start = null;
52 private Date stop = null;
53 private LineChart chart = null;
54 private Interval interval = Interval.MONTH;
55
56 /**
57 * Enum fuer die Intervall-Varianten.
58 */
59 private enum Interval
60 {
61 YEAR(Calendar.DAY_OF_YEAR,Calendar.YEAR,i18n.tr("Jahr")),
62 MONTH(Calendar.DAY_OF_MONTH,Calendar.MONTH,i18n.tr("Monat")),
63 WEEK(Calendar.DAY_OF_WEEK,Calendar.WEEK_OF_YEAR,i18n.tr("Woche")),
64
65 ;
66
67 private int type;
68 private int size;
69 private String name;
70
71 /**
72 * ct.
73 * @param type
74 * @param name
75 */
76 private Interval(int type, int size, String name)
77 {
78 this.type = type;
79 this.size = size;
80 this.name = name;
81 }
82
83 /**
84 * @see java.lang.Enum#toString()
85 */
86 @Override
87 public String toString()
88 {
89 return this.name;
90 }
91 }
4692
4793 /**
4894 * Speichert die anzuzeigenden Daten.
55101 this.data = data;
56102 this.start = start;
57103 this.stop = stop;
58
59 // Wenn das Start-Datum nicht angegeben ist, nehmen wir das
60 // aktuelle Jahr
61 if (this.start == null)
62 {
63 Calendar cal = Calendar.getInstance();
64 cal.set(Calendar.MONTH,Calendar.JANUARY);
65 cal.set(Calendar.DATE,1);
66 this.start = DateUtil.startOfDay(cal.getTime());
67 }
68 if (this.stop == null || !this.stop.after(this.start))
69 this.stop = new Date(); // Wenn das Stop-Datum ungueltig ist, machen wir heute draus
70104 }
71105
72106 /**
85119 for (int i=0;i<this.data.size();++i)
86120 {
87121 UmsatzTreeNode group = (UmsatzTreeNode) this.data.get(i);
88 ChartDataUmsatz cd = new ChartDataUmsatz(group);
122 ChartDataUmsatz cd = new ChartDataUmsatz(group, interval);
89123 if (cd.hasData)
90124 {
91125 this.chart.addData(cd);
94128 }
95129
96130 if (count <= 1)
97 this.chart.setTitle(i18n.tr("Bitte wählen Sie einen größeren Zeitraum (mindestens zwei Monate)"));
131 this.chart.setTitle(i18n.tr("Bitte wählen Sie einen größeren Zeitraum"));
98132 else
99 this.chart.setTitle(i18n.tr("Umsätze der Kategorien im Verlauf (gruppiert nach Monat)"));
133 this.chart.setTitle(i18n.tr("Umsätze der Kategorien im Verlauf (gruppiert nach {0})", this.interval.toString()));
100134
101135 this.chart.redraw();
102136 }
110144 {
111145 this.chart = new LineChart();
112146 this.chart.setStacked(false); // TODO Stacked Graph für "Umsätze nach Kategorieren" BUGZILLA 749
113 this.chart.setTitle(i18n.tr("Umsätze der Kategorien im Verlauf (gruppiert nach Monat)"));
147 this.chart.setTitle(i18n.tr("Umsätze der Kategorien im Verlauf (gruppiert nach {0})", this.interval.toString()));
114148 for (int i=0;i<this.data.size();++i)
115149 {
116150 UmsatzTreeNode group = (UmsatzTreeNode) this.data.get(i);
117 ChartDataUmsatz cd = new ChartDataUmsatz(group);
151 ChartDataUmsatz cd = new ChartDataUmsatz(group, interval);
118152 if (cd.hasData)
119153 this.chart.addData(cd);
120154 }
121155 this.chart.paint(parent);
156 addGroupingMenu();
122157 }
123158 catch (RemoteException re)
124159 {
128163 {
129164 Logger.error("unable to create chart",e);
130165 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Fehler beim Erzeugen des Diagramms"),StatusBarMessage.TYPE_ERROR));
166 }
167 }
168
169 /**
170 * Erweitert das Contextmenu des Chart um einen Menupunkt "Gruppierung nach".
171 */
172 private void addGroupingMenu()
173 {
174 Menu m = this.chart.getChart().getPlotArea().getMenu();
175
176 MenuItem groupMenuItem = new MenuItem(m, SWT.CASCADE, 0);
177 groupMenuItem.setText(i18n.tr("Gruppierung nach"));
178
179 new MenuItem(m,SWT.SEPARATOR,1);
180
181 Menu groupMenu = new Menu(groupMenuItem);
182 groupMenuItem.setMenu(groupMenu);
183
184 final List<MenuItem> items = new ArrayList<MenuItem>();
185 SelectionListener l = new SelectionAdapter()
186 {
187 /**
188 * @see org.eclipse.swt.events.SelectionAdapter#widgetSelected(org.eclipse.swt.events.SelectionEvent)
189 */
190 @Override
191 public void widgetSelected(SelectionEvent e)
192 {
193 MenuItem item = (MenuItem) e.getSource();
194
195 for (MenuItem i:items)
196 {
197 i.setSelection(i == item);
198 }
199
200 // aktuellen Wert uebernehmen
201 interval = (Interval) item.getData();
202
203 // Und neu zeichnen
204 try
205 {
206 redraw();
207 }
208 catch (RemoteException re)
209 {
210 Logger.error("unable to redraw chart",re);
211 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Fehler beim Aktualisieren"), StatusBarMessage.TYPE_ERROR));
212 }
213 }
214 };
215
216 for (Interval i:Interval.values())
217 {
218 final MenuItem item = new MenuItem(groupMenu, SWT.CHECK);
219 item.setText(i.toString());
220 item.setSelection(this.interval == i);
221 item.setData(i);
222 item.addSelectionListener(l);
223 items.add(item);
131224 }
132225 }
133226
139232 private UmsatzTreeNode group = null;
140233 private List<Entry> entries = new ArrayList<Entry>();
141234 private boolean hasData = false;
235 private Date chartStartDate = null;
236 private Date chartStopDate = null;
142237
143238 private List<Umsatz> getRecursiveUmsaetze(UmsatzTreeNode group) {
144239 List<Umsatz> result = new ArrayList<Umsatz>();
152247 /**
153248 * Erzeugt eine Liste mit den aggregierten Daten für eine Linie des Charts
154249 * @param group
250 * @param interval das ausgewaehlte Intervall.
155251 * @throws RemoteException
156252 */
157 private ChartDataUmsatz(UmsatzTreeNode group) throws RemoteException
253 private ChartDataUmsatz(UmsatzTreeNode group, final Interval interval) throws RemoteException
158254 {
159255 HashMap<Date,Double> verteilung = new HashMap<Date, Double>();
160256 Calendar calendar = Calendar.getInstance();
161257 this.group = group;
162258 this.entries.clear();
163259
164 for (Umsatz umsatz: getRecursiveUmsaetze(group)) {
165 if (umsatz.getDatum() == null) {
260 for (Umsatz umsatz:getRecursiveUmsaetze(group))
261 {
262 if (umsatz.getDatum() == null)
263 {
166264 Logger.warn("no date found for umsatz, skipping record");
167265 continue;
168266 }
169267 this.hasData = true;
170268 calendar.setTime(DateUtil.startOfDay(umsatz.getDatum()));
171 calendar.set(Calendar.DAY_OF_MONTH,1);
172 double aggMonatsWert = verteilung.containsKey(calendar.getTime())?verteilung.get(calendar.getTime()):0;
173 verteilung.put(calendar.getTime(), umsatz.getBetrag() + aggMonatsWert);
174 }
175
176 calendar.setTime(DateUtil.startOfDay(start));
177 calendar.set(Calendar.DAY_OF_MONTH, 1);
178 Date monat = calendar.getTime();
179
180 // BUGZILLA 1604 - wir wollen im End-Datum kein oberes Jahr fest vorgeben.
181 // Daher beenden wir hier die Iteration stattdessen nach maximal 1200 Monaten.
182 // Das sind 100 Jahre.
183 int limit = 0;
184 while(monat.before(stop) && limit++ < 1200) {
185 Entry aktuellerMonatswert = new Entry();
186 aktuellerMonatswert.monat = monat;
187 if (verteilung.containsKey(monat)) {
188 aktuellerMonatswert.betrag = verteilung.get(monat);
189 }
190 entries.add(aktuellerMonatswert);
191
192 calendar.setTime(monat);
193 calendar.add(Calendar.MONTH, 1);
194 monat = calendar.getTime();
195 }
269 calendar.set(interval.type, 1);
270
271 Date key = calendar.getTime();
272 double aggMonatsWert = verteilung.containsKey(key) ? verteilung.get(key) : 0;
273 verteilung.put(key, umsatz.getBetrag() + aggMonatsWert);
274 }
275
276 calculateChartInterval(verteilung.keySet());
277
278 calendar.setTime(DateUtil.startOfDay(chartStartDate));
279 calendar.set(interval.type, 1);
280 Date next = calendar.getTime();
281
282 while(!next.after(chartStopDate))
283 {
284 Entry aktuellerWert = new Entry();
285 aktuellerWert.monat = next;
286 if (verteilung.containsKey(next))
287 aktuellerWert.betrag = verteilung.get(next);
288 entries.add(aktuellerWert);
289
290 calendar.setTime(next);
291 calendar.add(interval.size, 1);
292 next = calendar.getTime();
293 }
294
295 //Dummy-Eintrag für das nächste Intervall, da das letzte reguläre sonst
296 //aufgrund der Normalisierung auf den ersten Tag des Intervalls
297 //ggf. gar nicht angezeigt wird
298 Entry lastEntry = new Entry();
299 lastEntry.monat = next;
300 entries.add(lastEntry);
301 }
302
303 /**
304 * Ermittelt das Minimum und Maximum aus dem Set von Datumswerten.
305 * @param chartDates das Set der Datumswerte.
306 */
307 private void calculateChartInterval(Set<Date> chartDates)
308 {
309 Date min = new Date();
310 Date max = new Date();
311
312 if (!chartDates.isEmpty())
313 {
314 min = Collections.min(chartDates);
315 max = Collections.max(chartDates);
316 }
317
318 // Wenn ein explizites Start-Datum angegeben ist und es sich hinter
319 // dem ermittelten befindet, nehmen wir das explizit angegebene
320 this.chartStartDate = (start != null && start.after(min)) ? start : min;
321
322 // Wenn ein explizites Stop-Datum angegeben ist und es sich vor
323 // dem ermittelten befindet, nehmen wir das explizit angegebene
324 this.chartStopDate = (stop != null && stop.before(max)) ? start : max;
196325 }
197326
198327 /**
1313
1414 import de.willuhn.jameica.gui.AbstractView;
1515 import de.willuhn.jameica.gui.GUI;
16 import de.willuhn.jameica.gui.input.MultiInput;
1617 import de.willuhn.jameica.gui.util.ColumnLayout;
1718 import de.willuhn.jameica.gui.util.SimpleContainer;
1819 import de.willuhn.jameica.hbci.HBCI;
7879 right.addHeadline(i18n.tr("Sonstige Informationen"));
7980 right.addLabelPair(i18n.tr("Art der Buchung"), control.getArt());
8081 right.addLabelPair(i18n.tr("Kundenreferenz"), control.getCustomerRef());
81 right.addLabelPair(i18n.tr("Primanota-Kennzeichen"), control.getPrimanota());
82 right.addLabelPair(i18n.tr("Geschäftsvorfall-Code"), control.getGvCode());
82 right.addInput(control.getEndToEndId());
83 right.addLabelPair(i18n.tr("Primanota/GV-Code"),new MultiInput(control.getPrimanota(),control.getGvCode()));
8384
8485 right.addHeadline(i18n.tr("Notizen"));
8586 right.addPart(control.getKommentar());
2828 import de.willuhn.jameica.hbci.HBCI;
2929 import de.willuhn.jameica.hbci.gui.action.EinnahmeAusgabeExport;
3030 import de.willuhn.jameica.hbci.gui.controller.EinnahmeAusgabeControl;
31 import de.willuhn.jameica.hbci.server.EinnahmeAusgabe;
31 import de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum;
3232 import de.willuhn.jameica.messaging.StatusBarMessage;
3333 import de.willuhn.jameica.system.Application;
3434 import de.willuhn.logging.Logger;
6060
6161 Container left = new SimpleContainer(cols.getComposite());
6262 left.addInput(control.getKontoAuswahl());
63 left.addInput(control.getInterval());
6364
6465 Container right = new SimpleContainer(cols.getComposite());
6566
7677 {
7778 try
7879 {
79 List data = control.getTable().getItems();
80 new EinnahmeAusgabeExport().handleAction(data.toArray(new EinnahmeAusgabe[data.size()]));
80 List data = control.getTree().getItems();
81 new EinnahmeAusgabeExport().handleAction(data.toArray(new EinnahmeAusgabeZeitraum[data.size()]));
8182 }
8283 catch (RemoteException re)
8384 {
99100 },null,true,"view-refresh.png");
100101 buttons.paint(getParent());
101102
102 control.getTable().paint(this.getParent());
103 control.getTree().paint(this.getParent());
103104 }
104105 }
1010
1111 import de.willuhn.jameica.gui.AbstractView;
1212 import de.willuhn.jameica.gui.GUI;
13 import de.willuhn.jameica.gui.parts.ButtonArea;
1413 import de.willuhn.jameica.hbci.HBCI;
15 import de.willuhn.jameica.hbci.gui.action.EmpfaengerNew;
1614 import de.willuhn.jameica.hbci.gui.controller.EmpfaengerControl;
1715 import de.willuhn.jameica.system.Application;
1816 import de.willuhn.util.I18N;
3432 EmpfaengerControl control = new EmpfaengerControl(this);
3533
3634 control.getEmpfaengerListe().paint(getParent());
37
38 ButtonArea buttons = new ButtonArea();
39 buttons.addButton(i18n.tr("Neue Adresse"),new EmpfaengerNew(),null,true,"contact-new.png");
40 buttons.paint(getParent());
4135 }
4236 }
43
44
45 /**********************************************************************
46 * $Log: EmpfaengerList.java,v $
47 * Revision 1.9 2011/04/08 15:19:13 willuhn
48 * @R Alle Zurueck-Buttons entfernt - es gibt jetzt einen globalen Zurueck-Button oben rechts
49 * @C Code-Cleanup
50 *
51 **********************************************************************/
99 package de.willuhn.jameica.hbci.gui.views;
1010
1111 import de.willuhn.jameica.gui.AbstractView;
12 import de.willuhn.jameica.gui.Action;
1312 import de.willuhn.jameica.gui.GUI;
14 import de.willuhn.jameica.gui.parts.ButtonArea;
1513 import de.willuhn.jameica.hbci.HBCI;
16 import de.willuhn.jameica.hbci.gui.action.KontoNew;
1714 import de.willuhn.jameica.hbci.gui.controller.KontoControl;
1815 import de.willuhn.jameica.system.Application;
19 import de.willuhn.util.ApplicationException;
2016 import de.willuhn.util.I18N;
2117
2218 /**
3430 {
3531
3632 final KontoControl control = new KontoControl(this);
37 GUI.getView().setTitle(i18n.tr("Vorhandene Bankverbindungen"));
33 GUI.getView().setTitle(i18n.tr("Vorhandene Konten"));
3834
3935 control.getKontoListe().paint(getParent());
40
41 ButtonArea buttons = new ButtonArea();
42 buttons.addButton(i18n.tr("Konten über den Bank-Zugang importieren..."), new Action() {
43 public void handleAction(Object context) throws ApplicationException
44 {
45 control.handleReadFromPassport();
46 }
47 },null,false,"mail-send-receive.png");
48 buttons.addButton(i18n.tr("Konto manuell anlegen"),new KontoNew(),null,false,"list-add.png");
49 buttons.paint(getParent());
5036 }
5137 }
1414 import org.eclipse.swt.widgets.Listener;
1515
1616 import de.willuhn.jameica.gui.AbstractView;
17 import de.willuhn.jameica.gui.Action;
1718 import de.willuhn.jameica.gui.GUI;
1819 import de.willuhn.jameica.gui.internal.parts.PanelButtonPrint;
20 import de.willuhn.jameica.gui.parts.PanelButton;
1921 import de.willuhn.jameica.hbci.HBCI;
22 import de.willuhn.jameica.hbci.gui.action.KontoauszugSettings;
2023 import de.willuhn.jameica.hbci.io.print.PrintSupportUmsatzList;
2124 import de.willuhn.jameica.hbci.rmi.Konto;
2225 import de.willuhn.jameica.system.Application;
26 import de.willuhn.jameica.system.OperationCanceledException;
27 import de.willuhn.util.ApplicationException;
2328 import de.willuhn.util.I18N;
2429
2530 /**
5055 print.setEnabled(list.getSelection() != null);
5156 }
5257 });
53
58
59 final PanelButton settings = new PanelButton("document-properties.png",new Action() {
60 @Override
61 public void handleAction(Object context) throws ApplicationException
62 {
63 try
64 {
65 new KontoauszugSettings().handleAction(null);
66 // Ein einfaches Reload reicht nicht, da die Spalten ggf. geaendert wurden
67 GUI.startView(GUI.getCurrentView(),getCurrentObject());
68 }
69 catch (OperationCanceledException oce)
70 {
71 // ignore
72 }
73 }
74 },i18n.tr("Einstellungen"));
75
76 GUI.getView().addPanelButton(settings);
5477 GUI.getView().addPanelButton(print);
5578
5679 list.paint(getParent());
1010 package de.willuhn.jameica.hbci.gui.views;
1111
1212 import de.willuhn.jameica.gui.AbstractView;
13 import de.willuhn.jameica.gui.Action;
1314 import de.willuhn.jameica.gui.GUI;
15 import de.willuhn.jameica.gui.parts.PanelButton;
1416 import de.willuhn.jameica.hbci.HBCI;
1517 import de.willuhn.jameica.hbci.gui.controller.KontoauszugPdfControl;
1618 import de.willuhn.jameica.system.Application;
19 import de.willuhn.util.ApplicationException;
1720 import de.willuhn.util.I18N;
1821
1922 /**
3336
3437 final KontoauszugPdfControl control = new KontoauszugPdfControl(this);
3538 final de.willuhn.jameica.hbci.gui.parts.KontoauszugPdfList list = control.getList();
39
3640
3741 list.paint(getParent());
42
43 PanelButton button = new PanelButton("document-properties.png",new Action() {
44 @Override
45 public void handleAction(Object context) throws ApplicationException
46 {
47 list.handleSettings();
48 }
49 },i18n.tr("Einstellungen"));
50 GUI.getView().addPanelButton(button);
51
3852 }
3953
4054 }
1111 import de.willuhn.jameica.gui.AbstractView;
1212 import de.willuhn.jameica.gui.GUI;
1313 import de.willuhn.jameica.gui.parts.ButtonArea;
14 import de.willuhn.jameica.gui.util.ScrolledContainer;
1415 import de.willuhn.jameica.gui.util.SimpleContainer;
1516 import de.willuhn.jameica.hbci.HBCI;
1617 import de.willuhn.jameica.hbci.HBCIProperties;
3940
4041 GUI.getView().setTitle(i18n.tr("System-Nachricht vom {0}", HBCI.DATEFORMAT.format(n.getDatum())));
4142
42 SimpleContainer container = new SimpleContainer(getParent());
43 container.addText(i18n.tr("{0} [BLZ: {1}]", new String[] {HBCIProperties.getNameForBank(n.getBLZ()),n.getBLZ()}) + "\n",true);
44 container.addText(n.getNachricht(),true);
43 SimpleContainer container = new SimpleContainer(getParent(),true);
44 String name = HBCIProperties.getNameForBank(n.getBLZ());
45 if (name != null)
46 container.addText(i18n.tr("{0} [BLZ: {1}]", new String[] {name,n.getBLZ()}) + "\n",true);
47 else
48 container.addText(i18n.tr("BLZ: {0}", new String[] {n.getBLZ()}) + "\n",true);
49
50 ScrolledContainer sc = new ScrolledContainer(container.getComposite());
51 String msg = n.getNachricht();
52 msg = msg.replace("\\n","\n"); // Falls die Zeilenumbrueche escaped waren
53 sc.addText(msg,true);
4554
4655 ButtonArea buttons = new ButtonArea();
4756 buttons.addButton(i18n.tr("In Zwischenablage kopieren"),new NachrichtCopy(),n,false,"edit-copy.png");
4958 buttons.paint(getParent());
5059 }
5160 }
52
53
54 /**********************************************************************
55 * $Log: NachrichtDetails.java,v $
56 * Revision 1.2 2011/04/08 15:19:14 willuhn
57 * @R Alle Zurueck-Buttons entfernt - es gibt jetzt einen globalen Zurueck-Button oben rechts
58 * @C Code-Cleanup
59 *
60 * Revision 1.1 2009/07/17 08:42:57 willuhn
61 * @N Detail-Ansicht fuer Systemnachrichten der Bank
62 * @N Systemnachrichten in Zwischenablage kopieren
63 *
64 **********************************************************************/
5353
5454 // Grund-Einstellungen
5555 TabGroup system = new TabGroup(getTabFolder(),i18n.tr("Grundeinstellungen"));
56 system.addCheckbox(control.getOnlineMode(),i18n.tr("Dauerhafte Internetverbindung, Aufforderung zum Verbinden nicht erforderlich"));
5756 system.addCheckbox(control.getCachePin(),i18n.tr("PIN-Eingaben für die aktuelle Sitzung zwischenspeichern"));
5857 system.addCheckbox(control.getStorePin(),i18n.tr("PIN-Eingaben permanent speichern (nur bei PIN/TAN)"));
59 system.addCheckbox(control.getDecimalGrouping(),i18n.tr("Tausender-Trennzeichen bei Geld-Beträgen anzeigen"));
6058 system.addCheckbox(control.getKontoCheck(),i18n.tr("Kontonummern und Bankleitzahlen mittels Prüfsumme testen"));
6159 system.addCheckbox(control.getKontoCheckExcludeAddressbook(),i18n.tr("Aufler Bankverbindungen des Adressbuches"));
6260 system.addLabelPair(i18n.tr("Limit für Aufträge"), control.getUeberweisungLimit());
6361
6462 // Farb-Einstellungen
65 TabGroup colors = new TabGroup(getTabFolder(),i18n.tr("Farben"));
66 colors.addLabelPair(i18n.tr("Textfarbe von Sollbuchungen"),control.getBuchungSollForeground());
67 colors.addLabelPair(i18n.tr("Textfarbe von Habenbuchungen"),control.getBuchungHabenForeground());
63 TabGroup ui = new TabGroup(getTabFolder(),i18n.tr("Benutzeroberfläche"));
64 ui.addLabelPair(i18n.tr("Textfarbe von Sollbuchungen"),control.getBuchungSollForeground());
65 ui.addLabelPair(i18n.tr("Textfarbe von Habenbuchungen"),control.getBuchungHabenForeground());
66 ui.addCheckbox(control.getDecimalGrouping(),i18n.tr("Tausender-Trennzeichen bei Geld-Beträgen anzeigen"));
6867
6968 // Umsatz-Kategorien
7069 TabGroup umsatztypes = new TabGroup(getTabFolder(),i18n.tr("Umsatz-Kategorien"));
2020 import org.apache.commons.lang.StringUtils;
2121 import org.kapott.hbci.GV.generators.ISEPAGenerator;
2222 import org.kapott.hbci.GV.generators.SEPAGeneratorFactory;
23 import org.kapott.hbci.sepa.PainVersion;
24 import org.kapott.hbci.sepa.PainVersion.Type;
23 import org.kapott.hbci.sepa.SepaVersion;
24 import org.kapott.hbci.sepa.SepaVersion.Type;
2525
2626 import de.willuhn.jameica.hbci.gui.dialogs.KontoAuswahlDialog;
2727 import de.willuhn.jameica.hbci.gui.dialogs.PainVersionDialog;
106106
107107 // User nach der SEPA-Version fragen, die verwendet werden soll.
108108 PainVersionDialog d = new PainVersionDialog(this.getPainType());
109 PainVersion version = (PainVersion) d.open();
109 SepaVersion version = (SepaVersion) d.open();
110110 ctx.version = version;
111111
112112 // Header-Infos zuweisen
196196 */
197197 protected class JobContext
198198 {
199 protected PainVersion version = null;
199 protected SepaVersion version = null;
200200 protected Properties props = new Properties();
201201 protected Map meta = new HashMap();
202202
2121
2222 import org.kapott.hbci.GV.parsers.ISEPAParser;
2323 import org.kapott.hbci.GV.parsers.SEPAParserFactory;
24 import org.kapott.hbci.sepa.PainVersion;
24 import org.kapott.hbci.sepa.SepaVersion;
25 import org.kapott.hbci.sepa.SepaVersion.Type;
2526
2627 import de.willuhn.io.IOUtil;
2728 import de.willuhn.jameica.hbci.gui.dialogs.KontoAuswahlDialog;
6970 ByteArrayOutputStream bos = new ByteArrayOutputStream();
7071 IOUtil.copy(is,bos);
7172
72 PainVersion version = PainVersion.autodetect(new ByteArrayInputStream(bos.toByteArray()));
73 SepaVersion version = SepaVersion.autodetect(new ByteArrayInputStream(bos.toByteArray()));
7374 if (version == null)
7475 throw new ApplicationException(i18n.tr("SEPA-Version der XML-Datei nicht ermittelbar"));
7576
7677 monitor.log(i18n.tr("SEPA-Version: {0}",version.getURN()));
7778
7879 // PAIN-Typ nicht kompatibel. User fragen, ob er trotzdem importieren moechte
79 PainVersion.Type type = this.getSupportedPainType();
80 SepaVersion.Type type = this.getSupportedPainType();
8081 if (type != null && type != version.getType())
8182 {
8283 String l = i18n.tr("Lastschrift");
8384 String u = i18n.tr("Überweisung");
8485 String q = i18n.tr("Sie versuchen, eine {0} als {1} zu importieren.\nVorgang wirklich fortsetzen?");
85 boolean b = type == PainVersion.Type.PAIN_001;
86 boolean b = type == SepaVersion.Type.PAIN_001;
8687 if (!Application.getCallback().askUser(q,new String[]{b ? l : u, b ? u : l}))
8788 throw new OperationCanceledException();
8889 }
183184 * Wird benötigt, damit eine Lastschrift nicht versehentlich als Überweisung importiert wird.
184185 * @return erlaubter SEPA PAIN-Typ.
185186 */
186 abstract PainVersion.Type getSupportedPainType();
187 abstract Type getSupportedPainType();
187188
188189 }
0 /**********************************************************************
1 *
2 * Copyright (c) 2004 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.io;
11
12 import java.io.ByteArrayInputStream;
13 import java.io.ByteArrayOutputStream;
14 import java.io.InputStream;
15 import java.rmi.RemoteException;
16 import java.util.ArrayList;
17 import java.util.List;
18
19 import org.kapott.hbci.GV.parsers.ISEPAParser;
20 import org.kapott.hbci.GV.parsers.SEPAParserFactory;
21 import org.kapott.hbci.GV_Result.GVRKUms;
22 import org.kapott.hbci.GV_Result.GVRKUms.BTag;
23 import org.kapott.hbci.GV_Result.GVRKUms.UmsLine;
24 import org.kapott.hbci.sepa.SepaVersion;
25
26 import de.willuhn.io.IOUtil;
27 import de.willuhn.jameica.hbci.HBCI;
28 import de.willuhn.jameica.hbci.gui.dialogs.KontoAuswahlDialog;
29 import de.willuhn.jameica.hbci.messaging.ImportMessage;
30 import de.willuhn.jameica.hbci.rmi.Protokoll;
31 import de.willuhn.jameica.hbci.rmi.Umsatz;
32 import de.willuhn.jameica.hbci.server.Converter;
33 import de.willuhn.jameica.system.Application;
34 import de.willuhn.jameica.system.BackgroundTask;
35 import de.willuhn.jameica.system.OperationCanceledException;
36 import de.willuhn.logging.Logger;
37 import de.willuhn.util.ApplicationException;
38 import de.willuhn.util.I18N;
39 import de.willuhn.util.ProgressMonitor;
40
41 /**
42 * Importer fuer Umsaetze im CAMT-Format.
43 */
44 public class CamtUmsatzImporter implements Importer
45 {
46
47 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
48
49 /**
50 * @see de.willuhn.jameica.hbci.io.Importer#doImport(java.lang.Object, de.willuhn.jameica.hbci.io.IOFormat, java.io.InputStream, de.willuhn.util.ProgressMonitor, de.willuhn.jameica.system.BackgroundTask)
51 */
52 public void doImport(Object context, IOFormat format, InputStream is, ProgressMonitor monitor, BackgroundTask t) throws RemoteException, ApplicationException
53 {
54
55 if (is == null)
56 throw new ApplicationException(i18n.tr("Keine zu importierende Datei ausgewählt"));
57
58 if (format == null)
59 throw new ApplicationException(i18n.tr("Kein Datei-Format ausgewählt"));
60
61 try
62 {
63
64 de.willuhn.jameica.hbci.rmi.Konto konto = null;
65
66 if (context != null && context instanceof de.willuhn.jameica.hbci.rmi.Konto)
67 konto = (de.willuhn.jameica.hbci.rmi.Konto) context;
68
69 if (konto == null)
70 {
71 KontoAuswahlDialog d = new KontoAuswahlDialog(KontoAuswahlDialog.POSITION_CENTER);
72 d.setText(i18n.tr("Bitte wählen Sie das zu verwendende Konto aus."));
73 konto = (de.willuhn.jameica.hbci.rmi.Konto) d.open();
74 }
75
76 if (monitor != null)
77 monitor.setStatusText(i18n.tr("Lese Datei ein"));
78
79 ByteArrayOutputStream bos = new ByteArrayOutputStream();
80 IOUtil.copy(is,bos);
81
82 SepaVersion version = SepaVersion.autodetect(new ByteArrayInputStream(bos.toByteArray()));
83 if (version == null)
84 throw new ApplicationException(i18n.tr("SEPA-Version der XML-Datei nicht ermittelbar"));
85
86 SepaVersion.Type type = version.getType();
87 if (type == null || type != SepaVersion.Type.CAMT_052)
88 throw new ApplicationException(i18n.tr("Keine gültige CAMT-Datei"));
89
90 monitor.log(i18n.tr("SEPA-Version: {0}",version.getURN()));
91
92 List<BTag> tage = new ArrayList<BTag>();
93 ISEPAParser<List<BTag>> parser = SEPAParserFactory.get(version);
94 parser.parse(new ByteArrayInputStream(bos.toByteArray()),tage);
95
96 List<UmsLine> lines = new ArrayList<UmsLine>();
97 for (BTag tag:tage)
98 {
99 lines.addAll(tag.lines);
100 }
101
102 if (lines.size() == 0)
103 {
104 konto.addToProtokoll(i18n.tr("Keine Umsätze importiert"),Protokoll.TYP_ERROR);
105 return;
106 }
107
108 double factor = 100d / (double) lines.size();
109
110 int created = 0;
111 int error = 0;
112
113 for (int i=0;i<lines.size();++i)
114 {
115 if (monitor != null)
116 {
117 monitor.log(i18n.tr("Umsatz {0}", "" + (i+1)));
118 // Mit diesem Factor sollte sich der Fortschrittsbalken
119 // bis zum Ende der Swift-MT940-Datei genau auf 100% bewegen
120 monitor.setPercentComplete((int)((i+1) * factor));
121 }
122
123 try
124 {
125 if (t != null && t.isInterrupted())
126 throw new OperationCanceledException();
127
128 final Umsatz umsatz = Converter.HBCIUmsatz2HibiscusUmsatz((GVRKUms.UmsLine)lines.get(i));
129 umsatz.setKonto(konto); // muessen wir noch machen, weil der Converter das Konto nicht kennt
130 umsatz.store();
131 created++;
132 try
133 {
134 Application.getMessagingFactory().sendMessage(new ImportMessage(umsatz));
135 }
136 catch (Exception ex)
137 {
138 Logger.error("error while sending import message",ex);
139 }
140 }
141 catch (ApplicationException ae)
142 {
143 monitor.log(" " + ae.getMessage());
144 error++;
145 }
146 catch (Exception e)
147 {
148 Logger.error("unable to import line",e);
149 monitor.log(" " + i18n.tr("Fehler beim Import des Datensatzes: {0}",e.getMessage()));
150 error++;
151 }
152 }
153 monitor.setStatusText(i18n.tr("{0} Umsätze erfolgreich importiert, {1} fehlerhafte übersprungen", new String[]{""+created,""+error}));
154 monitor.addPercentComplete(1);
155 }
156 catch (OperationCanceledException oce)
157 {
158 Logger.warn("operation cancelled");
159 throw new ApplicationException(i18n.tr("Import abgebrochen"));
160 }
161 catch (ApplicationException ae)
162 {
163 throw ae;
164 }
165 catch (Exception e)
166 {
167 Logger.error("error while reading file",e);
168 throw new ApplicationException(i18n.tr("Fehler beim Import der Datei"));
169 }
170 finally
171 {
172 IOUtil.close(is);
173 }
174 }
175
176 /**
177 * @see de.willuhn.jameica.hbci.io.IO#getName()
178 */
179 public String getName()
180 {
181 return i18n.tr("SEPA CAMT-Format (XML)");
182 }
183
184 /**
185 * @see de.willuhn.jameica.hbci.io.IO#getIOFormats(java.lang.Class)
186 */
187 public IOFormat[] getIOFormats(Class objectType)
188 {
189 if (!Umsatz.class.equals(objectType))
190 return null; // Wir bieten uns nur fuer Umsaetze an
191
192 IOFormat f = new IOFormat() {
193 public String getName()
194 {
195 return CamtUmsatzImporter.this.getName();
196 }
197
198 /**
199 * @see de.willuhn.jameica.hbci.io.IOFormat#getFileExtensions()
200 */
201 public String[] getFileExtensions()
202 {
203 return new String[] {"*.xml"};
204 }
205 };
206 return new IOFormat[] { f };
207 }
208 }
1111
1212 import java.io.OutputStream;
1313 import java.rmi.RemoteException;
14 import java.util.Date;
1415
1516 import com.itextpdf.text.BaseColor;
1617 import com.itextpdf.text.DocumentException;
1718 import com.itextpdf.text.Element;
18
19 import com.itextpdf.text.Font;
20 import com.itextpdf.text.pdf.PdfPCell;
21
22 import de.willuhn.datasource.GenericIterator;
23 import de.willuhn.datasource.GenericObject;
1924 import de.willuhn.jameica.hbci.HBCI;
25 import de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum;
2026 import de.willuhn.jameica.hbci.server.EinnahmeAusgabe;
27 import de.willuhn.jameica.hbci.server.EinnahmeAusgabeTreeNode;
2128 import de.willuhn.jameica.system.Application;
2229 import de.willuhn.logging.Logger;
2330 import de.willuhn.util.ApplicationException;
3643 */
3744 public void doExport(Object[] objects, IOFormat format, OutputStream os, ProgressMonitor monitor) throws RemoteException, ApplicationException
3845 {
39 if (objects == null || !(objects instanceof EinnahmeAusgabe[]))
46 if (objects == null || !(objects instanceof EinnahmeAusgabeZeitraum[]))
4047 throw new ApplicationException(i18n.tr("Bitte wählen Sie die zu exportierenden Daten aus"));
4148
42 EinnahmeAusgabe[] ea = (EinnahmeAusgabe[]) objects;
43 if (ea.length == 0)
49 if (objects.length == 0)
4450 throw new ApplicationException(i18n.tr("Bitte wählen Sie die zu exportierenden Daten aus"));
4551
52 EinnahmeAusgabeZeitraum[] data = (EinnahmeAusgabeZeitraum[]) objects;
4653 Reporter reporter = null;
4754
4855 try
4956 {
50 String sub = "";
51
52 if (ea[0].getStartdatum() != null && ea[0].getEnddatum() != null)
53 sub = i18n.tr("Zeitraum {0} - {1}", new String[]{HBCI.DATEFORMAT.format(ea[0].getStartdatum()),HBCI.DATEFORMAT.format(ea[0].getEnddatum())});
54
55 reporter = new Reporter(os, monitor, i18n.tr("Einnahmen/Ausgaben"), sub,ea.length);
57 reporter = new Reporter(os, monitor, i18n.tr("Einnahmen/Ausgaben"), getZeitraum(data), data.length);
5658 reporter.addHeaderColumn(i18n.tr("Konto"), Element.ALIGN_CENTER, 100, BaseColor.LIGHT_GRAY);
5759 reporter.addHeaderColumn(i18n.tr("Anfangssaldo"), Element.ALIGN_CENTER, 60, BaseColor.LIGHT_GRAY);
5860 reporter.addHeaderColumn(i18n.tr("Einnahmen"), Element.ALIGN_CENTER, 60, BaseColor.LIGHT_GRAY);
6264 reporter.addHeaderColumn(i18n.tr("Differenz"), Element.ALIGN_CENTER, 60, BaseColor.LIGHT_GRAY);
6365 reporter.createHeader();
6466
65 // Iteration ueber Umsaetze
66 for (int i=0;i<ea.length; ++i)
67 {
68 reporter.addColumn(reporter.getDetailCell(ea[i].getText(), Element.ALIGN_LEFT));
69 reporter.addColumn(reporter.getDetailCell(ea[i].getAnfangssaldo()));
70 reporter.addColumn(reporter.getDetailCell(ea[i].getEinnahmen()));
71 reporter.addColumn(reporter.getDetailCell(ea[i].getAusgaben()));
72 reporter.addColumn(reporter.getDetailCell(ea[i].getEndsaldo()));
73 reporter.addColumn(reporter.getDetailCell(ea[i].getPlusminus()));
74 reporter.addColumn(reporter.getDetailCell(ea[i].getDifferenz()));
75 reporter.setNextRecord();
76 }
67 for (EinnahmeAusgabeZeitraum e:data)
68 {
69 if (e instanceof EinnahmeAusgabeTreeNode)
70 report((EinnahmeAusgabeTreeNode)e, reporter);
71 else
72 report((EinnahmeAusgabe)e, reporter, 0);
73 }
74
7775 if (monitor != null)
7876 monitor.setStatus(ProgressMonitor.STATUS_DONE);
7977 }
10098 }
10199 }
102100 }
101
102 /**
103 * Liefert einen Text mit dem Zeitraum.
104 * @param objects die zu exportierenden Daten.
105 * @return der Text mit dem Zeitraum.
106 */
107 private String getZeitraum(EinnahmeAusgabeZeitraum[] objects)
108 {
109 Date start = null;
110 Date end = null;
111
112 for (EinnahmeAusgabeZeitraum n:objects)
113 {
114 Date s = n.getStartdatum();
115 if (start == null || (s != null && s.before(start)))
116 start = s;
117
118 Date e = n.getEnddatum();
119 if (end == null || (e != null && e.after(end)))
120 end = e;
121 }
122
123 if (start != null && end != null)
124 return i18n.tr("Zeitraum {0} - {1}", new String[]{HBCI.DATEFORMAT.format(start),HBCI.DATEFORMAT.format(end)});
125
126 return "";
127 }
128
129 /**
130 * Erzeugt die Report-Zeilen fuer den Knoten.
131 * @param treeNode der Knoten.
132 * @param reporter der Reporter.
133 * @throws RemoteException
134 */
135 private void report(EinnahmeAusgabeTreeNode treeNode, Reporter reporter) throws RemoteException
136 {
137 String range = HBCI.DATEFORMAT.format(treeNode.getStartdatum()) + " - " + HBCI.DATEFORMAT.format(treeNode.getEnddatum());
138 PdfPCell cell = reporter.getDetailCell(range, Element.ALIGN_LEFT, null, null, Font.BOLD);
139 cell.setColspan(7);
140 reporter.addColumn(cell);
141 reporter.setNextRecord();
142 GenericIterator eas = treeNode.getChildren();
143 while(eas.hasNext())
144 {
145 GenericObject ea = eas.next();
146 report((EinnahmeAusgabe)ea, reporter,5);
147 }
148 }
149
150 /**
151 * Erzeugt eine Zeile fuer den Report.
152 * @param ea die Zeile.
153 * @param reporter der Reporter.
154 * @param indent Einrueckungslevel.
155 */
156 private void report(EinnahmeAusgabe ea, Reporter reporter, float indent)
157 {
158 PdfPCell cell = reporter.getDetailCell(ea.getText(), Element.ALIGN_LEFT);
159 cell.setPaddingLeft(indent);
160 reporter.addColumn(cell);
161 reporter.addColumn(reporter.getDetailCell(ea.getAnfangssaldo(),BaseColor.BLACK));
162 reporter.addColumn(reporter.getDetailCell(ea.getEinnahmen(),BaseColor.BLACK));
163 reporter.addColumn(reporter.getDetailCell(ea.getAusgaben(),BaseColor.BLACK));
164 reporter.addColumn(reporter.getDetailCell(ea.getEndsaldo(),BaseColor.BLACK));
165
166 double sum = ea.getPlusminus();
167 reporter.addColumn(reporter.getDetailCell(sum,sum >= 0.01d ? BaseColor.GREEN : (sum <= -0.01d ? BaseColor.RED : BaseColor.BLACK)));
168
169 double diff = ea.getDifferenz();
170 reporter.addColumn(reporter.getDetailCell(diff,Math.abs(diff) >= 0.01d ? BaseColor.RED : BaseColor.BLACK));
171 reporter.setNextRecord();
172 }
103173
104174 /**
105175 * @see de.willuhn.jameica.hbci.io.Exporter#suppportsExtension(java.lang.String)
116186 public IOFormat[] getIOFormats(Class objectType)
117187 {
118188 // Wir unterstuetzen nur Umsatz-Trees
119 if (!EinnahmeAusgabe.class.equals(objectType))
189 if (!EinnahmeAusgabeZeitraum.class.equals(objectType))
120190 return null;
121191
122192 IOFormat myFormat = new IOFormat()
104104 out.write(NL);
105105
106106 out.write(":20:Hibiscus" + NL);
107 out.write(":25:" + k.getBLZ() + "/" + k.getKontonummer() + curr + NL);
107 out.write(":25:" + k.getBLZ() + "/" + k.getKontonummer() + NL);
108 out.write(":28C:1" + NL); // Auszugsnummer. Belegen wir hart mit "1", damit das Feld vorhanden ist. SAP braucht das fuer den Import
108109
109110 if (showSaldo)
110111 {
107107 boolean showSaldo = (b == null || !b.booleanValue());
108108
109109 out.write(":20:Hibiscus" + NL);
110 out.write(":25:" + k.getBLZ() + "/" + k.getKontonummer() + curr + NL);
110 out.write(":25:" + k.getBLZ() + "/" + k.getKontonummer() + NL);
111 out.write(":28C:1" + NL); // Auszugsnummer. Belegen wir hart mit "1", damit das Feld vorhanden ist. SAP braucht das fuer den Import
111112
112113 for (int i=0;i<list.size();++i)
113114 {
260260 */
261261 public PdfPCell getDetailCell(double value)
262262 {
263 Font f = FontFactory.getFont(FontFactory.HELVETICA, 8f, Font.NORMAL, value >= 0.01d ? BaseColor.BLACK : BaseColor.RED);
263 return this.getDetailCell(value,value >= 0.01d ? BaseColor.BLACK : BaseColor.RED);
264 }
265
266 /**
267 * Erzeugt eine Zelle fuer die uebergebene Zahl in der angegebenen Farbe.
268 * @param value die Zahl.
269 * @param color die Farbe.
270 * @return die erzeugte Zelle.
271 */
272 public PdfPCell getDetailCell(double value, BaseColor color)
273 {
274 Font f = FontFactory.getFont(FontFactory.HELVETICA, 8f, Font.NORMAL, color);
264275 PdfPCell cell = new PdfPCell(new Phrase(HBCI.DECIMALFORMAT.format(value), f));
265276 cell.setHorizontalAlignment(Element.ALIGN_RIGHT);
266277 return cell;
2121 import org.apache.commons.lang.StringUtils;
2222 import org.kapott.hbci.GV.SepaUtil;
2323 import org.kapott.hbci.manager.HBCIUtils;
24 import org.kapott.hbci.sepa.PainVersion.Type;
24 import org.kapott.hbci.sepa.SepaVersion.Type;
2525
2626 import de.willuhn.jameica.hbci.HBCI;
2727 import de.willuhn.jameica.hbci.HBCIProperties;
1717 import org.apache.commons.lang.StringUtils;
1818 import org.kapott.hbci.GV.SepaUtil;
1919 import org.kapott.hbci.GV.parsers.ISEPAParser;
20 import org.kapott.hbci.sepa.PainVersion;
20 import org.kapott.hbci.sepa.SepaVersion;
21 import org.kapott.hbci.sepa.SepaVersion.Type;
2122
2223 import de.willuhn.datasource.rmi.DBService;
2324 import de.willuhn.jameica.hbci.messaging.ImportMessage;
8788 * @see de.willuhn.jameica.hbci.io.AbstractSepaImporter#getSupportedPainType()
8889 */
8990 @Override
90 PainVersion.Type getSupportedPainType()
91 Type getSupportedPainType()
9192 {
92 return PainVersion.Type.PAIN_008;
93 return SepaVersion.Type.PAIN_008;
9394 }
9495
9596 }
2222 import org.apache.commons.lang.StringUtils;
2323 import org.kapott.hbci.GV.SepaUtil;
2424 import org.kapott.hbci.manager.HBCIUtils;
25 import org.kapott.hbci.sepa.PainVersion.Type;
25 import org.kapott.hbci.sepa.SepaVersion.Type;
2626
2727 import de.willuhn.jameica.hbci.HBCI;
2828 import de.willuhn.jameica.hbci.HBCIProperties;
1818 import org.apache.commons.lang.StringUtils;
1919 import org.kapott.hbci.GV.SepaUtil;
2020 import org.kapott.hbci.GV.parsers.ISEPAParser;
21 import org.kapott.hbci.sepa.PainVersion;
21 import org.kapott.hbci.sepa.SepaVersion;
22 import org.kapott.hbci.sepa.SepaVersion.Type;
2223
2324 import de.willuhn.datasource.rmi.DBService;
2425 import de.willuhn.jameica.hbci.HBCI;
103104 * @see de.willuhn.jameica.hbci.io.AbstractSepaImporter#getSupportedPainType()
104105 */
105106 @Override
106 PainVersion.Type getSupportedPainType()
107 Type getSupportedPainType()
107108 {
108 return PainVersion.Type.PAIN_008;
109 return SepaVersion.Type.PAIN_008;
109110 }
110111
111112 }
1515 import org.apache.commons.lang.StringUtils;
1616 import org.kapott.hbci.GV.SepaUtil;
1717 import org.kapott.hbci.manager.HBCIUtils;
18 import org.kapott.hbci.sepa.PainVersion.Type;
18 import org.kapott.hbci.sepa.SepaVersion.Type;
1919
2020 import de.willuhn.jameica.hbci.HBCIProperties;
2121 import de.willuhn.jameica.hbci.MetaKey;
1818 import org.apache.commons.lang.StringUtils;
1919 import org.kapott.hbci.GV.SepaUtil;
2020 import org.kapott.hbci.GV.parsers.ISEPAParser;
21 import org.kapott.hbci.sepa.PainVersion;
21 import org.kapott.hbci.sepa.SepaVersion;
22 import org.kapott.hbci.sepa.SepaVersion.Type;
2223
2324 import de.willuhn.datasource.rmi.DBService;
2425 import de.willuhn.jameica.hbci.HBCI;
9293 * @see de.willuhn.jameica.hbci.io.AbstractSepaImporter#getSupportedPainType()
9394 */
9495 @Override
95 PainVersion.Type getSupportedPainType()
96 Type getSupportedPainType()
9697 {
97 return PainVersion.Type.PAIN_001;
98 return SepaVersion.Type.PAIN_001;
9899 }
99100
100101 }
1515 import org.apache.commons.lang.StringUtils;
1616 import org.kapott.hbci.GV.SepaUtil;
1717 import org.kapott.hbci.manager.HBCIUtils;
18 import org.kapott.hbci.sepa.PainVersion.Type;
18 import org.kapott.hbci.sepa.SepaVersion.Type;
1919
2020 import de.willuhn.jameica.hbci.HBCIProperties;
2121 import de.willuhn.jameica.hbci.rmi.AuslandsUeberweisung;
1717 import org.apache.commons.lang.StringUtils;
1818 import org.kapott.hbci.GV.SepaUtil;
1919 import org.kapott.hbci.GV.parsers.ISEPAParser;
20 import org.kapott.hbci.sepa.PainVersion;
20 import org.kapott.hbci.sepa.SepaVersion;
21 import org.kapott.hbci.sepa.SepaVersion.Type;
2122
2223 import de.willuhn.datasource.rmi.DBService;
2324 import de.willuhn.jameica.hbci.messaging.ImportMessage;
7576 * @see de.willuhn.jameica.hbci.io.AbstractSepaImporter#getSupportedPainType()
7677 */
7778 @Override
78 PainVersion.Type getSupportedPainType()
79 Type getSupportedPainType()
7980 {
80 return PainVersion.Type.PAIN_001;
81 return SepaVersion.Type.PAIN_001;
8182 }
8283
8384 }
5050 if (this.profile == null)
5151 {
5252 this.profile = new Profile();
53 this.profile.setName(i18n.tr("Default-Profil"));
5354 this.profile.setSkipLines(1);
54 this.profile.setVersion(0);
55 this.profile.setSystem(true);
5556
5657 Serializer ts = new DefaultSerializer();
5758
4040 if (this.profile == null)
4141 {
4242 this.profile = new Profile();
43 this.profile.setName(i18n.tr("Default-Profil"));
4344 this.profile.setSkipLines(1);
44 this.profile.setVersion(0);
45 this.profile.setSystem(true);
4546
4647 Serializer s = new DefaultSerializer();
4748 List<Column> list = this.profile.getColumns();
138138 clone.serializer = this.serializer;
139139 return clone;
140140 }
141
142 /**
143 * @see java.lang.Object#equals(java.lang.Object)
144 */
145 @Override
146 public boolean equals(Object obj)
147 {
148 if (!(obj instanceof Column))
149 return false;
150
151 Column other = (Column) obj;
152 return this.property.equals(other.property);
153 }
141154 }
142
143
144
145 /**********************************************************************
146 * $Log: Column.java,v $
147 * Revision 1.1 2010/03/16 00:44:18 willuhn
148 * @N Komplettes Redesign des CSV-Imports.
149 * - Kann nun erheblich einfacher auch fuer andere Datentypen (z.Bsp.Ueberweisungen) verwendet werden
150 * - Fehlertoleranter
151 * - Mehrfachzuordnung von Spalten (z.Bsp. bei erweitertem Verwendungszweck) moeglich
152 * - modulare Deserialisierung der Werte
153 * - CSV-Exports von Hibiscus koennen nun 1:1 auch wieder importiert werden (Import-Preset identisch mit Export-Format)
154 * - Import-Preset wird nun im XML-Format nach ~/.jameica/hibiscus/csv serialisiert. Damit wird es kuenftig moeglich sein,
155 * CSV-Import-Profile vorzukonfigurieren und anschliessend zu exportieren, um sie mit anderen Usern teilen zu koennen
156 *
157 **********************************************************************/
1515 import java.io.IOException;
1616 import java.io.InputStream;
1717 import java.io.InputStreamReader;
18 import java.nio.charset.Charset;
19 import java.nio.charset.UnsupportedCharsetException;
1820 import java.rmi.RemoteException;
1921 import java.util.ArrayList;
2022 import java.util.HashMap;
9193 Profile p = (Profile) d.open();
9294
9395 CsvPreference prefs = p.createCsvPreference();
94 csv = new CsvListReader(new InputStreamReader(new ByteArrayInputStream(data),p.getFileEncoding()),prefs);
96
97 Charset charset = null;
98
99 try
100 {
101 charset = Charset.forName(p.getFileEncoding());
102 }
103 catch (UnsupportedCharsetException e)
104 {
105 Logger.warn("unsupported charset: " + p.getFileEncoding());
106 }
107
108 csv = new CsvListReader(new InputStreamReader(new ByteArrayInputStream(data),charset != null ? charset : Charset.defaultCharset()),prefs);
95109
96110 List<String> line = csv.read();
97111
247261 }
248262 catch (OperationCanceledException oce)
249263 {
250 Logger.info("operation cancelled");
251 monitor.setStatus(ProgressMonitor.STATUS_CANCEL);
252 monitor.setStatusText(i18n.tr("Import abgebrochen"));
253264 throw oce;
254265 }
255266 catch (ApplicationException ae)
1919 /**
2020 * Bean fuer ein Profil zum Import von CSV-Dateien.
2121 */
22 public class Profile implements Serializable
22 public class Profile implements Serializable, Comparable
2323 {
24 private String name = null;
25 private boolean system = false;
2426 private List<Column> columns = new ArrayList<Column>();
2527 private String separatorChar = ";";
2628 private String quotingChar = "\"";
2729 private int skipLines = 0;
2830 private String fileEncoding = System.getProperty("file.encoding");
2931
30 private int version = 0;
31
3232 /**
3333 * Liefert die Liste der Spalten fuer das Profil.
3434 * @return columns Liste der Spalten fuer das Profil.
125125 }
126126
127127 /**
128 * Liefert die Versionsnummer des Profils.
129 * Wenn das Default-Profil des Formats eine hoehere Versionsnummer
130 * liefert als die ggf. serialisierte Version im Benutzerverzeichnis,
131 * dann wird die serialisierte Version ignoriert und stattdessen
132 * wieder das Default-Profil verwendet. Andernfalls muesste der
133 * User die XML-Datei in ~/.jameica/hibiscus/csv manuell loeschen,
134 * damit eine ggf. aktualisierte Profil-Version verwendet wird.
135 * @return version Versionsnummer des Profils.
136 */
137 public int getVersion()
138 {
139 return version;
140 }
141
142 /**
143 * Speichert die Versionsnummer des Profils.
144 * @param version version
145 */
146 public void setVersion(int version)
147 {
148 this.version = version;
128 * Liefert den Namen des Profils.
129 * @return der Name des Profils.
130 */
131 public String getName()
132 {
133 return name;
134 }
135
136 /**
137 * Speichert den Namen des Profils.
138 * @param name der Name des Profils.
139 */
140 public void setName(String name)
141 {
142 this.name = name;
143 }
144
145 /**
146 * Liefert true, wenn es sich um ein System-Profil handelt.
147 * @return system true, wenn es sich um ein System-Profil handelt.
148 */
149 public boolean isSystem()
150 {
151 return system;
152 }
153
154 /**
155 * Legt fest, ob es sich um ein System-Profil handelt.
156 * @param system true, wenn es sich um ein System-Profil handelt.
157 */
158 public void setSystem(boolean system)
159 {
160 this.system = system;
149161 }
150162
151163 /**
168180 Builder builder = new CsvPreference.Builder(qc,sc,prefs.getEndOfLineSymbols());
169181 return builder.build();
170182 }
183
184 /**
185 * @see java.lang.Object#equals(java.lang.Object)
186 */
187 @Override
188 public boolean equals(Object obj)
189 {
190 if (!(obj instanceof Profile))
191 return false;
192
193 Profile other = (Profile) obj;
194 return this.getName() != null && this.getName().equals(other.getName());
195 }
196
197 /**
198 * @see java.lang.Comparable#compareTo(java.lang.Object)
199 */
200 @Override
201 public int compareTo(Object o)
202 {
203 // System-Profil immer vorn
204 if (this.isSystem())
205 return -1;
206
207 Profile other = (Profile) o;
208 if (other.isSystem())
209 return 1;
210
211 if (this.getName() == null)
212 return -1;
213
214 // Rest alphabetisch
215 return this.getName().compareTo(other.getName());
216 }
217
218 /**
219 * @see java.lang.Object#toString()
220 */
221 @Override
222 public String toString()
223 {
224 return this.getName() + ", encoding: " + this.getFileEncoding() + ", separator: " + this.getSeparatorChar() + ", quoting char: " + this.getQuotingChar() + ", skip lines: " + this.getSkipLines();
225 }
171226 }
0 /**********************************************************************
1 *
2 * Copyright (c) 2018 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.io.csv;
11
12 import java.beans.ExceptionListener;
13 import java.beans.XMLDecoder;
14 import java.beans.XMLEncoder;
15 import java.io.BufferedInputStream;
16 import java.io.BufferedOutputStream;
17 import java.io.File;
18 import java.io.FileInputStream;
19 import java.io.FileOutputStream;
20 import java.util.ArrayList;
21 import java.util.Collections;
22 import java.util.List;
23
24 import org.apache.commons.lang.StringUtils;
25
26 import de.willuhn.jameica.hbci.HBCI;
27 import de.willuhn.jameica.hbci.gui.dialogs.CSVProfileStoreDialog;
28 import de.willuhn.jameica.messaging.StatusBarMessage;
29 import de.willuhn.jameica.system.Application;
30 import de.willuhn.jameica.system.OperationCanceledException;
31 import de.willuhn.logging.Logger;
32 import de.willuhn.util.I18N;
33
34 /**
35 * Hilfeklasse zum Laden und Speichern von CSV-Import-Profilen.
36 */
37 public class ProfileUtil
38 {
39 private final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
40
41 /**
42 * Laedt die vorhandenen Profile fuer das Format.
43 * @param format das Format.
44 * @return die Liste der Profile.
45 */
46 public static List<Profile> read(Format format)
47 {
48 List<Profile> result = new ArrayList<Profile>();
49
50 if (format == null)
51 {
52 Logger.warn("no format given");
53 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Kein Format ausgewählt"),StatusBarMessage.TYPE_ERROR));
54 return result;
55 }
56
57 final Profile dp = format.getDefaultProfile();
58 result.add(dp); // System-Profil wird immer vorn einsortiert
59
60 // 1. Mal schauen, ob wir gespeicherte Profil fuer das Format haben
61 File dir = new File(Application.getPluginLoader().getPlugin(HBCI.class).getResources().getWorkPath(),"csv");
62 if (!dir.exists())
63 return result;
64
65 File file = new File(dir,format.getClass().getName() + ".xml");
66 if (!file.exists() || !file.canRead())
67 return result;
68
69 Logger.info("reading csv profile " + file);
70 XMLDecoder decoder = null;
71 try
72 {
73 decoder = new XMLDecoder(new BufferedInputStream(new FileInputStream(file)));
74 decoder.setExceptionListener(new ExceptionListener()
75 {
76 public void exceptionThrown(Exception e)
77 {
78 throw new RuntimeException(e);
79 }
80 });
81
82
83 // Es ist tatsaechlich so, dass "readObject()" nicht etwa NULL liefert, wenn keine Objekte mehr in der
84 // Datei sind sondern eine ArrayIndexOutOfBoundsException wirft.
85 try
86 {
87 for (int i=0;i<1000;++i)
88 {
89 Profile p = (Profile) decoder.readObject();
90 // Migration aus der Zeit vor dem Support mulitpler Profile:
91 // Da konnte der User nur das eine existierende Profil aendern, es wurde automatisch gespeichert
92 // Das hatte gar keinen Namen. Falls also ein Profil ohne Name existiert (inzwischen koennen keine
93 // mehr ohne Name gespeichert werden), dann ist es das vom User geaenderte Profil. Das machen wir
94 // automatisch zum ersten User-spezifischen Profil
95 if (StringUtils.trimToNull(p.getName()) == null)
96 {
97 p.setName(dp.getName() + " 2");
98 p.setSystem(false);
99 }
100 result.add(p);
101 }
102 }
103 catch (ArrayIndexOutOfBoundsException e)
104 {
105 // EOF
106 }
107
108 Logger.info("read " + (result.size() - 1) + " profiles from " + file);
109 Collections.sort(result);
110
111 // Der User hat beim letzten Mal eventuell nicht alle Spalten zugeordnet.
112 // Die wuerden jetzt hier in dem Objekt fehlen. Daher nehmen wir
113 // noch die Spalten aus dem Default-Profil und haengen die fehlenden noch an.
114 }
115 catch (Exception e)
116 {
117 Logger.error("unable to read profile " + file,e);
118 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Laden der Profile fehlgeschlagen: {0}",e.getMessage()),StatusBarMessage.TYPE_ERROR));
119 }
120 finally
121 {
122 if (decoder != null)
123 {
124 try
125 {
126 decoder.close();
127 }
128 catch (Exception e) { /* useless */}
129 }
130 }
131 return result;
132 }
133
134 /**
135 * Speichert die Profile.
136 * @param format das Format.
137 * @param profiles die zu speichernden Profile.
138 */
139 public static void store(Format format, List<Profile> profiles)
140 {
141 if (format == null)
142 {
143 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Kein Format ausgewählt"),StatusBarMessage.TYPE_ERROR));
144 return;
145 }
146
147 if (profiles == null)
148 {
149 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Keine Profile angegeben"),StatusBarMessage.TYPE_ERROR));
150 return;
151 }
152
153 // 2. Mal schauen, ob wir ein gespeichertes Profil fuer das Format haben
154 File dir = new File(Application.getPluginLoader().getPlugin(HBCI.class).getResources().getWorkPath(),"csv");
155 if (!dir.exists())
156 {
157 Logger.info("creating dir: " + dir);
158 if (!dir.mkdirs())
159 {
160 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Ordner {0} kann nicht erstellt werden",dir.getAbsolutePath()),StatusBarMessage.TYPE_ERROR));
161 return;
162 }
163 }
164
165 File file = new File(dir,format.getClass().getName() + ".xml");
166
167 Logger.info("writing csv profile " + file);
168 XMLEncoder encoder = null;
169 try
170 {
171 encoder = new XMLEncoder(new BufferedOutputStream(new FileOutputStream(file)));
172 encoder.setExceptionListener(new ExceptionListener()
173 {
174 public void exceptionThrown(Exception e)
175 {
176 throw new RuntimeException(e);
177 }
178 });
179
180 for (Profile p:profiles)
181 {
182 // Das System-Profil wird nicht mit gespeichert
183 if (p.isSystem())
184 continue;
185
186 // Ebenso Profile ohne Namen.
187 if (StringUtils.trimToNull(p.getName()) == null)
188 continue;
189
190 encoder.writeObject(p);
191 }
192 }
193 catch (Exception e)
194 {
195 Logger.error("unable to store profile " + file,e);
196 }
197 finally
198 {
199 if (encoder != null) {
200 try {
201 encoder.close();
202 }
203 catch (Exception e) { /* useless */}
204 }
205 }
206 }
207
208 /**
209 * Fuegt ein neues Profil hinzu.
210 * @param format das Format.
211 * @param profile das zu speichernde Profil.
212 * @return das hinzugefuegte oder geaenderte Profil. NULL, wenn nicht gespeichert wurde.
213 */
214 public static Profile add(Format format, Profile profile)
215 {
216 try
217 {
218 if (profile == null || format == null)
219 {
220 Application.getCallback().notifyUser(i18n.tr("Kein Profil angegeben"));
221 return null;
222 }
223
224 // Der Dialog uebernimmt auch gleich das Speichern.
225 CSVProfileStoreDialog d = new CSVProfileStoreDialog(format,profile);
226 return (Profile) d.open();
227 }
228 catch (OperationCanceledException oce)
229 {
230 // ignore
231 }
232 catch (Exception e)
233 {
234 Logger.error("unable to delete profile",e);
235 }
236 return null;
237 }
238
239 /**
240 * Loescht das angegebene Profil.
241 * @param format das Format.
242 * @param profile das zu speichernde Profil.
243 * @return true, wenn das Profil geloescht wurde.
244 */
245 public static boolean delete(Format format, Profile profile)
246 {
247 if (profile == null || format == null)
248 return false;
249
250 try
251 {
252 if (profile.isSystem())
253 {
254 Application.getCallback().notifyUser(i18n.tr("Das Default-Profil darf nicht gelöscht werden"));
255 return false;
256 }
257
258 List<Profile> profiles = ProfileUtil.read(format);
259 boolean found = false;
260 for (Profile p:profiles)
261 {
262 if (p.isSystem())
263 continue;
264
265 if (p.getName().equals(profile.getName()))
266 {
267 profiles.remove(p);
268 found = true;
269 break;
270 }
271 }
272
273 // Nichts zum Loeschen gefunden
274 if (!found)
275 return false;
276
277 // Speichern
278 ProfileUtil.store(format,profiles);
279 return true;
280 }
281 catch (OperationCanceledException oce)
282 {
283 // ignore
284 }
285 catch (Exception e)
286 {
287 Logger.error("unable to delete profile",e);
288 }
289 return false;
290 }
291 }
292
293
4545 if (this.profile == null)
4646 {
4747 this.profile = new Profile();
48 this.profile.setName(i18n.tr("Default-Profil"));
4849 this.profile.setSkipLines(1);
49 this.profile.setVersion(0);
50 this.profile.setSystem(true);
5051
5152 Serializer ts = new DefaultSerializer();
5253 Serializer vs = new ValueSerializer();
8989 {
9090 control.handleChangeBankData();
9191 }
92 },null,false,"user-info.png");
92 },null,false,"system-user.png");
9393 buttonArea.addButton(i18n.tr("Speichern"),new Action()
9494 {
9595 public void handleAction(Object context) throws ApplicationException
3737 */
3838 public KontoList(DDVConfig config) throws RemoteException
3939 {
40 super(PseudoIterator.fromArray(new Konto[0]),new KontoNew());
40 super(null,new KontoNew());
41 this.setShowFilter(false);
4142 this.setCheckable(true);
4243 this.setSummary(false);
4344 this.myConfig = config;
134134 if (mech == null || !mech.useUSB())
135135 return; // brauchen wir gar nicht weiter ueberlegen
136136
137 // Checken, ob der User schon entschieden hatte, dass er chipTAN USB NICHT nutzen moechte
138 Boolean use = config != null ? config.isChipTANUSB() : null;
139 if (use != null && !use.booleanValue())
140 return; // User hat explizit entschieden, chipTAN USB NICHT zu nutzen
141
137142 // Versuchen, die Verbindung zum Kartenleser herzustellen
138143 try
139144 {
145 Logger.info("searching for smartcards, please wait...");
140146 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Legen Sie die bitte Chipkarte ein."),StatusBarMessage.TYPE_INFO));
141147 this.service = SmartCardService.createInstance(ChipTanCardService.class,this.config != null ? StringUtils.trimToNull(this.config.getCardReader()) : null);
142148
143149 // Wir haben grundsaetzlich einen Kartenleser.
144150 if (this.service != null && this.config != null)
145151 {
146 if (config.isChipTANUSBAsked())
152 Logger.info("found smartcard, to be used: " + (use != null ? use : "<asking user>"));
153
154 // User hat explizit entschieden, den Kartenleser per USB zu nutzen.
155 if (use != null && use.booleanValue())
147156 {
148157 this.usb = this.config.isChipTANUSB();
149 }
150 else
151 {
152 // User fragen, ob er ihn auch nutzen moechte, wenn wir das noch nicht getan haben
153 this.usb = Application.getCallback().askUser(i18n.tr("Es wurde ein USB-Kartenleser gefunden.\nMöchten Sie diesen zur Erzeugung der TAN verwenden?"),false);
154
155 // Das Speichern der Antwort koennen wir nicht Jameica selbst ueberlassen, weil
156 // die Entscheidung ja pro PIN/TAN-Config gelten soll und nicht global.
157 this.config.setChipTANUSBAsked(true);
158 this.config.setChipTANUSB(this.usb);
159 }
158 return;
159 }
160
161 // User fragen, ob er ihn auch nutzen moechte, wenn wir das noch nicht getan haben
162 // Das Speichern der Antwort koennen wir nicht Jameica selbst ueberlassen, weil
163 // die Entscheidung ja pro PIN/TAN-Config gelten soll und nicht global.
164 this.usb = Application.getCallback().askUser(i18n.tr("Es wurde ein USB-Kartenleser gefunden.\nMöchten Sie diesen zur Erzeugung der TAN verwenden?"),false);
165 this.config.setChipTANUSB(this.usb);
160166 }
161167 }
162168 catch (Throwable t)
1919
2020 import org.apache.commons.lang.StringUtils;
2121 import org.eclipse.swt.SWT;
22 import org.eclipse.swt.widgets.Button;
2223 import org.eclipse.swt.widgets.Event;
2324 import org.eclipse.swt.widgets.Listener;
2425 import org.kapott.hbci.passport.AbstractHBCIPassport;
279280 if (this.useUsb != null)
280281 return this.useUsb;
281282
282 this.useUsb = new CheckboxInput(this.getConfig().isChipTANUSB());
283 final Boolean b = this.getConfig().isChipTANUSB();
284 this.useUsb = new CheckboxInput(b == null || b.booleanValue());
283285 this.useUsb.setName(i18n.tr("Kartenleser per USB zur TAN-Erzeugung verwenden"));
284286
285287 final Listener l = new Listener() {
289291 {
290292 try
291293 {
292 Boolean b = (Boolean) getChipTANUSB().getValue();
293 getCardReaders().setEnabled(b != null && b.booleanValue());
294 Boolean newValue = (Boolean) getChipTANUSB().getValue();
295
296 if (event != null && event.type == SWT.Selection)
297 {
298 // Wir kamen aus dem Gray-State. Der User hat entschieden
299 org.eclipse.swt.widgets.Button bt = (org.eclipse.swt.widgets.Button) useUsb.getControl();
300 if (bt.getGrayed())
301 {
302 bt.setGrayed(false);
303 bt.setSelection(true);
304 newValue = Boolean.TRUE;
305 }
306 }
307
308 if (event != null)
309 getCardReaders().setEnabled(newValue != null && newValue.booleanValue());
310 else
311 getCardReaders().setEnabled(b != null && b.booleanValue());
294312
295313 // Bei chipTAN USB wird die TAN grundsaetzlich angezeigt
296 if (b != null && b.booleanValue() && (event == null || event.type == SWT.Selection))
314 if (newValue != null && newValue.booleanValue() && (event == null || event.type == SWT.Selection))
297315 {
298316 Boolean showTan = (Boolean) getShowTan().getValue();
299317 if (showTan == null || !showTan.booleanValue())
440458 conf.setCurrentSecMech(null);
441459 conf.setStoredSecMech(null);
442460 conf.setTanMedia(null);
443 conf.setChipTANUSBAsked(false);
461 conf.setChipTANUSB(null);
444462
445463 Application.getMessagingFactory().sendMessage(new StatusBarMessage(i18n.tr("Vorauswahl der TAN-Verfahren zurückgesetzt"),StatusBarMessage.TYPE_SUCCESS));
446464 }
587605 config.setShowTan(((Boolean)getShowTan().getValue()).booleanValue());
588606 config.setHBCIVersion(version);
589607 config.setPort((Integer)getPort().getValue());
590 config.setChipTANUSB(((Boolean)getChipTANUSB().getValue()).booleanValue());
591608 config.setCardReader((String) getCardReaders().getValue());
609
610 PtSecMech secMech = config.getCurrentSecMech();
611 if (secMech != null && secMech.useUSB())
612 {
613 CheckboxInput check = this.getChipTANUSB();
614 Button button = (Button)check.getControl();
615 if (button != null && !button.isDisposed())
616 {
617 boolean gray = button.getGrayed();
618 config.setChipTANUSB((Boolean) (gray ? null : check.getValue()));
619 }
620 }
621
592622
593623 AbstractHBCIPassport p = (AbstractHBCIPassport)config.getPassport();
594624 PassportChangeRequest change = new PassportChangeRequest(p,(String)getCustomerId().getValue(),(String)getUserId().getValue());
1111 import de.willuhn.jameica.gui.AbstractView;
1212 import de.willuhn.jameica.gui.Action;
1313 import de.willuhn.jameica.gui.GUI;
14 import de.willuhn.jameica.gui.input.CheckboxInput;
1415 import de.willuhn.jameica.gui.parts.Button;
1516 import de.willuhn.jameica.gui.parts.ButtonArea;
1617 import de.willuhn.jameica.gui.util.ColumnLayout;
6970 if (secMech != null && secMech.useUSB())
7071 {
7172 group.addHeadline(i18n.tr("ChipTAN USB"));
72 group.addInput(control.getChipTANUSB());
73
74 CheckboxInput check = control.getChipTANUSB();
75 group.addInput(check);
7376 group.addInput(control.getCardReaders());
77
78 // Wenn der User die Entscheidung noch nicht getroffen hat, dann ausgrauen
79 if (control.getConfig().isChipTANUSB() == null)
80 {
81 org.eclipse.swt.widgets.Button b = (org.eclipse.swt.widgets.Button) check.getControl();
82 b.setGrayed(true);
83 }
7484 }
7585 }
7686
3838 */
3939 public KontoList(PinTanConfig config) throws RemoteException
4040 {
41 super(PseudoIterator.fromArray(new Konto[0]),new KontoNew());
41 super(null,new KontoNew());
42 this.setShowFilter(false);
4243 this.setCheckable(true);
4344 this.setSummary(false);
4445 this.myConfig = config;
142142 }
143143
144144 /**
145 * Liefert true, wenn es ein Verfahren ist, das USB-tauglich ist.
146 * @return true, wenn es ein Verfahren ist, das USB-tauglich ist.
145 * Liefert true, wenn es ein Verfahren ist, das prinzipiell USB-tauglich ist.
146 * @return true, wenn es ein Verfahren ist, das prinzipiell USB-tauglich ist.
147147 */
148148 public boolean useUSB()
149149 {
154154 return s.contains("usb") ||
155155 s.contains("optic") ||
156156 s.contains("optisch") ||
157 s.contains("flicker") ||
157158 s.contains("komfort") ||
158159 s.contains("comfort");
159160 }
199199 public void setCurrentSecMech(PtSecMech mech) throws RemoteException;
200200
201201 /**
202 * Prueft, ob der User schonmal gefragt wurde, ob er chipTAN USB nutzen moechte.
203 * @return true, wenn der User schonmal gefragt wurde, ob er chipTAN USB nutzen moechte.
204 * @throws RemoteException
205 */
206 public boolean isChipTANUSBAsked() throws RemoteException;
207
208 /**
209 * Legt fest, ob der User schonmal gefragt wurde, ob er chipTAN USB nutzen moechte.
210 * @param b true, wenn der User gefragt wurde, ob er chipTAN USB nutzen moechte.
211 * @throws RemoteException
212 */
213 public void setChipTANUSBAsked(boolean b) throws RemoteException;
214
215 /**
216202 * Liefert true, wenn chipTAN USB verwendet werden soll.
217203 * @return true, wenn chipTAN USB verwendet werden soll.
218 * @throws RemoteException
219 */
220 public boolean isChipTANUSB() throws RemoteException;
204 * false, wenn es nicht verwendet werden soll.
205 * NULL, wenn der User die Entscheidung noch nicht getroffen hat.
206 * @throws RemoteException
207 */
208 public Boolean isChipTANUSB() throws RemoteException;
221209
222210 /**
223211 * Legt fest, ob chipTAN USB genutzt werden soll.
224212 * @param b true, wenn chipTAN USB genutzt werden soll.
225 * @throws RemoteException
226 */
227 public void setChipTANUSB(boolean b) throws RemoteException;
213 * false, wenn es nicht verwendet werden soll.
214 * NULL, wenn der User die Entscheidung noch nicht getroffen hat.
215 * @throws RemoteException
216 */
217 public void setChipTANUSB(Boolean b) throws RemoteException;
228218
229219 /**
230220 * Liefert eine optionale Bezeichnung fuer den zu nutzenden Karteleser.
443443 * @see de.willuhn.jameica.hbci.passports.pintan.rmi.PinTanConfig#isChipTANUSB()
444444 */
445445 @Override
446 public boolean isChipTANUSB() throws RemoteException
447 {
448 return settings.getBoolean(getID() + ".chiptan.usb.enabled",false);
449 }
450
451 /**
452 * @see de.willuhn.jameica.hbci.passports.pintan.rmi.PinTanConfig#isChipTANUSBAsked()
446 public Boolean isChipTANUSB() throws RemoteException
447 {
448 String s = StringUtils.trimToNull(settings.getString(getID() + ".chiptan.usb.enabled",null));
449 return s != null ? Boolean.valueOf(s) : null;
450 }
451
452 /**
453 * @see de.willuhn.jameica.hbci.passports.pintan.rmi.PinTanConfig#setChipTANUSB(java.lang.Boolean)
453454 */
454455 @Override
455 public boolean isChipTANUSBAsked() throws RemoteException
456 {
457 return settings.getBoolean(getID() + ".chiptan.usb.asked",false);
458 }
459
460 /**
461 * @see de.willuhn.jameica.hbci.passports.pintan.rmi.PinTanConfig#setChipTANUSB(boolean)
462 */
463 @Override
464 public void setChipTANUSB(boolean b) throws RemoteException
465 {
466 settings.setAttribute(getID() + ".chiptan.usb.enabled",b);
467 }
468
469 /**
470 * @see de.willuhn.jameica.hbci.passports.pintan.rmi.PinTanConfig#setChipTANUSBAsked(boolean)
471 */
472 @Override
473 public void setChipTANUSBAsked(boolean b) throws RemoteException
474 {
475 settings.setAttribute(getID() + ".chiptan.usb.asked",b);
476 }
477
456 public void setChipTANUSB(Boolean b) throws RemoteException
457 {
458 settings.setAttribute(getID() + ".chiptan.usb.enabled",(String) (b != null ? b.toString() : null));
459 }
460
478461 /**
479462 * @see de.willuhn.jameica.hbci.passports.pintan.rmi.PinTanConfig#getTanMedias()
480463 */
3838 */
3939 public KontoList(RDHKey key) throws RemoteException
4040 {
41 super(PseudoIterator.fromArray(new Konto[0]),new KontoNew());
41 super(null,new KontoNew());
42 this.setShowFilter(false);
4243 this.setCheckable(true);
4344 this.setSummary(false);
4445 this.myKey = key;
0 /**********************************************************************
1 *
2 * Copyright (c) 2004 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.rmi;
11
12 import java.util.Date;
13
14 import de.willuhn.datasource.GenericObject;
15
16 /**
17 * Interface fuer einen Zeitraum von Einnahmen und Ausgaben.
18 */
19 public interface EinnahmeAusgabeZeitraum extends GenericObject
20 {
21 /**
22 * Liefert das Start-Datum.
23 * @return das Start-Datum.
24 */
25 public Date getStartdatum();
26
27 /**
28 * Liefert das End-Datum.
29 * @return das End-Datum.
30 */
31 public Date getEnddatum();
32 }
185185 * @throws RemoteException
186186 */
187187 public boolean isAssigned() throws RemoteException;
188
189 /**
190 * Liefert eine optionale Transaktions-ID, anhand derer der Umsatz eindeutig identifiziert werden kann.
191 * Die ID ist nur bei Umsaetzen vorhanden, die per CAMT abgerufen wurden.
192 * Wichtig: Hibiscus garantiert NICHT, dass die ID eindeutig ist. Weder durch Programmlogik noch durch einen Unique-Key.
193 * Denn wuerde es das tun - und es wuerde tatsaechlich zu einer doppelten ID kommen, koennte der Umsatz
194 * nicht angelegt werden. Die ID ist lediglich ein zusaetzliches Kriterium bei der Doppler-Erkennung.
195 * @return optionale Transaktions-ID, anhand derer der Umsatz eindeutig identifiziert werden kann.
196 * @throws RemoteException
197 */
198 public String getTransactionId() throws RemoteException;
199
200 /**
201 * Speichert eine optionale Transaktions-ID, anhand derer der Umsatz eindeutig identifiziert werden kann.
202 * Wichtig: Hibiscus garantiert NICHT, dass die ID eindeutig ist. Weder durch Programmlogik noch durch einen Unique-Key.
203 * Denn wuerde es das tun - und es wuerde tatsaechlich zu einer doppelten ID kommen, koennte der Umsatz
204 * nicht angelegt werden. Die ID ist lediglich ein zusaetzliches Kriterium bei der Doppler-Erkennung.
205 * @param id die eindeutige Transaktions-ID.
206 * @throws RemoteException
207 */
208 public void setTransactionId(String id) throws RemoteException;
209
210 /**
211 * Liefert den Purpose-Code der Buchung.
212 * Nur bei Umsaetzen vorhanden, die per CAMT abgerufen wurden.
213 * @return der Purpose-Code der Buchung.
214 * @throws RemoteException
215 */
216 public String getPurposeCode() throws RemoteException;
217
218 /**
219 * Speichern den Purpose-Code der Buchung.
220 * @param code der Purpose-Code der Buchung.
221 * @throws RemoteException
222 */
223 public void setPurposeCode(String code) throws RemoteException;
224
225
226 /**
227 * Liefert die EndToEnd-ID der Buchung.
228 * Nur bei Umsaetzen vorhanden, die per CAMT abgerufen wurden.
229 * @return der EndToEnd-ID der Buchung.
230 * @throws RemoteException
231 */
232 public String getEndToEndId() throws RemoteException;
233
234 /**
235 * Speichern die EndToEnd-ID der Buchung.
236 * @param id die EndToEnd-ID der Buchung.
237 * @throws RemoteException
238 */
239 public void setEndToEndId(String id) throws RemoteException;
240
188241 }
189
190
191 /**********************************************************************
192 * $Log: Umsatz.java,v $
193 * Revision 1.27 2011/10/18 09:28:14 willuhn
194 * @N Gemeinsames Basis-Interface "HibiscusDBObject" fuer alle Entities (ausser Version und DBProperty) mit der Implementierung "AbstractHibiscusDBObject". Damit koennen jetzt zu jedem Fachobjekt beliebige Meta-Daten in der Datenbank gespeichert werden. Wird im ersten Schritt fuer die Reminder verwendet, um zu einem Auftrag die UUID des Reminders am Objekt speichern zu koennen
195 *
196 * Revision 1.26 2011-07-25 17:17:19 willuhn
197 * @N BUGZILLA 1065 - zusaetzlich noch addkey
198 *
199 * Revision 1.25 2011-07-25 14:42:41 willuhn
200 * @N BUGZILLA 1065
201 *
202 * Revision 1.24 2010/04/22 12:42:02 willuhn
203 * @N Erste Version des Supports fuer Offline-Konten
204 *
205 * Revision 1.23 2010/03/16 00:44:18 willuhn
206 * @N Komplettes Redesign des CSV-Imports.
207 * - Kann nun erheblich einfacher auch fuer andere Datentypen (z.Bsp.Ueberweisungen) verwendet werden
208 * - Fehlertoleranter
209 * - Mehrfachzuordnung von Spalten (z.Bsp. bei erweitertem Verwendungszweck) moeglich
210 * - modulare Deserialisierung der Werte
211 * - CSV-Exports von Hibiscus koennen nun 1:1 auch wieder importiert werden (Import-Preset identisch mit Export-Format)
212 * - Import-Preset wird nun im XML-Format nach ~/.jameica/hibiscus/csv serialisiert. Damit wird es kuenftig moeglich sein,
213 * CSV-Import-Profile vorzukonfigurieren und anschliessend zu exportieren, um sie mit anderen Usern teilen zu koennen
214 *
215 * Revision 1.22 2009/09/15 00:23:34 willuhn
216 * @N BUGZILLA 745
217 *
218 * Revision 1.21 2009/02/23 17:01:58 willuhn
219 * @C Kein Abgleichen mehr bei vorgemerkten Buchungen sondern stattdessen vorgemerkte loeschen und neu abrufen
220 *
221 * Revision 1.20 2009/02/12 18:37:18 willuhn
222 * @N Erster Code fuer vorgemerkte Umsaetze
223 *
224 * Revision 1.19 2009/02/12 16:14:34 willuhn
225 * @N HBCI4Java-Version mit Unterstuetzung fuer vorgemerkte Umsaetze
226 *
227 * Revision 1.18 2009/02/04 23:06:24 willuhn
228 * @N BUGZILLA 308 - Umsaetze als "geprueft" markieren
229 *
230 * Revision 1.17 2009/01/04 01:25:47 willuhn
231 * @N Checksumme von Umsaetzen wird nun generell beim Anlegen des Datensatzes gespeichert. Damit koennen Umsaetze nun problemlos geaendert werden, ohne mit "hasChangedByUser" checken zu muessen. Die Checksumme bleibt immer erhalten, weil sie in UmsatzImpl#insert() sofort zu Beginn angelegt wird
232 * @N Umsaetze sind nun vollstaendig editierbar
233 *
234 * Revision 1.16 2007/04/23 18:07:14 willuhn
235 * @C Redesign: "Adresse" nach "HibiscusAddress" umbenannt
236 * @C Redesign: "Transfer" nach "HibiscusTransfer" umbenannt
237 * @C Redesign: Neues Interface "Transfer", welches von Ueberweisungen, Lastschriften UND Umsaetzen implementiert wird
238 * @N Anbindung externer Adressbuecher
239 *
240 * Revision 1.15 2006/11/23 17:25:37 willuhn
241 * @N Umsatz-Kategorien - in PROGRESS!
242 *
243 * Revision 1.14 2006/08/21 23:15:01 willuhn
244 * @N Bug 184 (CSV-Import)
245 *
246 * Revision 1.13 2005/12/29 01:22:12 willuhn
247 * @R UmsatzZuordnung entfernt
248 * @B Debugging am Pie-Chart
249 *
250 * Revision 1.12 2005/12/05 20:16:15 willuhn
251 * @N Umsatz-Filter Refactoring
252 *
253 * Revision 1.11 2005/11/14 23:47:21 willuhn
254 * @N added first code for umsatz categories
255 *
256 * Revision 1.10 2005/06/30 21:48:56 web0
257 * @B bug 75
258 *
259 * Revision 1.9 2005/06/13 23:11:01 web0
260 * *** empty log message ***
261 *
262 * Revision 1.8 2005/02/27 17:11:49 web0
263 * @N first code for "Sammellastschrift"
264 * @C "Empfaenger" renamed into "Adresse"
265 *
266 * Revision 1.7 2004/10/23 17:34:31 willuhn
267 * *** empty log message ***
268 *
269 * Revision 1.6 2004/10/17 16:28:46 willuhn
270 * @N Die ersten Dauerauftraege abgerufen ;)
271 *
272 * Revision 1.5 2004/05/25 23:23:17 willuhn
273 * @N UeberweisungTyp
274 * @N Protokoll
275 *
276 * Revision 1.4 2004/04/27 22:23:56 willuhn
277 * @N configurierbarer CTAPI-Treiber
278 * @C konkrete Passport-Klassen (DDV) nach de.willuhn.jameica.passports verschoben
279 * @N verschiedenste Passport-Typen sind jetzt voellig frei erweiterbar (auch die Config-Dialoge)
280 * @N crc32 Checksumme in Umsatz
281 * @N neue Felder im Umsatz
282 *
283 * Revision 1.3 2004/03/06 18:25:10 willuhn
284 * @D javadoc
285 * @C removed empfaenger_id from umsatz
286 *
287 * Revision 1.2 2004/03/05 00:04:10 willuhn
288 * @N added code for umsatzlist
289 *
290 * Revision 1.1 2004/02/27 01:10:18 willuhn
291 * @N passport config refactored
292 *
293 **********************************************************************/
8383
8484 if (StringUtils.trimToNull(getGegenkontoName()) == null)
8585 throw new ApplicationException(i18n.tr("Bitte geben Sie den Namen des Kontoinhabers des Gegenkontos ein"));
86 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
86 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
8787 HBCIProperties.checkChars(getGegenkontoName(), HBCIProperties.HBCI_SEPA_VALIDCHARS);
8888
8989
90 HBCIProperties.checkLength(getZweck(), HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
90 HBCIProperties.checkLength(getZweck(), HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
9191 HBCIProperties.checkChars(getZweck(), HBCIProperties.HBCI_SEPA_VALIDCHARS);
9292
9393 HBCIProperties.checkLength(getEndtoEndId(), HBCIProperties.HBCI_SEPA_ENDTOENDID_MAXLENGTH);
0 /**********************************************************************
1 *
2 * Copyright (c) 2018 Olaf Willuhn
3 * All rights reserved.
4 *
5 * This software is copyrighted work licensed under the terms of the
6 * Jameica License. Please consult the file "LICENSE" for details.
7 *
8 **********************************************************************/
9
10 package de.willuhn.jameica.hbci.server;
11
12 import java.io.StringReader;
13 import java.util.List;
14
15 import de.willuhn.jameica.hbci.rmi.DBSupport;
16 import de.willuhn.jameica.hbci.rmi.HBCIDBService;
17 import de.willuhn.jameica.system.Application;
18 import de.willuhn.logging.Logger;
19 import de.willuhn.sql.ScriptExecutor;
20 import de.willuhn.sql.version.Update;
21 import de.willuhn.sql.version.UpdateProvider;
22 import de.willuhn.util.ApplicationException;
23 import de.willuhn.util.I18N;
24
25 /**
26 * Abstrakte Basis-Klasse fuer Datenbank-Updates.
27 */
28 public abstract class AbstractUpdate implements Update
29 {
30 /**
31 * @see de.willuhn.sql.version.Update#execute(de.willuhn.sql.version.UpdateProvider)
32 */
33 public void execute(UpdateProvider provider) throws ApplicationException
34 {
35 HBCIUpdateProvider myProvider = (HBCIUpdateProvider) provider;
36 I18N i18n = myProvider.getResources().getI18N();
37
38 try
39 {
40 String driver = HBCIDBService.SETTINGS.getString("database.driver",DBSupportH2Impl.class.getName());
41 Class<? extends DBSupport> driverClass = Application.getClassLoader().load(driver);
42
43 List<String> sql = this.getStatements(driverClass);
44 if (sql == null)
45 throw new ApplicationException(i18n.tr("Datenbank {0} nicht wird unterstützt",driver));
46
47 if (sql.size() == 0)
48 {
49 myProvider.getProgressMonitor().log(i18n.tr("Update übersprungen, nicht notwendig"));
50 return;
51 }
52
53 // Wir packen alle Zeilen in einen String, damit es in einer gemeinsamen Transaktion ausgefuehrt wird.
54 StringBuilder sb = new StringBuilder();
55 for (String s:sql)
56 {
57 sb.append(s);
58 sb.append("\n");
59 }
60
61 ScriptExecutor.execute(new StringReader(sb.toString()),myProvider.getConnection(),myProvider.getProgressMonitor());
62 myProvider.getProgressMonitor().log(i18n.tr("Tabelle aktualisiert"));
63 }
64 catch (ApplicationException ae)
65 {
66 throw ae;
67 }
68 catch (Exception e)
69 {
70 Logger.error("unable to execute update",e);
71 throw new ApplicationException(i18n.tr("Fehler beim Ausführen des Updates"),e);
72 }
73 }
74
75 /**
76 * Liefert die auszufuehrenden Datenbank-Updates fuer den jeweiligen Treiber.
77 * @param driverClass die Klasse des Treibers.
78 * @return die Statements.
79 */
80 protected abstract List<String> getStatements(Class<? extends DBSupport> driverClass);
81
82 /**
83 * @see de.willuhn.sql.version.Update#getName()
84 */
85 public String getName()
86 {
87 return "database update " + this.getClass().getSimpleName();
88 }
89 }
113113
114114 if (StringUtils.trimToNull(getGegenkontoName()) == null)
115115 throw new ApplicationException(i18n.tr("Bitte geben Sie den Namen des Kontoinhabers des Gegenkontos ein"));
116 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
116 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
117117 HBCIProperties.checkChars(getGegenkontoName(), HBCIProperties.HBCI_SEPA_VALIDCHARS);
118118
119 HBCIProperties.checkLength(getZweck(), HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
119 HBCIProperties.checkLength(getZweck(), HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
120120 HBCIProperties.checkChars(getZweck(), HBCIProperties.HBCI_SEPA_VALIDCHARS);
121121
122122 HBCIProperties.checkLength(getEndtoEndId(), HBCIProperties.HBCI_SEPA_ENDTOENDID_MAXLENGTH);
6565 */
6666 KontoauszugPdf("KontoauszugPdf","HKEKP"),
6767
68 /**
69 * Query fuer Abruf der Umsaetze im CAMT-Format.
70 */
71 UmsatzCamt("KUmsZeitCamt","HKCAZ")
72
6873 ;
6974
7075 private String query = null;
364369 * Aktualisiert den Cache fuer den Passport.
365370 * @param passport der Passport.
366371 * @param prefix der Prefix.
367 */
368 public static void updateCache(HBCIPassport passport, Prefix prefix)
372 * @return true, wenn der Cache aktualisiert wurde.
373 */
374 public static boolean updateCache(HBCIPassport passport, Prefix prefix)
369375 {
370376 if (passport == null)
371 return;
377 return false;
372378
373379 try
374380 {
379385 if (version == null || version.length() == 0 || user == null || user.length() == 0 || data == null || data.size() == 0)
380386 {
381387 Logger.debug("[" + prefix + "] no version, no userid or no data found, skipping update");
382 return;
388 return false;
383389 }
384390
385391 // Wir machen das Update nicht jedesmal sondern periodisch. Denn unter
432438
433439 Logger.info(prefix + " cache update state [expired: " + expired + ", new version: " + newVersion + "]");
434440 if (!expired && !newVersion)
435 return;
441 return false;
436442
437443 BeanService service = Application.getBootLoader().getBootable(BeanService.class);
438444 SynchronizeSession session = service.get(HBCISynchronizeBackend.class).getCurrentSession();
450456 {
451457 int deleted = DBPropertyUtil.deleteScope(prefix,customerId);
452458 Logger.info("deleted " + deleted + " old " + prefix.name() + " cache entries");
459
460 int count2 = 0;
453461
454462 for (Enumeration keys = data.keys();keys.hasMoreElements();)
455463 {
456464 String name = (String) keys.nextElement();
457465 if (DBPropertyUtil.insert(prefix,customerId,null,name,data.getProperty(name)))
466 {
458467 count++;
468 count2++;
469 if (count2 > 0 && count2 % 50 == 0)
470 {
471 Logger.info("stored " + count2 + " " + prefix.name() + " entries");
472
473 if (monitor != null)
474 monitor.log(i18n.tr(" {0} {1}-Parameter aktualisiert",Integer.toString(count),prefix.name()));
475 }
476 }
459477
460 if (count > 0 && count % 20 == 0 && monitor != null)
461 monitor.log(" " + i18n.tr("{0} Datensätze",Integer.toString(count)));
462478 }
463479 }
464480 Logger.info("created " + count + " new " + prefix.name() + " cache entries");
468484
469485 // Datum des letzten Abrufs speichern
470486 DBPropertyUtil.set(prefix,user,null,"cacheupdate",Long.toString(now));
487 return true;
471488 }
472489 catch (Exception e)
473490 {
474491 Logger.error("error while updating " + prefix + " - will be ignored",e);
492 return false;
475493 }
476494 }
477495
479497 * Markiert den Cache als expired.
480498 * @param passport der Passport.
481499 * @param prefix der Prefix.
482 * @throws RemoteException
483 */
484 public static void expireCache(HBCIPassport passport, Prefix prefix) throws RemoteException
500 */
501 public static void expireCache(HBCIPassport passport, Prefix prefix)
485502 {
486503 final String user = passport.getUserId();
487504 if (user == null || user.length() == 0)
489506 Logger.debug("[" + prefix + "] no userid found, skipping cache expiry");
490507 return;
491508 }
492
493 Logger.info("expire " + prefix.name() + " cache");
494 DBPropertyUtil.set(prefix,user,null,"cacheupdate","0");
495 }
496
509
510 try
511 {
512 Logger.info("expire " + prefix.name() + " cache");
513 DBPropertyUtil.set(prefix,user,null,"cacheupdate","0");
514 }
515 catch (Exception e)
516 {
517 Logger.error("error while expiring " + prefix + " cache",e);
518 }
519 }
497520 }
88 **********************************************************************/
99 package de.willuhn.jameica.hbci.server;
1010
11 import java.math.BigDecimal;
1112 import java.rmi.RemoteException;
13 import java.util.Arrays;
1214 import java.util.Map;
1315
1416 import org.apache.commons.lang.StringUtils;
1517 import org.kapott.hbci.GV_Result.GVRDauerList;
1618 import org.kapott.hbci.GV_Result.GVRKUms;
19 import org.kapott.hbci.GV_Result.GVRKUms.UmsLine;
1720 import org.kapott.hbci.GV_Result.GVRKontoauszug.Format;
1821 import org.kapott.hbci.GV_Result.GVRKontoauszug.GVRKontoauszugEntry;
1922 import org.kapott.hbci.structures.Konto;
2023 import org.kapott.hbci.structures.Saldo;
2124 import org.kapott.hbci.structures.Value;
22 import org.kapott.hbci.swift.DTAUS;
2325
2426 import de.jost_net.OBanToo.SEPA.IBAN;
2527 import de.willuhn.datasource.rmi.DBIterator;
2830 import de.willuhn.jameica.hbci.rmi.Address;
2931 import de.willuhn.jameica.hbci.rmi.HibiscusAddress;
3032 import de.willuhn.jameica.hbci.rmi.Kontoauszug;
31 import de.willuhn.jameica.hbci.rmi.SammelLastschrift;
32 import de.willuhn.jameica.hbci.rmi.SammelTransfer;
33 import de.willuhn.jameica.hbci.rmi.SammelTransferBuchung;
34 import de.willuhn.jameica.hbci.rmi.SammelUeberweisung;
3533 import de.willuhn.jameica.hbci.rmi.SepaDauerauftrag;
3634 import de.willuhn.jameica.hbci.rmi.Umsatz;
3735 import de.willuhn.jameica.hbci.server.VerwendungszweckUtil.Tag;
4442 */
4543 public class Converter
4644 {
45 private final static double KURS_EUR = 1.95583;
4746
4847 /**
4948 * Konvertiert einen einzelnen Umsatz von HBCI4Java nach Hibiscus.
6160 umsatz.setArt(clean(u.text));
6261 umsatz.setCustomerRef(clean(u.customerref));
6362 umsatz.setPrimanota(clean(u.primanota));
64
65 double kurs = 1.95583;
63 umsatz.setTransactionId(u.id);
64 umsatz.setPurposeCode(u.purposecode);
65 umsatz.setEndToEndId(u.endToEndId);
6666
6767 //BUGZILLA 67 http://www.willuhn.de/bugzilla/show_bug.cgi?id=67
6868 Saldo s = u.saldo;
7575 double saldo = v.getDoubleValue();
7676 String curr = v.getCurr();
7777 if (curr != null && "DEM".equals(curr))
78 saldo /= kurs;
78 saldo /= KURS_EUR;
7979 umsatz.setSaldo(saldo);
8080 }
8181 }
8686
8787 // BUGZILLA 318
8888 if (curr != null && "DEM".equals(curr))
89 betrag /= kurs;
89 betrag /= KURS_EUR;
9090
9191 umsatz.setBetrag(betrag);
9292 umsatz.setDatum(u.bdate);
114114
115115 String[] lines = (String[]) u.usage.toArray(new String[u.usage.size()]);
116116
117 // die Bank liefert keine strukturierten Verwendungszwecke (gvcode=999).
118 // Daher verwenden wir den gesamten "additional"-Block und zerlegen ihn
119 // in 27-Zeichen lange Haeppchen
120 if (lines.length == 0)
121 lines = VerwendungszweckUtil.parse(u.additional);
122
123 // Es gibt eine erste Bank, die 40 Zeichen lange Verwendungszwecke lieferte.
124 // Siehe Mail von Frank vom 06.02.2014
125 lines = VerwendungszweckUtil.rewrap(HBCIProperties.HBCI_TRANSFER_USAGE_DB_MAXLENGTH,lines);
126 VerwendungszweckUtil.apply(umsatz,lines);
117 // Wenn es ein CAMT-Umsatz ist, koennen wir einfach die erste Zeile pauschal
118 // uebernehmen. Da gibt es ohnehin nur noch diese eine Zeile
119 if (u.isCamt)
120 {
121 if (lines.length > 0)
122 umsatz.setZweck(lines[0]);
123 }
124 else
125 {
126 // die Bank liefert keine strukturierten Verwendungszwecke (gvcode=999).
127 // Daher verwenden wir den gesamten "additional"-Block und zerlegen ihn
128 // in 27-Zeichen lange Haeppchen
129 if (lines.length == 0)
130 lines = VerwendungszweckUtil.parse(u.additional);
131
132 // Es gibt eine erste Bank, die 40 Zeichen lange Verwendungszwecke lieferte.
133 // Siehe Mail von Frank vom 06.02.2014
134 lines = VerwendungszweckUtil.rewrap(HBCIProperties.HBCI_TRANSFER_USAGE_DB_MAXLENGTH,lines);
135 VerwendungszweckUtil.apply(umsatz,lines);
136
137 // Wir checken mal, ob wir eine EndToEnd-ID haben. Falls ja, tragen wir die gleich
138 // in das dedizierte Feld ein
139 final String eref = clean(VerwendungszweckUtil.getTag(umsatz,Tag.EREF));
140 if (eref != null && eref.length() > 0)
141 umsatz.setEndToEndId(eref);
142 }
127143 //
128144 ////////////////////////////////////////////////////////////////////////////
129145
198214 }
199215
200216 /**
217 * Konvertiert einen einzelnen Umsatz von Hibiscus nach HBCI4Java.
218 * @param u der zu convertierende Umsatz.
219 * @return das neu erzeugte Umsatz-Objekt.
220 * @throws RemoteException
221 */
222 public static UmsLine HibiscusUmsatz2HBCIUmsatz(Umsatz u) throws RemoteException
223 {
224 final UmsLine line = new UmsLine();
225
226 final de.willuhn.jameica.hbci.rmi.Konto k = u.getKonto();
227
228 final String iban = u.getGegenkontoNummer();
229 final String bic = u.getGegenkontoBLZ();
230 final boolean isSepa = iban != null && iban.length() > HBCIProperties.HBCI_KTO_MAXLENGTH_HARD;
231 final Konto other = new Konto();
232 other.name = u.getGegenkontoName();
233 if (isSepa)
234 {
235 other.iban = iban;
236 other.bic = bic;
237 }
238 else
239 {
240 other.number = iban;
241 other.blz = bic;
242 }
243
244 line.addkey = u.getAddKey();
245 line.bdate = u.getDatum();
246 line.customerref = u.getCustomerRef();
247 line.gvcode = u.getGvCode();
248 line.id = u.getTransactionId();
249 line.isCamt = line.id != null && line.id.length() > 0;
250 line.isSepa = isSepa;
251 line.isStorno = false;
252 line.other = other;
253 line.primanota = u.getPrimanota();
254 line.purposecode = u.getPurposeCode();
255 line.saldo = new Saldo();
256 line.saldo.timestamp = u.getDatum();
257 line.saldo.value = new Value(new BigDecimal(u.getSaldo()),k.getWaehrung());
258 line.text = u.getArt();
259 line.usage = Arrays.asList(VerwendungszweckUtil.toArray(u));
260 line.value = new Value(new BigDecimal(u.getBetrag()),k.getWaehrung());
261 line.valuta = u.getValuta();
262
263 return line;
264 }
265
266 /**
201267 * Entfernt Zeichen, die in den Strings nicht enthalten sein sollten.
202268 * Typischerweise Zeilenumbrueche.
203269 * @param s der String.
435501 return e;
436502 }
437503
438 /**
439 * Konvertiert eine Sammel-Ueberweisung in DTAUS-Format.
440 * @param su Sammel-Ueberweisung.
441 * @return DTAUS-Repraesentation.
442 * @throws RemoteException
443 */
444 public static DTAUS HibiscusSammelUeberweisung2DTAUS(SammelUeberweisung su) throws RemoteException
445 {
446 // TYPE_CREDIT = Sammelüberweisung
447 // TYPE_DEBIT = Sammellastschrift
448 return HibiscusSammelTransfer2DTAUS(su, DTAUS.TYPE_CREDIT);
449 }
450
451 /**
452 * Konvertiert eine Sammel-Lastschrift in DTAUS-Format.
453 * @param sl Sammel-Lastschrift.
454 * @return DTAUS-Repraesentation.
455 * @throws RemoteException
456 */
457 public static DTAUS HibiscusSammelLastschrift2DTAUS(SammelLastschrift sl) throws RemoteException
458 {
459 // TYPE_CREDIT = Sammelüberweisung
460 // TYPE_DEBIT = Sammellastschrift
461 return HibiscusSammelTransfer2DTAUS(sl, DTAUS.TYPE_DEBIT);
462 }
463
464 /**
465 * Hilfsfunktion. Ist private, damit niemand aus Versehen den falschen Type angibt.
466 * @param s Sammel-Transfer.
467 * @param type Art des Transfers.
468 * @see DTAUS#TYPE_CREDIT
469 * @see DTAUS#TYPE_DEBIT
470 * @return DTAUS-Repraesentation.
471 * @throws RemoteException
472 */
473 private static DTAUS HibiscusSammelTransfer2DTAUS(SammelTransfer s, int type) throws RemoteException
474 {
475
476 DTAUS dtaus = new DTAUS(HibiscusKonto2HBCIKonto(s.getKonto()),type);
477 DBIterator buchungen = s.getBuchungen();
478 SammelTransferBuchung b = null;
479 while (buchungen.hasNext())
480 {
481 b = (SammelTransferBuchung) buchungen.next();
482 final DTAUS.Transaction tr = dtaus.new Transaction();
483
484 Konto other = new Konto("DE",b.getGegenkontoBLZ(),b.getGegenkontoNummer());
485 other.name = b.getGegenkontoName();
486
487 tr.otherAccount = other;
488 tr.value = new Value(String.valueOf(b.getBetrag()));
489
490 String key = b.getTextSchluessel();
491 if (key != null && key.length() > 0)
492 tr.key = key; // Nur setzen, wenn in der Buchung definiert. Gibt sonst in DTAUS#toString eine NPE
493
494 String[] lines = VerwendungszweckUtil.toArray(b);
495 for (String line:lines)
496 {
497 tr.addUsage(line);
498 }
499
500 dtaus.addEntry(tr);
501 }
502 return dtaus;
503 }
504
505504 }
4040 /**
4141 * Prefix fuer BPDs.
4242 */
43 BPD("bpd",new HashSet(Arrays.asList("DauerSEPAEditPar","KontoauszugPar","KontoauszugPdfPar"))),
43 BPD("bpd",new HashSet(Arrays.asList("DauerSEPAEditPar","KontoauszugPar","KontoauszugPdfPar","KUmsZeitCamtPar"))),
4444
4545 /**
4646 * Prefix fuer UPDs.
1313 import java.rmi.RemoteException;
1414 import java.util.Date;
1515
16 import de.willuhn.datasource.BeanUtil;
17 import de.willuhn.datasource.GenericObject;
18 import de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum;
1619 import de.willuhn.jameica.hbci.rmi.Konto;
1720
1821 /**
1922 * Container fuer die EinnahmeAusgabe-Daten.
2023 */
21
22 public class EinnahmeAusgabe
24 public class EinnahmeAusgabe implements EinnahmeAusgabeZeitraum
2325 {
2426 private String text;
2527 private double anfangssaldo;
149151 }
150152
151153 /**
152 * Liefert das Start-Datum.
153 * @return das Start-Datum.
154 * @see de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum#getStartdatum()
154155 */
155156 public Date getStartdatum()
156157 {
167168 }
168169
169170 /**
170 * Liefert das End-Datum.
171 * @return das End-Datum.
171 * @see de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum#getEnddatum()
172172 */
173173 public Date getEnddatum()
174174 {
201201 */
202202 public boolean hasDiff()
203203 {
204 return Math.abs(this.getDifferenz()) >= 0.01;
204 return Math.abs(this.getDifferenz()) >= 0.01d;
205205 }
206206
207207 /**
230230 {
231231 this.isSumme = b;
232232 }
233
234 /**
235 * @see de.willuhn.datasource.GenericObject#equals(de.willuhn.datasource.GenericObject)
236 */
237 @Override
238 public boolean equals(GenericObject arg0) throws RemoteException
239 {
240 return arg0 == this;
241 }
242
243 /**
244 * @see de.willuhn.datasource.GenericObject#getAttribute(java.lang.String)
245 */
246 @Override
247 public Object getAttribute(String arg0) throws RemoteException
248 {
249 try
250 {
251 // Wir koennen hier nicht direkt "BeanUtil.get(this,arg0)" aufrufen,
252 // da EinnahmeAusgabe selbst ja ein GenericObject ist und "BeanUtil.get()"
253 // in dem Fall intern wieder "this.getAttribute(arg0)" aufrufen wuerde.
254 // Das gaebe eine Endlos-Rekursion.
255 return BeanUtil.invoke(this,BeanUtil.toGetMethod(arg0),null);
256 }
257 catch (RemoteException re)
258 {
259 throw re;
260 }
261 catch (Exception e)
262 {
263 throw new RemoteException("unable to get value for attribute " + arg0,e);
264 }
265 }
266
267 /**
268 * @see de.willuhn.datasource.GenericObject#getAttributeNames()
269 */
270 @Override
271 public String[] getAttributeNames() throws RemoteException
272 {
273 return new String[] {
274 "text",
275 "anfangssaldo",
276 "einnahmen",
277 "ausgaben",
278 "endsaldo",
279 "startdatum",
280 "enddatum"
281 };
282
283 }
284
285 /**
286 * @see de.willuhn.datasource.GenericObject#getID()
287 */
288 @Override
289 public String getID() throws RemoteException
290 {
291 return null;
292 }
293
294 /**
295 * @see de.willuhn.datasource.GenericObject#getPrimaryAttribute()
296 */
297 @Override
298 public String getPrimaryAttribute() throws RemoteException
299 {
300 return "text";
301 }
302
303 /**
304 * @see java.lang.Object#toString()
305 */
306 @Override
307 public String toString()
308 {
309 return this.text + ":" +
310 this.anfangssaldo + ":" +
311 this.einnahmen + ":" +
312 this.ausgaben + ":" +
313 this.endsaldo + ":" +
314 this.getPlusminus() + ":" +
315 this.getDifferenz();
316 }
233317 }
234
235 /*******************************************************************************
236 * $Log: EinnahmeAusgabe.java,v $
237 * Revision 1.1 2010/08/24 17:38:04 willuhn
238 * @N BUGZILLA 896
239 *
240 * Revision 1.5 2010/06/07 22:41:13 willuhn
241 * @N BUGZILLA 844/852
242 *
243 * Revision 1.4 2010/04/06 22:49:54 willuhn
244 * @B BUGZILLA 844
245 *
246 * Revision 1.3 2010/02/17 10:43:41 willuhn
247 * @N Differenz in Einnahmen/Ausgaben anzeigen, Cleanup
248 ******************************************************************************/
0 package de.willuhn.jameica.hbci.server;
1
2 import java.rmi.RemoteException;
3 import java.util.Date;
4 import java.util.List;
5
6 import de.willuhn.datasource.GenericIterator;
7 import de.willuhn.datasource.GenericObject;
8 import de.willuhn.datasource.GenericObjectNode;
9 import de.willuhn.datasource.pseudo.PseudoIterator;
10 import de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum;
11 import de.willuhn.jameica.util.DateUtil;
12
13 /**
14 * Container für die EinnahmenAusgaben-Liste eines bestimmten Zeitraums.
15 */
16 public class EinnahmeAusgabeTreeNode implements EinnahmeAusgabeZeitraum, GenericObjectNode
17 {
18
19 private Date startdatum;
20 private Date enddatum;
21 private List<EinnahmeAusgabe> children;
22
23 /**
24 * @param from Startdatum des Zeitraums
25 * @param to Enddatum des Zeitraums
26 * @param children Liste der EinnameAusgabe-Daten für diesen Zeitraum
27 */
28 public EinnahmeAusgabeTreeNode(Date from, Date to, List<EinnahmeAusgabe> children)
29 {
30 this.startdatum = from;
31 this.enddatum = to;
32 this.children = children;
33 }
34
35 /**
36 * @see de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum#getStartdatum()
37 */
38 @Override
39 public Date getStartdatum()
40 {
41 return this.startdatum;
42 }
43
44 /**
45 * @see de.willuhn.jameica.hbci.rmi.EinnahmeAusgabeZeitraum#getEnddatum()
46 */
47 @Override
48 public Date getEnddatum()
49 {
50 return this.enddatum;
51 }
52
53 /**
54 * @see de.willuhn.datasource.GenericObject#equals(de.willuhn.datasource.GenericObject)
55 */
56 @Override
57 public boolean equals(GenericObject arg0) throws RemoteException
58 {
59 return this == arg0;
60 }
61
62 /**
63 * @see de.willuhn.datasource.GenericObject#getAttribute(java.lang.String)
64 */
65 @Override
66 public Object getAttribute(String arg0) throws RemoteException
67 {
68 if("text".equals(arg0))
69 return DateUtil.DEFAULT_FORMAT.format(this.startdatum) + " - " + DateUtil.DEFAULT_FORMAT.format(this.enddatum);
70
71 if ("startdatum".equals(arg0))
72 return this.startdatum;
73
74 if ("enddatum".equals(arg0))
75 return this.enddatum;
76
77 if ("children".equals(arg0))
78 return this.children;
79
80 return null;
81 }
82
83 /**
84 * @see de.willuhn.datasource.GenericObject#getAttributeNames()
85 */
86 @Override
87 public String[] getAttributeNames() throws RemoteException
88 {
89 return new String[]{"text","startdatum","enddatum","children"};
90 }
91
92 /**
93 * @see de.willuhn.datasource.GenericObject#getID()
94 */
95 @Override
96 public String getID() throws RemoteException
97 {
98 return null;
99 }
100
101 /**
102 * @see de.willuhn.datasource.GenericObject#getPrimaryAttribute()
103 */
104 @Override
105 public String getPrimaryAttribute() throws RemoteException
106 {
107 return "text";
108 }
109
110 /**
111 * @see de.willuhn.datasource.GenericObjectNode#getChildren()
112 */
113 @Override
114 public GenericIterator getChildren() throws RemoteException
115 {
116 return PseudoIterator.fromArray((EinnahmeAusgabe[]) children.toArray(new EinnahmeAusgabe[children.size()]));
117 }
118
119 /**
120 * @see de.willuhn.datasource.GenericObjectNode#getParent()
121 */
122 @Override
123 public GenericObjectNode getParent() throws RemoteException
124 {
125 return null;
126 }
127
128 /**
129 * @see de.willuhn.datasource.GenericObjectNode#getPath()
130 */
131 @Override
132 public GenericIterator getPath() throws RemoteException
133 {
134 throw new UnsupportedOperationException();
135 }
136
137 /**
138 * @see de.willuhn.datasource.GenericObjectNode#getPossibleParents()
139 */
140 @Override
141 public GenericIterator getPossibleParents() throws RemoteException
142 {
143 throw new UnsupportedOperationException();
144 }
145
146 /**
147 * @see de.willuhn.datasource.GenericObjectNode#hasChild(de.willuhn.datasource.GenericObjectNode)
148 */
149 @Override
150 public boolean hasChild(GenericObjectNode arg0) throws RemoteException
151 {
152 if (!(arg0 instanceof EinnahmeAusgabe))
153 return false;
154
155 return this.children.contains((EinnahmeAusgabe)arg0);
156 }
157 }
162162 }
163163 }
164164
165 Logger.info("init update provider");
166 UpdateProvider provider = new HBCIUpdateProvider(getConnection(),version);
167 Updater updater = new Updater(provider,"iso-8859-1");
168 updater.execute();
169 Logger.info("updates finished");
165 try
166 {
167 Logger.info("init update provider");
168 UpdateProvider provider = new HBCIUpdateProvider(getConnection(),version);
169 Updater updater = new Updater(provider,"iso-8859-1");
170 updater.execute();
171 Logger.info("updates finished");
172 }
173 catch (Exception e)
174 {
175 // Wir versuchen herauszufinden, ob es dieses Problem hier ist:
176 // https://homebanking-hilfe.de/forum/topic.php?p=139423#real139423
177 // Siehe auch https://www.h2database.com/javadoc/org/h2/api/ErrorCode.html#c90131
178 Throwable t = e;
179
180 for (int i=0;i<10;++i)
181 {
182 if (t == null)
183 break;
184
185 if (t instanceof SQLException)
186 {
187 SQLException se = (SQLException) t;
188 int code = se.getErrorCode();
189 if (code == 90131)
190 {
191 Logger.error("found buggy h2 driver, update jameica first",e);
192
193 I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
194 throw new ApplicationException(i18n.tr("Bitte aktualisiere erst Jameica auf Version 2.8.2 oder höher"));
195 }
196 }
197 t = t.getCause();
198 }
199
200 // Keine passende Exception gefunden. Dann Original weiterwerfen.
201 throw new ApplicationException(e);
202 }
170203 }
171204
172205
106106 }
107107 if (bank != null && bank.length() > 0)
108108 {
109 HBCIProperties.checkLength(bank, HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
109 HBCIProperties.checkLength(bank, HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
110110 }
111111 //
112112 //////////////////////////////////////////////////////////////////////////
2121 import de.willuhn.datasource.rmi.DBIterator;
2222 import de.willuhn.datasource.rmi.DBService;
2323 import de.willuhn.datasource.rmi.ResultSetExtractor;
24 import de.willuhn.jameica.hbci.MetaKey;
2425 import de.willuhn.jameica.hbci.Settings;
26 import de.willuhn.jameica.hbci.gui.dialogs.CamtSetupDialog;
2527 import de.willuhn.jameica.hbci.gui.filter.KontoFilter;
2628 import de.willuhn.jameica.hbci.rmi.HBCIDBService;
2729 import de.willuhn.jameica.hbci.rmi.Konto;
2830 import de.willuhn.jameica.hbci.rmi.Umsatz;
31 import de.willuhn.jameica.hbci.server.BPDUtil.Query;
32 import de.willuhn.jameica.hbci.server.BPDUtil.Support;
33 import de.willuhn.jameica.system.Application;
34 import de.willuhn.jameica.system.OperationCanceledException;
2935 import de.willuhn.jameica.util.DateUtil;
36 import de.willuhn.logging.Logger;
3037
3138 /**
3239 * Hilfsklasse mit statischen Funktionen fuer Konten.
110117
111118 return null;
112119 }
120
121 /**
122 * Prueft, ob die Umsaetze eines Kontos per CAMT abgerufen werden sollen.
123 * @param k das zu pruefende Konto.
124 * @param ask true, wenn der User hier auch gefragt werden darf, falls er die Entscheidung noch nicht getroffen hat.
125 * @return true, wenn CAMT verwendet werden soll.
126 */
127 public static boolean useCamt(Konto k, boolean ask)
128 {
129 if (k == null)
130 {
131 Logger.warn("unable to check if CAMT is supported, no account given");
132 return false;
133 }
134 try
135 {
136 // Erstmal checken, ob wir grundsaetzlich Support fuer CAMT haben
137 Logger.debug("checking if account supports CAMT");
138 Support support = BPDUtil.getSupport(k,Query.UmsatzCamt);
139 if (support == null)
140 {
141 Logger.debug("unable to determine CAMT support");
142 return false;
143 }
144
145 if (!support.isSupported())
146 {
147 Logger.debug("account does not support CAMT");
148 return false;
149 }
150
151 // Also grundsaetzlich haben wir Support.
152 // Jetzt checken, wir, was fuer das Konto konfiguriert ist.
153 String value = StringUtils.trimToNull(MetaKey.UMSATZ_CAMT.get(k));
154
155 // Wenn ein Wert drin steht, hat sich der User entschieden, dann halten wir uns dran
156 if (value != null)
157 {
158 Logger.debug("CAMT usage configured as: " + value);
159 return Boolean.valueOf(value);
160 }
161
162 // Wenn als Wert noch nichts drin steht, dann hat der User es noch nicht konfigutiert. In dem Fall entscheiden
163 // wir erstmal basierend auf den vorhandenen Umsaetzen. Wenn das Konto noch keine Umsaetze hat, verwenden wir
164 // CAMT und speichern das auch als Wert. Damit wird kuenftig bei neuen Usern automatisch CAMT verwendet.
165 // Wenn es Umsaetze hat, fragen wir den User, ob er umstellen moechte.
166 if (k.getNumUmsaetze() == 0)
167 {
168 Logger.debug("account does not have bookings yet, auto-activating CAMT");
169 MetaKey.UMSATZ_CAMT.set(k,Boolean.TRUE.toString());
170 return true;
171 }
172
173 if (!ask)
174 {
175 Logger.debug("CAMT support available but not yet activated");
176 return false;
177 }
178
179 // Wenn wir keine UI haben, koennen wir den User aber nicht fragen
180 if (Application.inServerMode())
181 {
182 Logger.debug("running in server mode, user cannot be asked if CAMT shall be used");
183 return false;
184 }
185
186 Logger.debug("asking user if CAMT shall be used");
187 CamtSetupDialog d = new CamtSetupDialog(k);
188 Boolean b = (Boolean) d.open();
189 Logger.debug("user answered for CAMT: " + b);
190 return b != null ? b.booleanValue() : false;
191 }
192 catch (OperationCanceledException oce)
193 {
194 Logger.debug("operation cancelled");
195 return false;
196 }
197 catch (Exception e)
198 {
199 Logger.error("unable to check if account supports CAMT",e);
200 return false;
201 }
202 }
203
113204
114205 /**
115206 * Sucht das Konto in der Datenbank.
3636 import de.willuhn.jameica.hbci.Settings;
3737 import de.willuhn.jameica.hbci.messaging.MessagingAvailableConsumer;
3838 import de.willuhn.jameica.hbci.messaging.ObjectChangedMessage;
39 import de.willuhn.jameica.hbci.messaging.ObjectDeletedMessage;
3940 import de.willuhn.jameica.hbci.rmi.HBCIDBService;
4041 import de.willuhn.jameica.hbci.rmi.Konto;
4142 import de.willuhn.jameica.hbci.rmi.Kontoauszug;
597598 Konto konto = k.getKonto();
598599 konto.addToProtokoll(i18n.tr("Elektronischen Kontoauszug gelöscht"),Protokoll.TYP_SUCCESS);
599600 k.delete();
601 Application.getMessagingFactory().sendMessage(new ObjectDeletedMessage(k));
600602 count++;
601603 }
602604
134134
135135 if (StringUtils.trimToNull(getGegenkontoName()) == null)
136136 throw new ApplicationException(i18n.tr("Bitte geben Sie den Namen des Kontoinhabers des Gegenkontos ein"));
137 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
137 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
138138 HBCIProperties.checkChars(getGegenkontoName(), HBCIProperties.HBCI_SEPA_VALIDCHARS);
139139
140140 String zweck = this.getZweck();
141141 if (zweck == null || zweck.length() == 0)
142142 throw new ApplicationException(i18n.tr("Bitte geben Sie einen Verwendungszweck ein"));
143143
144 HBCIProperties.checkLength(zweck, HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
144 HBCIProperties.checkLength(zweck, HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
145145 HBCIProperties.checkChars(zweck, HBCIProperties.HBCI_SEPA_VALIDCHARS);
146146
147147 HBCIProperties.checkLength(getEndtoEndId(), HBCIProperties.HBCI_SEPA_ENDTOENDID_MAXLENGTH);
136136
137137 if (StringUtils.trimToNull(getGegenkontoName()) == null)
138138 throw new ApplicationException(i18n.tr("Bitte geben Sie den Namen des Kontoinhabers des Gegenkontos ein"));
139 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
139 HBCIProperties.checkLength(getGegenkontoName(), HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
140140 HBCIProperties.checkChars(getGegenkontoName(), HBCIProperties.HBCI_SEPA_VALIDCHARS);
141141
142 HBCIProperties.checkLength(getZweck(), HBCIProperties.HBCI_FOREIGNTRANSFER_USAGE_MAXLENGTH);
142 HBCIProperties.checkLength(getZweck(), HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
143143 HBCIProperties.checkChars(getZweck(), HBCIProperties.HBCI_SEPA_VALIDCHARS);
144144
145145 HBCIProperties.checkLength(getEndtoEndId(), HBCIProperties.HBCI_SEPA_ENDTOENDID_MAXLENGTH);
7676 if (getValuta() == null)
7777 throw new ApplicationException(i18n.tr("Valuta fehlt."));
7878
79 // "35" ist das DB-Limit
80 int limit = HBCIProperties.HBCI_TRANSFER_USAGE_DB_MAXLENGTH;
81 HBCIProperties.checkLength(getZweck(),limit);
79 HBCIProperties.checkLength(getZweck(),HBCIProperties.HBCI_SEPATRANSFER_USAGE_MAXLENGTH);
80
81 int limit = HBCIProperties.HBCI_TRANSFER_USAGE_DB_MAXLENGTH;
8282 HBCIProperties.checkLength(getZweck2(),limit);
8383 String[] ewz = getWeitereVerwendungszwecke();
8484 if (ewz != null && ewz.length > 0)
9191
9292 HBCIProperties.checkLength(this.getGvCode(),HBCIProperties.HBCI_GVCODE_MAXLENGTH);
9393 HBCIProperties.checkLength(this.getAddKey(),HBCIProperties.HBCI_ADDKEY_MAXLENGTH);
94
95 // Bei TX-ID und PurposeCode muessen wir die Laenge nicht checken. Das sind CAMT-Umsaetze.
96 // Und die kommen schema-validiert im XML-Format. Hier extra nochmal zu pruefen, waere redundant.
97 // Zumal die korrespondierenden Datebank-Felder vorsorglich ohnehin deutlich laenger definiert
98 // sind als es das Schema zulaesst
9499 }
95100 catch (RemoteException e)
96101 {
113118 {
114119 // Wir speichern die Checksumme nun grundsaetzlich beim
115120 // Anlegen des Datensatzes. Dann koennen wir anschliessend
116 // beliebig aendern und muessens uns nicht mehr mit
121 // beliebig aendern und muessen uns nicht mehr mit
117122 // "hasChangedByUser" herumschlagen
118123 setAttribute("checksum",new Long(getChecksum()));
119124 super.insert();
303308 String id2 = other.getID();
304309 if (id1 != null && id2 != null)
305310 return id1.equals(id2);
306
311
312 // Wenn beide eine TX-ID haben, brauchen wir nur anhand der TX-ID vergleichen.
313 id1 = this.getTransactionId();
314 id2 = other.getTransactionId();
315 if (id1 != null && id2 != null)
316 return id1.equals(id2);
317
307318 return other.getChecksum() == getChecksum();
308319 }
309320 catch (Exception e)
406417 sv = valuta.toString();
407418 }
408419 }
409
420
410421 String s = (""+getArt()).toUpperCase() +
411422 getKonto().getID() + // wenigstens die ID vom Konto muss mit rein. Andernfalls haben zwei gleich aussehende Umsaetze auf verschiedenen Konten die gleiche Checksumme
412 getBetrag() +
413 getCustomerRef() +
414 getGegenkontoBLZ() +
415 getGegenkontoNummer() +
416 (""+getGegenkontoName()).toUpperCase() +
417 getPrimanota() +
423 getBetrag() +
424 getCustomerRef() +
425 getGegenkontoBLZ() +
426 getGegenkontoNummer() +
427 (""+getGegenkontoName()).toUpperCase() +
428 getPrimanota() +
418429 (Settings.getSaldoInChecksum() ? getSaldo() : "") +
419 ((String)getAttribute("mergedzweck")).toUpperCase() +
420 sd +
421 sv;
430 ((String)getAttribute("mergedzweck")).toUpperCase() +
431 sd +
432 sv;
422433
423434 // Bei Vormerkbuchungen haengen wir noch was hinten dran. Da der
424435 // Saldo per Default nicht mehr in der Checksumme ist, geht sonst
743754 copy.setZweck2(this.getZweck2());
744755 copy.setWeitereVerwendungszwecke(this.getWeitereVerwendungszwecke());
745756 copy.setGvCode(this.getGvCode());
757 copy.setPurposeCode(this.getPurposeCode());
758
759 // Das Duplizieren von Umsatzbuchungen machen wir z.Bsp. dann, wenn ein User
760 // per Hand eine Gegenbuchung erzeugt (per Kontextmenu-Eintrag "Gegenbuchung erzeugen auf...").
761 // Das Duplikat darf nicht die selbe Transaction-ID haben, dann waere sie
762 // nicht mehr eindeutig. Daher wird die TX-ID nicht mit dupliziert
763 // copy.setTransactionId(this.getTransactionId());
764
746765 return copy;
747766 }
767
768 /**
769 * @see de.willuhn.jameica.hbci.rmi.Umsatz#getTransactionId()
770 */
771 @Override
772 public String getTransactionId() throws RemoteException
773 {
774 return (String) this.getAttribute("txid");
775 }
776
777 /**
778 * @see de.willuhn.jameica.hbci.rmi.Umsatz#setTransactionId(java.lang.String)
779 */
780 @Override
781 public void setTransactionId(String id) throws RemoteException
782 {
783 this.setAttribute("txid",id);
784 }
785
786 /**
787 * @see de.willuhn.jameica.hbci.rmi.Umsatz#getPurposeCode()
788 */
789 @Override
790 public String getPurposeCode() throws RemoteException
791 {
792 return (String) this.getAttribute("purposecode");
793 }
794
795 /**
796 * @see de.willuhn.jameica.hbci.rmi.Umsatz#setPurposeCode(java.lang.String)
797 */
798 @Override
799 public void setPurposeCode(String code) throws RemoteException
800 {
801 this.setAttribute("purposecode",code);
802 }
803
804 /**
805 * @see de.willuhn.jameica.hbci.rmi.Umsatz#getEndToEndId()
806 */
807 @Override
808 public String getEndToEndId() throws RemoteException
809 {
810 return (String) this.getAttribute("endtoendid");
811 }
812
813 /**
814 * @see de.willuhn.jameica.hbci.rmi.Umsatz#setEndToEndId(java.lang.String)
815 */
816 @Override
817 public void setEndToEndId(String id) throws RemoteException
818 {
819 this.setAttribute("endtoendid",id);
820 }
748821 }
749
750
751 /**********************************************************************
752 * $Log: UmsatzImpl.java,v $
753 * Revision 1.92 2012/05/03 21:50:47 willuhn
754 * @B BUGZILLA 1232 - Saldo des Kontos bei Offline-Konten nur bei neuen Umsaetzen uebernehmen - nicht beim Bearbeiten existierender
755 *
756 * Revision 1.91 2012/04/29 19:32:07 willuhn
757 * @N Reihenfolge der Kategorien bei der Zuordnung beachten
758 *
759 * Revision 1.90 2012/04/05 21:44:18 willuhn
760 * @B BUGZILLA 1219
761 *
762 * Revision 1.89 2011/10/18 09:28:14 willuhn
763 * @N Gemeinsames Basis-Interface "HibiscusDBObject" fuer alle Entities (ausser Version und DBProperty) mit der Implementierung "AbstractHibiscusDBObject". Damit koennen jetzt zu jedem Fachobjekt beliebige Meta-Daten in der Datenbank gespeichert werden. Wird im ersten Schritt fuer die Reminder verwendet, um zu einem Auftrag die UUID des Reminders am Objekt speichern zu koennen
764 *
765 * Revision 1.88 2011-07-25 17:17:19 willuhn
766 * @N BUGZILLA 1065 - zusaetzlich noch addkey
767 *
768 * Revision 1.87 2011-07-25 14:42:40 willuhn
769 * @N BUGZILLA 1065
770 *
771 * Revision 1.86 2011-04-28 12:15:25 willuhn
772 * @N Wenn beide Umsaetze eine ID haben, muss nur anhand derer verglichen werden
773 *
774 * Revision 1.85 2011-04-28 07:50:07 willuhn
775 * @B BUGZILLA 692
776 *
777 * Revision 1.84 2011-03-11 15:05:14 willuhn
778 * @C Loeschen von Vormerkbuchungen nicht protokollieren - da Hibiscus die selbst loescht und das irritierende Protokoll-Meldungen fuer den User erzeugt
779 *
780 * Revision 1.83 2010-11-19 17:02:06 willuhn
781 * @N VWZUtil#toString
782 *
783 * Revision 1.82 2010-09-28 21:40:27 willuhn
784 * @C Vormerkbuchungen haben eine andere Checksumme als valutierte Buchungen - auch, wenn sie sonst identisch sind
785 *
786 * Revision 1.81 2010-09-27 11:51:38 willuhn
787 * @N BUGZILLA 804
788 *
789 * Revision 1.80 2010-08-30 14:25:37 willuhn
790 * @B NPE, wenn Konto angegeben, jedoch ohne ID
791 *
792 * Revision 1.79 2010-08-27 09:24:58 willuhn
793 * @B Generics-Deklaration im Cache hat javac nicht akzeptiert (der Eclipse-Compiler hats komischerweise gefressen)
794 *
795 * Revision 1.78 2010-08-26 12:53:08 willuhn
796 * @N Cache nur befuellen, wenn das explizit gefordert wird. Andernfalls wuerde der Cache u.U. unnoetig gefuellt werden, obwohl nur ein Objekt daraus geloescht werden soll
797 *
798 * Revision 1.77 2010-08-26 11:31:23 willuhn
799 * @N Neuer Cache. In dem werden jetzt die zugeordneten Konten von Auftraegen und Umsaetzen zwischengespeichert sowie die Umsatz-Kategorien. Das beschleunigt das Laden der Umsaetze und Auftraege teilweise erheblich
800 *
801 * Revision 1.76 2010-08-03 11:00:01 willuhn
802 * @N Konto-ID mit in Checksumme
803 *
804 * Revision 1.75 2010-06-17 15:31:27 willuhn
805 * @C BUGZILLA 622 - Defaultwert des checksum.saldo-Parameters geaendert - steht jetzt per Default auf false, sodass der Saldo NICHT mit in die Checksumme einfliesst
806 * @B BUGZILLA 709 - Konto ist nun ENDLICH nicht mehr Bestandteil der Checksumme, dafuer sind jetzt alle Verwendungszweck-Zeilen drin
807 *
808 * Revision 1.74 2010/05/30 23:29:31 willuhn
809 * @N Alle Verwendungszweckzeilen in Umsatzlist und -tree anzeigen (BUGZILLA 782)
810 *
811 * Revision 1.73 2010/05/06 22:08:45 willuhn
812 * @N BUGZILLA 622
813 *
814 * Revision 1.72 2010/04/27 11:02:32 willuhn
815 * @R Veralteten Verwendungszweck-Code entfernt
816 *
817 * Revision 1.71 2010/04/22 12:42:03 willuhn
818 * @N Erste Version des Supports fuer Offline-Konten
819 *
820 * Revision 1.70 2010/03/16 00:44:18 willuhn
821 * @N Komplettes Redesign des CSV-Imports.
822 * - Kann nun erheblich einfacher auch fuer andere Datentypen (z.Bsp.Ueberweisungen) verwendet werden
823 * - Fehlertoleranter
824 * - Mehrfachzuordnung von Spalten (z.Bsp. bei erweitertem Verwendungszweck) moeglich
825 * - modulare Deserialisierung der Werte
826 * - CSV-Exports von Hibiscus koennen nun 1:1 auch wieder importiert werden (Import-Preset identisch mit Export-Format)
827 * - Import-Preset wird nun im XML-Format nach ~/.jameica/hibiscus/csv serialisiert. Damit wird es kuenftig moeglich sein,
828 * CSV-Import-Profile vorzukonfigurieren und anschliessend zu exportieren, um sie mit anderen Usern teilen zu koennen
829 *
830 * Revision 1.69 2010/01/18 22:59:05 willuhn
831 * @B BUGZILLA 808
832 *
833 * Revision 1.68 2009/10/29 22:52:05 willuhn
834 * *** empty log message ***
835 *
836 * Revision 1.67 2009/09/15 00:23:35 willuhn
837 * @N BUGZILLA 745
838 *
839 * Revision 1.66 2009/03/12 10:56:01 willuhn
840 * @B Double.NaN geht nicht
841 *
842 * Revision 1.65 2009/03/11 17:53:12 willuhn
843 * *** empty log message ***
844 *
845 * Revision 1.64 2009/02/23 17:01:58 willuhn
846 * @C Kein Abgleichen mehr bei vorgemerkten Buchungen sondern stattdessen vorgemerkte loeschen und neu abrufen
847 *
848 * Revision 1.63 2009/02/13 10:52:18 willuhn
849 * @N Verwendungszweck mit in Tiny-Checksum uebernehmen, damit die Buchungen auch dann gefunden werden, wenn das Gegenkonto von der Bank nicht gefuellt wird
850 *
851 * Revision 1.62 2009/02/12 18:37:18 willuhn
852 * @N Erster Code fuer vorgemerkte Umsaetze
853 *
854 * Revision 1.61 2009/02/04 23:06:24 willuhn
855 * @N BUGZILLA 308 - Umsaetze als "geprueft" markieren
856 *
857 * Revision 1.60 2009/01/04 01:32:57 willuhn
858 * @N Laengen-Check - ist jetzt noetig, da Umsaetze nun manuell geaendert werden koennen
859 *
860 * Revision 1.59 2009/01/04 01:25:47 willuhn
861 * @N Checksumme von Umsaetzen wird nun generell beim Anlegen des Datensatzes gespeichert. Damit koennen Umsaetze nun problemlos geaendert werden, ohne mit "hasChangedByUser" checken zu muessen. Die Checksumme bleibt immer erhalten, weil sie in UmsatzImpl#insert() sofort zu Beginn angelegt wird
862 * @N Umsaetze sind nun vollstaendig editierbar
863 *
864 * Revision 1.58 2008/12/14 23:18:35 willuhn
865 * @N BUGZILLA 188 - REFACTORING
866 *
867 * Revision 1.57 2008/12/02 10:52:23 willuhn
868 * @B DecimalInput kann NULL liefern
869 * @B Double.NaN beruecksichtigen
870 *
871 * Revision 1.56 2008/11/26 00:39:36 willuhn
872 * @N Erste Version erweiterter Verwendungszwecke. Muss dringend noch getestet werden.
873 *
874 * Revision 1.55 2008/11/17 23:30:00 willuhn
875 * @C Aufrufe der depeicated BLZ-Funktionen angepasst
876 *
877 * Revision 1.54 2008/09/03 21:29:44 willuhn
878 * @C BUGZILLA 622 - Debug-Ausgaben
879 *
880 * Revision 1.53 2008/04/27 22:22:56 willuhn
881 * @C I18N-Referenzen statisch
882 *
883 * Revision 1.52 2008/02/15 17:39:10 willuhn
884 * @N BUGZILLA 188 Basis-API fuer weitere Zeilen Verwendungszweck. GUI fehlt noch
885 * @N DB-Update 0005. Speichern des Textschluessels bei Sammelauftragsbuchungen in der Datenbank
886 **********************************************************************/
285285 // Erst Ausgaben, dann Einnahmen, dann Rest
286286 int thisType = this.typ.getTyp();
287287 int otherType = other.typ.getTyp();
288 if (thisType != otherType)
288 if (thisType != otherType && thisType != UmsatzTyp.TYP_EGAL && otherType != UmsatzTyp.TYP_EGAL)
289289 return thisType < otherType ? -1 : 1;
290290
291291 String n1 = this.typ.getNummer(); if (n1 == null) n1 = "";
267267 return false;
268268
269269 String zweck = VerwendungszweckUtil.toString(umsatz,"");
270 String name = umsatz.getGegenkontoName();
271 String kto = umsatz.getGegenkontoNummer();
272 String kom = umsatz.getKommentar();
273 String art = umsatz.getArt();
274
275 if (name == null) name = "";
276 if (kto == null) kto = "";
277 if (kom == null) kom = "";
278 if (art == null) art = "";
279
270 String name = StringUtils.trimToEmpty(umsatz.getGegenkontoName());
271 String kto = StringUtils.trimToEmpty(umsatz.getGegenkontoNummer());
272 String kom = StringUtils.trimToEmpty(umsatz.getKommentar());
273 String art = StringUtils.trimToEmpty(umsatz.getArt());
274 String purp = StringUtils.trimToEmpty(umsatz.getPurposeCode());
275
280276 if (!isRegex())
281277 {
282278 zweck = zweck.toLowerCase();
284280 kto = kto.toLowerCase();
285281 kom = kom.toLowerCase();
286282 art = art.toLowerCase();
283 purp = purp.toLowerCase();
287284
288285 if (settings.getBoolean("search.ignore.whitespace",true))
289286 {
301298 name.indexOf(test) != -1 ||
302299 kto.indexOf(test) != -1 ||
303300 kom.indexOf(test) != -1 ||
304 art.indexOf(test) != -1)
301 art.indexOf(test) != -1 ||
302 purp.indexOf(test) != -1)
305303 {
306304 return true;
307305 }
325323 Matcher mKto = pattern.matcher(kto);
326324 Matcher mKom = pattern.matcher(kom);
327325 Matcher mArt = pattern.matcher(art);
328 Matcher mAll = pattern.matcher(name + " " + kto + " " + zweck + " " + kom + " " + art);
326 Matcher mPurp = pattern.matcher(purp);
327 Matcher mAll = pattern.matcher(name + " " + kto + " " + zweck + " " + kom + " " + art + " " + purp);
329328
330329 return (mZweck.matches() ||
331 mName.matches() ||
332 mKto.matches() ||
333 mKom.matches() ||
334 mArt.matches() ||
330 mName.matches() ||
331 mKto.matches() ||
332 mKom.matches() ||
333 mArt.matches() ||
334 mPurp.matches() ||
335335 mAll.matches()
336336 );
337337 }
122122 "LOWER(primanota) LIKE ? OR " +
123123 "LOWER(art) LIKE ? OR " +
124124 "LOWER(customerref) LIKE ? OR " +
125 "LOWER(purposecode) LIKE ? OR " +
125126 "LOWER(kommentar) LIKE ?)",
126 text,text,text,text,text,text,text,text);
127 text,text,text,text,text,text,text,text,text);
127128 }
128129 return list;
129130 }
163163 return null;
164164 }
165165
166 return result.get(tag);
166 // Sonderrolle SVWZ.
167 // Es kann sein, dass der Verwendungszweck so aussieht:
168 // "EREF+1234 MREF+1234 SVWZ+"
169 // Sprich: Das Tag ist zwar da, aber leer. Macht die "S-Bahn Berlin GmbH".
170 // In dem Fall liefern wir ebenfalls den kompletten Text
171 String value = result.get(tag);
172 if (tag == Tag.SVWZ && StringUtils.trimToNull(value) == null)
173 return toString(t);
174
175 return value;
167176 }
168177
169178 /**
4848 public abstract class AbstractHBCIJob
4949 {
5050 protected final static I18N i18n = Application.getPluginLoader().getPlugin(HBCI.class).getResources().getI18N();
51
52 private final static String NL = System.getProperty("line.separator","\n");
5153
5254 private org.kapott.hbci.GV.HBCIJob job = null;
5355 private boolean exclusive = false;
377379 }
378380 String sDetail = sb.toString();
379381 if (sDetail != null && sDetail.length() > 0)
380 sr += System.getProperty("line.separator","\n") + sDetail;
382 sr += NL + sDetail;
381383 if (sJob != null && sJob.length() > 0)
382 sr += System.getProperty("line.separator","\n") + sJob;
384 sr += NL + sJob;
383385 if (sGlob != null && sGlob.length() > 0)
384 sr += System.getProperty("line.separator","\n") + sGlob;
386 sr += NL + sGlob;
385387 }
386388 catch (ArrayIndexOutOfBoundsException aio)
387389 {
3131 import de.willuhn.jameica.hbci.rmi.Protokoll;
3232 import de.willuhn.jameica.hbci.rmi.Umsatz;
3333 import de.willuhn.jameica.hbci.server.Converter;
34 import de.willuhn.jameica.hbci.server.KontoUtil;
3435 import de.willuhn.jameica.hbci.server.hbci.rewriter.RewriterRegistry;
3536 import de.willuhn.jameica.hbci.server.hbci.rewriter.UmsatzRewriter;
3637 import de.willuhn.jameica.messaging.StatusBarMessage;
130131 * @see de.willuhn.jameica.hbci.server.hbci.AbstractHBCIJob#getIdentifier()
131132 */
132133 public String getIdentifier() {
133 return "KUmsAll";
134 return KontoUtil.useCamt(this.konto,true) ? "KUmsAllCamt" : "KUmsAll";
134135 }
135136
136137 /**
6969 * angezeigt werden sollen. Wird z.Bsp. vom ScriptingBackend verwendet, um dort
7070 * die Zugangsdaten zur Webseite hinterlegen zu koennen, ohne dafuer Kontonummer,
7171 * Benutzerkennung, usw. des Kontos "missbrauchen" zu muessen.
72 * Die vom Benutzer eingegebenen Werte werden als Meta-Daten zum Konto gespeichert.
73 * Sie koennen mittels {@link Konto#getMeta(String, String)} wieder abgerufen werden.
74 * Besitzt ein Property den Suffix "(true/false)" wird es als Checkbox angezeigt.
75 * Besitzt ein Property den Suffix "(pwd)" oder "(password)" wird es als Passwort-Eingabe angezeigt.
76 * Der Suffix wird vor dem Speichern des Property in den Meta-Daten des Konto entfernt.
7277 * @param k das Konto.
7378 * @return Liste von lesbaren Property-Namen. Die werden dem Benutzer 1:1 als
7479 * Label von Eingabefeldern angezeigt.
6868 */
6969 public String getName()
7070 {
71 return "HBCI";
71 return "FinTS/HBCI";
7272 }
7373
7474 /**
1919 Mit einem Rechtsklick auf die Legende kann ein Kontext-Menü zum Ein- oder
2020 Ausblenden aller Datenreihen geöffnet werden.
2121 </p>
22
22 <p>
23 <b>Hinweis:</b> Klicken Sie mit der rechten Maustaste in die Grafik
24 und wählen Sie &quot;Gruppierung nach&quot;, um nach Jahr, Monat oder Woche zu gruppieren.
25 </p>
2326 </form>
Binary diff not shown
src/img/150/user-info.png less more
Binary diff not shown
Binary diff not shown
src/img/200/user-info.png less more
Binary diff not shown
Binary diff not shown
src/img/300/user-info.png less more
Binary diff not shown
Binary diff not shown
Binary diff not shown
src/img/user-info.png less more
Binary diff not shown
156156 Vorhandene\ SEPA-Sammellastschriften=Existing\ collective\ SEPA Direct\ Debits
157157 BLZ\ nicht\ achtstellig=Bank\ Code\ (BLZ)\ must\ be\ eight\ Digits
158158 Aktualisieren=Refresh
159 Ums\u00E4tze\ der\ Kategorien\ im\ zeitlichen\ Verlauf=Timeline\ of\ Transactions\ in\ Categories
159 Fehler\ beim\ Aktualisieren=Error\ while\ refreshing
160 Fehler\ beim\ Erzeugen\ des\ Diagramms=Error\ while\ creating\ the\ chart
161 Ums\u00E4tze\ der\ Kategorien\ im\ Verlauf\ (gruppiert\ nach\ {0})=Timeline\ of\ Transactions\ in\ Categories\ (aggregated\ by\ {0})
162 Gruppierung\ nach=Aggregate\ by
163 Bitte\ w\u00E4hlen\ Sie\ einen\ gr\u00F6ßeren\ Zeitraum=Please\ select\ a longer interval
164 Woche=Week
160165 Neue\ Lastschrift...=New\ Direct\ Debit...
161166 Ausgaben=Expense
162167 SEPA-Sammel\u00FCberweisung\ {0}\:\ Buchung\ bearbeiten=Collective\ SEPA\ Credit\ Transfer\ {0}\:\ Edit\ Booking
433438 SEPA-Lastschriften=SEPA\ Direct\ Debits
434439 <Keine\ Kategorie>=<No\ Category>
435440 Als\ gelesen\ markieren=Mark\ as\ read
441 Als\ ungelesen\ markieren=Mark\ as\ unread
436442 Gegenkonto/Betrag=Counter\ Account/Amount
437443 Art=Type
438444 Bezeichnung\ des\ Kontos=Account\ Description
9961002 Valuta/Datum=Valuta/Date
9971003 Zeitraum\:\ {0}\ -\ {1}=Timeframe\:\ {0}\ -\ {1}
9981004 {0}\ Auftr\u00E4ge,\ {1}\ markiert,\ Summe\:\ {2}\ {3}={0}\ Records,\ {1}\ selected,\ Total\:\ {2}\ {3}
999
1005 Elektr.\ Kontoausz\u00E4ge=Electr.\ bank\ statements
1006 Nur\ ungelesene\ Kontoausz\u00E4ge anzeigen=Show\ only\ unread\ bank\ statements
1007 Speichern\ unter...=Save\ as...
1008 Kontoausz\u00E4ge abrufen...=Fetch\ bank\ statements...
1009 Empfangsquittung\ senden...=Send\ acknowledgment\ of\ receipt...
1010 Jahr=Year
1011 Nummer=Number
1012 Abgerufen\ am=Fetched\ at
1013 Quittiert\ am=Receipted\ at
1014 Saldo=Balance
1015 Letzte\ 30\ Tage=Last 30 Days
1016 Letzte\ 7\ Tage=Last 7 Days
1017 Kein\ Konto\ angegeben=No\ account\ specified
1018 Bitte\ w\u00E4hlen\ Sie\ ein\ Konto\ aus=Please\ select\ an\ account
1019 N\u00E4chster\ Abruf=Next\ call
0 /**********************************************************************
1 *
2 * Copyright (c) by Olaf Willuhn
3 * All rights reserved
4 *
5 **********************************************************************/
6
7 import java.util.Arrays;
8 import java.util.HashMap;
9 import java.util.List;
10 import java.util.Map;
11
12 import de.willuhn.jameica.hbci.rmi.DBSupport;
13 import de.willuhn.jameica.hbci.server.AbstractUpdate;
14 import de.willuhn.jameica.hbci.server.DBSupportH2Impl;
15 import de.willuhn.jameica.hbci.server.DBSupportMySqlImpl;
16 import de.willuhn.jameica.hbci.server.DBSupportPostgreSQLImpl;
17
18
19 /**
20 * Macht die Umsatz-Tabelle fit fuer CAMT.
21 */
22 public class update0063 extends AbstractUpdate
23 {
24 private Map<Class<? extends DBSupport>,List<String>> statements = new HashMap()
25 {{
26 // Update fuer H2
27 put(DBSupportH2Impl.class,Arrays.asList(
28 "ALTER TABLE umsatz ALTER COLUMN zweck varchar(255);",
29 "ALTER TABLE umsatz ADD txid varchar(100);",
30 "ALTER TABLE umsatz ADD purposecode varchar(10);"
31 ));
32
33 // Update fuer MySQL
34 put(DBSupportMySqlImpl.class,Arrays.asList(
35 "ALTER TABLE umsatz CHANGE zweck zweck varchar(255);",
36 "ALTER TABLE umsatz ADD txid varchar(100);",
37 "ALTER TABLE umsatz ADD purposecode varchar(10);"
38 ));
39
40 // Update fuer PostGreSQL
41 put(DBSupportPostgreSQLImpl.class,Arrays.asList(
42 "ALTER TABLE umsatz ALTER COLUMN zweck TYPE varchar(255);",
43 "ALTER TABLE umsatz ADD txid varchar(100);",
44 "ALTER TABLE umsatz ADD purposecode varchar(10);"
45 ));
46 }};
47
48 /**
49 * @see de.willuhn.jameica.hbci.server.AbstractUpdate#getStatements(java.lang.Class)
50 */
51 @Override
52 protected List<String> getStatements(Class<? extends DBSupport> driverClass)
53 {
54 return statements.get(driverClass);
55 }
56 }
0 -- ----------------------------------------------------------------------
1 -- Fuehrt die neue Spalte "endtoendid" ein.
2 -- ----------------------------------------------------------------------
3
4 ALTER TABLE umsatz ADD endtoendid varchar(100);