ASP.NET Core 2.0 MVC项目实战
一、前言
毕业后入职现在的公司快有一个月了,公司主要的产品用的是C/S架构,再加上自己现在还在学习维护很老的delphi项目,还是有很多不情愿的。之前实习时主要是做.NET的B/S架构的项目,主要还是用的那种传统的开发模式,只有一个项目用到了Web API,自己负责后端的接口功能实现。既然现在没办法改变现状,那就先改变自己吧。定了个计划,下班后慢慢的开始学习ASP.NET Core Web API和Vue,准备从前端到后端自己写一个小项目玩玩,毕竟代码这个东西,时间长了是会忘的。
嗯,有点扯远了。这个MVC项目是我的毕业设计,虽然写的比较烂,而且当时为了赶紧写完,代码的冗余程度有点高,但还是希望能给一些准备入门ASP.NET Core MVC的童鞋提供些借鉴吧。代码我放到Github上了,源码地址https://github.com/Lanesra712/Danvic.PSU,欢迎大神们拍砖,指出不足处。
二、项目介绍
毕业论文的课题是一个大学生的一个报名系统,主要是为了完成大学生报名过程中的一些数据维护,当然最后因为实在来不及了,好多都没做。。。项目主要使用到的相关技术如下所示:
- 项目框架:ASP.NET Core 2.0 MVC
- ORM:Entity Framework Core(使用Code First)
- 数据库引擎:MySQL SERVER 5.7
- 权限验证:基于策略的权限验证(Policy-Based Authorization)
- 前端框架:AdminLte(一个基于Bootstrap的开源前端UI)
- 表格控件:Jquery Datatables
- 数据可视化组件:Echarts
- 日志记录:nlog
三、设计与实现介绍
项目架构采用的是多层架构,通过拆分不同的功能领域,实现各个功能间的相对独立,项目在VS中搭建完成后如下图所示。

01_Entity:实体层,包含PSU.Entity这一个系统组件,用于存储数据库中表所对应的C#对象实体。
02_Infrastructure:基础架构层,包含PSU.EFCore、PSU.Utility两个系统组件。PSU.EFCore类库通过引用Entity Framework Core来完成对于数据库的操作。PSU.Utility类库中包含系统开发过程中可能用到的帮助类文件。
03_Logic:逻辑层,包含PSU.Domain、PSU.Repository两个系统组件。PSU.Domain用于继承每个领域的接口类库(PSU.IService),实现领域接口中的功能。PSU.Repository用来实现PSU.Domain类库中所包含的对于数据库的操作。
04_Rule:规则层,包含PSU.IService、PSU.Model这两个系统组件。PSU.IService为系统领域功能接口类库,PSU.Model为视图所对应的数据充血模型,对应MVC模式中的实体Model。
Controller.PSU:控制器层,.NET Core类库,用来存放MVC模式中的各种控制器文件。
PSU.Site:表现层,ASP.NET Core MVC项目,项目主程序。
系统权限验证设计:
整个系统分为三种角色,分别为管理员、教职工、学生用户,通过使用Area搭建每个角色的页面,通过在Controller上添加Area特性,指定当前Controller属于的角色。在创建用户时,会指定用户的角色字段,当用户登录成功后,会根据用户角色进行Claim的创建,通过自定义的AuthorizztionHandler来实现对于当前系统的角色权限控制。
当用户登录成功后,会将当前的用户信息赋值给一个静态类(使用Session进行存储),对于判断用户是否登录,则是通过自定义一个控制器的基类,重写OnActionExecuting方法来实现对于用户是否登录的判断,实现代码如下。
public class DanvicController : Controller
{
/// <summary>
/// 判断用户是否登录
/// </summary>
/// <param name="filterContext"></param>
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
if (CurrentUser.UserId == )
{
string path = filterContext.HttpContext.Request.Path;
filterContext.Result = new RedirectResult($"/Secret/Login?ReturnUrl={path}");
return;
}
base.OnActionExecuting(filterContext);
}
}
自定义控制器基类
public static class CurrentUser
{
#region Initialize private static IHttpContextAccessor _httpContextAccessor; private static ISession _session => _httpContextAccessor.HttpContext.Session; public static void Configure(IHttpContextAccessor httpContextAccessor)
{
_httpContextAccessor = httpContextAccessor;
} #endregion #region Attribute /// <summary>
/// 用户主键
/// </summary>
public static string UserOID
{
get => _session == null ? "" : _session.GetString("CurrentUser_UserOID");
set => _session.SetString("CurrentUser_UserOID", !string.IsNullOrEmpty(value) ? value : "");
} /// <summary>
///用户编号
/// </summary>
public static long UserId
{
get => _session == null ? : Convert.ToInt64(_session.GetString("CurrentUser_UserId"));
set => _session.SetString("CurrentUser_UserId", value != ? value.ToString() : "");
} /// <summary>
/// 用户姓名
/// </summary>
public static string UserName
{
get => _session == null ? "" : _session.GetString("CurrentUser_UserName");
set => _session.SetString("CurrentUser_UserName", !string.IsNullOrEmpty(value) ? value : "");
} /// <summary>
/// 用户登录账户
/// </summary>
public static string UserAccount
{
get => _session == null ? "" : _session.GetString("CurrentUser_UserAccount");
set => _session.SetString("CurrentUser_UserAccount", !string.IsNullOrEmpty(value) ? value : "");
} /// <summary>
/// 用户头像地址
/// </summary>
public static string UserImage
{
get => _session == null ? "" : _session.GetString("CurrentUser_UserImage");
set => _session.SetString("CurrentUser_UserImage", !string.IsNullOrEmpty(value) ? value : "");
} /// <summary>
/// 用户角色
/// </summary>
public static string UserRole
{
get => _session == null ? "" : _session.GetString("CurrentUser_UserRole");
set => _session.SetString("CurrentUser_UserRole", !string.IsNullOrEmpty(value) ? value : "");
} /// <summary>
/// 主页地址
/// </summary>
public static string UserPage
{
get => _session == null ? "" : _session.GetString("CurrentUser_UserPage");
set => _session.SetString("CurrentUser_UserPage", !string.IsNullOrEmpty(value) ? value : "");
} #endregion
}
CurrentUser类
权限验证代码如下截图所示:
控制器示例图:

