// // Class: DBManager // Current CLR: 4.0.30319.34209 // System: Microsoft Visual Studio 10.0 // Author: dani // Created: 3/10/2015 7:25:55 AM // // Copyright (c) 2015 Informatikbüro Daniel Schick. All rights reserved. using System; using System.Collections.Generic; using System.Data; using System.Data.SqlClient; using log4net; namespace bsmd.database { public class DBManager { private SqlConnection _con; private static DBManager _instance; private static ILog _log = LogManager.GetLogger(typeof(DBManager)); #region Properties public static DBManager Instance { get { if (_instance == null) _instance = new DBManager(); return _instance; } } public string ConnectionString { get; set; } #endregion #region public DB funcs public bool Connect(string dbConnectionString) { try { _con = new SqlConnection(dbConnectionString); _con.Open(); return true; } catch (Exception ex) { _log.Error("DBManager cannot connect", ex); return false; } } public void Disconnect() { if ((this._con != null) && (this._con.State == ConnectionState.Open)) this._con.Close(); } #endregion #region public helper funcs public Dictionary GetToSendMessageCoreList() { MessageCore aMessageCore = new MessageCore(); SqlCommand cmd = new SqlCommand(); Message.LoadFilter filter = Message.LoadFilter.BSMDSTATUS; aMessageCore.PrepareLoadCommand(cmd, filter, Message.BSMDStatus.TOSEND); SqlDataReader reader = this.PerformCommand(cmd); List cores = aMessageCore.LoadList(reader); Dictionary result = new Dictionary(); foreach (MessageCore core in cores) result.Add(core.Id.Value, core); return result; } public MessageCore GetHerbergFormMessage(Guid herbergFormGuid) { MessageCore aMessageCore = new MessageCore(); SqlCommand cmd = new SqlCommand(); aMessageCore.PrepareLoadCommand(cmd, Message.LoadFilter.HERBERG_FORMGUID, herbergFormGuid); SqlDataReader reader = this.PerformCommand(cmd); List cores = aMessageCore.LoadList(reader); if (cores.Count > 1) _log.WarnFormat("Herberg form message: {0} cores found for guid {1}", cores.Count, herbergFormGuid); if(cores.Count > 0) return (MessageCore) cores[0]; return null; } public List GetToSendMessageList() { Message aMessage = new Message(); SqlCommand cmd = new SqlCommand(); Message.LoadFilter filter = Message.LoadFilter.BSMDSTATUS; aMessage.PrepareLoadCommand(cmd, filter, Message.BSMDStatus.TOSEND); SqlDataReader reader = this.PerformCommand(cmd); List messages = aMessage.LoadList(reader); List messageList = new List(); foreach (Message message in messages) messageList.Add(message); List result = this.LoadMessageDependencies(messageList); return result; } public Dictionary GetReportingPartyDict() { ReportingParty aRep = new ReportingParty(); SqlCommand cmd = new SqlCommand(); aRep.PrepareLoadCommand(cmd, Message.LoadFilter.ALL); SqlDataReader reader = this.PerformCommand(cmd); List reportingParties = aRep.LoadList(reader); Dictionary result = new Dictionary(); foreach (ReportingParty rp in reportingParties) result.Add(rp.Id.Value, rp); return result; } public void Save(DatabaseEntity entity) { SqlCommand cmd = new SqlCommand(); entity.PrepareSave(cmd); int queryResult = this.PerformNonQuery(cmd); switch(queryResult) { case 1: _log.InfoFormat("Message {0} saved", entity.Id); break; case 0: _log.WarnFormat("Message {0} save affected no rows", entity.Id); break; case -1: _log.WarnFormat("Message {0} save: error occurred", entity.Id); break; default: _log.WarnFormat("Message {0} save affected {1} rows", entity.Id, queryResult); break; } } public void Save(MessageCore core) { SqlCommand cmd = new SqlCommand(); core.PrepareSave(cmd); int queryResult = this.PerformNonQuery(cmd); if (queryResult == 1) _log.InfoFormat("MessageCore {0} saved", core.Id); else _log.WarnFormat("MessageCore {0} save affected {1} rows", core.Id, queryResult); } #endregion #region internal/private funcs internal List LoadMessageDependencies(List messageList) { Dictionary messageCoreDict = this.GetToSendMessageCoreList(); Dictionary reportingPartyDict = this.GetReportingPartyDict(); List result = new List(); // Zuordnung MessageCore,Zuordnung Reporting party Message.AssignReportingParties(messageList, reportingPartyDict); Message.AssignMessageCores(messageList, messageCoreDict); foreach (Message message in messageList) { this.LoadErrorList(message); this.LoadViolationList(message); SqlCommand cmd = new SqlCommand(); DatabaseEntity msgClass = DBManager.CreateMessage(message.MessageNotificationClass); if (msgClass != null) { msgClass.PrepareLoadCommand(cmd, Message.LoadFilter.MESSAGEHEADER, message.Id); SqlDataReader reader = this.PerformCommand(cmd); List statList = msgClass.LoadList(reader); if (statList.Count > 0) message.DerivedMessage = statList[0]; ((IMessageClass)msgClass).MessageHeader = message; this.LoadDependingLists(msgClass); result.Add(msgClass); } else { _log.ErrorFormat("cannot create a message class for notification type {0}", message.MessageNotificationClass); result.Add(message); } } return result; } #region CreateMessage() /// /// factory method for messages by type /// internal static DatabaseEntity CreateMessage(Message.NotificationClass notificationClass) { DatabaseEntity result = null; switch (notificationClass) { case Message.NotificationClass.NOA_NOD: result = new NOA_NOD(); break; case Message.NotificationClass.ATA: result = new ATA(); break; case Message.NotificationClass.ATD: result = new ATD(); break; case Message.NotificationClass.SEC: result = new SEC(); break; case Message.NotificationClass.POBA: result = new POBA(); break; case Message.NotificationClass.POBD: result = new POBD(); break; case Message.NotificationClass.NAME: result = new NAME(); break; case Message.NotificationClass.TIEFA: result = new TIEFA(); break; case Message.NotificationClass.TIEFD: result = new TIEFD(); break; case Message.NotificationClass.BKRA: result = new BRKA(); break; case Message.NotificationClass.BKRD: result = new BRKD(); break; case Message.NotificationClass.STAT: result = new STAT(); break; case Message.NotificationClass.LADG: result = new LADG(); break; case Message.NotificationClass.INFO: result = new INFO(); break; case Message.NotificationClass.SERV: result = new SERV(); break; case Message.NotificationClass.PRE72H: result = new PRE72H(); break; case Message.NotificationClass.MDH: result = new MDH(); break; case Message.NotificationClass.WAS: result = new WAS(); break; case Message.NotificationClass.CREW: result = new CREW(); break; case Message.NotificationClass.PAS: result = new PAS(); break; case Message.NotificationClass.BPOL: result = new BPOL(); break; case Message.NotificationClass.TOWA: result = new TOWA(); break; case Message.NotificationClass.TOWD: result = new TOWD(); break; case Message.NotificationClass.HAZA: case Message.NotificationClass.HAZD: _log.WarnFormat("CreateMessage: message type {0} is not supported", notificationClass.ToString()); break; default: break; // VISIT, TRANSIT } return result; } #endregion /// /// Loads inner lists / collections /// internal void LoadDependingLists(DatabaseEntity databaseEntity) { SqlCommand cmd = new SqlCommand(); #region MDH if (databaseEntity.GetType().IsAssignableFrom(typeof(MDH))) { MDH mdh = databaseEntity as MDH; PortOfCallLast30Days poc30 = new PortOfCallLast30Days(); poc30.PrepareLoadCommand(cmd, Message.LoadFilter.MDH_ID, mdh.Id); SqlDataReader reader = this.PerformCommand(cmd); List poc30s = poc30.LoadList(reader); foreach (PortOfCallLast30Days apoc30 in poc30s) { mdh.PortOfCallLast30Days.Add(apoc30); apoc30.MDH = mdh; this.LoadDependingLists(apoc30); } } #endregion #region PortOfCallLast30Days if (databaseEntity.GetType().IsAssignableFrom(typeof(PortOfCallLast30Days))) { PortOfCallLast30Days poc30 = databaseEntity as PortOfCallLast30Days; PortOfCallLast30DaysCrewJoinedShip poc30s = new PortOfCallLast30DaysCrewJoinedShip(); poc30s.PrepareLoadCommand(cmd, Message.LoadFilter.POC30_ID, poc30.Id); SqlDataReader reader = this.PerformCommand(cmd); List poc30Names = poc30s.LoadList(reader); foreach (PortOfCallLast30DaysCrewJoinedShip poc30Name in poc30Names) { poc30.CrewJoinedShip.Add(poc30Name); poc30Name.PortOfCallLast30Days = poc30; } } #endregion #region SEC if (databaseEntity.GetType().IsAssignableFrom(typeof(SEC))) { SEC sec = databaseEntity as SEC; LastTenPortFacilitiesCalled ltp = new LastTenPortFacilitiesCalled(); ltp.PrepareLoadCommand(cmd, Message.LoadFilter.SEC_ID, sec.Id); SqlDataReader reader = this.PerformCommand(cmd); List ltps = ltp.LoadList(reader); foreach (LastTenPortFacilitiesCalled altp in ltps) { sec.LastTenPortFacilitesCalled.Add(altp); altp.SEC = sec; } cmd = new SqlCommand(); ShipToShipActivitiesDuringLastTenPortFacilitiesCalled sts = new ShipToShipActivitiesDuringLastTenPortFacilitiesCalled(); sts.PrepareLoadCommand(cmd, Message.LoadFilter.SEC_ID, sec.Id); reader = this.PerformCommand(cmd); List stss = sts.LoadList(reader); foreach (ShipToShipActivitiesDuringLastTenPortFacilitiesCalled asts in stss) { sec.ShipToShipActivitiesDuringLastTenPortFacilitiesCalled.Add(asts); asts.SEC = sec; } } #endregion #region WAS if(databaseEntity.GetType().IsAssignableFrom(typeof(WAS))) { WAS was = databaseEntity as WAS; WasteDisposalServiceProvider wdsp = new WasteDisposalServiceProvider(); wdsp.PrepareLoadCommand(cmd, Message.LoadFilter.WAS_ID, was.Id); SqlDataReader reader = this.PerformCommand(cmd); List wdsps = wdsp.LoadList(reader); foreach (WasteDisposalServiceProvider awdsp in wdsps) { was.WasteDisposalServiceProvider.Add(awdsp); awdsp.WAS = was; this.LoadDependingLists(awdsp); } } #endregion #region WasteDisposalServiceProvider if(databaseEntity.GetType().IsAssignableFrom(typeof(WasteDisposalServiceProvider))) { WasteDisposalServiceProvider wdsp = databaseEntity as WasteDisposalServiceProvider; Waste waste = new Waste(); waste.PrepareLoadCommand(cmd, Message.LoadFilter.WDSP_ID, wdsp.Id); SqlDataReader reader = this.PerformCommand(cmd); List wastes = wdsp.LoadList(reader); foreach (Waste aWaste in wastes) { wdsp.Waste.Add(aWaste); aWaste.WasteDisposalServiceProvider = wdsp; } } #endregion } internal void LoadErrorList(Message message) { MessageError aMessageError = new MessageError(); SqlCommand cmd = new SqlCommand(); aMessageError.PrepareLoadCommand(cmd, Message.LoadFilter.MESSAGEHEADER, message.Id); SqlDataReader reader = this.PerformCommand(cmd); List errorList = aMessageError.LoadList(reader); foreach (MessageError error in errorList) message.ErrorList.Add(error); } internal void LoadViolationList(Message message) { MessageViolation aMessageViolation = new MessageViolation(); SqlCommand cmd = new SqlCommand(); aMessageViolation.PrepareLoadCommand(cmd, Message.LoadFilter.MESSAGEHEADER, message.Id); SqlDataReader reader = this.PerformCommand(cmd); List violationList = aMessageViolation.LoadList(reader); foreach (MessageViolation violation in violationList) message.ViolationList.Add(violation); } #region DB access methods internal SqlDataReader PerformCommand(SqlCommand cmd) { try { cmd.Connection = this._con; SqlDataReader reader = cmd.ExecuteReader(); return reader; } catch (SqlException ex) { System.Diagnostics.Trace.WriteLine("SQL Exception:" + ex.Message); _log.Error("Error performing command", ex); return null; } } internal int PerformNonQuery(SqlCommand cmd) { try { cmd.Connection = this._con; return cmd.ExecuteNonQuery(); } catch (SqlException ex) { System.Diagnostics.Trace.WriteLine("SQL Exception:" + ex.Message); _log.Error("Error performing command", ex); return -1; } } #endregion #endregion } }