struts

来源:互联网 发布:c语言代码大全下载 编辑:程序博客网 时间:2024/06/10 02:33
struts2介绍    Struts 2是Struts的下一代产品,是在 struts 1和WebWork的技术基础上进行了合并的全新MVC框架    核心功能        action可以是普通类(POJO)        一次请求对应一个action实例 (请求一次,创建一个action对象)        struts不依赖于servlet api        封装请求参数        整合了OGNL(Object Graph NavigationLanguage)对象图形导航语言。比EL表达式更强大        将值传递给视图时,使用"ValueStack"技术。--值栈        类型转换        数据校验        基于Spring AOP思想的拦截器机制,更易扩展    struts资源        struts-2.3.14-all.zip    struts目录结构        apps : 应用(demo例子),例如:struts2-blank.war        docs : 帮助文档        lib :struts需要的所有jar        src : 源码helloword搭建    1 创建web项目    2 导入最少jar包(/struts/struts-2.3.14)        位置:/apps/struts2-blank.war/WEB-INF/lib 所有jar        注意:            将war扩展名改成zip,进行解压            不要使用 /lib 中的内容        jar介绍            struts2-core-2.3.14.jar     核心jar            xwork-core-2.3.14.jar       依赖jar,使用webwork的            ognl-3.0.6.jar              对象图导航语言            freemarker-2.3.19.jar       struts2的ui标签模板            commons-lang3-3.1.jar       对java.lang包的增强             commons-fileupload-1.2.2.jar文件上传组件            commons-io-2.0.1.jar        文件上传依赖jar            asm-3.3.jar                 提供了对字节码操作的功能            asm-commons-3.3.jar         提供了基于事件的表现形式            asm-tree-3.3.jar            提供了基于对象的表现形式            javassist-3.11.0.GA.jar     代码生成工具,用于在运行时扩展java类    3 编写实现类Action        public String execute(){            System.out.println("hello action execute 执行...");            return "success";        }    4 编写核心配置文件        名称:struts.xml        位置:src        内容:            <?xml version="1.0" encoding="UTF-8" ?>            <!DOCTYPE struts PUBLIC                "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"                "http://struts.apache.org/dtds/struts-2.3.dtd">            <struts>                <package name="day01" namespace="/primer" extends="struts-default" >                    <action name="helloAction" class="Action全限定名" method="execute">                        <result name="success">/a_hello/demo.jsp</result>                    </action>                </package>            </struts>    5 配置struts提供的过滤器web.xml        过滤器类名:StrutsPrepareAndExecuteFilter        <filter>            <filter-name>struts2</filter-name>            <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>        </filter>        <filter-mapping>            <filter-name>struts2</filter-name>            <url-pattern>/*</url-pattern>        </filter-mapping>    启动服务器,访问 http://localhost:8080/项目/primer/helloActionstruts执行流程    服务器软件启动时执行过滤器的init方法,加载struts.xml    当每次请求时        执行过滤器的service方法,生成Action类的代理对象,去执行拦截器,然后执行Action中的指定方法,        并返回结果,然后生成模板(jsp),然后返回拦截器,返回过滤器,最后响应给浏览器struts配置文件    1 default.properties (默认设置配置文件)        位置:struts2-core-2.3.14.jar/org/apache/struts2/default.properties    2 struts-default.xml (stures核心配置文件)        位置:struts2-core-2.3.14.jar/struts-default.xml        内容:struts2编写拦截器,默认拦截器栈等    3 struts-plugin.xml (插件配置文件)        位置:插件jar中    4 struts.xml (程序核心配置文件)    5 web.xml (web配置文件,可以设置初始化参数覆盖struts默认配置)    注意:如果多个文件配置了同一个struts2 常量,则后一个文件中配置的常量值会覆盖前面文件配置的常量值struts常量    struts框架用于给整个框架配置的固定key    struts常量默认配置文件:default.properties    用法:        1.src/struts.xml配置            <constant name="键" value="值"></constant>        2.src/struts.properties,在struts.xml文件之后被加载            键=值        3.web.xml配置过滤器时,配置初始化参数            <init-param>                <param-name>键</param-name>                <param-value>值</param-value>            </init-param>    常见常量        1 struts.i18n.encoding ,用于设置编码            例如:struts.i18n.encoding=UTF-8        2 struts.action.extension 配置struts action的扩展名,多个扩展名之间使用,分割            例如:struts.action.extension=action,,                访问:http://localhost:8080/struts_day01/helloAction        没有扩展名                访问:http://localhost:8080/struts_day01/helloAction.action 指定了扩展名        3 struts.devMode 是否开启开发模式            例如:struts.devMode = true 开启,默认值为false,建议开发时开启            作用                 struts.i18n.reload = true  ,自动加载国际化资源文件                 struts.configuration.xml.reload = true , xml配置文件添加或修改后将自动加载        4 struts.ui.theme struts标签的主题(布局风格)            例如:struts.ui.theme=xhtml ,默认值。其他取值:simple 简单风格,没有任何样式        5 struts.objectFactory 三大框架整合使用            例如:struts.objectFactory = spring ,使用spring创建对象        其它            struts.serve.static.browserCache 设置浏览器是否缓存静态内容,默认为ture,开发阶段建议关闭            struts.multipart.maxSize 上传文件的最大长度,单位字节struts.xml    示例        <?xml version="1.0" encoding="UTF-8" ?>        <!DOCTYPE struts PUBLIC            "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN"            "http://struts.apache.org/dtds/struts-2.3.dtd">        <struts>            <!-- 开启开发模式,xml配置文件将自动加载 -->            <constant name="struts.devMode" value="true"></constant>            <!-- 标签样式为基本样式 -->            <constant name="struts.ui.theme" value="simple"></constant>            <package name="defaultPackage" namespace="/" extends="struts-default">                <action name="oneAction_*" class="action.OneAction" method="{1}">                    <result name="success">/success.jsp</result>                </action>            </package>        </struts>    package标签        <package> struts用于管理所有的action            name : 给当前的包进行一个唯一的命名,用于提供给其他包继承。            namespace : 给当前的包给一个统一访问的根路径。默认值,/            extends : 确定需要继承的包。                常用 : struts提供默认实现,固定值:struts-default                    位置:struts-default.xml文件中                    源码:<package name="struts-default" abstract="true">        <action> : 用于配置action类            name : 给当前类进行命名。在当前package内部不能重复。            class : action实现类全限定类名。默认类,ActionSupport            method : action类中执行的方法名称。默认值 execute            访问路径:package.namespace + "/" + action.name        <result> : 用于配置结果            name : action方法返回值 ,默认值 success            type :从acton到jsp方法方式。                常用值(struts-default.xml,<package name="struts-default" abstract="true"><result-types><result-type>)                    dispatcher,请求转发到jsp页面,默认值                    redirect , 重定向到jsp页面 <result name="success" type="redirect">/success.jsp</result>                    redirectAction ,重定向到指定的action                    stream ,向浏览器发送流,如图片                重定向到action示例                    <result name="success" type="redirectAction">                        <param name="namespace">/</param>                        <param name="actionName">twoAction</param>                    </result>                    或                    <result name="success" type="redirectAction">twoAction</result>                    注意:下面的写法只能重定向到同一个namespace下的action,不加/            <result name="input">比较特殊,可以配置错误页面,当封装数据发生错误时,返回值为input        通配符            星号*                使用位置: struts.xml配置文件中,<action>的name属性中                作用: 在其他的配置项中可以通过{n}方式获得匹配的内容,n表示星号的位置,从1开始                例如 <action name="*_*_*"  class="" method=""                     访问url: http:..../part1_part2_part3 ,使用{1}获得part1内容 ; {2} part2 {3} part3                注意:{0} 匹配整个 URI                建议:<action name="userAction_*" method="{1}" ,访问时 userAction_add 或 userAction_delete            感叹号!                使用位置: 在访问action的url中                作用: 可以用!号代替一个符号(只能是符号,且只能是一个)                例: http://localhost:8080/client/UserAction!add    include标签        可以将多个struts配置文件整合到一起            <include file=""></include>编写action    POJO 普通类    可以选择 实现接口 Action        提供5个java常量(字段)            public static final String SUCCESS = "success"; 表示访问成功            public static final String NONE = "none"; 没有结果集result,没有返回页面。Ajax            public static final String ERROR = "error"; 服务器出现错误            public static final String INPUT = "input"; 浏览器发送用户输入的数据有误            public static final String LOGIN = "login"; 没有权限,需要登录        默认方法             public String execute() throws Exception;    可以选择 继承类 ActionSupport         提供默认实现:验证、提示、国际化等    方法结构        public String 名称自定义(){return ...} ,非静态    action访问servlet api    间接的访问servlet三个作用域,相当于只能执行xxxAttribute方法.        工具类ActionContext,action的上下文(action管理者)        api            获得对象:ActionContext.getContext()            放置request作用域:actionContext.put(key,value) (其实不是request作用域,而是直接添加到值栈的content中)            放置session作用域:actionContext.getSession().put(key,value)            放置application作用域:actionContext.getApplication().put(key,value)    直接访问servlet api ,获得servlet对象        工具类ServletActionContext,action中servlet的上下文        获取servlet对象            HttpServletRequest request = ServletActionContext.getRequest();            HttpSession session = request.getSession();            ServletContext application = ServletActionContext.getServletContext();            HttpServletResponse response = ServletActionContext.getResponse();封装数据    第一种,使用struts提供的ModelDriven机制,将数据封装到指定javabean (推荐)        步骤:            1 实现接口,并提供javabean泛型信息 implements ModelDriven<User>            2 创建成员变量javabean实例,new User()            3 实现方法:getModel,返回javabean实例        拦截器中调用getModel方法获得javabean实例,然后进行数据填充    第二种,将数据封装到action的属性        步骤:给action添加属性(必须提供setter方法)        struts会通过setter方法自动填充数据    第三种,将数据封装到action的javabean属性的属性中        步骤:            给action添加属性,javabean对象(可以不new,必须提供给setter和getter方法)            在页面表单元素的name使用ognl表达式直接为javabean中的属性赋值,如user.username,为action的user属性中的username属性赋值        执行流程             页面 文本框name分别为 user.username 和 user.password            则struts倒着填充,先填充user.password, 首先调用user的getter方法                如果对象存在,调用password属性setter方法进行赋值                如果对象不存在,或user的getter方法不存在,将创建User对象,并执行setter方法赋值            填充user.username和上面相同类型转换    默认实现        字符串  -->  基本类型或包装类型        字符串  -->  时间类型(格式:yyyy-MM-dd , yyyy-MM-dd HH:mm:ss)        字符串  -->  数组 | 集合(将复选框的值封装到数组或集合中)    自定义实现--类型转换器        实现接口:TypeConverter,建议继承默认实现类:DefaultTypeConverter            复写方法:convertValue(java.lang.Object value, java.lang.Class toType)                 浏览器 --> 服务器 (提交 String[]-->Date)                    value ,浏览器提交的内容,String[] 通过request.getParameterValues("birthday")得到的                    toType , 需要转换的类型 java.util.Date                服务器 --> 浏览器 (struts标签 回显 Date-->String)                    value , 标签回显时需要提供的数据 ,java.util.Date                    toType, 浏览器需要的数据(字符串进行显示) , java.lang.String        注册转换器-添加配置文件            注册全局转换器,当前web项目都可以使用(对所有封装数据方式有效)                文件名称:xwork-conversion.properties                文件位置:src                文件内容:需要转换的类型全限定类名=实现类全限定类名                    例如:java.util.Date = util.MyDateConverter            局部转换器,只对当前action有效。                文件名称:Action类名-conversion.properties                文件位置:与action同包                文件内容:action属性=实现类全限定类名                注意:只能使用action属性封装数据的方式,向javaBean封装数据时失效        自定义日期转换器示例            页面                <s:form namespace="/" action="oneAction" method="post">                    <s:textfield name="birthday" label="生日"></s:textfield>                    <s:submit value="提交"></s:submit>                </s:form>            action.UserAction                提供一个birthday属性,并提供getter和setter方法            转换器实现类                public class MyDateConverter extends DefaultTypeConverter {                    SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd");//日期格式化工厂                    @SuppressWarnings("rawtypes")                    public Object convertValue(Object value, Class toType) {                        try {                            //浏览器 --> 服务器,String[] --> Date                            if(java.util.Date.class == toType){                                String[] values = (String[]) value;                                String birthday = values[0]; //2014/5/15                                java.util.Date date = dateFormat.parse(birthday);                                return date;                            }                            //服务器 --> 浏览器,Date --> String                            if(String.class == toType){                                java.util.Date date = (Date) value;                                String birthday = dateFormat.format(date);                                return birthday;                            }                            return null;                        } catch (Exception e) {                            e.printStackTrace();                            throw new RuntimeException();                        }                    }                }            注册转换器(二选一)                全局:src/xwork-conversion.properties                    java.util.Date=util.MyDateConverter                局部:src/action/UserAction-conversion.properties                    birthday=util.MyDateConverter数据校验    将浏览器已经封装到javabean中的数据进行合理校验。    校验方式        手动方法            校验action全部方法                必须实现接口Validateable,实现validate方法                validate方法会在所有方法执行之前执行                ActionSupport类已实现此接口            校验action单个方法                添加方法,方法名为validate+验证方法名称,例 add --> validateAdd                验证方法将在方法执行之前先执行            注意:                先执行单个校验,再执行全部校验。                在action中使用:this.addFieldError("username", "此处错误"); 添加错误信息,使目标方法不能继续执行(全局校验方法还会执行)                手动验证时需要自己编写java代码进行验证        xml配置方法            添加xml配置文件即可,xml文件位置:action类同包            校验action全部方法:                文件名称:action类名-validation.xml            校验action单个方法:                文件名称:action类名-action配置name-validation.xml                    action配置name 是<action>标签中的name属性的值                    例:userAction_add --> UserAction-userAction_add-validation.xml                    如果使用了通配符,如userAction_*,则按实际请求的路径写            xml文件                约束DTD位置:xwork-core-*.jar/xwork-validator-1.0.3.dtd                基本内容:                    <!DOCTYPE validators PUBLIC                        "-//Apache Struts//XWork Validator 1.0.3//EN"                        "http://struts.apache.org/dtds/xwork-validator-1.0.3.dtd">                    <validators>                        <!-- 要验证的字段 -->                        <field name="">                            <!-- 验证器 -->                            <field-validator type="">                                <!-- 验证器参数,没有就不写-->                                <param name="">值</param>                                <!-- 不符合要求显示的消息提示 -->                                <message></message>                            </field-validator>                        </field>                    </validators>                    注意:在<message>中可以使用${param的name}引用上面指定<param>的值            struts提供验证器                <field-validator type=""> type的值                所有验证器位置:xwork-core-*.jar/最后一个包                    /com/opensymphony/xwork2/validator/validators/default.xml                常用验证器                    required, requiredstring, int, date, expression,                     fieldexpression, email, url, stringlength, regex                验证器的参数看源码setter方法            校验文件示例                <?xml version="1.0" encoding="UTF-8"?>                <!DOCTYPE validators PUBLIC                        "-//Apache Struts//XWork Validator 1.0.3//EN"                        "http://struts.apache.org/dtds/xwork-validator-1.0.3.dtd">                <validators>                    <!-- 用户名 -->                    <field name="username">                        <!-- 必填 -->                        <field-validator type="requiredstring">                            <message>用户名不能为空</message>                        </field-validator>                        <!-- 长度 -->                        <field-validator type="stringlength">                            <param name="minLength">3</param>                            <param name="maxLength">12</param>                            <message>用户名长度应为${minLength}-${maxLength}位</message>                        </field-validator>                    </field>                    <!-- 密码 -->                    <field name="password">                        <!-- 必填 -->                        <field-validator type="requiredstring">                            <message>密码不能为空</message>                        </field-validator>                        <!-- 长度 -->                        <field-validator type="stringlength">                            <param name="minLength">6</param>                            <param name="maxLength">12</param>                            <message>密码长度应为${minLength}-${maxLength}位</message>                        </field-validator>                    </field>                    <!-- 确认密码 -->                    <field name="repassword">                        <!-- 必填 -->                        <field-validator type="requiredstring">                            <message>确认密码不能为空</message>                        </field-validator>                        <!-- 匹配 -->                        <field-validator type="fieldexpression">                            <param name="expression">repassword==password</param>                            <message>密码与确认密码不一致</message>                        </field-validator>                    </field>                    <!-- 年龄 -->                    <field name="age">                        <!-- 必填 -->                        <field-validator type="required">                            <message>年龄不能为空</message>                        </field-validator>                        <!-- 范围 -->                        <field-validator type="int">                            <param name="min">3</param>                            <param name="max">100</param>                            <message>请输入正确的年龄</message>                        </field-validator>                    </field>                    <!-- 生日 -->                    <field name="birthday">                        <!-- 必填 -->                        <field-validator type="required">                            <message>生日不能为空</message>                        </field-validator>                        <!-- 范围 -->                        <field-validator type="date">                            <param name="min">1930-01-01</param>                            <param name="max">2010-01-01</param>                            <message>请输入正确的生日</message>                        </field-validator>                    </field>                    <!-- 邮箱 -->                    <field name="email">                        <!-- 必填 -->                        <field-validator type="requiredstring">                            <message>邮箱不能为空</message>                        </field-validator>                        <!-- 格式 -->                        <field-validator type="email">                            <message>邮箱格式不正确</message>                        </field-validator>                    </field>                    <!-- 电话 -->                    <field name="tel">                        <!-- 必填 -->                        <field-validator type="requiredstring">                            <message>电话不能为空</message>                        </field-validator>                        <!-- 格式 -->                        <field-validator type="regex">                            <param name="regexExpression">((\d{11})|^((\d{7,8})|(\d{4}|\d{3})-(\d{7,8})|(\d{4}|\d{3})-(\d{7,8})-(\d{4}|\d{3}|\d{2}|\d{1})|(\d{7,8})-(\d{4}|\d{3}|\d{2}|\d{1}))$)</param>                            <message>电话格式不正确</message>                        </field-validator>                    </field>                </validators>        校验执行步骤:先进行数据封装-->执行xml配置的数据校验-->执行单个方法校验手动方法-->执行全部方法校验手动方法拦截器    拦截器栈:struts将多个拦截器组合成一个整体,存在先后顺序。        默认拦截器:defaultStack    拦截器,必须实现Interceptor接口,与过滤器filter相似。        interceptor 拦截器:struts特有的功能,依赖于struts框架。放行:invocation.invoke();        filter 过滤器:java web 提供过滤器程序。放行:chain.doFilter();    默认拦截器执行顺序(了解)        modelDriven     获得javabean,将javabean压入到root栈顶,等待数据填充        fileUpload      如果有则获取上传文件        params          数据填充,将数据依次填充到root栈的对象的属性中        conversionError 校验封装数据时是否存在转换异常        validation      校验        workflow        检测是否有错误,有错误返回"input",没错误则放行    自定义拦截器        编写实现类            实现Interceptor接口,重写intercept方法                放行:invocation.invoke();                获得请求的action类对象:invocation.getAction();                添加错误信息:invocation.getAction().addFieldError("username", "此处错误");                返回值会去struts.xml中寻找匹配结果        注册拦截器栈            位置:<package>中,<action>之前            <interceptors>                <!-- 注册拦截器 -->                <interceptor name="拦截器名称" class="拦截器实现类"></interceptor>                <!-- 注册拦截器栈 -->                <interceptor-stack name="拦截器栈名称">                    <!--默认拦截器栈-->                    <interceptor-ref name="defaultStack"></interceptor-ref>                    <!--追加自己的拦截器-->                    <interceptor-ref name="拦截器名称"></interceptor-ref>                </interceptor-stack>            </interceptors>        使用拦截器栈            仅在指定action中使用                位置:<action>中                内容:<interceptor-ref name="拦截器栈名称"></interceptor-ref>            一个包内所有action使用                位置:<package>中,<action>之前,<interceptors>之后                内容:<default-interceptor-ref name="拦截器栈名称"></default-interceptor-ref>i18n    国际化资源文件:baseName[_语言_国家|地区].properties        例如:message_zh_CN.properties    struest默认国际化配置文件        位置:            struts-core.jar /org/apache/struts2/struts-messages.properties            xwork-core.jar /com/opensymphony/xwork2/xwork-messages.properties        全局字段错误提示消息(不建议修改)            xwork-messages.properties中                xword.default.invalid.fieldvalue=Invalid field value for field "{0}".            上面只是字段错误提示消息,其它错误提示消息在默认配置文件其它位置查找    自定义资源文件        位置            action同包,对指定action有效                文件名:action类名.properties , baseName是action类名            action父包,所有的子包都有效                文件名:package.properties , baseName是"package"固定串,不是包名            全局配置                位置任意,名称任意                需要在struts.xml配置常量                    struts.custom.i18n.resources=baseName,baseName2   -->多个资源文件使用逗号分隔 message,cn/itcast/message                    即<constant name="struts.custom.i18n.resources" value="baseName|包/baseName"></constant>        内容            invalid.fieldvalue.字段名称=提示信息            名称=值            //以invalid.fieldvalue开头的键,为字段错误提示消息,当字段输入错误时,自动提示            //其它错误消息固定key在struest默认国际化配置文件中查找    使用        可由ActionSupport类中的getText(key)获得value        可使用sturts的国际化标签在页面显示        以invalid.fieldvalue开头的键,为字段错误提示消息,当字段输入错误时,自动提示    sturts的国际化标签        <s:i18n name="cn/itcast/msg">   --> 加载指定位置的国际化资源文件,msg为文件名,不加后缀            <s:text name="studentInfo"> --> 获得指定key的value                <s:param>四儿</s:param> --> 给第一个位置设置值,用于填充获得内容的{n}位置            </s:text>        </s:i18n>文件上传    回顾        浏览器            <form method="post" enctype="multipart/form-data">                <input type="file" name="imageName"/>                <input type="submit" />        服务器            1 手动解析,request.getInputStream() ,获得请求体所有内容            2 commons fileupload,第三方            3 servlet 3.0 Part对象,使用注解            4 struts提供上传支持    struts文件上传        必须提供三个属性setter方法获得所有内容            File image;             //记录文件内容,image为表单提交时file控件name的值            String imageFileName;   //记录文件名称,image同上,FileName为固定字符串            String imageContentType;//记录文件类型,image同上,ContentType为固定字符串        多文件上传,将以上三个属性的类型变为数组或集合即可.注意:多文件上传表单中多个file控件的name应一致        文件拷贝:FileUtils.copyFile(File srcFile,File destFile); --commons-io.jar中的工具类,struts2自带        方法完成后struts会自动将原来的文件删除    struts文件上传常量        struts.multipart.parser=jakarta     ,确定struts解析文件上传方法,apache commons fileupload        struts.multipart.maxSize=2097152    ,默认大小,2M ,注意不能写 1024*1024*2    扩展名限制        在struts.xml的<action>中添加            <interceptor-ref name="defaultStack">                <param name="fileUpload.allowedExtensions">.jpg,.png</param>            </interceptor-ref>        上面设置的是允许的扩展名,不符合会返回input        上面是给某个拦截器设置参数的方式,fileUpload为拦截器名称,allowedExtensions为属性名称    文件上传action示例        public class UserAction extends ActionSupport {            private File image; //表单名称为image            private String imageFileName;            private String imageContentType;            public void setImage(File image) {                this.image = image;            }            public void setImageFileName(String imageFileName) {                this.imageFileName = imageFileName;            }            public void setImageContentType(String imageContentType) {                this.imageContentType = imageContentType;            }            public String upload(){                try {                    String dir = "/uploadFile";//文件存放路径                    dir = ServletActionContext.getServletContext().getRealPath(dir);                    File destFile = new File(dir,imageFileName);                    FileUtils.copyFile(image, destFile);//原来的文件自动删除                } catch (Exception e) {                    System.out.println("文件拷贝失败");                }                return SUCCESS;            }        }文件下载    回顾        将文件资源流发送到浏览器,response.getOutputStream()        设置响应头:content-disposition = attachement;filename=1.jpg        发送流    步骤        1.在action中            添加一个InputStream属性,并提供get方法,将要发送的数据放到属性中            添加一个String属性fileName,并提供get方法,将文件名称放到属性中(名称不是固定的,是和下面对应的)        2.在struts.xml中配置result            <result name="success" type="stream">                <param name="inputName">属性名称</param>                <param name="contentDisposition>attachment;filename=${fileName}</param>            </result>            说明                inputName设置action的流属性名称                contentDisposition设置响应头,说明文件时需要下载的                ${fileName}表示在action类中获取fileName属性的值,所以在action中要提供fileName属性                可选操作:<param name="contentType>${contentType}</param>                contentType设置文件类型,需要在action中提供属性,一般赋值方法:contentType=ServletActionContext.getServletContext().getMimeType(fileName);        文件名称中文乱码问题还是fileName = new String(fileName.getBytes("gbk"),"iso8859-1");        如果用户取消下载会抛异常,可使用插件解决struts2-sunspoter-stream-1.0.zipognl表达式    OGNL是Object Graphic Navigation Language(对象图导航语言)的缩写,比EL更强大的表达式语言(开源项目)    Struts2框架使用OGNL作为默认的表达式语言。        在JSP中执行OGNL表达式需要struts标签,<s:property>将ognl表达式的结果发送到浏览器 ,等价于<c:out/>    优势        支持对象方法调用        支持类静态的方法调用和常量访问        支持赋值操作和表达式串联 ,user.username        访问OGNL上下文(OGNL context)和ActionContext;         操作集合对象。        可以直接new一个对象    语法        对象方法调用            <s:property value="'abc'.length()"/>            <s:property value="page"/>  //会访问action中的属性,调用getPage方法(如果存在的话)        类静态的方法调用和常量访问            表达式的格式: @[全限定类名]@[方法名 | 常量名]                <s:property value="@java.lang.Math@PI"/>                <s:property value="@java.lang.Math@PI"/>            默认情况静态方法不能执行,需要设置struts常量                struts.ognl.allowStaticMethodAccess=false        支持赋值操作和表达式串联             <s:property value="#page.data[0].birthday"/><br>            <s:property value="#page.data[0].birthday='2000-1-1'"/><br>        访问OGNL上下文(OGNL context)和ActionContext;         操作集合对象。        可以直接new一个对象    特殊符号        # : 通过key获得context值,可以用于创建对象            创建List:{'元素1','元素2','元素3'}            创建Map:#{'key1':'value1','key2':'value2'}        % : 在struts标签中确定语法            %{ognl表达式}:表示里面的内容必须按照ognl表达式去执行            %{'字符串'}:表示里面的内容为普通字符串        $ : 在配置文件struts.xml 和 国际化资源文件*.properties 使用${ognl表达式},从值栈中获取内容。ValueStack    值栈:struts用于传递数据的对象。        一个action对应一个值栈,贯穿整个action生命周期。在action创建之后就有一个值栈,一次请求对应一个action和一个值栈。请求结束,action销毁,值栈也销毁。        struts将值栈对象放置到servlet 的request域中        值栈实际上是一个接口,在Struts2中利用ognl时,实际上使用的是实现了该接口的OgnlValueStack类.所以,struts2的值栈对象其实是OgnlValueStack类的一个实例    获得值栈        1 通过Action上下文:ActionContext.getContext().getValueStack()         2 通过指定的属性名称获得:ServletActionContext.getRequest().getAttribute("struts.valueStack");    值栈结构        root和context是OgnlValueStack实例的两个属性        root : 类型为CompoundRoot,extends ArrayList 底层是List。称为:对象栈,只能存放对象,对象不能添加名称。            提供了压栈和出栈的操作(方法),模拟栈结构.            struts2默认将当前action实例放入到栈顶        context:类型为Map<String,Object> ,可以给保存数据添加名称,通过名称获得指定对象。            struts规定了若干固定key,可以间接对servlet不同的域进行操作                application ,application作用域内容。Map<属性名称,属性值>                session,session作用域内容。Map<属性名称,属性值>                request,request作用域内容。Map<属性名称,属性值>                attr,依次的page/request/session/application作用域的所有值。Map<属性名称,属性值>                parameters,请求参数 ,Map<name,values>    root操作        root就是平常所说的值栈            ValueStack vs = ActionContext.getContext().getValueStack();        存放数据            push(Object obj)    //压栈,将对象压入到栈顶            set(key,value)      //将key-value存入栈顶的Map中(栈顶如果不是Map,则先创建,再将Map压入栈顶)        获得数据            <s:property value="名称" />     //通过指定属性获得第一个值,匹配root对象栈中对象的属性或Map的key.            <s:property value="top" />      //获得栈顶的数据            <s:property value="[2]" />      //从第三个开始,将之后的所有内容组成一个新的栈,并输出            <s:property value="[2].top">    //获得新栈的第一个值    context操作        context是一个Map,可以间接对servlet不同域进行操作            ActionContext.getContext()可以获得ActionContext对象            ActionContext对象的put和getSession等方法其实是向context中添加和获得数据        存放数据            ActionContext.getContext().put(key,value) ,直接添加到context对象中,不会存到request域中,不过用request可以取到(进行了方法增强)            ActionContext.getContext().getSession().put(key,value) , 添加到context对象固定key为session对应的Map中,会存到session作用域中            ActionContext.getContext().getApplication().put(key,value) 添加到context对象固定key为application对应的Map中,会存到application作用域中        获得数据            通过 #key获得数据, <s:property value="#session.person.personName"/>    获取数据的特殊方法        <s:property value="gf"/>            底层使用findValue(gf)                先从root对象栈中获取内容                如果没有,再从content获取        <s:property value="#request.gf"/> <br/>            request被struts使用装饰者默认进行修改(方法增强)                request实现类 org.apache.struts2.dispatcher.StrutsRequestWrapper ,<%=request.getClass() %>            struts对request的getAttribute方法进行增强                先从servlet 的request作用域获得数据                如果没有,再从值栈获得,执行findValue                    先从root对象栈中获取内容                    如果没有,再从content获取    使用标签查看值栈 <s:debug/>    因为request.getAttribute方法被增强,可以获取到值栈中的值,所以el表达式也可以获取值栈中的值struts标签    好处 : 回显,自动提示错误消息(在每个表单元素上方添加<s:fielderror>标签),url自带JSESSIONID,布局    引入标签库 : <%@ taglib uri="/struts-tags" prefix="s" %>    常用标签        <s:property>    获取值栈中的数据            value       表达式            default     默认值,当表达式的值为空时,会显示默认值            escapeHtml  是否进行html转义        <s:set>         将数据放置到作用域        <s:url>            namespace   action的namespace            action      action的name            var         变量名    流程控制标签        <s:iterator>    遍历            value       要遍历的数据            var         将当前压入栈顶            begin       开始值            end         结束值            status      将遍历信息存储在context中,可用属性count,index等 如 #status值.index            注意:每次循环开始默认将集合中的每一个对象压入到栈顶,下一次循环弹出.使用var,可同时在context中起名存储        <s:if><s:elseif><s:else>            test        条件    表单标签        在表单标签中class和style属性用cssClass和cssStyle属性指定        在表单标签中使用theme属性修改标签模板,则包含的标签都会使用统一的模板,如theme="simple"        <s:fielderror>  显示用户输入的错误提示        <s:actionerror> 显示action的错误提示        <s:form> 表单            namespace   struts.xml中<package>的namespace            action      struts.xml中<action>的name            enctype     和普通form相同            method      和普通form相同        <s:submit> 提交按钮            value       显示文本        <s:textfield> 文本框            name        同原来的name            label       前面的文本,simple风格无效        <s:password> 密码框            showPassword    显示value属性,默认为false,不显示        <s:hidden> 隐藏域        <s:date> 格式化显示时间            name        要显示的属性            format      格式    表单标签2        <s:checkboxlist> 复选框列表            name        必须            list        取值为list集合或map集合,使用ognl表达式                            如果取值为list,则value和显示的数据一致                            如果取值为map,则value为map的key,显示的数据为map的value            value       默认选中,通常要使用%{值}        <s:radio> 单选框列表            使用方法同<s:checkboxlist>        <s:select> 下拉列表            使用方法同<s:checkboxlist>            headerKey       默认头的value            headerValue     默认头的显示文本            listKey         value为集合中的javaBean的哪个属性            listValue       显示的数据为集合中的javaBean的哪个属性        示例            <s:select list="#{'1':'小班','2','大班'}" name="edu"                headerKey="" headerValue="--请选择--">            </s:select>            或            <s:select list="#request.sexList" name="sexID"                 listKey="ddlCode" listValue="ddlName"                headerKey="" headerValue="请选择">            </s:select>    注意        在<s:if>标签的test属性中,注意test="a==1"和test="a=='1'",两者有截然不同的效果        在<s:set>的value属性中,将变量赋值为1:value="%{'1'}",不能为value="1"token(struts令牌机制)    回顾:一次性验证码原理    token机制,防止表单重复提交。 (验证码防止表单重复提交已经解决方案)        1.服务器缓存一份数据,浏览器也要缓存相同一份数据        2 浏览器提交数据,自动获得服务器缓存的数据            比较,并删除服务器缓存数据                相同,正常请求                不相同,重复提交    使用token        1 在表单中添加一个标签<s:token/> (会生成一个随机数,保存到session,同时在页面生成一个隐藏域,记录值)        2 在struts.xml中配置,添加struts的token拦截器 (拦截器做的事:获取隐藏域的value与session对比,并删除session的数据)        例:            注册新拦截器栈                在<package>标签中添加                <interceptors>                    <interceptor-stack name="tokenStack">                        <interceptor-ref name="defaultStack"></interceptor-ref>                        <interceptor-ref name="token"></interceptor-ref>                    </interceptor-stack>                </interceptors>            使用新拦截器栈                在<action>标签中添加                <interceptor-ref name="tokenStack"></interceptor-ref>            配置token错误处理页                <result name="invalid.token>/form.jsp</result>                在错误处理页可以使用<s:actionerror>标签 显示错误提示
0 0