七层登陆

举报
Laura_张 发表于 2022/08/27 01:12:21 2022/08/27
【摘要】 【前言】 三层 UI层(界面层):主要是指与用户交互的界面,用于接收用户的请求然后通过一系列的处理然后返回给用户相应的数据。 BLL层(业务处理层):是UI层和DAL层的桥梁,通过BLL层事项UI...

【前言】

三层

UI层(界面层):主要是指与用户交互的界面,用于接收用户的请求然后通过一系列的处理然后返回给用户相应的数据。

BLL层(业务处理层):是UI层和DAL层的桥梁,通过BLL层事项UI和DAL的业务逻辑。

DAL层(数据访问层):与数据库打交道,主要实现对数据的增删改查,将存储在数据库中的数据提交给业务层,同时将业务层处理的数据保存到数据库。(当然这些操作都是基于UI层的。用户的需求反映给界面(UI),UI反映给BLL,BLL反映给DAL,DAL进行数据的操作,操作后再一一返回,直到将用户所需数据反馈给用户)。

使用三层最主要的目的是解耦,三层各司其职,任何一层都不会影响到其他的两层。

【正文】

七层比三层多了外观层(Facade)、工厂层(Factory)、实体层(Entity)和接口层(IDAL)

七层的功能:
在这里插入图片描述

七层之间的引用如下:
在这里插入图片描述

七层架构:
在这里插入图片描述

一、创建登陆窗体

在这里插入图片描述

二、配置App.config文件

配置文件在UI层里面

在这里插入图片描述

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <startup> 
        <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7.2" />
    </startup>
	
	<!--配置数据库-->
	<appSettings>
		<add key="DB" value="DAL"/>
		<add key="conStr" value="server=ZYW;Database=charge_sys;UserID=sa;PassWord=123456"/>
	</appSettings>
</configuration>

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

三、实体层(Entity)代码

每一层设计都会用到到实体层,实体层也是比较简答的一层,实体层中的命名和数据库中的命名要一致。

namespace Entity
{
    public class UserInfo
    {
        //定义 用户ID
        private string userid;
        public string UserID
        {
            get { return userid; }
            set { userid = value; }
        }
        //定义用户密码
        private string userpwd;
        public string UserPwd
        {
            get { return userpwd;}
            set { userpwd = value;}
        }
        //定义用户类型字段
        private string userlevel;
        public string UserLevel
        {
            get { return userlevel; }
            set { userlevel = value; }
        }
        //定义用户名字
        private string username;
        public string UserName
        {
            get { return username; }
            set { username = value; }
        }
    }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35

四、接口层(IDAL)

定义一个接口层,用于使用D层中的各个功能,具体实现要靠D层实现。

using System.Data;

namespace IDAL
{
    //接口层
    public interface LoginIDAL
    {
        //接口函数,判断要登录的用户名是否在数据表中存在
        DataTable SelectUser(Entity.UserInfo user);
    }
}

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

五、DAL层

IDAL层完成之后是DAL层,主要目的是访问数据。

SQLHelper

using System.Configuration;//配置文件
using System.Data.SqlClient;
using System.Data;

namespace DAL
{
    /// <summary>
    /// 数据操作类
    /// </summary>
    public class SQLHelper
    {
        //定义数据库连接操作,指定在数据库上操作的类型
        private SqlConnection conn = null;
        private SqlCommand cmd = null;
        private SqlDataReader sdr = null;//定义数据库只读

        //数据库连接
        public SQLHelper()
        {
            string connStr = ConfigurationManager.AppSettings["ConStr"];
            conn = new SqlConnection(connStr);

        }
        /// <summary>
        /// 
        /// 打开数据库连接
        /// </summary>
        /// <returns></returns>
        private SqlConnection GetConn()
        {
            if (conn.State == System.Data.ConnectionState.Closed)
            {
                conn.Open();
            }
            return conn;

        }

