Chinaunix首页 | 论坛 | 博客
  • 博客访问: 1004242
  • 博文数量: 78
  • 博客积分: 1473
  • 博客等级: 上尉
  • 技术积分: 2124
  • 用 户 组: 普通用户
  • 注册时间: 2012-05-23 12:50
文章分类

全部博文(78)

文章存档

2016年(6)

2015年(2)

2014年(13)

2013年(4)

2012年(53)

分类: 嵌入式

2012-06-23 18:24:06

基于角色的安全性编程入门示例

为了能更好地理解.NET基于角色的安全性,从一个最简单的实例导入角色的应用。首先创建一个简单的控制台程序,如代码清单1-1所示。

代码清单1-1  未添加角色验证的程序

using System;

namespace角色实例

{

    classProgram

    {

        static void Main(string[] args)

        {

            OutHello();

            Console.Read();

        }

        staticvoid OutHello()

        {

            Console.WriteLine("hello world!");

        }

    }

}

如代码清单1-1,这个程序只有两个方法:Main方法和OutHello方法,OutHello方法输出“hello world!”,在Main方法中调用OutHello方法。运行程序会打印字符串“hello world!”。下面对这个简单的程序做略微的修改,为它添加一些声明,如代码清单1-2所示。

代码清单1-2  运行主体和主体权限要求的主体不一致的代码

using System;

using System.Security.Permissions;

using System.Security.Principal;

using System.Threading;

namespace 角色实例

{

    class Program

    {

        static void Main(string[] args)

        {

            Thread.CurrentPrincipal = new WindowsPrincipal(WindowsIdentity.GetAnonymous());

           try

            {

                OutHello();

            }

            catch(SecurityException e)

            {

                Console.WriteLine(e.Message);

            }

            Console.Read();

        }

        [PrincipalPermission(SecurityAction.Demand,Role="Administrators")]

        static void OutHello()

        {

            Console.WriteLine("hello world!");

        }

    }

}

在代码清单1-2中,主要有三处变化:

1)        新添了三个名称空间的引用,分别为System.Security.Permissions、System.Security.Principal和System.Threading。通过第4章的讲解,我们对System.Security.Permissions名称空间已经很熟悉了,这里要使用其中的主体权限(PrincipalPermission)。System.Security.Principal是包含有关主体操作内容的名称空间。System.Threading是有关线程操作的名称空间。

2)        对于OutHello方法,声明了PrincipalPermission权限,要求Administrators组成员才有权限执行此方法。

3)        对于Main方法,使用以下语句设置当前线程的主体为匿名用户:

Thread.CurrentPrincipal = new WindowsPrincipal(WindowsIdentity.GetAnonymous())

下面来看代码清单1-2的运行结果,如图1-1所示。

image

图1-1  代码清单1-2运行结果

图1-1表明,Main方法在调用OutHello方法时引发了SecurityException 异常。因为Main方法设置的主体为匿名用户,而OutHello方法要求的是Administrators组用户。下面把Main方法的执行线程设置为当前的Administrators用户,再看看运行结果。修改后的Main方法如代码清单1-3所示。

代码清单1-3  运行主体和主体权限要求的主体一致的代码

  staticvoid Main(string[] args)

        {

            Thread.CurrentPrincipal = new System.Security.Principal.WindowsPrincipal(WindowsIdentity.GetCurrent());

            try

            {

                OutHello();

            }

            catch (SecurityException e)

            {

                Console.WriteLine(e.Message);

            }

            Console.Read();

        }

代码清单1-3设置了Main方法运行线程的主体为当前用户,本书测试的当前用户为Administrator(最高权限用户,属于Administrators组),此时的运行结果如图1-2所示。

image

图1-2  代码清单1-3的运行结果

 

通过代码清单1-1、代码清单1-2和代码请单1-3的对比,可以粗略地了解主体验证的作用。在前面的代码中采用了声明式安全检查的方法,同其他权限一样,这里仍然可以使用命令式安全检查的方法来达到同样的效果,对于声明式和命令式安全检查还不太熟悉的读者可以回顾第4章的相关内容。修改后的代码如代码清单1-4所示。

代码清单1-4  使用命令式安全检查来指定主体权限

namespace 角色实例

{

    class Program

    {

        static void Main(string[] args)

        {

            Thread.CurrentPrincipal = new System.Security.Principal.WindowsPrincipal(WindowsIdentity.GetCurrent());

            try

            {

                OutHello();

            }

            catch (SecurityException e)

            {

                Console.WriteLine(e.Message);

            }

            Console.Read();

        }

        static void OutHello()

        {

            new PrincipalPermission("", "Administrators").Demand();

            Console.WriteLine("hello world!");

        }

    }

}

代码清单1-4中,通过创建PrincipalPermission类的实例的方式来标识当前方法的主体权限请求。使用PrincipalPermission类比使用PrincipalPermissioAtrribute进行声明的方法更加灵活,可以充分运用它的多个重载方法。下面继续修改Main方法,使用标识对象,如代码清单1-5所示。

代码清单1-5  使用标识

namespace 角色实例

{

    class Program

    {

        static void Main(string[] args)

        {

            GenericIdentity identity = new GenericIdentity("xuanhun");

            string[] roles = new string[] { "Administrators" };

              GenericPrincipal principal = new GenericPrincipal(identity, roles);

              AppDomain.CurrentDomain.SetThreadPrincipal(principal);

            OutHello(); 

 Console.Read();

}

    static void OutHello()

        {

            new PrincipalPermission("xx", "Administrators").Demand();

            Console.WriteLine("hello world!");  }   }

}

在代码清单1-5的Main方法中,首先创建用户自定义的标识对象identity,然后创建角色数组roles,并指定主体拥有的角色数组,最后设定当前应用程序域的主体。在OutHello方法中,要求标识名称为xx;而在Main方法中指定的标识为xuanhun,运行程序将引发异常,如图1-3所示。

image

图1-3  标识不一致的运行结果

到目前为止,我们体验了.NET的角色验证,在感性上有了简单的认识。更详细内容,可以参考《.NET 安全揭秘》第五章。

阅读(1390) | 评论(0) | 转发(1) |
给主人留下些什么吧!~~