/* * To change this template, choose Tools | Templates * and open the template in the editor. */ package model.database; import tools.Helper; import model.object.BikeUsage; import java.sql.ResultSet; import java.sql.SQLException; import java.sql.Timestamp; import java.util.ArrayList; import java.util.List; import java.util.Set; import java.util.logging.Level; import model.object.Payment; import resource.log.ProjectLogger; /** * * @author Yoldark34 <yoldark@gmail.com> */ public class BikeUsageMapper extends AbstractMapper { /** * get all bike usages from the database * * @return ArrayList<BikeUsage> * @throws SQLException * @throws ClassNotFoundException */ public ArrayList<BikeUsage> getAllBikeUsages() throws SQLException, ClassNotFoundException { DbConnection adapter = DbConnection.getDbConnection(); adapter.executeSelectQuery("Select * from " + DataBaseElements.BIKEUSAGE); return (ArrayList<BikeUsage>) adapter.getModelsFromRequest(this); } /** * Insert bikeUsage if id == -1 or update bikeUsage instead * * @param bikeUsage * @return int number of rows */ public int save(BikeUsage bikeUsage) { int nbRows = 0; int idResult = -1; String query; if (bikeUsage.getId() != -1) { query = "UPDATE `" + DataBaseElements.BIKEUSAGE + "` SET "; //query += "`"+DataBaseElements.BIKEUSAGE_ID+"` = '"+bikeUsage.getId()+"',";Can't be updated because used in where query += "`" + DataBaseElements.BIKEUSAGE_IDNEMOUSER + "` = '" + bikeUsage.getIdNemoUser() + "',"; query += "`" + DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE + "` = '" + bikeUsage.getIdBikeUsageType() + "',"; query += "`" + DataBaseElements.BIKEUSAGE_IDBIKE + "` = '" + bikeUsage.getIdBike() + "',"; query += "`" + DataBaseElements.BIKEUSAGE_IDENDSTORAGE + "` = '" + bikeUsage.getIdEndStorage() + "',"; if (bikeUsage.getStartDate() == null) { query += "`" + DataBaseElements.BIKEUSAGE_STARTDATE + "` = " + bikeUsage.getStartDate() + ","; } else { query += "`" + DataBaseElements.BIKEUSAGE_STARTDATE + "` = '" + bikeUsage.getStartDate() + "',"; } if (bikeUsage.getEndDate() == null) { query += "`" + DataBaseElements.BIKEUSAGE_ENDDATE + "` = " + bikeUsage.getEndDate() + ","; } else { query += "`" + DataBaseElements.BIKEUSAGE_ENDDATE + "` = '" + bikeUsage.getEndDate() + "',"; } if (bikeUsage.getComments() == null) { query += "`" + DataBaseElements.BIKEUSAGE_COMMENTS + "` = NULL "; } else { query += "`" + DataBaseElements.BIKEUSAGE_COMMENTS + "` = '" + bikeUsage.getComments() + "' "; } query += "WHERE `" + DataBaseElements.BIKEUSAGE_ID + "` = '" + bikeUsage.getId() + "';"; try { DbConnection adapter = DbConnection.getDbConnection(); nbRows = adapter.executeUpdateQuery(query); } catch (Exception e) { } return nbRows; } else { query = "INSERT INTO " + DataBaseElements.BIKEUSAGE + " ("; //query += "`" + DataBaseElements.BIKEUSAGE_ID + "`,"; query += "`" + DataBaseElements.BIKEUSAGE_IDNEMOUSER + "`,"; query += "`" + DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE + "`,"; query += "`" + DataBaseElements.BIKEUSAGE_IDBIKE + "`,"; query += "`" + DataBaseElements.BIKEUSAGE_IDENDSTORAGE + "`,"; query += "`" + DataBaseElements.BIKEUSAGE_STARTDATE + "`,"; query += "`" + DataBaseElements.BIKEUSAGE_ENDDATE + "`,"; query += "`" + DataBaseElements.BIKEUSAGE_COMMENTS + "` "; query += ") VALUES ("; //query += "'" + bikeUsage.getId() + "',"; query += "'" + bikeUsage.getIdNemoUser() + "',"; query += "'" + bikeUsage.getIdBikeUsageType() + "',"; query += "'" + bikeUsage.getIdBike() + "',"; query += "'" + bikeUsage.getIdEndStorage() + "',"; if (bikeUsage.getStartDate() == null) { query += bikeUsage.getStartDate() + ","; } else { query += "'" + bikeUsage.getStartDate() + "',"; } if (bikeUsage.getEndDate() == null) { query += bikeUsage.getEndDate() + ","; } else { query += "'" + bikeUsage.getEndDate() + "',"; } if (bikeUsage.getComments() == null) { query += "NULL "; } else { query += "'" + bikeUsage.getComments() + "' "; } query += ")"; try { DbConnection adapter = DbConnection.getDbConnection(); idResult = adapter.executeInsertQuery(query); } catch (Exception e) { } return idResult; } } /** * book a number of bikes until the payment or the cancel process. * * @param terminalId * @param nemoUserId * @param numberOfBikes * @param idBikeUsagesToResetEndDate * @param idBikeUsagesToDelete * @return true if book if ok, no if not */ public boolean bookAvailableBikesForTerminal(int terminalId, int nemoUserId, int numberOfBikes, List<Integer> idBikeUsagesToResetEndDate, List<Integer> idBikeUsagesToDelete) { boolean result; String query; ArrayList<BikeUsage> requestResult = null; BikeUsage bu; query = "SELECT "; query += DataBaseElements.BikeUsageColSet.FULL; query += " FROM "; query += DataBaseElements.TERMINAL + " " + DataBaseElements.ALIAS_TERMINAL + ", "; query += DataBaseElements.STOCK + " " + DataBaseElements.ALIAS_STOCK + ", "; query += DataBaseElements.STORAGE + " " + DataBaseElements.ALIAS_STORAGE + ", "; query += DataBaseElements.BIKEUSAGETYPE + " " + DataBaseElements.ALIAS_BIKEUSAGETYPE + ", "; query += DataBaseElements.BIKEUSAGE + " " + DataBaseElements.ALIAS_BIKEUSAGE + " "; query += " WHERE "; query += DataBaseElements.ALIAS_STOCK + "." + DataBaseElements.STOCK_ID + " = " + DataBaseElements.ALIAS_STORAGE + "." + DataBaseElements.STORAGE_IDSTOCK; query += " AND "; query += DataBaseElements.ALIAS_STORAGE + "." + DataBaseElements.STORAGE_ID + " = " + DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDENDSTORAGE; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_ID + " = " + DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_NAME + " = '" + DataBaseElements.BikeUsageType.STOCKING + "'"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_ENDDATE + " is NULL"; query += " AND "; query += DataBaseElements.ALIAS_TERMINAL + "." + DataBaseElements.TERMINAL_ID + " = " + terminalId; query += " AND "; query += DataBaseElements.ALIAS_TERMINAL + "." + DataBaseElements.TERMINAL_IDSTOCK + " = " + DataBaseElements.ALIAS_STOCK + "." + DataBaseElements.STOCK_ID; try { DbConnection adapter = DbConnection.getDbConnection(); adapter.executeSelectQuery(query); requestResult = (ArrayList<BikeUsage>) adapter.getModelsFromRequest(this); } catch (SQLException | ClassNotFoundException ex) { ProjectLogger.log(this, Level.SEVERE, "Erreur d'exécution de la requête de la fonction bookFirstAvailableBikeForTerminal", ex); } if (requestResult != null && !requestResult.isEmpty()) { java.sql.Timestamp sqlToday = Helper.getSqlDateNow(); StorageMapper sm = new StorageMapper(); for (int i = 0; i < numberOfBikes; i++) { bu = requestResult.get(i); idBikeUsagesToResetEndDate.add(bu.getId()); bu.setEndDate(sqlToday); //TODO ask user to login before or create anonymous user //bu.setIdNemoUser(); this.save(bu); bu.setId(-1); bu.setIdNemoUser(-1); BikeUsageTypeMapper btm = new BikeUsageTypeMapper(); bu.setIdBikeUsageType(btm.getBikeUsagesType(DataBaseElements.BikeUsageType.BOOKING).getId()); bu.setIdNemoUser(nemoUserId); bu.setStartDate(sqlToday); bu.setEndDate(null); sm.setStorageUsed(bu.getIdEndStorage()); int newId = this.save(bu); idBikeUsagesToDelete.add(newId); } result = true; } else { result = false; } return result; } /** * rent previously booked bikes for a user * * @param anonymousUserId * @param today * @param idBikeUsagesToDelete * @return true if ok, false if not */ public boolean rentBookedBikesForNemoUser(int anonymousUserId, Timestamp today, List<Integer> idBikeUsagesToDelete) { boolean result; String query; ArrayList<BikeUsage> requestResult = null; BikeUsage bu; boolean error = false; int nbRow; query = "SELECT "; query += DataBaseElements.BikeUsageColSet.FULL; query += " FROM "; query += DataBaseElements.BIKEUSAGETYPE + " " + DataBaseElements.ALIAS_BIKEUSAGETYPE + ", "; query += DataBaseElements.BIKEUSAGE + " " + DataBaseElements.ALIAS_BIKEUSAGE + " "; query += " WHERE "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_ID + " = " + DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_NAME + " = '" + DataBaseElements.BikeUsageType.BOOKING + "'"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_ENDDATE + " is NULL"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDNEMOUSER + " = " + anonymousUserId; try { DbConnection adapter = DbConnection.getDbConnection(); adapter.executeSelectQuery(query); requestResult = (ArrayList<BikeUsage>) adapter.getModelsFromRequest(this); } catch (SQLException | ClassNotFoundException ex) { ProjectLogger.log(this, Level.SEVERE, "Erreur d'exécution de la requête de la fonction bookFirstAvailableBikeForTerminal", ex); } if (requestResult != null && !requestResult.isEmpty()) { StorageMapper sm = new StorageMapper(); for (int i = 0; i < requestResult.size(); i++) { bu = requestResult.get(i); bu.setEndDate(today); //TODO ask user to login before or create anonymous user //bu.setIdNemoUser(); nbRow = this.save(bu); if (nbRow <= 0) { error = true; } bu.setId(-1); BikeUsageTypeMapper btm = new BikeUsageTypeMapper(); bu.setIdBikeUsageType(btm.getBikeUsagesType(DataBaseElements.BikeUsageType.RENTING).getId()); bu.setStartDate(today); bu.setEndDate(null); sm.setStorageAvailable(bu.getIdEndStorage()); int newId = this.save(bu); if (newId <= 0) { error = true; } else { idBikeUsagesToDelete.add(newId); } } result = !error; } else { result = false; } return result; } /** * retrive bike usages from a start date and an id nemo user * * @param idNemoUser * @param startDate * @param bikeSerialNumbers * @return ArrayList<BikeUsage> */ public ArrayList<BikeUsage> getBikesFromNemoUserAndDateForBikes(int idNemoUser, Timestamp startDate, Set<Integer> bikeSerialNumbers) { String query; ArrayList<BikeUsage> result = null; query = "SELECT "; query += DataBaseElements.BikeUsageColSet.FULL; query += " FROM "; query += DataBaseElements.BIKEUSAGETYPE + " " + DataBaseElements.ALIAS_BIKEUSAGETYPE + ", "; query += DataBaseElements.BIKEUSAGE + " " + DataBaseElements.ALIAS_BIKEUSAGE + " "; query += " WHERE "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_ID + " = " + DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDBIKE; query += " IN "; query += " ( "; int size = bikeSerialNumbers.size() - 1; for (Integer idBike : bikeSerialNumbers) { query += "'" + idBike + "'"; if (size != 0) { query += ", "; } size--; } query += " ) "; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_NAME + " = '" + DataBaseElements.BikeUsageType.RENTING + "'"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDNEMOUSER + " = '" + idNemoUser + "'"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_STARTDATE + " = '" + startDate + "'"; try { DbConnection adapter = DbConnection.getDbConnection(); adapter.executeSelectQuery(query); result = (ArrayList<BikeUsage>) adapter.getModelsFromRequest(this); } catch (SQLException | ClassNotFoundException ex) { ProjectLogger.log(this, Level.SEVERE, "Erreur d'exécution de la requête de la fonction bookFirstAvailableBikeForTerminal", ex); } return result; } @Override public Object populateModel(ResultSet row) throws SQLException { BikeUsage obj = new BikeUsage(); if (this.hasColumn(DataBaseElements.BIKEUSAGE_ID, row)) { obj.setId(row.getInt(DataBaseElements.BIKEUSAGE_ID)); } if (this.hasColumn(DataBaseElements.BIKEUSAGE_IDNEMOUSER, row)) { obj.setIdNemoUser(row.getInt(DataBaseElements.BIKEUSAGE_IDNEMOUSER)); } if (this.hasColumn(DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE, row)) { obj.setIdBikeUsageType(row.getInt(DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE)); } if (this.hasColumn(DataBaseElements.BIKEUSAGE_IDBIKE, row)) { obj.setIdBike(row.getInt(DataBaseElements.BIKEUSAGE_IDBIKE)); } if (this.hasColumn(DataBaseElements.BIKEUSAGE_IDENDSTORAGE, row)) { obj.setIdEndStorage(row.getInt(DataBaseElements.BIKEUSAGE_IDENDSTORAGE)); } if (this.hasColumn(DataBaseElements.BIKEUSAGE_STARTDATE, row)) { obj.setStartDate(row.getTimestamp(DataBaseElements.BIKEUSAGE_STARTDATE)); } if (this.hasColumn(DataBaseElements.BIKEUSAGE_ENDDATE, row)) { obj.setEndDate(row.getTimestamp(DataBaseElements.BIKEUSAGE_ENDDATE)); } if (this.hasColumn(DataBaseElements.BIKEUSAGE_COMMENTS, row)) { obj.setComments(row.getString(DataBaseElements.BIKEUSAGE_COMMENTS)); } if (this.hasColumn("number_of_bike_usages", row)) { obj.setNumberOfBikeUsages(row.getInt("number_of_bike_usages")); } return obj; } @Override Object getEmptyModel() { return new BikeUsage(); } /** * reset bikes location process ( cancel book and set available bikes) * * @param idBikeUsagesToResetEndDate * @param idBikeUsagesToDelete * @return */ public boolean resetBikesLocationProcess(ArrayList<Integer> idBikeUsagesToResetEndDate, ArrayList<Integer> idBikeUsagesToDelete) { boolean error = false; boolean result; for (Integer id : idBikeUsagesToResetEndDate) { result = this.resetEndDateForBikeUsage(id); if (!result ) { error = true; } } for (Integer id : idBikeUsagesToDelete) { result = this.deleteBikeUsage(id); if (!result) { error = true; } } return !error; } /** * reset end date for bike usage (in case of cancel) * * @param id * @return boolean */ private boolean resetEndDateForBikeUsage(Integer id) { String query; int nbRows = 0; query = "UPDATE "; query += DataBaseElements.BIKEUSAGE; query += " SET "; query += DataBaseElements.BIKEUSAGE_ENDDATE + " = NULL"; query += " WHERE "; query += DataBaseElements.BIKEUSAGE_ID + " = '" + id + "'"; try { DbConnection adapter = DbConnection.getDbConnection(); nbRows = adapter.executeUpdateQuery(query); } catch (Exception e) { } if (nbRows <= 0) { return false; } return true; } /** * delete a bike usage from id * * @param id * @return boolean */ private boolean deleteBikeUsage(Integer id) { String query; int nbRows = 0; query = "DELETE"; query += " FROM "; query += DataBaseElements.BIKEUSAGE; query += " WHERE "; query += DataBaseElements.BIKEUSAGE_ID + " = '" + id + "';"; try { DbConnection adapter = DbConnection.getDbConnection(); nbRows = adapter.executeUpdateQuery(query); } catch (Exception e) { } if (nbRows <= 0) { return false; } return true; } /** * return bike (after a renting) after a return of a bike.(in a storage) * * @param serialNumber * @param today * @param terminalId * @param payments * @return boolean */ public boolean returnBikeForTerminal(int serialNumber, Timestamp today, int terminalId, List<Payment> payments) { BikeUsageTypeMapper butm = new BikeUsageTypeMapper(); String query; BikeUsage result; query = "SELECT "; query += DataBaseElements.BikeUsageColSet.FULL; query += " FROM "; query += DataBaseElements.BIKEUSAGETYPE + " " + DataBaseElements.ALIAS_BIKEUSAGETYPE + ", "; query += DataBaseElements.BIKEUSAGE + " " + DataBaseElements.ALIAS_BIKEUSAGE + " "; query += " WHERE "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_ID + " = " + DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDBIKE + " = " + serialNumber; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_NAME + " = '" + DataBaseElements.BikeUsageType.RENTING + "'"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_ENDDATE + " is NULL"; try { PaymentMapper pm = new PaymentMapper(); StorageMapper sm = new StorageMapper(); SubscriptionMapper subM = new SubscriptionMapper(); DbConnection adapter = DbConnection.getDbConnection(); adapter.executeSelectQuery(query); result = (BikeUsage) adapter.getModelFromRequest(this); int availableStorage = sm.getFirstAvailableStorageForTerminal(terminalId); result.setEndDate(today); this.save(result); result.setId(-1); result.setIdBikeUsageType(butm.getBikeUsagesType(DataBaseElements.BikeUsageType.STOCKING).getId()); result.setStartDate(today); result.setEndDate(null); result.setIdEndStorage(availableStorage); this.save(result); sm.setStorageUsed(availableStorage); for (Payment payment : payments) { if (payment.getAmount() > 0) { pm.save(payment); } subM.closeSubscriptionIfFinish(payment.getIdSubscription(), today); } return true; } catch (SQLException | ClassNotFoundException ex) { ProjectLogger.log(this, Level.SEVERE, "Erreur d'exécution de la requête de la fonction bookFirstAvailableBikeForTerminal", ex); } return false; } /** * get number of rented bikes for a user from a start date * * @param idNemoUser * @param startDate * @return number of rented bikes */ int getNumberOfRentedBikes(int idNemoUser, Timestamp startDate) { BikeUsageTypeMapper butm = new BikeUsageTypeMapper(); String query; BikeUsage result = (BikeUsage) this.getEmptyModel(); query = "SELECT "; query += " COUNT(*) as 'number_of_bike_usages'"; query += " FROM "; query += DataBaseElements.BIKEUSAGETYPE + " " + DataBaseElements.ALIAS_BIKEUSAGETYPE + ", "; query += DataBaseElements.BIKEUSAGE + " " + DataBaseElements.ALIAS_BIKEUSAGE + " "; query += " WHERE "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_ID + " = " + DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_IDBIKEUSAGETYPE; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGETYPE + "." + DataBaseElements.BIKEUSAGETYPE_NAME + " = '" + DataBaseElements.BikeUsageType.RENTING + "'"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_ENDDATE + " is NULL"; query += " AND "; query += DataBaseElements.ALIAS_BIKEUSAGE + "." + DataBaseElements.BIKEUSAGE_STARTDATE + " = '" + startDate + "'"; try { DbConnection adapter = DbConnection.getDbConnection(); adapter.executeSelectQuery(query); result = (BikeUsage) adapter.getModelFromRequest(this); } catch (SQLException | ClassNotFoundException ex) { ProjectLogger.log(this, Level.SEVERE, "Erreur d'exécution de la requête de la fonction bookFirstAvailableBikeForTerminal", ex); } return result.getNumberOfBikeUsages(); } }