        ///<summary>
        ///执行不带参数的数据库操作或者存储过程
        /// 增删改查操作
        /// 返回受影响的行数
        ///</summary>
        public int ExecuteNonQuery(string cmdText, CommandType ct)
        {
            int res;
            cmd = new SqlCommand(cmdText, GetConn());
            cmd.CommandType = ct;
            res = cmd.ExecuteNonQuery();
            if (conn.State == System.Data.ConnectionState.Open)
            {
                conn.Close();
            }
            return res;
        }
        /// <summary>
        /// 执行带参数的数据库操作或者存储过程
        /// </summary>
        /// <param name="cmdText">SQL语句或者存储过程名</param>
        /// <param name="paras">SQLCommand参数集合</param>
        /// <param name="ct">执行的命令类型</param>
        /// <returns></returns>

        public int ExecuteNonQuery(string cmdText, SqlParameter[] paras, CommandType ct)
        {
            int res;
            using (cmd = new SqlCommand(cmdText, GetConn()))
            {
                cmd.CommandType = ct;
                cmd.Parameters.AddRange(paras);
                res = cmd.ExecuteNonQuery();

            }
            return res;
        }
        //执行不带参数的SqL查询语句或者存储过程
        public DataTable ExecuteQuery(string cmdText, CommandType ct)
        {
            DataTable dt = new DataTable();
            cmd = new SqlCommand(cmdText, GetConn());
            cmd.CommandType = ct;
            using (sdr = cmd.ExecuteReader(System.Data.CommandBehavior.CloseConnection))
            {
                dt.Load(sdr);

            }
            return dt;

        }

        //执行带参数的SQL查询语句或存储过程
        public DataTable ExecuteQuery(string cmdText, SqlParameter[] paras, CommandType ct)
        {
            DataTable dt = new DataTable();
            cmd = new SqlCommand(cmdText, GetConn());

            cmd.CommandType = ct;
            cmd.Parameters.AddRange(paras);
            //System.Data.SqlClient.SqlException:“对象名 'user_info' 无效。”
            using (sdr = cmd.ExecuteReader(CommandBehavior.CloseConnection))
            {
                dt.Load(sdr);
            }
            return dt;

        }

    }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110

LoginDAL

using System.Data;
using System.Data.SqlClient;

namespace DAL
{
    public class LoginDAL:IDAL.LoginIDAL
    {
        public DataTable SelectUser(Entity.UserInfo user)
        {
            //实例化操作类,进行数据查询,并获取返回值
            SQLHelper sqlHelper = new SQLHelper();
            SqlParameter[] sqlparams =
            { 
                new SqlParameter(@"Userid",user.UserID),
                new SqlParameter (@"Userpwd",user.UserPwd)
            };
            //执行数据库的查询
            string sql = @"SELECT * FROM User WHERE userId=@UserID AND userpwd=@UserPwd";//构造语句,匹配数据库表
            //执行数据库操作
            DataTable dt = sqlHelper.ExecuteQuery(sql, sqlparams, CommandType.Text);
            //返回表到到BLL层
            return dt;
        }

    }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27

六、工厂层(Factory)

工厂层用了配置文件—反射的知识(抽象工厂里面有介绍)。

using System.Reflection;


namespace Factory
{
    /// <summary>
    /// 机房配置文件和反射
    /// </summary>
    public class LoginFactory
    {
        //获取配置文件
        //ConfigurationManager类需要在引用中添加systems.Configuration
        string StrDB = System.Configuration.ConfigurationManager.AppSettings["DB"];
        //应用反射来获取DAL层操作
        public IDAL.LoginIDAL CreatUser()
        {
            string ClassName = StrDB + "." + "LoginDAL";
            //Assembly.Load()在给定程序集的情况下,加载该程序集;CreateInstance()方法:
            //使用默认构造函数创建指定类型的实例;
            //使用反射机制也就是将原来实例化的new DAL.LoginDAL这一步交给了外部容器去做,
            //现在需要更改实例化对象时,只需更改配置文件即可。使用更方便灵活
            return (IDAL.LoginIDAL)Assembly.Load(StrDB).CreateInstance(ClassName);
            //将DAL属性的路径改为UI/bin/Debug(否则出现错误)

        }
    }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28

七、数据传输层(BLL)

BLL层的作用是根据句返回值判断账户是否存在。

B层并没有直接调用DAL层,而是调用了Factory层和IDAL层,这样的目的是为了解耦。

using System.Data;

namespace Login.BLL
{
    public class LoginBLL
    {
        public bool UserBLL(Entity.UserInfo user)
        {
            //实例化工厂
            Factory.LoginFactory fact = new Factory.LoginFactory();
            //调用工厂方法创建接口
            IDAL.LoginIDAL idal = fact.CreatUser();

            //接受D层的返回值
            //System.Data.SqlClient.SqlException:“对象名 'user_info' 无效。”
            //System.MissingMethodException:“找不到方法:“System.String Entity.UserInfo.get_PassWord()”。”
            //应该是数据库里面字段和代码不一致
            DataTable table = idal.SelectUser(user);

            bool flag;
            if (table.Rows.Count==0)//返回数据表类型,如果行数=0;说明没有符合该账号密码的用户
            {
                flag = false;
            }
            else
            {
                flag = true;
            }
            return flag;//返回数值,账号存在
        }
    }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33

八、外观层(Facade)

Facade层用于降低UI层和BLL层之间的耦合,外观层接收UI层传来的数据,然后调用B层的方法对信息进行验证。

using System;

namespace Facade
{
    /// <summary>
    /// 外观类,解除U层和B层的耦合,外观类中包含B层对D层的所有操作
    /// </summary>
    public class LoginFacade
    {
        //判断用户是否存在,并提供返回值flag
        public Boolean SelectUser(Entity.UserInfo user)
        {
            bool flag;
            //实例化逻辑类的一个实例
            Login.BLL.LoginBLL userBLL =new Login.BLL.LoginBLL ();

            flag = userBLL.UserBLL(user);
            return flag;
        }
    }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22

九、UI层

调用Facade层的数据操作方法,然后实现登陆。

using System;
using System.Windows.Forms;

namespace UI
{
    public partial class FrmLogin : Form
    {
        public FrmLogin()
        {
            InitializeComponent();
        }