基于策略的权限验证实现:

自定义验证Claim:

四、总结
接下来我要开始学习ASP.NET Core Web API和Vue了,希望可以保持住,能够不间断的在博客上分享自己的学习经历与见解。当学的差不多的时候,争取把这个项目精简,重构,让自己在成为更好的自己的路途上前进一大步。
因为也是第一次使用ASP.NET Core MVC进行项目的开发,所以遇到了一些自己没办法解决的东西,很感谢博客园里的各位大佬以及一些帮助我的大佬,正是因为有这么多乐于分享的人在,才能更好的推动.NET Core在国内的生态发展,在写毕业设计的过程中,参考了很多位博主的博文,真的是很感谢,致敬。
还是要推广下自己的个人博客啊,点击这里,去看看我的博客啊~~~
项目实现图如下。



ASP.NET Core 2.0 MVC项目实战的更多相关文章
- ASP.NET CORE 1.0 MVC API 文档用 SWASHBUCKLE SWAGGER实现
from:https://damienbod.com/2015/12/13/asp-net-5-mvc-6-api-documentation-using-swagger/ 代码生成工具: https ...
- ASP.NET Core 2.0 : 三. 项目结构
本章我们一起来对比着ASP.NET Framework版本看一下ASP.NET Core 2.0的项目结构.(此后的文章也尽量这样对比着, 方便学习理解.) 关注差异, 也为项目迁移做准备. 新建项目 ...
- 快读《ASP.NET Core技术内幕与项目实战》EFCore2.5:集合查询原理揭秘(IQueryable和IEnumerable)
本节内容,涉及4.6(P116-P130).主要NuGet包:如前述章节 一.LINQ和EFCore的集合查询扩展方法的区别 1.LINQ和EFCore中的集合查询扩展方法,虽然命名和使用完全一样,都 ...
- 快读《ASP.NET Core技术内幕与项目实战》WebApi3.1:WebApi最佳实践
本节内容,涉及到6.1-6.6(P155-182),以WebApi说明为主.主要NuGet包:无 一.创建WebApi的最佳实践,综合了RPC和Restful两种风格的特点 1 //定义Person类 ...
- asp.net core 3.0 MVC JSON 全局配置
asp.net core 3.0 MVC JSON 全局配置 System.Text.Json(default) startup配置代码如下: using System.Text.Encodings. ...
- 简读《ASP.NET Core技术内幕与项目实战》之3:配置
特别说明:1.本系列内容主要基于杨中科老师的书籍<ASP.NET Core技术内幕与项目实战>及配套的B站视频视频教程,同时会增加极少部分的小知识点2.本系列教程主要目的是提炼知识点,追求 ...
- 《ASP.NET Core技术内幕与项目实战》精简集-目录
本系列是杨中科2022年最新作品<ASP.NET Core技术内幕与项目实战>及B站配套视频(强插点赞)的精简集,是一个读书笔记.总结和提炼了主要知识点,遵守代码优先原则,以利于快速复习和 ...
- asp.net Core 2.0 MVC为Controller或Action添加定制特性实现登录验证
前言:最近在倒腾 微软的新平台 asp.net Core 2.0,在这个过程中有些东西还是存在差异.下面是我在学习过程的一点笔记.有不妥之处,望各位大虾指正! 一.先创建一个控制器继承于Control ...
- ASP.NET Core 2.0 MVC - 获取当前登录用户信息
一.前言 上篇实战完成后,没想到会有那么多的圈友给了那么多的支持,甚至连只是作为代码仓储的git上也给了一些小星星,真的感觉很惶恐啊,哈哈哈,毕竟代码写的很烂啊.由于上一篇只是大概说了下项目,所以准备 ...
随机推荐
- HTML5+CSS3 1
html5标准模板 <!DOCTYPE html> //<!DOCTYPE>标签 向浏览器声明当前文档使用的HTML版本,<!DOCTYPE html>适用于所 ...
- Codeforces 939E Maximize! (三分 || 尺取)
<题目链接> 题目大意:给定一段序列,每次进行两次操作,输入1 x代表插入x元素(x元素一定大于等于之前的所有元素),或者输入2,表示输出这个序列的任意子集$s$,使得$max(s)-me ...
- 【Linux】如何在Linux上安装使用SSH
SSH是什么? Secure Shell 安全外壳协议 建立在应用层基础上的安全协议 可靠,专为远程登录会话和其他网络服务提供安全性的协议 有效防止远程管理过程中的信息泄露问题 SSH客户端适用于多种 ...
- C#实现 单点登录(SSO)
SSO的基本概念 SSO英文全称Single Sign On(单点登录).SSO是在多个应用系统中,用户只需要登录一次就可以访问所有相互信任的应用系统.它包括可以将这次主要的登录映射到其他应用中用于同 ...
- [OC] 添加 pch 文件
第一步: Xcode左上角 File - New - File, Other - PCH File 第二步, 在图中位置,写入 pch 的路径. 路径可以将 pch 文件拖入终端来得到.
- VB用API模拟截屏键PrintScreen
很多人用 SendKeys "{PRTSC}" 模拟截屏键 PrintScreen 的时候提示<错误:'70' 拒绝的权限>,于是经常遇到人问...干脆写下来 '声明 ...
- hadoop2-MapReduce详解
本文是对Hadoop2.2.0版本的MapReduce进行详细讲解.请大家要注意版本,因为Hadoop的不同版本,源码可能是不同的. 以下是本文的大纲: 1.获取源码2.WordCount案例分析3. ...
- Mac软件安装提示程序已损坏解决方案
---恢复内容开始--- 最近下载好的Mac软件安装时,系统跳出该程序已损坏: 嗯……估计是因为下载了破解版,被系统屏蔽,重设一下安全设置就好: 很兴奋的打开系统偏好设置->安全性与隐私: 然而 ...
- Javaweb-request与response
Javaweb-request与response Servlet 生命周期(什么时候创建的,什么时候销毁的); Se ...
- Android Studio 去除上方标题
选中代码再Ctrl+shift+'/' 可加/***/注释 https://blog.csdn.net/wuqingsen1/article/details/78554117 styles.xml & ...