ABP框架中导航菜单的使用及JavaScript API获取菜单的方法
每一个web应用程序都有导航菜单,abp也为用户提供了通用的创建和显示菜单方式。
创建菜单
一个应用程序可能包含不同的模块,而每个模块都可能有它自己的菜单项。在abp中,需要创建一个派生自navigationprovider的类来定义一个菜单项。
假设我们有一个这样的主菜单:
- tasks
- reports
- administration 1 user management 2 role management
由上可知,administration菜单项有两个子菜单项。对应的生成方法如下:
public class simpletasksystemnavigationprovider : navigationprovider { public override void setnavigation(inavigationprovidercontext context) { context.manager.mainmenu .additem( new menuitemdefinition( "tasks", new localizablestring("tasks", "simpletasksystem"), url: "/tasks", icon: "fa fa-tasks" ) ).additem( new menuitemdefinition( "reports", new localizablestring("reports", "simpletasksystem"), url: "/reports", icon: "fa fa-bar-chart" ) ).additem( new menuitemdefinition( "administration", new localizablestring("administration", "simpletasksystem"), icon: "fa fa-cogs" ).additem( new menuitemdefinition( "usermanagement", new localizablestring("usermanagement", "simpletasksystem"), url: "/administration/users", icon: "fa fa-users", requiredpermissionname: "simpletasksystem.permissions.usermanagement" ) ).additem( new menuitemdefinition( "rolemanagement", new localizablestring("rolemanagement", "simpletasksystem"), url: "/administration/roles", icon: "fa fa-star", requiredpermissionname: "simpletasksystem.permissions.rolemanagement" ) ) ); } }
menuitemdefinition可以有一个唯一的名字,一个用于本地化显示的名字,一个url和一个icon,此外,菜单项可能需要与特定用户权限相结合(相关权限系统正在开发,暂时还没有说明文档)。
inavigationprovidercontext方法能够获取现有的菜单项、添加菜单或菜单项。因此,不同的模块可以添加各自的菜单。
创建完成导航后,还需要在对应模块预初始化时注册到abp配置文件中:
configuration.navigation.providers.add<simpletasksystemnavigationprovider>();
显示菜单
iusernavigationmanager可以注入、获取和显示菜单。可以在服务器端创建菜单。
abp自动生成的javascript api使得用户能够在客户端获取菜单,对应的方法和对象在命名空间abp.nav中。例如,在客户端使用abp.nav.menus.mainmenu可以用来获取主菜单。
下面我们就来看一下javascript的相关方面。
ajax
现代的应用经常会使用ajax,尤其是单页应用,几乎是和服务器通信的唯一手段,执行ajax通常会有以下步骤:
在客户端,你需要提供一个url,选择一个和服务器通信的方法(get,post,put,delete)。在请求完成后执行回调函数,请求结果可更是成功或失败,失败时你需要给出提示,成功时你需要根据返回值执行操作。通常情况下,在请求开始时,你需要给出类似正在处理或者相关的繁忙等待信息(如页面遮盖),请求完成后恢复。
服务端接收到请求后,对请求参数进行验证,执行服务端代码,如果发生错误或者验证失败,应给出具体的原因,成功时返回客户端想要的数据。
abp服务端支持标准的ajax的请求/输出。建议大家使用abp.jquery.js中提供的ajax请求方法,这个方法基于jquery的ajax方法,可以自动处理服务端的异常信息,当然,如果你对js很熟练的话,也可以根据自己的需要写ajax。
asp.net boilerplate的ajax请求实例:
//构建要传输的参数对象 var newperson = { name: 'dougles adams', age: 42 }; //调用abp的ajax方法 abp.ajax({ url: '/people/saveperson', data: json.stringify(newperson) //转换成json字符串 }).done(function(data) { abp.notify.success('created new person with id = ' + data.personid); });
你也可以使用jquery的ajax方法调用,但是需要设置一下默认请求参数,datatype 设置为 'json', type 设置为 'post' and contenttype 设置为 'application/json,在发送请求时需要将js对象转换成json字符串,和$.ajax一样,你也可以传递参数覆盖abp.ajax的默认参数abp.ajax返回一个promise类型,你可以链式编程写如下的方法:
.done() //成功, .fail() //失败, .then() //回调嵌套。
下面的一个简单的例子展示ajax请求peoplecontroller的saveperson方法,在.done()中可以获取到服务端创建记录成功后返回的记录id。
public class peoplecontroller : abpcontroller { [httppost] public jsonresult saveperson(savepersonmodel person) { //todo: save new person to database and return new person's id //todo: 创建一个新的person记录并返回此记录的id return json(new {personid = 42}); } }
savepersonmodel 包含name,age等属性. saveperson 上标记了 httppost 特性 abp.ajax默认以 post 方式请求. 返回值被简化成了一个匿名对象。
savepersonmodel 包含name,age等属性. saveperson 上标记了 httppost 特性 abp.ajax默认以 post 方式请求. 返回值被简化成了一个匿名对象。
ajax 返回值(ajax return messages)
我们直接返回了一个匿名对象, abp 通过 mvcajaxresponse 类型包装了返回值. 实际的返回值类型如下:
{ "success": true, //正确处理标志 "result": { "personid": 42 //返回的数据 }, "error": null, //如果发生错误,result为null,此处为错误信息的对象,包含message和details两个属性 "targeturl": null, //可以提供一个url供客户端重定向,例如自动构建下一页的url "unauthorizedrequest": false //是否通过了授权,如果返回true,客户端应重新登录 }
如果你继承了abpcontroller,json方法返回的对象总会被这样包装,如果未发生错误,你在abp.ajax的done(function(result,data){})中,第一个参数result是{"personid": 42}对象,data是原始对象,webapi中继承abpapicontroller也是同样的机制。
错误处理(handling errors)
返回值如下:
{ "targeturl": null, "result": null, "success": false, //代表出现异常 "error": { "message": "an internal error occured during your request!", //未捕捉到的异常,通常为系统异常,会自动记录日志,具体提示信息在配置文件配置,可以搜索一下,如果是业务抛出的userfriendlyexception异常,message为具体的错误信息 "details": "..." //发生异常时默认会调用abp.message.error函数,你可以在abp.jquery.js修改,统一处理错误信息。 }, "unauthorizedrequest": false }
动态webapi(dynamic web api layer)
此处会根据services动态生成webapi调用函数:
//通常我们使用ajax会按照如下写法,做一个简单的封装来重用ajax,此处框架可以帮你生成简单的调用方法 var saveperson = function(person) { return abp.ajax({ url: '/people/saveperson', data: json.stringify(person) }); }; //调用时你需要构建参数 var newperson = { name: 'dougles adams', age: 42 }; //直接调用方法,如何生成上面的调用方法可以参考源码中的abp.web.api项目中/ webapi/ controllers/ scripting/ jquery下的实现 saveperson(newperson).done(function(data) { abp.notify.success('created new person with id = ' + data.personid); });
上一篇: SuperSlide2实现图片滚动特效
下一篇: 简介Django中内置的一些中间件