        //执行登陆窗体
        private void btnLogin_Click(object sender, EventArgs e)
        {
            //判断账号和密码是否为空
            if (txtUserID.Text == "" || txtUserPwd.Text == "")
            {
                MessageBox.Show("账号或密码不能为空!", "温馨提示",
                    MessageBoxButtons.OK, MessageBoxIcon.Information);
            }
            else
            {

                //实例化一个外观
                Facade.LoginFacade Facade = new Facade.LoginFacade();
                //实例化一个用户
                Entity.UserInfo user = new Entity.UserInfo();

                //实例的用户接受信息
                user.UserID  = txtUserID.Text;
                user.UserPwd = txtUserPwd.Text;

                //调用外观方法,返回给user
                Boolean flag = false;
                Facade.LoginFacade FLogin = new Facade.LoginFacade();

                flag = FLogin.SelectUser(user);
                bool Flase = false;

                //判断是否登录成功
                if (flag != Flase)
                {
                    MessageBox.Show("登录成功");
                    this.Hide();

                    this.DialogResult = System.Windows.Forms.DialogResult.OK;
                    Form a = new Form();

                    a.Show();
                }
                else
                {
                    MessageBox.Show("用户名或密码不正确");
                }
            }
        }
    }
}


  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61

【写在后面】

现在UI层、Facade层、BLL层、Factory层是根据系统功能分类,比如类名是frmLogin、LoginFacede、LoginManager、LoginFactory,而IDAL层、DAL层、Entity层根据数据表分类比如IUserInfo、UserInfoDAO、UserInfo。

欢迎斧正~

文章来源: blog.csdn.net,作者:张艳伟_Laura,版权归原作者所有,如需转载,请联系作者。

原文链接:blog.csdn.net/Laura__zhang/article/details/113234692

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。