dp2 icon indicating copy to clipboard operation
dp2 copied to clipboard

如何为一个工作人员账户设置最小权限,执行出纳操作

Open DigitalPlatform opened this issue 4 years ago • 4 comments

本文尝试探讨如何为一个工作人员账户设置最小权限,执行出纳操作。

在快捷出纳窗扫入读者证条码号之后,显示出读者信息,这时需要 getreaderinfo 权限。getreaderinfo 权限可以查看读者记录的全部字段。这里需要一个略低的权限,可以查看读者记录的一些基本字段,而其它字段在响应中被过滤掉了。

(这里需要改进一下快捷出纳窗,即便当前账户不具备 setreaderinfo 权限,也要让借书操作能顺利进行(假定当前账户仅具有 borrow 权限))

被过滤掉的字段内容被设置了标记,这样当前端把读者记录提交回 dp2library 服务器保存的时候(假设请求者的账户具有 setreaderinfo 权限),服务器能识别出这些字段内容被过滤掉了,从而会避免原记录中的该字段被修改。

DigitalPlatform avatar Jul 10 '21 13:07 DigitalPlatform

获取读者记录字段信息的详细级别

        // 获得一个 level 可以传输的读者 XML 元素名字列表
        // 注: 名字前面有个问号的,表示元素正文在传输中要被马赛克遮盖部分字符
        static List<string> GetElementNames(string level)
        {
            List<string> names = new List<string>();

            // 基本字段。高级信息,借阅的册,违约金, 预约未取参数
            names.AddRange(new string[] {
                "info",
                "borrows",
                "overdues",
                "reservations",
                "outofReservations" });

            // 第一级:证状态,发证日期,失效日期,姓名(除第一字以后都被马赛克)
            names.AddRange(new string[] { "state", "createDate", "expireDate" });
            if (level == "1")
            {
                names.Add("?name");
                return names;
            }
            // 第二级:+ 完整姓名,姓名拼音,显示名,性别,民族,证条码号,参考ID,OI,注释
            names.AddRange(new string[] { "name", "namePinyin", "displayName", "gender", "nation", "barcode", "refID", "oi", "comment" });
            if (level == "2")
                return names;
            // 第三级:+ 单位,职务,地址,读者类型
            names.AddRange(new string[] { "department", "post", "address", "readerType" });
            if (level == "3")
                return names;
            // 第四级:+ 电话,email
            names.AddRange(new string[] { "tel", "email" });
            if (level == "4")
                return names;
            // 第五级:+ 权限,存取定义,书斋名称,好友
            names.AddRange(new string[] { "rights", "access", "personalLibrary", "friends" });
            if (level == "5")
                return names;
            // 第六级:+ 身份证号,出生日期
            names.AddRange(new string[] { "idCardNumber", "birthDate" });
            if (level == "6")
                return names;
            // 第七级:+ 借阅历史,个性化参数等字段
            names.AddRange(new string[] { "borrowHistory", "preference" });
            if (level == "7")
                return names;
            // 第八级:+ 租金押金字段 
            names.AddRange(new string[] { "hire", "foregift" });
            if (level == "8")
                return names;
            // 第九级:+ 指纹,掌纹,人脸特征
            names.AddRange(new string[] { "fingerprint", "palmprint", "face" });
            if (level == "9")
                return names;
            return names;
        }

20210721 更改

dp2installer 测试版 dp2libraryxe 测试和 dp2ssl 测试版更新了。最新版 dp2library 中对各个级别的权限做了调整,充实了基本权限,目的是让基本操作能顺利进行。调整后的各个级别如下:
         // 获得一个 level 可以传输的读者 XML 元素名字列表
        // 注: 名字前面有个问号的,表示元素正文在传输中要被马赛克遮盖部分字符
        static List<string> GetElementNames(string level)
        {
            List<string> names = new List<string>();

            // 基本字段。馆代码,读者类型,证条码号,证号,参考 ID,机构代码(OI),高级信息,借阅的册,违约金, 预约信息,预约到书未取次数
            names.AddRange(new string[] {
                "libraryCode",
                "readerType",
                "barcode",
                "cardNumber",
                "refID",
                "oi",
                "info",
                "borrows",
                "overdues",
                "reservations",   //预约信息
                "outofReservations" });  //预约到书未取次数

            // 第一级:证状态,发证日期,失效日期,姓名(除第一字以后都被马赛克)
            names.AddRange(new string[] { "state", "createDate", "expireDate" });
            if (level == "1")
            {
                names.Add("?name");
                return names;
            }
            // 第二级:+ 完整姓名,姓名拼音,显示名,性别,民族,注释
            names.AddRange(new string[] { "name", "namePinyin", "displayName", "gender", "nation", "comment" });
            if (level == "2")
                return names;
            // 第三级:+ 单位,职务,地址
            names.AddRange(new string[] { "department", "post", "address" });
            if (level == "3")
                return names;
            // 第四级:+ 电话,email
            names.AddRange(new string[] { "tel", "email" });
            if (level == "4")
                return names;
            // 第五级:+ 权限,存取定义,书斋名称,好友
            names.AddRange(new string[] { "rights", "access", "personalLibrary", "friends" });
            if (level == "5")
                return names;
            // 第六级:+ 身份证号,出生日期
            names.AddRange(new string[] { "idCardNumber", "dateOfBirth" });
            if (level == "6")
                return names;
            // 第七级:+ 借阅历史,个性化参数等字段
            names.AddRange(new string[] { "borrowHistory", "preference" });
            if (level == "7")
                return names;
            // 第八级:+ 租金押金字段 
            names.AddRange(new string[] { "hire", "foregift" });
            if (level == "8")
                return names;
            // 第九级:+ 指纹,掌纹,人脸特征,对象(证照片,人脸图片等)
            names.AddRange(new string[] { "fingerprint", "palmprint", "face", "http://dp2003.com/dprms:file" });
            if (level == "9")
                return names;

            return names;
        }

