使用Entity Framework Core访问数据库(Oracle篇)

前言

哇。。看看时间 真的好久好久没写博客了 将近一年了。html

最近一直在忙各类家中事务和公司的新框架  终于抽出时间来更新一波了。mysql

本篇主要讲一下关于Entity Framework Core访问oracle数据库的采坑。。linux

强调一下,本篇文章发布以前 关于Entity Framework Core访问oracle数据库的甲骨文官方dll还未正式发布。sql

不过我已经在项目中用起来了。。介意的兄弟能够先等等。。甲骨文说的是本年第三季度。。docker

 

环境

1.官方文档中支持的环境

首先咱们来看看所谓的官方支持吧。数据库

操做系统:oracle

1. Windows x64
  1.1Windows 8.1 (Pro and Enterprise Editions)
  1.2Windows 10 x64 (Pro, Enterprise, and Education Editions)
  1.3Windows Server 2012 R2 x64 (Standard, Datacenter, Essentials, and FoundationEditions)
  1.4Windows Server 2016 x64 (Standard and Datacenter Editions)
2.Linux x64
  2.1Oracle Linux 7
  2.2Red Hat Enterprise Linux 7框架


.NET版本:
  1.NET Core 2.1 或者更高
  2.NET Framework 4.6.1 或者更高less


· Entity Framework Core版本:
  1.   2.1版本或者更高ide


依赖库:
  1. ODP.NET Core 18.3或者更高
  2.Microsoft.EntityFrameworkCore.Relational 2.1或者更高
  3.Access to Oracle Database 11g Release 2 (11.2) 或者更高

 

正文

 

本篇将采起CodeFirst的形式来建立数据库。。

1.建立数据库

咱们建立上下文与实体以下:

    public class BloggingContext : DbContext
    {
        public DbSet<Blog> Blogs { get; set; }
        public DbSet<Post> Posts { get; set; }

        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
        {
            optionsBuilder.UseOracle(@"SQL Contion", b => b.UseOracleSQLCompatibility("11"));
        }

        protected override void OnModelCreating(ModelBuilder modelBuilder)
        {

        }
    }

    public class Blog
    {
        public int BlogId { get; set; }
        public string Url { get; set; }
        //public int Rating { get; set; }
        public List<Post> Posts { get; set; }
    }

    public class Post
    {
        public int PostId { get; set; }
        public string Title { get; set; }
        public string Content { get; set; }

        public int BlogId { get; set; }
        public Blog Blog { get; set; }
    }

这里咱们先介绍第一个要注意的地方,UseOracle参数里面跟的UseOracleSQLCompatibility方法,里面参数传递的11,指的是oracle11g版本。若是你是12g版本 请传递12.

由于11g和12g的SQL语法有较多不一样的地方,因此用这个来区分。

 

而后咱们add一个版本 执行nuget命令以下:(PS:不懂如何使用codeFirst的请移步:Entity Framework Core 之数据库迁移)

Add-Migration BanBen1

而后将版本更新到数据库以下:

Update-Database

数据库生成成功。

 

2.关于oracle序列的坑

咱们这时候编写插入语句以下:

using (BloggingContext db = new BloggingContext())
            {
                db.Blogs.Add(new Blog { Url = "aaaaa1" });
                db.SaveChanges();
            }

看似没问题的语句,会获得一个错误消息以下:

Index was out of range. Must be non-negative and less than the size of the collection.
Parameter name: index

这是由于咱们没有给主键赋值致使的错误信息。(由于oracle没有自增主键,只能经过序列自增)

那么自增序列如何使用呢?

咱们查看数据库会发现,如图:

codefirst已经帮咱们生成了序列,可是并不会自动使用。咱们须要配置一下:

在上下文中的OnModelCreating方法添加以下代码:

 protected override void OnModelCreating(ModelBuilder modelBuilder)
        {
            modelBuilder.Entity<Post>(entity =>
            {
                entity.ToTable("Posts");
                entity.Property(o => o.PostId).ForOracleUseSequenceHiLo("Posts_PostId_sq3");

            });
            modelBuilder.Entity<Blog>(entity =>
            {
                entity.ToTable("Blogs");
                entity.Property(o => o.BlogId).ForOracleUseSequenceHiLo("Blogs_BlogId_sq1");

            });
        }

指定对应表的序列。

而后在运行。便可添加成功了。

 

3.关于在Docker中部署的坑

在个人生产项目中。应该是打包到docker直接运行部署的。

不过在打包到docker的过程当中又出现了诡异的问题。

就不重现了。。反正就是开发环境没有问题。。直接放到linux中也没问题。可是一旦打包到docker运行 就会查询不到数据。

通过多方查证 最终发现是微软提供的rumtime镜像,由于是精简版系统 因此里面的市区有问题。

在dockerfile中添加以下语句 在生成的时候 设置好时区:

FROM microsoft/dotnet:2.1-aspnetcore-runtime
ENV TZ=Asia/Shanghai

这样就能成功的操做到数据库了。。

 

 

结束语

近期移植了好些个项目到.NET CORE 或多或少遇到了很多坑。。应该算是采坑无数了。。

其实大部分都集中在数据库链接这一块。。好比oracle  DB2 。。(PS:感受也就mysql与sql server支持是最好的。。)

DB2虽然官方发布了。可是他的坑其实比oracle还大。。咱们下篇在写。。

相关文章
相关标签/搜索