Java tutorial
/* * To change this license header, choose License Headers in Project Properties. * To change this template file, choose Tools | Templates * and open the template in the editor. */ package synergyj; import java.sql.Connection; import java.sql.PreparedStatement; import java.io.File; import java.sql.DriverManager; import java.sql.ResultSet; import java.sql.SQLException; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.logging.Level; import javax.swing.JFileChooser; import javax.swing.JOptionPane; import javax.swing.JTextArea; import nwd.tools.FileSystemHandler; import org.apache.commons.io.FilenameUtils; /** * * @author Brent */ class ListController implements IController { private final FileSystemHandler fsh = new FileSystemHandler(); private JTextArea taDetail; private JFileChooser dlgFileChooser; private final Map<Integer, String> listIdsToNameMap = new HashMap<>(); //key is for list name private final MultiMap<String, ToDoItem> items = new MultiMap<>(); private final MultiMap<String, ToDoItem> staging = new MultiMap<>(); private Connection conn = null; private PreparedStatement pSt = null; //private final File defaultExportDir = // new File("C:/NWD-SYNC/sandbox/tablet/synergy/"); private final File defaultImportDir = new File("C:/NWD/synergy/toBeImported/"); private final List<File> exportDirectories = new ArrayList<>(); private final List<File> filesForConsumption = new ArrayList<>(); public ListController() { exportDirectories.add(new File("C:/NWD-SYNC/tablet/NWD/synergy/")); exportDirectories.add(new File("C:/NWD-SYNC/phone/NWD/synergy/")); } private String removeTimeStamp(String fileNameWithoutExt) { SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss"); sdf.setLenient(false); int idx = fileNameWithoutExt.lastIndexOf("-"); String timestamp = fileNameWithoutExt.substring(idx + 1); try { //validate date by parsing it sdf.parse(timestamp); //if parse didn't error, we're good fileNameWithoutExt = fileNameWithoutExt.substring(0, idx); } catch (ParseException ex) { Logger.log(ex.getMessage()); } return fileNameWithoutExt; } private void importFile(File f) { try { String listName = FilenameUtils.removeExtension(f.getName()); listName = removeTimeStamp(listName); filesForConsumption.add(f); List<String> lines = fsh.getLines(f.getAbsolutePath(), "UTF-8"); for (String l : lines) { String item = l.trim(); if (item.startsWith("completed={") && item.endsWith("}")) { item = item.replace("completed={", ""); item = item.replace("}", ""); ToDoItem i = new ToDoItem(); i.setText(item); i.setCompleted(true); i.setListName(listName); items.add(listName, i); } else { ToDoItem i = new ToDoItem(); i.setText(item); i.setCompleted(false); i.setListName(listName); items.add(listName, i); } } displayItemsWithHeader(items, "imported from: " + f.getAbsolutePath()); } catch (Exception ex) { Logger.log(ex.getMessage()); } } @Override public void performImport() { dlgFileChooser.setCurrentDirectory(defaultImportDir); dlgFileChooser.setMultiSelectionEnabled(true); if (dlgFileChooser.showOpenDialog(null) == javax.swing.JFileChooser.APPROVE_OPTION) { // // File f = dlgFileChooser.getSelectedFile(); // // importFile(f); for (File f : dlgFileChooser.getSelectedFiles()) { importFile(f); } } } @Override public void performExport() { String fNames = ""; for (File exportDir : exportDirectories) { for (String listName : staging.keySet()) { dlgFileChooser.setCurrentDirectory(exportDir); String fName = listName + ".txt"; dlgFileChooser.setSelectedFile(new File(exportDir, fName)); if (dlgFileChooser.showOpenDialog(null) == javax.swing.JFileChooser.APPROVE_OPTION) { File f = dlgFileChooser.getSelectedFile(); fsh.writeLines(f.getAbsolutePath(), toStringList(staging.get(listName))); //in case a different file name was selected fName = f.getName(); if (fNames.length() > 0) { fNames += ", "; } fNames += fName; } } } displayItemsWithHeader(staging, "exported to: " + fNames); } private List<String> toStringList(List<ToDoItem> lst) { List<String> strLst = new ArrayList<>(); for (ToDoItem tdi : lst) { strLst.add(tdi.getText()); } return strLst; } @Override public void performExportStaging() { staging.clear(); for (ToDoItem tdi : getPendingItems()) { staging.add(tdi.getListName(), tdi); } displayItemsWithHeader(staging, "staged for export:"); } @Override public void initController(JTextArea taDetail, JFileChooser dlgFileChooser) { this.taDetail = taDetail; this.dlgFileChooser = dlgFileChooser; } private void displayItemsWithHeader(MultiMap<String, ToDoItem> itemsMap, String itemPathHeader) { String output = itemPathHeader; for (String listName : itemsMap.keySet()) { output += "\n\nListName={" + listName + "}:\n\n"; for (ToDoItem tdi : itemsMap.get(listName)) { output += tdi + "\n"; } } taDetail.setText(output); } @Override public void performDbSyncNew() { for (ToDoItem tdi : items.getAllValues()) { if (!existsInDatabase(tdi)) { addToDatabase(tdi); } } } private Connection getDbConnection() throws ClassNotFoundException, SQLException { // This will load the MySQL driver, each DB has its own driver Class.forName("com.mysql.jdbc.Driver"); // Setup the connection with the DB return DriverManager .getConnection("jdbc:mysql://localhost/nwd?" + "user=swingaccess&" + "password=vbtjJAmU7QsYMEZH"); } private int getEnsuredIdForListName(String listName) { if (getIdForListName(listName) < 0) { addListToDatabase(listName); } return getIdForListName(listName); } private int getIdForListName(String listName) { int id = -1; try { conn = getDbConnection(); String stmt = "SELECT ListId, ListName FROM todolists WHERE ListName = ?"; pSt = conn.prepareStatement(stmt); pSt.setString(1, listName); ResultSet rs = pSt.executeQuery(); if (rs.next()) { id = rs.getInt("ListId"); } } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } return id; } private List<String> getIdList(ToDoItem item) { List<String> lst = new ArrayList<>(); try { int listId = getEnsuredIdForListName(item.getListName()); conn = getDbConnection(); String stmt = "SELECT ToDoItemId FROM todoitems " + "WHERE ToDoItemText = ? " + "AND ListId = ?"; pSt = conn.prepareStatement(stmt); pSt.setString(1, item.getText()); pSt.setInt(2, listId); ResultSet rs = pSt.executeQuery(); while (rs.next()) { lst.add(rs.getString("ToDoItemId")); } } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } return lst; } private boolean existsInDatabase(ToDoItem item) { try { int listId = getEnsuredIdForListName(item.getListName()); conn = getDbConnection(); String stmt = "SELECT * FROM todoitems " + "WHERE ToDoItemText = ? " + "AND ListId = ? "; pSt = conn.prepareStatement(stmt); pSt.setString(1, item.getText()); pSt.setInt(2, listId); ResultSet rs = pSt.executeQuery(); //per javadoc, returns false if no rows if (rs.isBeforeFirst()) { Logger.log("ToDoItemText={" + item.getText() + "} ListName={" + item.getListName() + "} found in database."); } else { Logger.log("ToDoItemText={" + item.getText() + "} ListName={" + item.getListName() + "} not found in database."); return false; } } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } return true; } private void addListToDatabase(String listName) { Logger.log("adding ListName={" + listName + "}"); try { conn = getDbConnection(); String stmt = "INSERT INTO todolists (ListName) Values (?)"; pSt = conn.prepareStatement(stmt); pSt.setString(1, listName); pSt.executeUpdate(); } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } } private void addToDatabase(ToDoItem item) { Logger.log("adding ToDoItemText={" + item + "}"); try { int listId = getEnsuredIdForListName(item.getListName()); conn = getDbConnection(); String stmt = "INSERT INTO todoitems (ToDoItemText, ListId) " + "VALUES (?, ?)"; pSt = conn.prepareStatement(stmt); pSt.setString(1, item.getText()); pSt.setInt(2, listId); pSt.executeUpdate(); } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } } @Override public void performDbSyncCompleted() { for (ToDoItem item : items.getAllValues()) { if (item.isCompleted()) { List<String> lst = getIdList(item); if (lst.isEmpty()) { Logger.log("ToDoItemText={" + item + "} not found in db"); } else if (lst.size() > 1) { Logger.log("completion request ambiguous for " + "ToDoItemText={" + item + "}, " + "too many rows"); } else if (lst.size() == 1) { markCompleted(lst.get(0)); } } } } void markCompleted(String toDoItemId) { Logger.log("completing item with ToDoItemId={" + toDoItemId + "}"); try { conn = getDbConnection(); String stmt = "UPDATE todoitems " + "SET ToDoItemCompleted = 1 " + "WHERE ToDoItemId = ?"; pSt = conn.prepareStatement(stmt); pSt.setString(1, toDoItemId); pSt.executeUpdate(); } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } } private void refreshListIdsToNameMap() { listIdsToNameMap.clear(); try { conn = getDbConnection(); String stmt = "SELECT ListId, ListName " + "FROM todolists"; pSt = conn.prepareStatement(stmt); ResultSet rs = pSt.executeQuery(); while (rs.next()) { listIdsToNameMap.put(rs.getInt("ListId"), rs.getString("ListName")); } } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } } List<ToDoItem> getPendingItems() { List<ToDoItem> lst = new ArrayList<>(); try { refreshListIdsToNameMap(); conn = getDbConnection(); String stmt = "SELECT ToDoItemText, ListId " + "FROM todoitems " + "WHERE ToDoItemCompleted = 0"; pSt = conn.prepareStatement(stmt); ResultSet rs = pSt.executeQuery(); while (rs.next()) { ToDoItem tdi = new ToDoItem(); tdi.setText(rs.getString("ToDoItemText")); tdi.setCompleted(false); tdi.setListName(listIdsToNameMap.get(rs.getInt("ListId"))); lst.add(tdi); } } catch (ClassNotFoundException | SQLException ex) { Logger.log(ex.getMessage()); } finally { try { if (pSt != null) { pSt.close(); } if (conn != null) { conn.close(); } } catch (SQLException ex) { Logger.log(ex.getMessage()); } } return lst; } @Override public void consume() { String filesList = ""; for (File f : filesForConsumption) { f.delete(); if (filesList.length() > 0) { filesList += ", "; } filesList += f.getName(); } taDetail.setText("consumed: " + filesList); filesForConsumption.clear(); } }