DigitalPlatform avatar Jul 10 '21 13:07 DigitalPlatform

dp2library 账户权限 getreaderinfo 和 setreaderinfo 的增强

最新版 dp2library 对账户权限 getreaderinfo 和 setreaderinfo 做了增强。原先的 getreaderinfo 和 setreaderinfo 权限依然可用,效果和以前版本兼容,即:可以读取读者 XML 记录的所有字段、修改读者 XML 记录的所有字段。(注: password 元素除外)

新增了形态 getreaderinfo:n 和 setreaderinfo:n。其中 n 代表一个数字,表示可存取的字段权限级别,目前是从 1 到 9,可存取的字段从少到多。(如果 n 缺省,则表示可以存取全部字段,相当于最高级别)

从 1 到 9 每一级可以存取的具体字段列表见 "获取读者记录字段信息的详细级别"。

如果字段名前面有个问号,例如 ?name,表示这个字段内容被马赛克部分字符以后传输。

保存读者记录时的 m n 交叉算法

当一个账户同时具备 getreaderinfo:m 和 setreaderinfo:n 权限的时候,表示从服务器获取读者记录的时候,采用 m 级过滤;而前端向服务器提交读者记录保存的时候,会采用 n 级过滤。当 n 级包含的字段超出 m 级的范围的时候,为了防止超出的这部分字段内容在保存瞬间被清空(后面解释),软件规定实际上保存的时候只修改 m 和 n 的交叉部分字段。

为何 m n 情况下单纯地保存记录,部分字段会被清空?因为获取读者记录的时候得到的字段,少于保存时候能修改的字段。这部分保存时候多出来的字段,前端通常无法提供给服务器,那么服务器保存的实际效果就只能是把数据库中的读者记录的这些字段“删除”,也就是清空。

测试建议

  1. 用内务的读者窗,装载读者 XML 记录进行观察。针对账户中 getreaderinfo:m 不同的 m 值的情况。注意,也包括 m 缺乏(为空)的情况。
  2. 先装载已经存在的读者 XML 记录,然后在读者窗里面修改各字段内容后,尝试保存读者记录到 dp2library 服务器。针对账户中没有 setreaderinfo 权限,和有 setreaderinfo:n 权限的情况。注意,也包括 n 缺乏的情况。最后用 dp2rms 前端观察读者记录是否被正确修改。
  3. 账户中同时具备 getreaderinfo:m 权限和 setreaderinfo:n 权限,m 和 n 的各种组合。获取读者记录,然后尝试修改后保存。最后用 dp2rms 前端观察读者记录是否被正确修改。
  4. 用内务的读者窗,创建新的读者记录。针对账户中没有 setreaderinfo 权限,和有 setreaderinfo:n 权限的情况。注意,也包括 n 缺乏的情况。最后用 dp2rms 前端观察读者记录是否被正确创建。
  5. 以上测试过程中,注意观察读者窗中 HTML 格式的显示是否正确。
  6. 用内务的读者窗,删除已经存在的读者记录。针对账户中没有 setreaderinfo 权限,和有 setreaderinfo:n 权限的情况。注意,也包括 n 缺乏的情况。最后用 dp2rms 前端观察读者记录是否被正确删除。目前 dp2library 中删除读者记录的功能,要求当前账户具有对全部读者字段的修改权,也就是 setreaderinfo 权限(注意后面没有冒号和数字)
  7. 用内务的读者查询窗,观察在不同的 getreaderinfo:n 权限情况下浏览列的内容情况,并留意固定面板区“属性”属性页中显示的当前选择行的内容是否正确(符合字段权限规定)。


