diff --git a/Backend/Data/Configurations/ConfigurationBase.cs b/Backend/Data/Configurations/ConfigurationBase.cs
index 205004ee..c0f416b1 100644
--- a/Backend/Data/Configurations/ConfigurationBase.cs
+++ b/Backend/Data/Configurations/ConfigurationBase.cs
@@ -13,9 +13,12 @@
// You should have received a copy of the GNU General Public License
// along with AlarmWorkflow. If not, see .
+using System;
using System.ComponentModel.DataAnnotations.Schema;
-using System.Data.Entity.ModelConfiguration;
+using System.Linq.Expressions;
using AlarmWorkflow.Backend.Data.Types;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Metadata.Builders;
namespace AlarmWorkflow.Backend.Data.Configurations
{
@@ -23,34 +26,17 @@ namespace AlarmWorkflow.Backend.Data.Configurations
/// Abstract base class for a entity type configuration.
///
///
- abstract class ConfigurationBase : EntityTypeConfiguration where TEntity : EntityBase
+ abstract class ConfigurationBase : IEntityTypeConfiguration where TEntity : EntityBase
{
- #region Constructors
-
- ///
- /// Initializes a new instance of the class.
- ///
- protected ConfigurationBase()
- : base()
- {
- ToTable(GetTableName());
-
- MapKeys();
- }
-
- #endregion
-
#region Methods
- ///
- /// Performs automatic mapping of the key.
- ///
- protected virtual void MapKeys()
+ public virtual void Configure(EntityTypeBuilder builder)
{
- HasKey(e => e.Id);
- Property(e => e.Id).HasColumnName("id").HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
+ builder.ToTable(GetTableName());
+ builder.HasKey(e => e.Id);
+ builder.Property(e => e.Id).HasColumnName("id").ValueGeneratedOnAdd();
}
-
+
///
/// When overridden in a derived class, customizes the table name for the provided .
///
diff --git a/Backend/Data/Configurations/DispositionedResourceConfiguration.cs b/Backend/Data/Configurations/DispositionedResourceConfiguration.cs
index abc2bd13..834b3995 100644
--- a/Backend/Data/Configurations/DispositionedResourceConfiguration.cs
+++ b/Backend/Data/Configurations/DispositionedResourceConfiguration.cs
@@ -14,23 +14,24 @@
// along with AlarmWorkflow. If not, see .
using AlarmWorkflow.Backend.Data.Types;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Metadata.Builders;
namespace AlarmWorkflow.Backend.Data.Configurations
{
+ // ReSharper disable once UnusedMember.Global
class DispositionedResourceConfiguration : ConfigurationBase
{
- #region Constructors
+ #region Methods
- public DispositionedResourceConfiguration()
+ public override void Configure(EntityTypeBuilder builder)
{
- Property(dr => dr.OperationId).HasColumnName("operation_id").IsRequired();
- Property(dr => dr.Timestamp).HasColumnName("timestamp").IsRequired();
- Property(dr => dr.EmkResourceId).HasColumnName("emkresourceid").IsRequired();
- }
-
- #endregion
+ base.Configure(builder);
- #region Methods
+ builder.Property(dr => dr.OperationId).HasColumnName("operation_id").IsRequired();
+ builder.Property(dr => dr.Timestamp).HasColumnName("timestamp").IsRequired();
+ builder.Property(dr => dr.EmkResourceId).HasColumnName("emkresourceid").IsRequired();
+ }
protected override string GetTableName()
{
diff --git a/Backend/Data/Configurations/OperationConfiguration.cs b/Backend/Data/Configurations/OperationConfiguration.cs
index 18d7512b..8557d4b6 100644
--- a/Backend/Data/Configurations/OperationConfiguration.cs
+++ b/Backend/Data/Configurations/OperationConfiguration.cs
@@ -14,68 +14,64 @@
// along with AlarmWorkflow. If not, see .
using AlarmWorkflow.Backend.Data.Types;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Metadata.Builders;
namespace AlarmWorkflow.Backend.Data.Configurations
{
+ // ReSharper disable once UnusedMember.Global
class OperationConfiguration : ConfigurationBase
{
- #region Constructors
+ #region Methods
- public OperationConfiguration()
+ public override void Configure(EntityTypeBuilder builder)
{
- Property(o => o.IsAcknowledged).HasColumnName("acknowledged").IsRequired();
- Property(o => o.Guid).HasColumnName("operationguid").IsRequired();
- Property(o => o.OperationNumber).HasColumnName("operationnumber");
- Property(o => o.IncomeAt).HasColumnName("timestampincome");
- Property(o => o.AlarmAt).HasColumnName("timestampalarm");
- Property(o => o.Messenger).HasColumnName("messenger");
- Property(o => o.Comment).HasColumnName("comment");
- Property(o => o.Plan).HasColumnName("plan");
- Property(o => o.Picture).HasColumnName("picture");
- Property(o => o.Priority).HasColumnName("priority");
+ base.Configure(builder);
- Property(o => o.Einsatzort.Street).HasColumnName("einsatzortstreet");
- Property(o => o.Einsatzort.StreetNumber).HasColumnName("einsatzortstreetnumber");
- Property(o => o.Einsatzort.City).HasColumnName("einsatzortcity");
- Property(o => o.Einsatzort.ZipCode).HasColumnName("einsatzortzipcode");
- Property(o => o.Einsatzort.Intersection).HasColumnName("einsatzortintersection");
- Property(o => o.Einsatzort.Property).HasColumnName("einsatzortproperty");
- Property(o => o.Einsatzort.Location).HasColumnName("einsatzortlocation");
- Property(o => o.Einsatzort.GeoLatLng).HasColumnName("einsatzortlatlng");
+ builder.Property(o => o.IsAcknowledged).HasColumnName("acknowledged").IsRequired();
+ builder.Property(o => o.Guid).HasColumnName("operationguid").IsRequired();
+ builder.Property(o => o.OperationNumber).HasColumnName("operationnumber");
+ builder.Property(o => o.IncomeAt).HasColumnName("timestampincome");
+ builder.Property(o => o.AlarmAt).HasColumnName("timestampalarm");
+ builder.Property(o => o.Messenger).HasColumnName("messenger");
+ builder.Property(o => o.Comment).HasColumnName("comment");
+ builder.Property(o => o.Plan).HasColumnName("plan");
+ builder.Property(o => o.Picture).HasColumnName("picture");
+ builder.Property(o => o.Priority).HasColumnName("priority");
- Property(o => o.Zielort.Street).HasColumnName("zielortstreet");
- Property(o => o.Zielort.StreetNumber).HasColumnName("zielortstreetnumber");
- Property(o => o.Zielort.City).HasColumnName("zielortcity");
- Property(o => o.Zielort.ZipCode).HasColumnName("zielortzipcode");
- Property(o => o.Zielort.Intersection).HasColumnName("zielortintersection");
- Property(o => o.Zielort.Property).HasColumnName("zielortproperty");
- Property(o => o.Zielort.Location).HasColumnName("zielortlocation");
- Property(o => o.Zielort.GeoLatLng).HasColumnName("zielortlatlng");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.Street).HasColumnName("einsatzortstreet");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.StreetNumber).HasColumnName("einsatzortstreetnumber");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.City).HasColumnName("einsatzortcity");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.ZipCode).HasColumnName("einsatzortzipcode");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.Intersection).HasColumnName("einsatzortintersection");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.Property).HasColumnName("einsatzortproperty");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.Location).HasColumnName("einsatzortlocation");
+ builder.OwnsOne(o => o.Einsatzort).Property(o => o.GeoLatLng).HasColumnName("einsatzortlatlng");
- Property(o => o.Keywords.Keyword).HasColumnName("keyword");
- Property(o => o.Keywords.EmergencyKeyword).HasColumnName("keywordmisc");
- Property(o => o.Keywords.B).HasColumnName("keywordb");
- Property(o => o.Keywords.R).HasColumnName("keywordr");
- Property(o => o.Keywords.S).HasColumnName("keywords");
- Property(o => o.Keywords.T).HasColumnName("keywordt");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.Street).HasColumnName("zielortstreet");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.StreetNumber).HasColumnName("zielortstreetnumber");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.City).HasColumnName("zielortcity");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.ZipCode).HasColumnName("zielortzipcode");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.Intersection).HasColumnName("zielortintersection");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.Property).HasColumnName("zielortproperty");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.Location).HasColumnName("zielortlocation");
+ builder.OwnsOne(o => o.Zielort).Property(o => o.GeoLatLng).HasColumnName("zielortlatlng");
- Property(o => o.Loops).HasColumnName("loopscsv");
- Property(o => o.CustomData).HasColumnName("customdatajson");
+ builder.OwnsOne(o => o.Keywords).Property(o => o.Keyword).HasColumnName("keyword");
+ builder.OwnsOne(o => o.Keywords).Property(o => o.EmergencyKeyword).HasColumnName("keywordmisc");
+ builder.OwnsOne(o => o.Keywords).Property(o => o.B).HasColumnName("keywordb");
+ builder.OwnsOne(o => o.Keywords).Property(o => o.R).HasColumnName("keywordr");
+ builder.OwnsOne(o => o.Keywords).Property(o => o.S).HasColumnName("keywords");
+ builder.OwnsOne(o => o.Keywords).Property(o => o.T).HasColumnName("keywordt");
- HasMany(o => o.Resources)
- .WithRequired(r => r.Operation)
- .HasForeignKey(r => r.OperationId)
- .WillCascadeOnDelete();
+ builder.Property(o => o.Loops).HasColumnName("loopscsv");
+ builder.Property(o => o.CustomData).HasColumnName("customdatajson");
- HasMany(o => o.DispositionedResources)
- .WithRequired(dr => dr.Operation)
- .HasForeignKey(dr => dr.OperationId)
- .WillCascadeOnDelete();
- }
+ builder.HasMany(o => o.Resources).WithOne(r => r.Operation).IsRequired().OnDelete(DeleteBehavior.Cascade);
- #endregion
+ builder.HasMany(o => o.DispositionedResources).WithOne(r => r.Operation).IsRequired().OnDelete(DeleteBehavior.Cascade);
+ }
- #region Methods
protected override string GetTableName()
{
diff --git a/Backend/Data/Configurations/OperationResourceConfiguration.cs b/Backend/Data/Configurations/OperationResourceConfiguration.cs
index a456d19a..835b95c5 100644
--- a/Backend/Data/Configurations/OperationResourceConfiguration.cs
+++ b/Backend/Data/Configurations/OperationResourceConfiguration.cs
@@ -14,24 +14,25 @@
// along with AlarmWorkflow. If not, see .
using AlarmWorkflow.Backend.Data.Types;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Metadata.Builders;
namespace AlarmWorkflow.Backend.Data.Configurations
{
+ // ReSharper disable once UnusedMember.Global
class OperationResourceConfiguration : ConfigurationBase
{
- #region Constructors
+ #region Methods
- public OperationResourceConfiguration()
+ public override void Configure(EntityTypeBuilder builder)
{
- Property(or => or.OperationId).HasColumnName("operation_id").IsRequired();
- Property(or => or.Timestamp).HasColumnName("timestamp");
- Property(or => or.FullName).HasColumnName("fullname");
- Property(or => or.Equipment).HasColumnName("equipmentcsv");
- }
-
- #endregion
+ base.Configure(builder);
- #region Methods
+ builder.Property(or => or.OperationId).HasColumnName("operation_id").IsRequired();
+ builder.Property(or => or.Timestamp).HasColumnName("timestamp");
+ builder.Property(or => or.FullName).HasColumnName("fullname");
+ builder.Property(or => or.Equipment).HasColumnName("equipmentcsv");
+ }
protected override string GetTableName()
{
diff --git a/Backend/Data/Configurations/SettingConfiguration.cs b/Backend/Data/Configurations/SettingConfiguration.cs
index cff91725..b538a6e4 100644
--- a/Backend/Data/Configurations/SettingConfiguration.cs
+++ b/Backend/Data/Configurations/SettingConfiguration.cs
@@ -14,24 +14,24 @@
// along with AlarmWorkflow. If not, see .
using AlarmWorkflow.Backend.Data.Types;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Metadata.Builders;
namespace AlarmWorkflow.Backend.Data.Configurations
{
+ // ReSharper disable once UnusedMember.Global
class SettingConfiguration : ConfigurationBase
{
- #region Constructors
+ #region Methods
- public SettingConfiguration()
- : base()
+ public override void Configure(EntityTypeBuilder builder)
{
- Property(s => s.Identifier).IsRequired().HasColumnName("identifier");
- Property(s => s.Name).IsRequired().HasColumnName("name");
- Property(s => s.Value).HasColumnName("value");
- }
-
- #endregion
+ base.Configure(builder);
- #region Methods
+ builder.Property(s => s.Identifier).IsRequired().HasColumnName("identifier");
+ builder.Property(s => s.Name).IsRequired().HasColumnName("name");
+ builder.Property(s => s.Value).HasColumnName("value");
+ }
protected override string GetTableName()
{
diff --git a/Backend/Data/Contexts/ContextCreationOptions.cs b/Backend/Data/Contexts/ContextCreationOptions.cs
index baaad94d..f4acb6e6 100644
--- a/Backend/Data/Contexts/ContextCreationOptions.cs
+++ b/Backend/Data/Contexts/ContextCreationOptions.cs
@@ -14,14 +14,27 @@
// along with AlarmWorkflow. If not, see .
using AlarmWorkflow.Backend.ServiceContracts.Communication;
+using AlarmWorkflow.Shared.Core;
+using AlarmWorkflow.Shared.Diagnostics;
+using System;
+using System.Linq;
+using System.Threading;
namespace AlarmWorkflow.Backend.Data.Contexts
{
sealed class ContextCreationOptions
{
+ #region Enums
+
+ public enum DatabaseEngine { MySQL, SQLite }
+
+ #endregion
+
#region Constants
- private const string ConnectionStringTemplate = "server={0};Port={1};User Id={2};Password={3};database={4};Persist Security Info=True";
+ private const string ConnectionStringTemplateMySQL = "server={0};Port={1};User Id={2};Password={3};database={4};Persist Security Info=True";
+
+ private const string ConnectionStringTemplateSQLite = "Data Source={0};";
#endregion
@@ -32,6 +45,10 @@ sealed class ContextCreationOptions
///
public string HostName { get; set; }
///
+ /// Gets/sets the host name of the server to connect to.
+ ///
+ public DatabaseEngine Engine { get; set; }
+ ///
/// Gets/sets the port of the server to connect to.
///
public int Port { get; set; }
@@ -47,30 +64,31 @@ sealed class ContextCreationOptions
/// Gets/sets the name of the database to connect to.
///
public string DatabaseName { get; set; }
+ ///
+ /// Gets/sets the name of the database path to connect to.
+ ///
+ public string SQLiteDatabase { get; set; }
#endregion
- #region Constructors
+ #region Methods
///
- /// Initializes a new instance of the class.
+ /// Returns the connection string from the values of this instancefor a MySQL database.
///
- public ContextCreationOptions()
+ ///
+ public string GetMySqlConnectionString()
{
-
+ return string.Format(ConnectionStringTemplateMySQL, HostName, Port, UserId, Password, DatabaseName);
}
- #endregion
-
- #region Methods
-
///
- /// Returns the connection string from the values of this instance.
+ /// Returns the connection string from the values of this instance for a sqlite database.
///
///
- public string GetConnectionString()
+ public string GetSQLiteConnectionString()
{
- return string.Format(ConnectionStringTemplate, HostName, Port, UserId, Password, DatabaseName);
+ return string.Format(ConnectionStringTemplateSQLite, SQLiteDatabase);
}
#endregion
@@ -83,15 +101,34 @@ public string GetConnectionString()
/// An instance of which uses the values from the backend configuration.
public static ContextCreationOptions CreateFromSettings()
{
- ContextCreationOptions options = new ContextCreationOptions();
- options.HostName = ServiceFactory.BackendConfigurator.Get("Server.DB.HostName");
- options.Port = int.Parse(ServiceFactory.BackendConfigurator.Get("Server.DB.Port"));
- options.UserId = ServiceFactory.BackendConfigurator.Get("Server.DB.UserId");
- options.Password = ServiceFactory.BackendConfigurator.Get("Server.DB.Password");
- options.DatabaseName = ServiceFactory.BackendConfigurator.Get("Server.DB.DatabaseName");
+ var options = new ContextCreationOptions
+ {
+ Engine = GetEngine(),
+ HostName = ServiceFactory.BackendConfigurator.Get("Server.DB.HostName"),
+ Port = int.Parse(ServiceFactory.BackendConfigurator.Get("Server.DB.Port")),
+ UserId = ServiceFactory.BackendConfigurator.Get("Server.DB.UserId"),
+ Password = ServiceFactory.BackendConfigurator.Get("Server.DB.Password"),
+ DatabaseName = ServiceFactory.BackendConfigurator.Get("Server.DB.DatabaseName"),
+ SQLiteDatabase = Utilities.GetLocalAppDataFolderFileName(ServiceFactory.BackendConfigurator.Get("Server.DB.SQLite.Database"))
+ };
return options;
}
+ private static DatabaseEngine GetEngine()
+ {
+ string engineName = ServiceFactory.BackendConfigurator.Get("Server.DB.Engine");
+
+ try
+ {
+ return (DatabaseEngine)Enum.Parse(typeof(DatabaseEngine), engineName, true);
+ }
+ catch (ArgumentException)
+ {
+ Logger.Instance.LogFormat(LogType.Warning, typeof(ContextCreationOptions), Properties.Resources.EngineNotFound, engineName, "MySQL");
+ return DatabaseEngine.MySQL;
+ }
+ }
+
#endregion
}
}
diff --git a/Backend/Data/Contexts/MainDbContext.cs b/Backend/Data/Contexts/MainDbContext.cs
index adc69012..874ccf29 100644
--- a/Backend/Data/Contexts/MainDbContext.cs
+++ b/Backend/Data/Contexts/MainDbContext.cs
@@ -13,17 +13,14 @@
// You should have received a copy of the GNU General Public License
// along with AlarmWorkflow. If not, see .
+using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Concurrent;
-using System.Data.Common;
-using System.Data.Entity;
using System.Diagnostics;
-using AlarmWorkflow.Shared.Core;
-using MySql.Data.MySqlClient;
+using System.Threading.Tasks;
namespace AlarmWorkflow.Backend.Data.Contexts
{
- [DbConfigurationType(typeof(MainDbContextConfiguration))]
class MainDbContext : DbContext, IUnitOfWork
{
#region Constants
@@ -44,17 +41,12 @@ class MainDbContext : DbContext, IUnitOfWork
#region Constructors
- static MainDbContext()
- {
- Database.SetInitializer(new MainDbContextInitializer());
- }
-
///
/// Initializes a new instance of the class
/// creates a connection to either the local server (when EF uses it) or the configured server (otherwise) and owns it.
///
public MainDbContext()
- : base(CreateConnection(), true)
+ : base()
{
_workCache = new ConcurrentDictionary();
}
@@ -63,44 +55,36 @@ public MainDbContext()
#region Methods
- private static DbConnection CreateConnection()
- {
- /* Hint: The MainDbContext is currently hard-wired to use MySQL.
- * However, with very little effort it is perfectly possible of using any EF provider (PostgreSQL, SQLite etc.).
- */
-
- return new MySqlConnection(CreateConnectionString());
- }
-
- private static string CreateConnectionString()
+ protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
+ base.OnConfiguring(optionsBuilder);
+
try
{
- return ContextCreationOptions.CreateFromSettings().GetConnectionString();
+ var options = ContextCreationOptions.CreateFromSettings();
+ switch (options.Engine)
+ {
+ case ContextCreationOptions.DatabaseEngine.MySQL:
+ optionsBuilder.UseMySql(options.GetMySqlConnectionString());
+ break;
+ case ContextCreationOptions.DatabaseEngine.SQLite:
+ optionsBuilder.UseSqlite(options.GetSQLiteConnectionString());
+ break;
+ }
}
catch (Exception ex)
{
Debug.WriteLine("MainDbContext.CreateConnectionString() failed: {0}", ex.Message);
- }
- return FallbackConnectionString;
+ optionsBuilder.UseMySql(FallbackConnectionString);
+ }
}
- ///
- /// Overridden.
- ///
- ///
- protected override void OnModelCreating(DbModelBuilder modelBuilder)
+ protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
- modelBuilder.Configurations.AddFromAssembly(GetType().Assembly);
-
- /* Hint: We have to ignore certain properties from being mapped to the database.
- * In favor of a clean design, we will in future clean up the database schema, i.e. split the lat/lng column in two.
- */
- modelBuilder.ComplexType().Ignore(pl => pl.GeoLatitude);
- modelBuilder.ComplexType().Ignore(pl => pl.GeoLongitude);
+ modelBuilder.ApplyConfigurationsFromAssembly(GetType().Assembly);
}
#endregion
@@ -119,6 +103,11 @@ void IUnitOfWork.Commit()
SaveChanges();
}
+ public Task CommitAsync()
+ {
+ return SaveChangesAsync();
+ }
+
#endregion
}
}
diff --git a/Backend/Data/Contexts/MainDbContextConfiguration.cs b/Backend/Data/Contexts/MainDbContextConfiguration.cs
deleted file mode 100644
index 7cdf038f..00000000
--- a/Backend/Data/Contexts/MainDbContextConfiguration.cs
+++ /dev/null
@@ -1,41 +0,0 @@
-// This file is part of AlarmWorkflow.
-//
-// AlarmWorkflow is free software: you can redistribute it and/or modify
-// it under the terms of the GNU General Public License as published by
-// the Free Software Foundation, either version 3 of the License, or
-// (at your option) any later version.
-//
-// AlarmWorkflow is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with AlarmWorkflow. If not, see .
-
-using System.Data.Entity;
-using MySql.Data.Entity;
-using MySql.Data.MySqlClient;
-
-namespace AlarmWorkflow.Backend.Data.Contexts
-{
- ///
- /// Implementation of to set up the required classes for the Entity Framework.
- ///
- class MainDbContextConfiguration : DbConfiguration
- {
- #region Constructors
-
- internal MainDbContextConfiguration()
- {
- SetDefaultConnectionFactory(new MySqlConnectionFactory());
-
- SetProviderFactory("MySql.Data.MySqlClient", new MySqlClientFactory());
- SetProviderServices("MySql.Data.MySqlClient", new MySqlProviderServices());
- SetHistoryContext("MySql.Data.MySqlClient", (conn, schema) => new MySqlHistoryContext(conn, schema));
- SetMigrationSqlGenerator("MySql.Data.MySqlClient", () => new MySqlMigrationSqlGenerator());
- }
-
- #endregion
- }
-}
diff --git a/Backend/Data/Contexts/MainDbContextInitializer.cs b/Backend/Data/Contexts/MainDbContextInitializer.cs
deleted file mode 100644
index beb3aebd..00000000
--- a/Backend/Data/Contexts/MainDbContextInitializer.cs
+++ /dev/null
@@ -1,25 +0,0 @@
-// This file is part of AlarmWorkflow.
-//
-// AlarmWorkflow is free software: you can redistribute it and/or modify
-// it under the terms of the GNU General Public License as published by
-// the Free Software Foundation, either version 3 of the License, or
-// (at your option) any later version.
-//
-// AlarmWorkflow is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with AlarmWorkflow. If not, see .
-
-using System.Data.Entity;
-using AlarmWorkflow.Backend.Data.Migrations;
-
-namespace AlarmWorkflow.Backend.Data.Contexts
-{
- class MainDbContextInitializer : MigrateDatabaseToLatestVersion
- {
-
- }
-}
diff --git a/Backend/Data/Contexts/MySqlHistoryContext.cs b/Backend/Data/Contexts/MySqlHistoryContext.cs
deleted file mode 100644
index 0279bf80..00000000
--- a/Backend/Data/Contexts/MySqlHistoryContext.cs
+++ /dev/null
@@ -1,53 +0,0 @@
-// This file is part of AlarmWorkflow.
-//
-// AlarmWorkflow is free software: you can redistribute it and/or modify
-// it under the terms of the GNU General Public License as published by
-// the Free Software Foundation, either version 3 of the License, or
-// (at your option) any later version.
-//
-// AlarmWorkflow is distributed in the hope that it will be useful,
-// but WITHOUT ANY WARRANTY; without even the implied warranty of
-// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-// GNU General Public License for more details.
-//
-// You should have received a copy of the GNU General Public License
-// along with AlarmWorkflow. If not, see .
-
-using System.Data.Common;
-using System.Data.Entity;
-using System.Data.Entity.Migrations.History;
-
-namespace AlarmWorkflow.Backend.Data.Contexts
-{
- ///
- /// Required class to support EF for MySQL.
- ///
- class MySqlHistoryContext : HistoryContext
- {
- #region Constructors
-
- internal MySqlHistoryContext(DbConnection connection, string defaultSchema)
- : base(connection, defaultSchema)
- {
-
- }
-
- #endregion
-
- #region Methods
-
- ///
- /// Overridden. Downsizes some columns which are too large for MySQL...
- ///
- ///
- protected override void OnModelCreating(DbModelBuilder modelBuilder)
- {
- base.OnModelCreating(modelBuilder);
-
- modelBuilder.Entity().Property(h => h.MigrationId).HasMaxLength(100).IsRequired();
- modelBuilder.Entity().Property(h => h.ContextKey).HasMaxLength(200).IsRequired();
- }
-
- #endregion
- }
-}
diff --git a/Backend/Data/Data.csproj b/Backend/Data/Data.csproj
index 0bf9d131..33ba83ce 100644
--- a/Backend/Data/Data.csproj
+++ b/Backend/Data/Data.csproj
@@ -18,18 +18,20 @@
pdbonly
-
-
-
+
+
+
+
+ all
+ runtime; build; native; contentfiles; analyzers
+
+
-
-
-
+
+
+
-
- 201510221659525_Initial.cs
-
True
True
@@ -37,14 +39,15 @@
-
- 201510221659525_Initial.cs
-
+
-
+
-
+
+ ResXFileCodeGenerator
+ Resources.Designer.cs
+
\ No newline at end of file
diff --git a/Backend/Data/Data/IUnitOfWork.cs b/Backend/Data/Data/IUnitOfWork.cs
index 49bcde28..0e00f054 100644
--- a/Backend/Data/Data/IUnitOfWork.cs
+++ b/Backend/Data/Data/IUnitOfWork.cs
@@ -15,6 +15,7 @@
using System;
using AlarmWorkflow.Backend.Data.Types;
+using Microsoft.EntityFrameworkCore.Infrastructure;
namespace AlarmWorkflow.Backend.Data
{
@@ -30,6 +31,8 @@ public interface IUnitOfWork : IDisposable
///
IRepository For() where TEntity : EntityBase, new();
+ DatabaseFacade Database { get; }
+
///
/// Commits all changes and persists them to the data context.
///
diff --git a/Backend/Data/Data/Repository.cs b/Backend/Data/Data/Repository.cs
index f5d8cc86..6638b0c4 100644
--- a/Backend/Data/Data/Repository.cs
+++ b/Backend/Data/Data/Repository.cs
@@ -13,9 +13,9 @@
// You should have received a copy of the GNU General Public License
// along with AlarmWorkflow. If not, see .
-using System.Data.Entity;
using System.Linq;
using AlarmWorkflow.Backend.Data.Types;
+using Microsoft.EntityFrameworkCore;
namespace AlarmWorkflow.Backend.Data
{
@@ -23,7 +23,7 @@ namespace AlarmWorkflow.Backend.Data
{
#region Fields
- private DbContext _context;
+ private readonly DbContext _context;
#endregion
@@ -38,19 +38,13 @@ internal Repository(DbContext context)
#region IRepository Members
- IQueryable IRepository.Query
- {
- get { return _context.Set(); }
- }
+ IQueryable IRepository.Query => _context.Set();
- TEntity IRepository.Create()
- {
- return new TEntity();
- }
+ TEntity IRepository.Create() => new TEntity();
TEntity IRepository.Insert(TEntity entity)
{
- return _context.Set().Add(entity);
+ return _context.Set().Add(entity).Entity;
}
void IRepository.Delete(TEntity entity)
diff --git a/Backend/Data/Migrations/201510221659525_Initial.Designer.cs b/Backend/Data/Migrations/201510221659525_Initial.Designer.cs
deleted file mode 100644
index ef31f672..00000000
--- a/Backend/Data/Migrations/201510221659525_Initial.Designer.cs
+++ /dev/null
@@ -1,29 +0,0 @@
-//
-namespace AlarmWorkflow.Backend.Data.Migrations
-{
- using System.CodeDom.Compiler;
- using System.Data.Entity.Migrations;
- using System.Data.Entity.Migrations.Infrastructure;
- using System.Resources;
-
- [GeneratedCode("EntityFramework.Migrations", "6.1.3-40302")]
- public sealed partial class Initial : IMigrationMetadata
- {
- private readonly ResourceManager Resources = new ResourceManager(typeof(Initial));
-
- string IMigrationMetadata.Id
- {
- get { return "201510221659525_Initial"; }
- }
-
- string IMigrationMetadata.Source
- {
- get { return null; }
- }
-
- string IMigrationMetadata.Target
- {
- get { return Resources.GetString("Target"); }
- }
- }
-}
diff --git a/Backend/Data/Migrations/201510221659525_Initial.cs b/Backend/Data/Migrations/201510221659525_Initial.cs
deleted file mode 100644
index 8ee34751..00000000
--- a/Backend/Data/Migrations/201510221659525_Initial.cs
+++ /dev/null
@@ -1,112 +0,0 @@
-namespace AlarmWorkflow.Backend.Data.Migrations
-{
- using System.Data.Entity.Migrations;
-
- ///
- /// Represents the initial migration.
- ///
- public partial class Initial : DbMigration
- {
- ///
- ///
- ///
- public override void Up()
- {
- CreateTable(
- "dbo.dispresource",
- c => new
- {
- id = c.Int(nullable: false, identity: true),
- operation_id = c.Int(nullable: false),
- timestamp = c.DateTime(nullable: false, precision: 0),
- emkresourceid = c.String(nullable: false, unicode: false),
- })
- .PrimaryKey(t => t.id)
- .ForeignKey("dbo.operation", t => t.operation_id, cascadeDelete: true)
- .Index(t => t.operation_id);
-
- CreateTable(
- "dbo.operation",
- c => new
- {
- id = c.Int(nullable: false, identity: true),
- acknowledged = c.Boolean(nullable: false),
- operationguid = c.Guid(nullable: false),
- operationnumber = c.String(unicode: false),
- timestampincome = c.DateTime(nullable: false, precision: 0),
- timestampalarm = c.DateTime(nullable: false, precision: 0),
- messenger = c.String(unicode: false),
- comment = c.String(unicode: false),
- plan = c.String(unicode: false),
- picture = c.String(unicode: false),
- priority = c.String(unicode: false),
- einsatzortlocation = c.String(unicode: false),
- einsatzortzipcode = c.String(unicode: false),
- einsatzortcity = c.String(unicode: false),
- einsatzortstreet = c.String(unicode: false),
- einsatzortstreetnumber = c.String(unicode: false),
- einsatzortintersection = c.String(unicode: false),
- einsatzortproperty = c.String(unicode: false),
- einsatzortlatlng = c.String(unicode: false),
- zielortlocation = c.String(unicode: false),
- zielortzipcode = c.String(unicode: false),
- zielortcity = c.String(unicode: false),
- zielortstreet = c.String(unicode: false),
- zielortstreetnumber = c.String(unicode: false),
- zielortintersection = c.String(unicode: false),
- zielortproperty = c.String(unicode: false),
- zielortlatlng = c.String(unicode: false),
- keyword = c.String(unicode: false),
- keywordmisc = c.String(unicode: false),
- keywordb = c.String(unicode: false),
- keywordr = c.String(unicode: false),
- keywords = c.String(unicode: false),
- keywordt = c.String(unicode: false),
- loopscsv = c.String(unicode: false),
- customdatajson = c.String(unicode: false),
- })
- .PrimaryKey(t => t.id);
-
- CreateTable(
- "dbo.operationresource",
- c => new
- {
- id = c.Int(nullable: false, identity: true),
- operation_id = c.Int(nullable: false),
- timestamp = c.String(unicode: false),
- fullname = c.String(unicode: false),
- equipmentcsv = c.String(unicode: false),
- })
- .PrimaryKey(t => t.id)
- .ForeignKey("dbo.operation", t => t.operation_id, cascadeDelete: true)
- .Index(t => t.operation_id);
-
- CreateTable(
- "dbo.usersetting",
- c => new
- {
- id = c.Int(nullable: false, identity: true),
- identifier = c.String(nullable: false, unicode: false),
- name = c.String(nullable: false, unicode: false),
- value = c.String(unicode: false),
- })
- .PrimaryKey(t => t.id);
-
- }
-
- ///
- ///
- ///
- public override void Down()
- {
- DropForeignKey("dbo.operationresource", "operation_id", "dbo.operation");
- DropForeignKey("dbo.dispresource", "operation_id", "dbo.operation");
- DropIndex("dbo.operationresource", new[] { "operation_id" });
- DropIndex("dbo.dispresource", new[] { "operation_id" });
- DropTable("dbo.usersetting");
- DropTable("dbo.operationresource");
- DropTable("dbo.operation");
- DropTable("dbo.dispresource");
- }
- }
-}
diff --git a/Backend/Data/Migrations/201510221659525_Initial.resx b/Backend/Data/Migrations/201510221659525_Initial.resx
deleted file mode 100644
index 4038d374..00000000
--- a/Backend/Data/Migrations/201510221659525_Initial.resx
+++ /dev/null
@@ -1,126 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- text/microsoft-resx
-
-
- 2.0
-
-
- System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
-
-
- System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
-
-
- 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
-
-
- dbo
-
-
\ No newline at end of file
diff --git a/Backend/Data/Migrations/20181230152708_Initial.Designer.cs b/Backend/Data/Migrations/20181230152708_Initial.Designer.cs
new file mode 100644
index 00000000..53a6bb3d
--- /dev/null
+++ b/Backend/Data/Migrations/20181230152708_Initial.Designer.cs
@@ -0,0 +1,276 @@
+//
+using System;
+using AlarmWorkflow.Backend.Data.Contexts;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Migrations;
+using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
+
+namespace AlarmWorkflow.Backend.Data.Migrations
+{
+ [DbContext(typeof(MainDbContext))]
+ [Migration("20181230152708_Initial")]
+ partial class Initial
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+#pragma warning disable 612, 618
+ modelBuilder
+ .HasAnnotation("ProductVersion", "2.2.0-rtm-35687")
+ .HasAnnotation("Relational:MaxIdentifierLength", 64);
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.DispositionedResourceData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("EmkResourceId")
+ .IsRequired()
+ .HasColumnName("emkresourceid");
+
+ b.Property("OperationId")
+ .HasColumnName("operation_id");
+
+ b.Property("Timestamp")
+ .HasColumnName("timestamp");
+
+ b.HasKey("Id");
+
+ b.HasIndex("OperationId");
+
+ b.ToTable("dispresource");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("AlarmAt")
+ .HasColumnName("timestampalarm");
+
+ b.Property("Comment")
+ .HasColumnName("comment");
+
+ b.Property("CustomData")
+ .HasColumnName("customdatajson");
+
+ b.Property("Guid")
+ .HasColumnName("operationguid");
+
+ b.Property("IncomeAt")
+ .HasColumnName("timestampincome");
+
+ b.Property("IsAcknowledged")
+ .HasColumnName("acknowledged");
+
+ b.Property("Loops")
+ .HasColumnName("loopscsv");
+
+ b.Property("Messenger")
+ .HasColumnName("messenger");
+
+ b.Property("OperationNumber")
+ .HasColumnName("operationnumber");
+
+ b.Property("Picture")
+ .HasColumnName("picture");
+
+ b.Property("Plan")
+ .HasColumnName("plan");
+
+ b.Property("Priority")
+ .HasColumnName("priority");
+
+ b.HasKey("Id");
+
+ b.ToTable("operation");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationResourceData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("Equipment")
+ .HasColumnName("equipmentcsv");
+
+ b.Property("FullName")
+ .HasColumnName("fullname");
+
+ b.Property("OperationId")
+ .HasColumnName("operation_id");
+
+ b.Property("Timestamp")
+ .HasColumnName("timestamp");
+
+ b.HasKey("Id");
+
+ b.HasIndex("OperationId");
+
+ b.ToTable("operationresource");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.SettingData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("Identifier")
+ .IsRequired()
+ .HasColumnName("identifier");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnName("name");
+
+ b.Property("Value")
+ .HasColumnName("value");
+
+ b.HasKey("Id");
+
+ b.ToTable("usersetting");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.DispositionedResourceData", b =>
+ {
+ b.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData", "Operation")
+ .WithMany("DispositionedResources")
+ .HasForeignKey("OperationId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationData", b =>
+ {
+ b.OwnsOne("AlarmWorkflow.Shared.Core.OperationKeywords", "Keywords", b1 =>
+ {
+ b1.Property("OperationDataId");
+
+ b1.Property("B")
+ .HasColumnName("keywordb");
+
+ b1.Property("EmergencyKeyword")
+ .HasColumnName("keywordmisc");
+
+ b1.Property("Keyword")
+ .HasColumnName("keyword");
+
+ b1.Property("R")
+ .HasColumnName("keywordr");
+
+ b1.Property("S")
+ .HasColumnName("keywords");
+
+ b1.Property("T")
+ .HasColumnName("keywordt");
+
+ b1.HasKey("OperationDataId");
+
+ b1.ToTable("operation");
+
+ b1.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData")
+ .WithOne("Keywords")
+ .HasForeignKey("AlarmWorkflow.Shared.Core.OperationKeywords", "OperationDataId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+
+ b.OwnsOne("AlarmWorkflow.Shared.Core.PropertyLocation", "Einsatzort", b1 =>
+ {
+ b1.Property("OperationDataId");
+
+ b1.Property("City")
+ .HasColumnName("einsatzortcity");
+
+ b1.Property("GeoLatLng")
+ .HasColumnName("einsatzortlatlng");
+
+ b1.Property("GeoLatitude");
+
+ b1.Property("GeoLongitude");
+
+ b1.Property("Intersection")
+ .HasColumnName("einsatzortintersection");
+
+ b1.Property("Location")
+ .HasColumnName("einsatzortlocation");
+
+ b1.Property("Property")
+ .HasColumnName("einsatzortproperty");
+
+ b1.Property("Street")
+ .HasColumnName("einsatzortstreet");
+
+ b1.Property("StreetNumber")
+ .HasColumnName("einsatzortstreetnumber");
+
+ b1.Property("ZipCode")
+ .HasColumnName("einsatzortzipcode");
+
+ b1.HasKey("OperationDataId");
+
+ b1.ToTable("operation");
+
+ b1.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData")
+ .WithOne("Einsatzort")
+ .HasForeignKey("AlarmWorkflow.Shared.Core.PropertyLocation", "OperationDataId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+
+ b.OwnsOne("AlarmWorkflow.Shared.Core.PropertyLocation", "Zielort", b1 =>
+ {
+ b1.Property("OperationDataId");
+
+ b1.Property("City")
+ .HasColumnName("zielortcity");
+
+ b1.Property("GeoLatLng")
+ .HasColumnName("zielortlatlng");
+
+ b1.Property("GeoLatitude");
+
+ b1.Property("GeoLongitude");
+
+ b1.Property("Intersection")
+ .HasColumnName("zielortintersection");
+
+ b1.Property("Location")
+ .HasColumnName("zielortlocation");
+
+ b1.Property("Property")
+ .HasColumnName("zielortproperty");
+
+ b1.Property("Street")
+ .HasColumnName("zielortstreet");
+
+ b1.Property("StreetNumber")
+ .HasColumnName("zielortstreetnumber");
+
+ b1.Property("ZipCode")
+ .HasColumnName("zielortzipcode");
+
+ b1.HasKey("OperationDataId");
+
+ b1.ToTable("operation");
+
+ b1.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData")
+ .WithOne("Zielort")
+ .HasForeignKey("AlarmWorkflow.Shared.Core.PropertyLocation", "OperationDataId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationResourceData", b =>
+ {
+ b.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData", "Operation")
+ .WithMany("Resources")
+ .HasForeignKey("OperationId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+#pragma warning restore 612, 618
+ }
+ }
+}
diff --git a/Backend/Data/Migrations/20181230152708_Initial.cs b/Backend/Data/Migrations/20181230152708_Initial.cs
new file mode 100644
index 00000000..e77d3a74
--- /dev/null
+++ b/Backend/Data/Migrations/20181230152708_Initial.cs
@@ -0,0 +1,149 @@
+using System;
+using Microsoft.EntityFrameworkCore.Metadata;
+using Microsoft.EntityFrameworkCore.Migrations;
+
+namespace AlarmWorkflow.Backend.Data.Migrations
+{
+ public partial class Initial : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.CreateTable(
+ name: "operation",
+ columns: table => new
+ {
+ id = table.Column(nullable: false)
+ .Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn)
+ .Annotation("Sqlite:Autoincrement", true),
+ acknowledged = table.Column(nullable: false),
+ operationguid = table.Column(nullable: false),
+ operationnumber = table.Column(nullable: true),
+ timestampincome = table.Column(nullable: false),
+ timestampalarm = table.Column(nullable: false),
+ messenger = table.Column(nullable: true),
+ comment = table.Column(nullable: true),
+ plan = table.Column(nullable: true),
+ picture = table.Column(nullable: true),
+ priority = table.Column(nullable: true),
+ einsatzortlocation = table.Column(nullable: true),
+ einsatzortzipcode = table.Column(nullable: true),
+ einsatzortcity = table.Column(nullable: true),
+ einsatzortstreet = table.Column(nullable: true),
+ einsatzortstreetnumber = table.Column(nullable: true),
+ einsatzortintersection = table.Column(nullable: true),
+ Einsatzort_GeoLatitude = table.Column(nullable: true),
+ Einsatzort_GeoLongitude = table.Column(nullable: true),
+ einsatzortproperty = table.Column(nullable: true),
+ einsatzortlatlng = table.Column(nullable: true),
+ zielortlocation = table.Column(nullable: true),
+ zielortzipcode = table.Column(nullable: true),
+ zielortcity = table.Column(nullable: true),
+ zielortstreet = table.Column(nullable: true),
+ zielortstreetnumber = table.Column(nullable: true),
+ zielortintersection = table.Column(nullable: true),
+ Zielort_GeoLatitude = table.Column(nullable: true),
+ Zielort_GeoLongitude = table.Column(nullable: true),
+ zielortproperty = table.Column(nullable: true),
+ zielortlatlng = table.Column(nullable: true),
+ keyword = table.Column(nullable: true),
+ keywordmisc = table.Column(nullable: true),
+ keywordb = table.Column(nullable: true),
+ keywordr = table.Column(nullable: true),
+ keywords = table.Column(nullable: true),
+ keywordt = table.Column(nullable: true),
+ loopscsv = table.Column(nullable: true),
+ customdatajson = table.Column(nullable: true)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_operation", x => x.id);
+ });
+
+ migrationBuilder.CreateTable(
+ name: "usersetting",
+ columns: table => new
+ {
+ id = table.Column(nullable: false)
+ .Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn)
+ .Annotation("Sqlite:Autoincrement", true),
+ identifier = table.Column(nullable: false),
+ name = table.Column(nullable: false),
+ value = table.Column(nullable: true)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_usersetting", x => x.id);
+ });
+
+ migrationBuilder.CreateTable(
+ name: "dispresource",
+ columns: table => new
+ {
+ id = table.Column(nullable: false)
+ .Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn)
+ .Annotation("Sqlite:Autoincrement", true),
+ operation_id = table.Column(nullable: false),
+ timestamp = table.Column(nullable: false),
+ emkresourceid = table.Column(nullable: false)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_dispresource", x => x.id);
+ table.ForeignKey(
+ name: "FK_dispresource_operation_operation_id",
+ column: x => x.operation_id,
+ principalTable: "operation",
+ principalColumn: "id",
+ onDelete: ReferentialAction.Cascade);
+ });
+
+ migrationBuilder.CreateTable(
+ name: "operationresource",
+ columns: table => new
+ {
+ id = table.Column(nullable: false)
+ .Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn)
+ .Annotation("Sqlite:Autoincrement", true),
+ operation_id = table.Column(nullable: false),
+ timestamp = table.Column(nullable: true),
+ fullname = table.Column(nullable: true),
+ equipmentcsv = table.Column(nullable: true)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_operationresource", x => x.id);
+ table.ForeignKey(
+ name: "FK_operationresource_operation_operation_id",
+ column: x => x.operation_id,
+ principalTable: "operation",
+ principalColumn: "id",
+ onDelete: ReferentialAction.Cascade);
+ });
+
+ migrationBuilder.CreateIndex(
+ name: "IX_dispresource_operation_id",
+ table: "dispresource",
+ column: "operation_id");
+
+ migrationBuilder.CreateIndex(
+ name: "IX_operationresource_operation_id",
+ table: "operationresource",
+ column: "operation_id");
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropTable(
+ name: "dispresource");
+
+ migrationBuilder.DropTable(
+ name: "operationresource");
+
+ migrationBuilder.DropTable(
+ name: "usersetting");
+
+ migrationBuilder.DropTable(
+ name: "operation");
+ }
+ }
+}
diff --git a/Backend/Data/Migrations/Configuration.cs b/Backend/Data/Migrations/Configuration.cs
deleted file mode 100644
index 7c8064cb..00000000
--- a/Backend/Data/Migrations/Configuration.cs
+++ /dev/null
@@ -1,29 +0,0 @@
-using System.Data.Entity.Migrations;
-using AlarmWorkflow.Backend.Data.Contexts;
-
-namespace AlarmWorkflow.Backend.Data.Migrations
-{
- sealed class Configuration : DbMigrationsConfiguration
- {
- public Configuration()
- {
- AutomaticMigrationsEnabled = false;
- }
-
- protected override void Seed(MainDbContext context)
- {
- // This method will be called after migrating to the latest version.
-
- // You can use the DbSet.AddOrUpdate() helper extension method
- // to avoid creating duplicate seed data. E.g.
- //
- // context.People.AddOrUpdate(
- // p => p.FullName,
- // new Person { FullName = "Andrew Peters" },
- // new Person { FullName = "Brice Lambson" },
- // new Person { FullName = "Rowan Miller" }
- // );
- //
- }
- }
-}
diff --git a/Backend/Data/Migrations/MainDbContextModelSnapshot.cs b/Backend/Data/Migrations/MainDbContextModelSnapshot.cs
new file mode 100644
index 00000000..cac1f434
--- /dev/null
+++ b/Backend/Data/Migrations/MainDbContextModelSnapshot.cs
@@ -0,0 +1,274 @@
+//
+using System;
+using AlarmWorkflow.Backend.Data.Contexts;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
+
+namespace AlarmWorkflow.Backend.Data.Migrations
+{
+ [DbContext(typeof(MainDbContext))]
+ partial class MainDbContextModelSnapshot : ModelSnapshot
+ {
+ protected override void BuildModel(ModelBuilder modelBuilder)
+ {
+#pragma warning disable 612, 618
+ modelBuilder
+ .HasAnnotation("ProductVersion", "2.2.0-rtm-35687")
+ .HasAnnotation("Relational:MaxIdentifierLength", 64);
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.DispositionedResourceData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("EmkResourceId")
+ .IsRequired()
+ .HasColumnName("emkresourceid");
+
+ b.Property("OperationId")
+ .HasColumnName("operation_id");
+
+ b.Property("Timestamp")
+ .HasColumnName("timestamp");
+
+ b.HasKey("Id");
+
+ b.HasIndex("OperationId");
+
+ b.ToTable("dispresource");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("AlarmAt")
+ .HasColumnName("timestampalarm");
+
+ b.Property("Comment")
+ .HasColumnName("comment");
+
+ b.Property("CustomData")
+ .HasColumnName("customdatajson");
+
+ b.Property("Guid")
+ .HasColumnName("operationguid");
+
+ b.Property("IncomeAt")
+ .HasColumnName("timestampincome");
+
+ b.Property("IsAcknowledged")
+ .HasColumnName("acknowledged");
+
+ b.Property("Loops")
+ .HasColumnName("loopscsv");
+
+ b.Property("Messenger")
+ .HasColumnName("messenger");
+
+ b.Property("OperationNumber")
+ .HasColumnName("operationnumber");
+
+ b.Property("Picture")
+ .HasColumnName("picture");
+
+ b.Property("Plan")
+ .HasColumnName("plan");
+
+ b.Property("Priority")
+ .HasColumnName("priority");
+
+ b.HasKey("Id");
+
+ b.ToTable("operation");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationResourceData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("Equipment")
+ .HasColumnName("equipmentcsv");
+
+ b.Property("FullName")
+ .HasColumnName("fullname");
+
+ b.Property("OperationId")
+ .HasColumnName("operation_id");
+
+ b.Property("Timestamp")
+ .HasColumnName("timestamp");
+
+ b.HasKey("Id");
+
+ b.HasIndex("OperationId");
+
+ b.ToTable("operationresource");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.SettingData", b =>
+ {
+ b.Property("Id")
+ .ValueGeneratedOnAdd()
+ .HasColumnName("id");
+
+ b.Property("Identifier")
+ .IsRequired()
+ .HasColumnName("identifier");
+
+ b.Property("Name")
+ .IsRequired()
+ .HasColumnName("name");
+
+ b.Property("Value")
+ .HasColumnName("value");
+
+ b.HasKey("Id");
+
+ b.ToTable("usersetting");
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.DispositionedResourceData", b =>
+ {
+ b.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData", "Operation")
+ .WithMany("DispositionedResources")
+ .HasForeignKey("OperationId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationData", b =>
+ {
+ b.OwnsOne("AlarmWorkflow.Shared.Core.OperationKeywords", "Keywords", b1 =>
+ {
+ b1.Property("OperationDataId");
+
+ b1.Property("B")
+ .HasColumnName("keywordb");
+
+ b1.Property("EmergencyKeyword")
+ .HasColumnName("keywordmisc");
+
+ b1.Property("Keyword")
+ .HasColumnName("keyword");
+
+ b1.Property("R")
+ .HasColumnName("keywordr");
+
+ b1.Property("S")
+ .HasColumnName("keywords");
+
+ b1.Property("T")
+ .HasColumnName("keywordt");
+
+ b1.HasKey("OperationDataId");
+
+ b1.ToTable("operation");
+
+ b1.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData")
+ .WithOne("Keywords")
+ .HasForeignKey("AlarmWorkflow.Shared.Core.OperationKeywords", "OperationDataId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+
+ b.OwnsOne("AlarmWorkflow.Shared.Core.PropertyLocation", "Einsatzort", b1 =>
+ {
+ b1.Property("OperationDataId");
+
+ b1.Property("City")
+ .HasColumnName("einsatzortcity");
+
+ b1.Property("GeoLatLng")
+ .HasColumnName("einsatzortlatlng");
+
+ b1.Property("GeoLatitude");
+
+ b1.Property("GeoLongitude");
+
+ b1.Property("Intersection")
+ .HasColumnName("einsatzortintersection");
+
+ b1.Property("Location")
+ .HasColumnName("einsatzortlocation");
+
+ b1.Property("Property")
+ .HasColumnName("einsatzortproperty");
+
+ b1.Property("Street")
+ .HasColumnName("einsatzortstreet");
+
+ b1.Property("StreetNumber")
+ .HasColumnName("einsatzortstreetnumber");
+
+ b1.Property("ZipCode")
+ .HasColumnName("einsatzortzipcode");
+
+ b1.HasKey("OperationDataId");
+
+ b1.ToTable("operation");
+
+ b1.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData")
+ .WithOne("Einsatzort")
+ .HasForeignKey("AlarmWorkflow.Shared.Core.PropertyLocation", "OperationDataId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+
+ b.OwnsOne("AlarmWorkflow.Shared.Core.PropertyLocation", "Zielort", b1 =>
+ {
+ b1.Property("OperationDataId");
+
+ b1.Property("City")
+ .HasColumnName("zielortcity");
+
+ b1.Property("GeoLatLng")
+ .HasColumnName("zielortlatlng");
+
+ b1.Property("GeoLatitude");
+
+ b1.Property("GeoLongitude");
+
+ b1.Property("Intersection")
+ .HasColumnName("zielortintersection");
+
+ b1.Property("Location")
+ .HasColumnName("zielortlocation");
+
+ b1.Property("Property")
+ .HasColumnName("zielortproperty");
+
+ b1.Property("Street")
+ .HasColumnName("zielortstreet");
+
+ b1.Property("StreetNumber")
+ .HasColumnName("zielortstreetnumber");
+
+ b1.Property("ZipCode")
+ .HasColumnName("zielortzipcode");
+
+ b1.HasKey("OperationDataId");
+
+ b1.ToTable("operation");
+
+ b1.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData")
+ .WithOne("Zielort")
+ .HasForeignKey("AlarmWorkflow.Shared.Core.PropertyLocation", "OperationDataId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+ });
+
+ modelBuilder.Entity("AlarmWorkflow.Backend.Data.Types.OperationResourceData", b =>
+ {
+ b.HasOne("AlarmWorkflow.Backend.Data.Types.OperationData", "Operation")
+ .WithMany("Resources")
+ .HasForeignKey("OperationId")
+ .OnDelete(DeleteBehavior.Cascade);
+ });
+#pragma warning restore 612, 618
+ }
+ }
+}
diff --git a/Backend/Data/Properties/Resources.Designer.cs b/Backend/Data/Properties/Resources.Designer.cs
index 3a1b86f3..457ecdbd 100644
--- a/Backend/Data/Properties/Resources.Designer.cs
+++ b/Backend/Data/Properties/Resources.Designer.cs
@@ -19,7 +19,7 @@ namespace AlarmWorkflow.Backend.Data.Properties {
// class via a tool like ResGen or Visual Studio.
// To add or remove a member, edit your .ResX file then rerun ResGen
// with the /str option, or rebuild your VS project.
- [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")]
+ [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "15.0.0.0")]
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
[global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
internal class Resources {
@@ -59,5 +59,14 @@ internal Resources() {
resourceCulture = value;
}
}
+
+ ///
+ /// Looks up a localized string similar to The database engine '{0}' could not be found. Use {1} instead ....
+ ///
+ internal static string EngineNotFound {
+ get {
+ return ResourceManager.GetString("EngineNotFound", resourceCulture);
+ }
+ }
}
}
diff --git a/Backend/Data/Properties/Resources.resx b/Backend/Data/Properties/Resources.resx
index 4fdb1b6a..587fe910 100644
--- a/Backend/Data/Properties/Resources.resx
+++ b/Backend/Data/Properties/Resources.resx
@@ -1,101 +1,123 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- text/microsoft-resx
-
-
- 1.3
-
-
- System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.3500.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
-
-
- System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.3500.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
-
+ mimetype: application/x-microsoft.net.object.bytearray.base64
+ value : The object must be serialized into a byte array
+ : using a System.ComponentModel.TypeConverter
+ : and then encoded with base64 encoding.
+ -->
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ text/microsoft-resx
+
+
+ 2.0
+
+
+ System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ The database engine '{0}' could not be found. Use {1} instead ...
+
\ No newline at end of file
diff --git a/Backend/Service/Service.csproj b/Backend/Service/Service.csproj
index d112fb4d..98f8f12c 100644
--- a/Backend/Service/Service.csproj
+++ b/Backend/Service/Service.csproj
@@ -24,6 +24,7 @@
+
diff --git a/Backend/ServiceContracts/Backend.config b/Backend/ServiceContracts/Backend.config
index b4ae6a3e..e210bad1 100644
--- a/Backend/ServiceContracts/Backend.config
+++ b/Backend/ServiceContracts/Backend.config
@@ -8,11 +8,15 @@
+
+
+
+
diff --git a/BackendServices/Management/DataExtensions.cs b/BackendServices/Management/DataExtensions.cs
index 63f66a9a..d656aed2 100644
--- a/BackendServices/Management/DataExtensions.cs
+++ b/BackendServices/Management/DataExtensions.cs
@@ -26,23 +26,24 @@ static class DataExtensions
internal static OperationData ToData(this Operation operation)
{
- OperationData data = new OperationData();
-
- data.Guid = operation.OperationGuid;
- data.IsAcknowledged = operation.IsAcknowledged;
- data.OperationNumber = operation.OperationNumber;
- data.IncomeAt = operation.TimestampIncome;
- data.AlarmAt = operation.Timestamp;
- data.Comment = operation.Comment;
- data.Messenger = operation.Messenger;
- data.Plan = operation.OperationPlan;
- data.Picture = operation.Picture;
- data.Priority = operation.Priority;
- data.Loops = operation.Loops.ToString();
- data.Einsatzort = operation.Einsatzort;
- data.Zielort = operation.Zielort;
- data.Keywords = operation.Keywords;
- data.CustomData = JsonHelper.ToJson(operation.CustomData);
+ var data = new OperationData
+ {
+ Guid = operation.OperationGuid,
+ IsAcknowledged = operation.IsAcknowledged,
+ OperationNumber = operation.OperationNumber,
+ IncomeAt = operation.TimestampIncome,
+ AlarmAt = operation.Timestamp,
+ Comment = operation.Comment,
+ Messenger = operation.Messenger,
+ Plan = operation.OperationPlan,
+ Picture = operation.Picture,
+ Priority = operation.Priority,
+ Loops = operation.Loops.ToString(),
+ Einsatzort = operation.Einsatzort,
+ Zielort = operation.Zielort,
+ Keywords = operation.Keywords,
+ CustomData = JsonHelper.ToJson(operation.CustomData)
+ };
foreach (OperationResource item in operation.Resources)
{
@@ -54,7 +55,7 @@ internal static OperationData ToData(this Operation operation)
internal static Operation ToOperation(this OperationData data)
{
- Operation operation = new Operation()
+ var operation = new Operation()
{
Id = data.Id,
IsAcknowledged = data.IsAcknowledged,
diff --git a/BackendServices/System/DatabaseChecker.cs b/BackendServices/System/DatabaseChecker.cs
index c845a720..c9b75ee8 100644
--- a/BackendServices/System/DatabaseChecker.cs
+++ b/BackendServices/System/DatabaseChecker.cs
@@ -13,13 +13,15 @@
// You should have received a copy of the GNU General Public License
// along with AlarmWorkflow. If not, see .
-using System;
-using System.Linq;
-using System.Threading;
using AlarmWorkflow.Backend.Data;
using AlarmWorkflow.Backend.Data.Types;
using AlarmWorkflow.Shared.Core;
using AlarmWorkflow.Shared.Diagnostics;
+using Microsoft.EntityFrameworkCore;
+using MySql.Data.MySqlClient;
+using System;
+using System.Linq;
+using System.Threading;
namespace AlarmWorkflow.BackendService.System.Data
{
@@ -56,14 +58,35 @@ private static bool CheckDatabaseReachable(IServiceProvider services)
*/
using (IUnitOfWork work = services.GetService().Get().Create())
{
+ // Migrate to new database versions
+ work.Database.Migrate();
+
work.For().Query.FirstOrDefault();
}
return true;
}
- catch (Exception)
+ catch (MySqlException ex)
+ {
+ if (ex.Number == 1050)
+ {
+ // Table already exists.
+ // This happens when the user upgrade from the entity framework to entity framework core.
+ // The script tries to execute the migration, but the table already exist. So we have to add the migration by hand
+ // into the table. This is really dirty and should be changed ..
+ using (IUnitOfWork work = services.GetService().Get().Create())
+ {
+ work.Database.ExecuteSqlCommand(@"REPLACE INTO `__efmigrationshistory` (`MigrationId`, `ProductVersion`) VALUES ('20181230152708_Initial', '2.2.0-rtm-35687');");
+ }
+ }
+ else
+ {
+ Logger.Instance.LogException("DatabaseChecker", ex);
+ }
+ }
+ catch (Exception ex)
{
- // Intentionally left blank --> database not reachable or other error.
+ Logger.Instance.LogException("DatabaseChecker", ex);
}
return false;