/src/mpv5/db/objects/Account.java
Java | 505 lines | 301 code | 58 blank | 146 comment | 28 complexity | 6ae73988e2ab8871d0d9dfa47af66e46 MD5 | raw file
1/* 2 * This file is part of YaBS. 3 * 4 * YaBS is free software: you can redistribute it and/or modify 5 * it under the terms of the GNU General Public License as published by 6 * the Free Software Foundation, either version 3 of the License, or 7 * (at your option) any later version. 8 * 9 * YaBS is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 * GNU General Public License for more details. 13 * 14 * You should have received a copy of the GNU General Public License 15 * along with YaBS. If not, see <http://www.gnu.org/licenses/>. 16 */ 17package mpv5.db.objects; 18 19import mpv5.db.common.DataNotCachedException; 20import java.util.ArrayList; 21import java.util.Enumeration; 22import java.util.HashMap; 23import java.util.List; 24import java.util.logging.Level; 25import java.util.logging.Logger; 26import javax.swing.Icon; 27import javax.swing.JComponent; 28 29import javax.swing.tree.DefaultMutableTreeNode; 30import javax.swing.tree.DefaultTreeModel; 31import mpv5.db.common.Context; 32import mpv5.db.common.DatabaseObject; 33import mpv5.db.common.NodataFoundException; 34import mpv5.db.common.QueryCriteria; 35import mpv5.db.common.QueryHandler; 36import mpv5.globals.Messages; 37import mpv5.logging.Log; 38import mpv5.ui.frames.MPView; 39import mpv5.utils.arrays.ArrayUtilities; 40import mpv5.utils.images.MPIcon; 41 42/** 43 * 44 * 45 */ 46public class Account extends DatabaseObject { 47 48 private static ArrayList<DatabaseObject> accounts; 49 50 /** 51 * ANLAGEGUT KOSTEN Eigenkapital UNKOSTEN EINKOMMEN HAFTUNG 52 * @param type 53 * @return 54 */ 55 public static String getTypeString(int type) { 56 switch (type) { 57 case Account.OTHER: 58 return Messages.MISC.toString(); 59 case Account.COST: 60 return Messages.COST.toString(); 61 case Account.EXPENSE: 62 return Messages.EXPENSE.toString(); 63 case Account.INCOME: 64 return Messages.INCOME.toString(); 65 case Account.TAXES: 66 return Messages.TAXES.toString(); 67 case Account.RESERVE: 68 return Messages.RESERVE.toString(); 69 default: 70 return "N/A"; 71 } 72 } 73 74 /** 75 * Cache accounts 76 * @return 77 */ 78 public synchronized static ArrayList<DatabaseObject> cacheAccounts() { 79 Runnable runnable = new Runnable() { 80 81 @Override 82 public void run() { 83 try { 84 accounts = DatabaseObject.getObjects(Context.getAccounts(), false); 85 } catch (NodataFoundException ex) { 86 Log.Debug(ex); 87 } 88 } 89 }; 90 new Thread(runnable).start(); 91 92 return accounts; 93 } 94 95 public Account() { 96 setContext(Context.getAccounts()); 97 } 98 private int intparentaccount; 99 private int intaccountclass; 100 public final static int OTHER = 0; 101 public final static int COST = 1;//Direkte Kosten (Wareneinkauf), 102 public final static int EXPENSE = 2;//Sonstige Kosten, Aufwandskonto 103 public final static int INCOME = 3;//Ertragskonto 104 public final static int TAXES = 4;//Steuern 105 public final static int RESERVE = 5; 106 107 private String description = ""; 108 private double taxvalue; 109 private int intaccounttype; 110 private int intprofitfid; 111 private int inttaxfid; 112 private int inttaxuid; 113 private String frame = "buildin"; 114 private String hierarchypath = ""; 115 116 @Override 117 public JComponent getView() { 118// throw new UnsupportedOperationException("Not supported yet."); 119 return null; 120 } 121 122 /** 123 * @return the description 124 */ 125 public String __getDescription() { 126 return description; 127 } 128 129 /** 130 * @param description the description to set 131 */ 132 public void setDescription(String description) { 133 this.description = description; 134 } 135 136 /** 137 * A (preferably cached) view to the accounts 138 * @return 139 * @throws DataNotCachedException 140 */ 141 public synchronized static ArrayList<DatabaseObject> getAccounts() throws DataNotCachedException { 142 if (accounts != null) { 143 return accounts; 144 } else { 145 throw new DataNotCachedException(Context.getAccounts()); 146 } 147 } 148 149 /** 150 * Get all Items which are assigned to this account 151 * @return 152 * @throws mpv5.db.common.NodataFoundException 153 */ 154 public List<Item> getItemsInAccount() throws NodataFoundException { 155 List<Item> tmp = DatabaseObject.getReferencedObjects((Item) DatabaseObject.getObject(Context.getItem()), Context.getItemsToAccounts()); 156 157 QueryCriteria c = new QueryCriteria("defaultaccountsids", this.__getIDS()); 158 ArrayList<Item> tmp2 = DatabaseObject.getObjects(new Item(), c); 159 160 tmp.addAll(tmp2); 161 162 return tmp; 163 } 164 165 /** 166 * Get all additional accounts where the given item is currently assigned to 167 * @param item 168 * @return 169 * @throws mpv5.db.common.NodataFoundException 170 */ 171 public static ArrayList<Account> getAccountsOfItem(Item item) throws NodataFoundException { 172 Object[][] tmp = QueryHandler.instanceOf().clone(Context.getItemsToAccounts()).select("accountsids", new String[]{"itemsids", item.__getIDS().toString(), ""}); 173 ArrayList<Account> l = new ArrayList<Account>(); 174 175 l.add((Account) DatabaseObject.getObject(Context.getAccounts(), item.__getAccountsids())); 176 177 for (int i = 0; i < tmp.length; i++) { 178 int id = Integer.valueOf(tmp[i][0].toString()); 179 l.add((Account) DatabaseObject.getObject(Context.getAccounts(), id)); 180 } 181 182 return l; 183 } 184 185 /** 186 * 187 * <li> 1: Assets: Aktiva, 188 * <li>2: Cost: direkte Kosten (Wareneinkauf), 189 * <li>3: Expenses: sonstige Kosten, Aufwandskonto, 190 * <li>4: Income: Ertragskonto, 191 * <li>5: Liablities: Verbindlichkeiten (Mittelherkunft), 192 * <li>6: Equity: Passiva 193 * 194 * @return the accounttype 195 */ 196 public int __getIntaccounttype() { 197 return intaccounttype; 198 } 199 200 /** 201 * 202 * <li> 1: Assets: Aktiva, 203 * <li>2: Cost: direkte Kosten (Wareneinkauf), 204 * <li>3: Expenses: sonstige Kosten, Aufwandskonto, 205 * <li>4: Income: Ertragskonto, 206 * <li>5: Liablities: Verbindlichkeiten (Mittelherkunft), 207 * <li>6: Equity: Passiva 208 * 209 * @param accounttype the accounttype to set 210 */ 211 public void setIntaccounttype(int accounttype) { 212 this.intaccounttype = accounttype; 213 } 214 215 /** 216 * @return the intaccountclass 217 */ 218 public int __getIntaccountclass() { 219 return intaccountclass; 220 } 221 222 /** 223 * @param intaccountclass the intaccountclass to set 224 */ 225 public void setIntaccountclass(int intaccountclass) { 226 this.intaccountclass = intaccountclass; 227 } 228 229 /** 230 * @return the intparentaccount 231 */ 232 public int __getIntparentaccount() { 233 return intparentaccount; 234 } 235 236 /** 237 * @param intparentaccount the intparentaccount to set 238 */ 239 public void setIntparentaccount(int intparentaccount) { 240 this.intparentaccount = intparentaccount; 241 } 242 243 /** 244 * Create a tree model 245 * @param data 246 * @param rootNode 247 * @return 248 */ 249 public static DefaultTreeModel toTreeModel(ArrayList<Account> data, Account rootNode) { 250 251 DefaultMutableTreeNode node1 = null; 252 if (data.size() > 0) { 253 node1 = new DefaultMutableTreeNode(rootNode); 254 data.remove(rootNode);//remove root if in list 255 try { 256 mpv5.YabsViewProxy.instance().setWaiting(true); 257 node1 = addToParents(node1, data); 258 } catch (Exception e) { 259 Log.Debug(e); 260 } finally { 261 mpv5.YabsViewProxy.instance().setWaiting(false); 262 } 263 } 264 DefaultTreeModel model = new DefaultTreeModel(node1); 265 return model; 266 } 267 268 @SuppressWarnings("unchecked") 269 private static DefaultMutableTreeNode addToParents(DefaultMutableTreeNode firstnode, ArrayList<Account> dobjlist) { 270 for (int i = 0; i < dobjlist.size(); i++) { 271 Account dobj = dobjlist.get(i); 272 if (dobj.__getIntparentaccount() <= 0 && firstnode.isRoot()) { 273// Log.Debug(Account.class, "Node is root child, adding it to root and removing it from the list."); 274 firstnode.add(new DefaultMutableTreeNode(dobj)); 275// Log.Debug(Account.class, "Added 1st " + dobj); 276 dobjlist.remove(dobj);//First level groups 277 i--; 278 } else { 279// Log.Debug(Account.class, "Check " + dobj); 280 int parentid = dobj.__getIntparentaccount(); 281 if (((Account) firstnode.getUserObject()).__getIDS().intValue() == parentid) { 282 firstnode.add(new DefaultMutableTreeNode(dobj)); 283// Log.Debug(Account.class, " Parent " + firstnode); 284// Log.Debug(Account.class, " Added " + dobj); 285 dobjlist.remove(dobj); 286 i--; 287 } else { 288 @SuppressWarnings("unchecked") 289 Enumeration<DefaultMutableTreeNode> nodes = firstnode.children(); 290 while (nodes.hasMoreElements()) { 291 addToParents(nodes.nextElement(), dobjlist); 292 } 293 294 295 } 296 } 297 } 298 return firstnode; 299 } 300 301 /** 302 * Create a tree model 303 * @param data 304 * @param rootaccount 305 * @return 306 */ 307 public static DefaultTreeModel toTreeModel2(ArrayList<Account> data, Account rootaccount) { 308 309 HashMap<Account, DefaultMutableTreeNode> map = new HashMap<Account, DefaultMutableTreeNode>(); 310 for (Account c : data) { 311 map.put(c, new DefaultMutableTreeNode(c)); 312 } 313 314 DefaultMutableTreeNode root = new DefaultMutableTreeNode(rootaccount); 315 getChildrenOf(root, data, map); 316 DefaultTreeModel model = new DefaultTreeModel(root); 317 return model; 318 } 319 320 private static synchronized void getChildrenOf(DefaultMutableTreeNode node, ArrayList<Account> data, HashMap<Account, DefaultMutableTreeNode> map) { 321 for (int i = 0; i < data.size(); i++) { 322 Account account = data.get(i); 323 DefaultMutableTreeNode anode = map.get(account); 324 if(account.__getIntparentaccount() == ((Account)node.getUserObject()).__getIDS()){ 325 node.add(anode); 326 data.remove(account); 327 i--; 328 getChildrenOf(anode, data, map); 329 } 330 } 331 } 332 333 /** 334 * @return the taxvalue 335 */ 336 public double __getTaxvalue() { 337 return taxvalue; 338 } 339 340 /** 341 * @param taxvalue the taxvalue to set 342 */ 343 public void setTaxvalue(double taxvalue) { 344 this.taxvalue = taxvalue; 345 } 346 347 @Override 348 public boolean delete() { 349 try { 350 ArrayList<Account> childs = DatabaseObject.getObjects(getContext(), new QueryCriteria("intparentaccount", ids)); 351 for (int i = 0; i < childs.size(); i++) { 352 DatabaseObject databaseObject = childs.get(i); 353 if (!databaseObject.delete()) { 354 return false; 355 } 356 } 357 } catch (NodataFoundException ex) { 358 Log.Debug(this, ex.getMessage()); 359 } 360 try { 361 return super.delete(); 362 } catch (Exception e) { 363 return false; 364 } 365 } 366 367 @Override 368 public MPIcon getIcon() { 369 return null; 370 } 371 372 /** 373 * @return the frame 374 */ 375 public String __getFrame() { 376 return frame; 377 } 378 379 /** 380 * @param frame the frame to set 381 */ 382 public void setFrame(String frame) { 383 this.frame = frame; 384 } 385 386 /** 387 * @return the intprofitfid 388 */ 389 public int __getIntprofitfid() { 390 return intprofitfid; 391 } 392 393 /** 394 * @param intprofitfid the intprofitfid to set 395 */ 396 public void setIntprofitfid(int intprofitfid) { 397 this.intprofitfid = intprofitfid; 398 } 399 400 /** 401 * @return the inttaxfid 402 */ 403 public int __getInttaxfid() { 404 return inttaxfid; 405 } 406 407 /** 408 * @param inttaxfid the inttaxfid to set 409 */ 410 public void setInttaxfid(int inttaxfid) { 411 this.inttaxfid = inttaxfid; 412 } 413 414 /** 415 * @return the inttaxuid 416 */ 417 public int __getInttaxuid() { 418 return inttaxuid; 419 } 420 421 /** 422 * @param inttaxuid the inttaxuid to set 423 */ 424 public void setInttaxuid(int inttaxuid) { 425 this.inttaxuid = inttaxuid; 426 } 427 428 /** 429 * @return the hierarchypath 430 */ 431 public String __getHierarchypath() { 432 if (hierarchypath == null || hierarchypath.equals("")) { 433 int intp = __getIDS(); 434 do { 435 try { 436 Account p = (Account) getObject(Context.getAccounts(), intp); 437 hierarchypath = Group.GROUPSEPARATOR + p + hierarchypath; 438 intp = p.__getIntparentaccount(); 439 } catch (NodataFoundException ex) { 440 break; 441 } 442 } while (intp >= 1); 443 } 444 return hierarchypath.replaceFirst(Group.GROUPSEPARATOR, ""); 445 } 446 447 /** 448 * @param hierarchypath the hierarchypath to set 449 */ 450 public void setHierarchypath(String hierarchypath) { 451 this.hierarchypath = hierarchypath; 452 } 453 454 @Override 455 public HashMap<String, Object> resolveReferences(HashMap<String, Object> map) { 456 super.resolveReferences(map); 457 458 try { 459 if (map.containsKey("intaccounttype")) { 460 map.put("type", getTypeString(Integer.valueOf(map.get("intaccounttype").toString()))); 461 map.remove("intaccounttype"); 462 } 463 } catch (NumberFormatException numberFormatException) { 464 //already resolved? 465 Log.Debug(numberFormatException); 466 } 467 468 if (map.containsKey("intparentaccount")) { 469 try { 470 try { 471 map.put("parentaccount", DatabaseObject.getObject(Context.getAccounts(), Integer.valueOf(map.get("intparentaccount").toString())).__getCname()); 472 map.remove("intparentaccount"); 473 } catch (NodataFoundException ex) { 474 map.put("parentaccount", null); 475 Log.Debug(this, ex.getMessage()); 476 } 477 } catch (NumberFormatException numberFormatException) { 478 //already resolved? 479 } 480 } 481 482 return map; 483 } 484 485 /** 486 * Safely import a database object from external sources (xml, csv etc)<br/> 487 * Override this for ensuring the existance of DObject specific mandatory values. 488 * @return 489 */ 490 @Override 491 public boolean saveImport() { 492 Log.Debug(this, "Starting import.."); 493 Log.Debug(this, "Setting IDS to -1"); 494 ids = -1; 495 Log.Debug(this, "Setting intaddedby to " + mpv5.db.objects.User.getCurrentUser().__getIDS()); 496 setIntaddedby(mpv5.db.objects.User.getCurrentUser().__getIDS()); 497 498 if (__getGroupsids() <= 0 || !DatabaseObject.exists(Context.getGroup(), __getGroupsids())) { 499 Log.Debug(this, "Setting groups to users group."); 500 setGroupsids(mpv5.db.objects.User.getCurrentUser().__getGroupsids()); 501 } 502 503 return save(); 504 } 505}