public class Post { public int PostId { get; set; } public string Title { get; set; } public string Content { get; set; }
public List<PostTag> PostTags { get; set; } }
public class Tag { public string TagId { get; set; }
public List<PostTag> PostTags { get; set; } }
public class PostTag { public int PostId { get; set; } public Post Post { get; set; }
public string TagId { get; set; } public Tag Tag { get; set; } }
一对多
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
// 博客 public class Blog { public int BlogId { get; set; } public string Url { 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; } }
Post是依赖实体
Blog是主体实体
Blog.BlogId是主体键(在本例中为主密钥,而不是备用密钥)
Post.BlogId为外键
Post.Blog是一个引用导航属性
Blog.Posts是集合导航属性
Post.Blog是的反向导航属性
一对一
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
public class Blog { public int BlogId { get; set; } public string Url { get; set; }
public BlogImage BlogImage { get; set; } }
public class BlogImage { public int BlogImageId { get; set; } public byte[] Image { get; set; } public string Caption { get; set; }
public int BlogId { get; set; } public Blog Blog { get; set; } }
await using (var context = new BloggingContext()) { var blog = await context.Blogs.Include(b => b.Posts).FirstAsync(); var post = new Post { Title = "Intro to EF Core" };
await using (var context = new BloggingContext()) { var blog = new Blog { Url = "http://blogs.msdn.com/visualstudio" }; var post = await context.Posts.FirstAsync();
public class Group { public Guid ID { get; set; } public string Name { get; set; } public Guid? ParentID { get; set; } public Group Parent { get; set; } public ICollection<Group> Children { get; } = new List<Group>(); }
查询子树
1 2 3
var data = (await _context.Group.ToListAsync()) .Where(g => g.ID == new Guid(groupId)) .ToList();
EntityFrameworkCore.SqlServer.HierarchyId 数据库上下文需要配置启用HierarchyId,否则出现下述异常 The property is of type ‘HierarchyId’ which is not supported by current database provider. Either change the property CLR type or ignore the property using the ‘[NotMapped]’ attribute or by using ‘EntityTypeBuilder.Ignore’ in ‘OnModelCreating’.
public class Group { public Guid ID { get; set; } public string Name { get; set; } public HierarchyId GroupLevel { get; set; } public ICollection<Group> Children { get; } = new List<Group>(); }
查询linq
1 2 3 4 5 6 7 8 9
public async Task<List<Group>> GetChildrenByGroupIDAsync(Guid groupID) { Group self = await _context.Groups.FindAsync(groupID); List<Group> groups = await _context.Groups .Where(g => g.GroupLevel.IsDescendantOf(self.GroupLevel)) .ToListAsync();
Exception: An exception has been raised that is likely due to a transient failure. Consider enabling transient error resiliency by adding ‘EnableRetryOnFailure()’ to the ‘UseSqlServer’ call.
如上一个insert数据的接口,在有限的并发条件下(也就是for循环几条请求),个别错误数据可以造成其他正常数据插入失败 报 this sqltransaction has completed it is no longer usable 以及 zombie check等解释 查了2天资料未能解决 次日反思 问题或许出在多条线程同时向数据库上下文中推数据(即_context.Add)其中一个错误数据的出错,事务自动回滚,导致了其他线程中访问该事务已不可用。 此处使用_context.AddAsync方法可以解决 即,该问题就是个ef方法的线程安全的问题,可见StackOverflow: AddAsync vs Add 那么我一个需求要添加user并为其分配新的group,一个事务里两个add操作怎么办呢,另起一小节:
关于以事务作为上下文生命周期的配置, 见StackOverflow:Configuring Dbcontext as Transient然而!经实践同一接口的并发测试 仍然会出现this sqltransaction has completed it is no longer usable的异常 依赖注入的DBContext 在Startup的ConfigureServices中注册MyDBContext服务提供程序:
public void RunWorkers() { using (var context = new MyDbContext(_dbOptions)) { using (var tran = context.Database.BeginTransaction()) { foreach (var worker in _workers) worker.DoWork(() => { // This won't work var db = new MyDbContext(_dbOptions); // And this one will even throw exception when used with in-memory database (during unit testing) db.Database.UseTransaction(tran.GetDbTransaction()); return context; });
SELECT CAST(t1.num AS varchar) from t1; SELECT CONVERT(varchar, t1.num) from t1;
将自然键替换为人工键
原实体以序列号为主键,现添加ID列并填充GUID
1 2 3
ALTER TABLE dbo.Table1 DROP CONSTRAINT PK_Table1 // 移除原主键 ALTER TABLE dbo.Table1 DROP COLUMN SerialNumber // 移除列 ALTER TABLE dbo.Table1 ADD ID uniqueidentifier NOT NULL default newID()
exception The object ‘DFTable1ID__34C8D9D1’ is dependent on column ‘ID’. ALTER TABLE DROP COLUMN failed because one or more objects access this column
ID作为列名会默认添加CONSTRAINT,如上所提及的DFTable1ID34C8D9D1 因此要删除这个ID列需要先 ALTER TABLE dbo.Table1 DROP CONSTRAINT DFTable1ID34C8D9D1
层次结构数据
具有父级、子级关系的层次结构数据 Oracle的递归查询语法:
1
select * from t_dw CONNECT BY PRIOR id = parentID START WITH id='dw001'
-- 根节点 / update t_dw set orgLvl=HierarchyID::GetRoot() where parentID is null -- 子树 /1/,/2/ update t_dw set orgLvl=HierarchyID::Parse('/1/') where name='dw1' update t_dw set orgLvl=HierarchyID::Parse('/2/') where name='dw2' -- 叶 /1/3/ update t_dw set orgLvl=HierarchyID::Parse('/1/1/') where name='dw1-a'
插入
1 2 3
insert t_dw (id,name,ParentID,orgLvl) values(newid(),'dw1-b','xxxxxxxxxxxxxxx', HierarchyID::Parse('/1/').GetDescendant(CAST('/1/1/' AS hierarchyid), NULL))
得到/1/2/ dw1-b 即在/1/的子节点,左树为/1/1/右树为null位置插入新节点
层级
1
SELECT CAST('/1/2/' AS hierarchyid).GetLevel() -- 结果:2
后代
1 2 3
SELECT name, orgLvl.ToString() FROM t_dw WHERE orgLvl.IsDescendantOf(CAST('/1/' AS hierarchyid)) = 1
select schema_name(t.schema_id) as [Schema], t.name as TableName,i.rows as [RowCount] from sys.tables as t, sysindexes as i where t.object_id = i.id and i.indid <=1
按rownumber删除
1 2 3 4
; with cte(rownum)as( select row_number () over(partition by [Col1], [Col2] order by Col3) from [table] ) delete from cte where rownum > 1
$DOCUMENTS 文档目录。一个当前用户典型的路径形如 C:\Documents and Settings\Foo\My Documents。这个常量的内容(所有用户或当前用户)取决于 SetShellVarContext 设置。默认为当前用户。 该常量在 Windows 95 且 Internet Explorer 4 没有安装时无效。
$SENDTO 该目录包含了“发送到”菜单快捷项。
$RECENT 该目录包含了指向用户最近文档的快捷方式。
$FAVORITES 该目录包含了指向用户网络收藏夹、文档等的快捷方式。这个常量的内容(所有用户或当前用户)取决于 SetShellVarContext 设置。默认为当前用户。 该常量在 Windows 95 且 Internet Explorer 4 没有安装时无效。
$MUSIC 用户的音乐文件目录。这个常量的内容(所有用户或当前用户)取决于 SetShellVarContext 设置。默认为当前用户。 该常量仅在 Windows XP、ME 及以上才有效。
$PICTURES 用户的图片目录。这个常量的内容(所有用户或当前用户)取决于 SetShellVarContext 设置。默认为当前用户。 该常量仅在 Windows 2000、XP、ME 及以上才有效。
$VIDEOS 用户的视频文件目录。这个常量的内容(所有用户或当前用户)取决于 SetShellVarContext 设置。默认为当前用户。 该常量仅在 Windows XP、ME 及以上才有效。
$NETHOOD 该目录包含了可能存在于我的网络位置、网上邻居文件夹的链接对象。 该常量在 Windows 95 且 Internet Explorer 4 和活动桌面没有安装时无效。
$APPDATA 应用程序数据目录。当前用户路径的检测需要 Internet Explorer 4 及以上。所有用户路径的检测需要 Internet Explorer 5 及以上。这个常量的内容(所有用户或当前用户)取决于 SetShellVarContext 设置。默认为当前用户。 该常量在 Windows 95 且 Internet Explorer 4 和活动桌面没有安装时无效。
$PRINTHOOD 该目录包含了可能存在于打印机文件夹的链接对象。 该常量在 Windows 95 和 Windows 98 上无效。
$INTERNET_CACHE Internet Explorer 的临时文件目录。 该常量在 Windows 95 和 Windows NT 且 Internet Explorer 4 和活动桌面没有安装时无效。
$COOKIES Internet Explorer 的 Cookies 目录。 该常量在 Windows 95 和 Windows NT 且 Internet Explorer 4 和活动桌面没有安装时无效。
$HISTORY Internet Explorer 的历史记录目录。 该常量在 Windows 95 和 Windows NT 且 Internet Explorer 4 和活动桌面没有安装时无效。
$PROFILE 用户的个人配置目录。一个典型的路径如 C:\Documents and Settings\Foo。 该常量在 Windows 2000 及以上有效。
$ADMINTOOLS 一个保存管理工具的目录。这个常量的内容(所有用户或当前用户)取决于 SetShellVarContext 设置。默认为当前用户。 该常量在 Windows 2000、ME 及以上有效。
$RESOURCES 该资源目录保存了主题和其他 Windows 资源(通常为 C:\Windows\Resources 但在运行时会检测)。 该常量在 Windows XP 及以上有效。
$RESOURCES_LOCALIZED 该本地的资源目录保存了主题和其他 Windows 资源(通常为 C:\Windows\Resources\1033 但在运行时会检测)。 该常量在 Windows XP 及以上有效。
$CDBURN_AREA 一个在烧录 CD 时储存文件的目录。. 该常量在 Windows XP 及以上有效。
$HWNDPARENT 父窗口的十进制 HWND。
$PLUGINSDIR 该路径是一个临时目录,当第一次使用一个插件或一个调用 InitPluginsDir 时被创建。该文件夹当解压包退出时会被自动删除。这个文件夹的用意是用来保存给 InstallOptions 使用的 INI 文件、启动画面位图或其他插件运行需要的文件。
NGX-Translate is an internationalization library for Angular. NGX-Translate is also extremely modular. It is written in a way that makes it really easy to replace any part with a custom implementation in case the existing one doesn’t fit your needs.
export class AppComponent { constructor(translate: TranslateService) { // this language will be used as a fallback when a translation isn't found in the current language translate.setDefaultLang('en'); // the lang to use, if the lang isn't available, it will use the current loader to get them translate.use('en'); } }
msgctxt "ErrorMessage|" msgid "" "Application preferences have been damaged. Reinstall the application to " "solve the problem." msgstr "" "Předvolby aplikace byly poškozeny. Problém vyřešíte opětovnou instalací " "aplikace." ====> { ... "ErrorMessage|":{ msgctxt:"ErrorMessage|", msgid:"Application preferences have been damaged. Reinstall the application to solve the problem.", msgstr:["Předvolby aplikace byly poškozeny. Problém vyřešíte opětovnou instalací aplikace."] } }
ng build, ng serve是JIT, ng build —aot, ng build —prod, ng serve —aot是AOT 从Angular 9开始,默认情况下,对于提前编译器,编译选项设置为true。
JIT(Just in Time)由浏览器将源码编译成js执行,QQs:浏览器居然可以编译代码! AOT(Ahead of Time)先编译成可执行的js,再交给浏览器
The Angular ahead-of-time (AOT) compiler converts Angular HTML and TypeScript code into efficient JavaScript code during the build phase, before the browser downloads and runs that code. This is the best compilation mode for production environments, with decreased load time and increased performance compared to just-in-time (JIT) compilation.AOT 编译器在浏览器下载并运行之前,将Angular HTML、 ts代码转为es5代码,是生产环境的最佳实践,相比JIT更能缩短加载时间并提高性能 (aot会根据angular.json 的配置生成到/dist之类的目录) 在angular.json中配置build命令的选项,包括生成目录等