权限定义 getreaderinfo:m 和 setreaderinfo:n 其中 m 或 n 的用法做了扩展。

以前版本 m 和 n 都必须是数字。最新版这里也可以是 XML 元素名,或者数字和元素名的组合。 例如:getreaderinfo:2|department 表示在二级的基础上增加了 face 元素 再例如: getreaderinfo:2|department|face 表示增加了两个元素。竖线可以用很多次

DigitalPlatform avatar Jul 15 '21 14:07 DigitalPlatform

读者记录中 dprms:file 元素修改的测试

设想一个测试项目:

  1. 创建一个测试用的账户 test,权限为 getreaderinfo,getres,writeobject,setreaderinfo:1 这个账户是可以查看读者记录的全部元素,但修改读者记录只能是 1 级的元素,注意,并不包含dprms.file 元素。
  2. 预先用其它权限较高的账户为这条读者记录增添对象。方法是在读者窗的对象属性页,用上下文菜单增添一个图像文件对象,对象的用途可以输入 "face",这样在读者窗的常规属性页可以看到这个图像。
  3. 用 test 账户登录内务,在读者窗中装入刚才那条读者记录,然后在对象属性页中,标记删除一个对象。然后保存读者记录。应当看到报错说当前账户没有修改 dprms.file 的权限

再有第二个测试项目: 和上面项目的步骤相似,在最后一步,在读者窗对象属性页增添一个新对象,然后保存读者记录,应当看到明确报错。

再有第三个测试项目: 和上面项目的步骤相似,在最后一步,在读者窗对象属性页修改一个对象的内容,但不要修改用途。这时候保存读者记录,应该是成功。因为读者记录 XML 中的 dprms:file 元素并没有发生修改,而是对象被重新上传了,而当前用户是具有修改对象本身的权限的(writeobject)。

再有一个测试项目: 把 test 账户的权限修改为: getreaderinfo,getres,writeobject,setreaderinfo:1|dprms.file 这个权限是可以查看读者记录的全部元素,但修改读者记录的权限改变了,是 1 级的元素加上dprms.file 元素。 操作步骤和上面两个项目相同。最后一步保存读者记录的时候应该成功。关掉读者窗,然后重新装载读者记录进入读者窗,检查修改是否确实兑现了。检查的时候不但要检查读者 XML 记录中的 dprms:file 元素,而且要检查读者窗对象属性页中的对象是否存在,字节数是否发生了修改。

DigitalPlatform avatar Jul 23 '21 03:07 DigitalPlatform

读者身份登录过程中的权限字符串合并

getreaderinfo 和 setreaderinfo 权限控制细化到元素以后,原先的一些处理过程需要改进。

在读者身份利用 dp2library API Login() 登录的过程中,有一步是把 reader 账户的权限字符串和读者 XML 记录中 rights 元素内容,二者合并起来。

假设 reader 账户权限字符串中包含 getreaderinfo 这个权限,读者 XML 记录中的 rights 元素内容中包含 getreaderinfo:1,那么需要妥善处理这两个字符串的合并,具体来说就是如果后者(rights元素内容)中有以 getreaderinfo 开头的权限(包括带冒号和不带冒号的情况),那么对前者(reader 的权限字符串)中要检查去除 getreaderinfo 开头的权限。setreaderinfo 同理。

注意读者身份使用 SetReaderInfo() API 修改读者记录的时候,只允许修改 displayName 和 preferrence 两个元素。所以测试的时候要用这两个元素进行验证

测试建议:

  1. 让 reader 账户权限字符串中包含 getreaderinfo,读者 XML 记录 rights 元素内容中包含 getreaderinfo:1
  2. 让 reader 账户权限字符串中包含 getreaderinfo:1,读者 XML 记录 rights 元素内容中包含 getreaderinfo
  3. 让 reader 账户权限字符串中包含 setreaderinfo,读者 XML 记录 rights 元素内容中包含 setreaderinfo:displayName
  4. 让 reader 账户权限字符串中包含 setreaderinfo:displayName,读者 XML 记录 rights 元素内容中包含 setreaderinfo
  5. 将上述 3) 项改用 setreaderinfo:preferrence 来验证测试
  6. 将上述 4) 项改用 setreaderinfo:preferrence 来验证测试

注:对于读者身份来说,setreaderinfo 实际上只有两个元素的修改权。也就是说 setreaderinfo 等于 setreaderinfo:displayName|preferrence

DigitalPlatform avatar Jul 30 '21 01:07 DigitalPlatform