Difference between revisions of "NHibernate"
(→Insert, Updates und Save()) |
(→one to one) |
||
(4 intermediate revisions by the same user not shown) | |||
Line 221: | Line 221: | ||
</source> | </source> | ||
− | == | + | == one to one == |
− | |||
<source lang="csharp"> | <source lang="csharp"> | ||
− | var | + | using System; |
− | + | using FluentNHibernate.Cfg; | |
− | + | using FluentNHibernate.Cfg.Db; | |
− | + | using NHibernate; | |
− | + | using FluentNHibernate.Mapping; | |
+ | |||
+ | namespace NhOneToOne | ||
+ | { | ||
+ | public class Program | ||
+ | { | ||
+ | static void Main(string[] args) | ||
+ | { | ||
+ | try | ||
+ | { | ||
+ | |||
+ | var sessionFactory = Fluently.Configure() | ||
+ | .Database( | ||
+ | MsSqlConfiguration.MsSql2005 | ||
+ | .ConnectionString(@"Data Source=(localdb)\MSSQLLocalDB;Initial Catalog=NHTest;Integrated Security=True;Connect Timeout=30;Encrypt=False;TrustServerCertificate=True;ApplicationIntent=ReadWrite;MultiSubnetFailover=False") | ||
+ | .ShowSql() | ||
+ | ) | ||
+ | .Mappings(m => m | ||
+ | .FluentMappings.AddFromAssemblyOf<Program>()) | ||
+ | .BuildSessionFactory(); | ||
+ | |||
+ | ISession session = sessionFactory.OpenSession(); | ||
+ | |||
+ | |||
+ | Child c = session.Get<Child>(1); | ||
+ | Parent p = c.Parent; | ||
+ | Child c2 = p.Child; | ||
+ | |||
+ | session.Clear(); | ||
+ | |||
+ | p = session.Get<Parent>(2); | ||
+ | c2 = p.Child; | ||
+ | |||
+ | } | ||
+ | catch (Exception e) | ||
+ | { | ||
+ | Console.Write(e.Message); | ||
+ | } | ||
+ | } | ||
+ | |||
+ | } | ||
+ | |||
+ | public class Child | ||
+ | { | ||
+ | public virtual string Name { get; set; } | ||
+ | public virtual int Id { get; set; } | ||
+ | |||
+ | public virtual Parent Parent { get; set; } | ||
+ | } | ||
+ | |||
+ | public class Parent | ||
+ | { | ||
+ | public virtual string Name { get; set; } | ||
+ | public virtual int Id { get; set; } | ||
+ | |||
+ | public virtual Child Child { get; set; } | ||
+ | |||
+ | } | ||
+ | |||
+ | public class ChildMap : ClassMap<Child> | ||
+ | { | ||
+ | public ChildMap() | ||
+ | { | ||
+ | Table("ChildTable"); | ||
+ | Id(x => x.Id).GeneratedBy.Native(); | ||
+ | Map(x => x.Name); | ||
+ | |||
+ | References(x => x.Parent).Column("IdParent"); | ||
+ | |||
+ | } | ||
+ | } | ||
+ | |||
+ | public class ParentMap : ClassMap<Parent> | ||
+ | { | ||
+ | public ParentMap() | ||
+ | { | ||
+ | Table("ParentTable"); | ||
+ | Id(x => x.Id).GeneratedBy.Native(); | ||
+ | Map(x => x.Name); | ||
+ | |||
+ | HasOne(x => x.Child).PropertyRef("Parent"); | ||
+ | } | ||
+ | |||
+ | } | ||
+ | } | ||
+ | |||
</source> | </source> | ||
− | |||
<source lang="sql"> | <source lang="sql"> | ||
− | + | CREATE TABLE [dbo].[ChildTable] ( | |
− | + | [Id] INT IDENTITY (1, 1) NOT NULL, | |
− | + | [IdParent] INT NOT NULL, | |
− | + | [Name] VARCHAR (50) NULL | |
− | + | ); | |
− | + | ||
− | + | CREATE TABLE [dbo].[ParentTable] ( | |
− | + | [Id] INT IDENTITY (1, 1) NOT NULL, | |
− | + | [Name] VARCHAR (MAX) NULL | |
− | ) | + | ); |
+ | ALTER TABLE [dbo].[ChildTable] | ||
+ | ADD CONSTRAINT [FK_ChildTable_ToTable] FOREIGN KEY ([IdParent]) REFERENCES [dbo].[ParentTable] ([Id]); | ||
</source> | </source> | ||
− | === | + | == Queries == |
− | + | [[NHibernateQueries]] | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
== Insert, Updates und Save() == | == Insert, Updates und Save() == |
Latest revision as of 22:17, 8 March 2017
Contents
Konfigurationsdatei Sample
sqlserver sample
<?xml version="1.0" encoding="utf-8" ?>
<hibernate-configuration xmlns="urn:nhibernate-configuration-2.2">
<session-factory>
<property name="connection.provider">NHibernate.Connection.DriverConnectionProvider</property>
<property name="dialect">NHibernate.Dialect.MsSql2008Dialect</property>
<property name="connection.driver_class">NHibernate.Driver.SqlClientDriver</property>
<property name="connection.connection_string">Server=(local);Database=nhibernate;Trusted_Connection=true;</property>
<property name="show_sql">true</property>
</session-factory>
</hibernate-configuration>
Mysql example
<?xml version="1.0" encoding="utf-8" ?>
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<configSections>
<section name="nlog" type="NLog.Config.ConfigSectionHandler, NLog"/>
<section name="hibernate-configuration" type="NHibernate.Cfg.ConfigurationSectionHandler, NHibernate" />
</configSections>
<appSettings>
<add key="loglevel" value="info"/>
<add key="logimplementation" value="NLOG"/>
<add key="exportdirectory" value="/tmp" />
</appSettings>
<connectionStrings>
<add name="testmasterconnection"
connectionString="server=localhost;user=root;pwd=dukannstmichmal;database=mydb;port=3306;"
providerName="MySql.Data.MySqlClient" />
</connectionStrings>
<hibernate-configuration xmlns="urn:nhibernate-configuration-2.2">
<session-factory>
<property name="connection.provider">NHibernate.Connection.DriverConnectionProvider</property>
<property name="dialect">NHibernate.Dialect.MySQL5Dialect</property>
<property name="connection.connection_string_name">testmasterconnection</property>
<property name="show_sql">true</property>
<property name="hbm2ddl.keywords">none</property>
</session-factory>
</hibernate-configuration>
<nlog xmlns="http://www.nlog-project.org/schemas/NLog.xsd"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<targets>
<target name="logfile" xsi:type="File" fileName="out.txt" />
<target name="console" xsi:type="Console" />
</targets>
<rules>
<logger name="*" minLevel="Info" writeTo="logfile" />
<logger name="*" minLevel="Info" writeTo="console" />
<logger name="TagsManagement" minLevel="Debug" writeTo="console" />
</rules>
</nlog>
</configuration>
many to many mapping
Mapping:
<?xml version="1.0" encoding="utf-8" ?>
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2"
assembly="ConsoleApplication2"
namespace="ConsoleApplication2">
<class name="MyItem">
<id name="ID" generator="native"/>
<property name="Name" />
<!-- Many-to-many mapping: OrderItems -->
<bag name="Tags"
table="MyItem_MyTag"
cascade="none"
lazy="true">
<key column ="MyItemID" />
<many-to-many class="MyTag" column="MyTagID" />
</bag>
</class>
</hibernate-mapping>
Klasse:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApplication2
{
public class MyItem
{
public virtual string Name { get; set; }
public virtual int ID { get; set; }
IList<MyTag> _tags = new List<MyTag>();
public virtual IList<MyTag> Tags {
get
{
return this._tags;
}
set
{
_tags = value;
}
}
}
}
Konfiguration mit fluet configuration
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using NHibernate.Cfg;
using FluentNHibernate.Cfg;
using FluentNHibernate.Cfg.Db;
using NHibernate;
namespace ConsoleApplication2
{
class Program
{
/// <summary>
///
/// </summary>
/// <param name="args"></param>
static void Main(string[] args)
{
try
{
var sessionFactory = Fluently.Configure()
.Database(
MsSqlConfiguration.MsSql2005
.ConnectionString(
"Server=(local);Database=nhibernate;Trusted_Connection=true;")
.ShowSql()
)
.Mappings(m => m
.FluentMappings.AddFromAssemblyOf<Program>())
.BuildSessionFactory();
ISession session = sessionFactory.OpenSession();
...
}
catch (Exception e)
{
Console.Write(e.Message);
}
}
}
}
using FluentNHibernate.Mapping;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApplication2.Mappings
{
class MyItemMap : ClassMap<MyItem>
{
public MyItemMap()
{
Id(x => x.ID).GeneratedBy.Native();
Map(x => x.Name);
HasManyToMany(x => x.Tags)
.Table("MyItem_MyTag")
.ParentKeyColumn("MyItemID")
.ChildKeyColumn("MyTagID")
.Cascade.None().LazyLoad();
}
}
}
Wenn Fremdschlüssel kein Constraint aufweist:
//Cache einschalten:
Cache.ReadOnly().Region("Keep15Min");
//Fremdschlüssel ohne Fremdschlüsselconstraint
References(x => x.Verantwortlicher, "strVerantwortlicher").Nullable()
.ForeignKey("FK_Vertrag_Verantwortlicher_Employee")
.Index("IX_strVerantwortlicherId")
.NotFound.Ignore()
.Access.CamelCaseField(Prefix.Underscore);
one to one
using System;
using FluentNHibernate.Cfg;
using FluentNHibernate.Cfg.Db;
using NHibernate;
using FluentNHibernate.Mapping;
namespace NhOneToOne
{
public class Program
{
static void Main(string[] args)
{
try
{
var sessionFactory = Fluently.Configure()
.Database(
MsSqlConfiguration.MsSql2005
.ConnectionString(@"Data Source=(localdb)\MSSQLLocalDB;Initial Catalog=NHTest;Integrated Security=True;Connect Timeout=30;Encrypt=False;TrustServerCertificate=True;ApplicationIntent=ReadWrite;MultiSubnetFailover=False")
.ShowSql()
)
.Mappings(m => m
.FluentMappings.AddFromAssemblyOf<Program>())
.BuildSessionFactory();
ISession session = sessionFactory.OpenSession();
Child c = session.Get<Child>(1);
Parent p = c.Parent;
Child c2 = p.Child;
session.Clear();
p = session.Get<Parent>(2);
c2 = p.Child;
}
catch (Exception e)
{
Console.Write(e.Message);
}
}
}
public class Child
{
public virtual string Name { get; set; }
public virtual int Id { get; set; }
public virtual Parent Parent { get; set; }
}
public class Parent
{
public virtual string Name { get; set; }
public virtual int Id { get; set; }
public virtual Child Child { get; set; }
}
public class ChildMap : ClassMap<Child>
{
public ChildMap()
{
Table("ChildTable");
Id(x => x.Id).GeneratedBy.Native();
Map(x => x.Name);
References(x => x.Parent).Column("IdParent");
}
}
public class ParentMap : ClassMap<Parent>
{
public ParentMap()
{
Table("ParentTable");
Id(x => x.Id).GeneratedBy.Native();
Map(x => x.Name);
HasOne(x => x.Child).PropertyRef("Parent");
}
}
}
CREATE TABLE [dbo].[ChildTable] (
[Id] INT IDENTITY (1, 1) NOT NULL,
[IdParent] INT NOT NULL,
[Name] VARCHAR (50) NULL
);
CREATE TABLE [dbo].[ParentTable] (
[Id] INT IDENTITY (1, 1) NOT NULL,
[Name] VARCHAR (MAX) NULL
);
ALTER TABLE [dbo].[ChildTable]
ADD CONSTRAINT [FK_ChildTable_ToTable] FOREIGN KEY ([IdParent]) REFERENCES [dbo].[ParentTable] ([Id]);
Queries
Insert, Updates und Save()
Hier gibt es keine Änderung an der Datenbank:
ISession session = sessionFactory.OpenSession();
MyTag tag = session.Get<MyTag>(17);
tag.Name = "Furunkel"; //Wird nicht in DB übernommen.
session.Close();
Ohne Transaktion kein Update.
Änderung an der Datenbank ohne Save:
ISession session = sessionFactory.OpenSession();
ITransaction tx = session.BeginTransaction();
MyTag tag = session.Get<MyTag>(17);
tag.Name = "Furunkel";
tx.Commit(); //Schreibt die Änderung in die DB.
Save:
ISession session = sessionFactory.OpenSession();
ITransaction tx = session.BeginTransaction();
MyTag tag = new MyTag();
tag.Name = "test";
session.Save(tag); //Insert Statement wird hier zur DB ausgegeben. Id von db wird hier gelöst.
tx.Commit();
Save mit Update:
ISession session = sessionFactory.OpenSession();
ITransaction tx = session.BeginTransaction();
MyTag tag = session.Get<MyTag>(17);
tag.Name = "Elefant";
session.Save(tag); //Da die Entität bereits eine Id hat, wird hier kein Update SQL ausgegeben.
tx.Commit(); //Schreibt die Änderung in die DB.
session.Close();
Das macht gar nichts:
ISession session = sessionFactory.OpenSession();
MyTag tag = session.Get<MyTag>(17);
tag.Name = "Elefant";
session.Save(tag); //Das macht gar nichts, da keine Tx vorhanden ist.
session.Close();
Cascading bei Many to Many
Insert
ISession session = sessionFactory.OpenSession();
ITransaction tx = session.BeginTransaction();
MyItem item = new MyItem { Name = "CascadeAllItem" };
MyTag tag = new MyTag { Name = "CascadeAllTag" };
item.Tags.Add(tag);
session.Save(item);
tx.Commit();
session.Close();
- None(): NHibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing or set cascade action for the property to something that would make it autosave.
- SaveUpdate(): Beide Entitäten werden in die Datenbank eingefügt.
- Delete(): NHibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing or set cascade action for the property to something that would make it autosave.
- Merge(): NHibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing or set cascade action for the property to something that would make it autosave.
- All(): Beide Entitäten werden in die Datenbank eingefügt.
- AllDeleteOrphan(): Beide Entitäten werden in die Datenbank eingefügt.
Delete
ISession session = sessionFactory.OpenSession();
ITransaction tx = session.BeginTransaction();
MyItem item = session.Get<MyItem>(27); //Item enthält ein Tag.
session.Delete(item);
tx.Commit();
session.Close();
- None(): Nur MyItem wird gelöscht.
- All(): MyItem und MyTag wird gelöscht.
- Merge(): Nur MyItem wird gelöscht.
- Delete(): MyItem und MyTag wird gelöscht.
- DeleteAll(): MyItem und MyTag wird gelöscht.
- DeleteOrphan(): MyItem und MyTag wird gelöscht.
- AllDeleteOrphan(): MyItem und MyTag wird gelöscht.
Remove from collection
ISession session = sessionFactory.OpenSession();
ITransaction tx = session.BeginTransaction();
MyItem item = session.Get<MyItem>(37); //Item enthält ein Tag.
item.Tags.Clear();
tx.Commit();
session.Close();
- None(): Tag wird nicht gelöscht. Verknüpfung zwischen Tag und Item wird entfernt.
- All(): Tag wird nicht gelöscht. Verknüpfung zwischen Tag und Item wird entfernt.
- Merge(): Tag wird nicht gelöscht. Verknüpfung zwischen Tag und Item wird entfernt.
- Delete(): Tag wird nicht gelöscht. Verknüpfung zwischen Tag und Item wird entfernt.
- DeleteAll(): Tag wird nicht gelöscht. Verknüpfung zwischen Tag und Item wird entfernt.
- DeleteOrphan(): Tag wird gelöscht.
- AllDeleteOrphan(): Tag wird gelöscht.