java - Spring MVC,从请求生成表单支持对象?

标签 java hibernate spring-mvc

我正在使用 Spring MVC 2.5,我正在尝试获取一个 JSTL 表单对象以从 GET 请求加载。我将 Hibernate POJO 作为我的支持对象。

请求中有一个页面指向另一个页面,其中有一个class id(行主键)。该请求看起来像“newpage.htm?name=RowId”。这将进入一个带有表单支持对象的页面,

上面的新页面,将对象的字段加载到可编辑字段中,并填充行的现有值。这个想法是,您应该能够编辑这些字段,然后将它们保存回数据库中。

这个页面的 View 看起来像这样

<form:form commandName="thingie">
    <span>Name:</span>
    <span><form:input path="name" /></span>
    <br/>
    <span>Scheme:</span>
    <span><form:input path="scheme" /></span>
    <br/>
    <span>Url:</span>
    <span><form:input path="url" /></span>
    <br/>
    <span>Enabled:</span>
    <span><form:checkbox path="enabled"/></span>
    <br/>

    <input type="submit" value="Save Changes" />
</form:form>

Controller 里面有这个,

public class thingieDetailController extends SimpleFormController {

    public thingieDetailController() {    
        setCommandClass(Thingie.class);
        setCommandName("thingie");
    }

    @Override
    protected Object formBackingObject(HttpServletRequest request) throws Exception {
        Thingie thingieForm = (Thingie) super.formBackingObject(request);

        //This output is always null, as the ID is not being set properly
        logger.debug("thingieForm.getName(): [" + thingieForm.getName() + "]");
        //thingieForm.setName(request.getParameter("name"));
        SimpleDAO.loadThingie(thingieForm);

        return thingieForm;
    }

    @Override
    protected void doSubmitAction(Object command) throws Exception {            
        Thingie thingie = (Thingie) command;
        SimpleDAO.saveThingie(thingie);
    }
}

正如您从注释代码中看到的那样,我已经尝试从请求中手动设置对象 ID(名称是这种情况)。但是,当我尝试将数据保存在表单中时,Hibernate 提示对象被取消同步。

org.hibernate.StaleObjectStateException: Row was updated or deleted by another transaction (or unsaved-value mapping was incorrect)

这个错误似乎对整个 session 有影响,它停止为我的整个 Web 应用程序工作,不断抛出上面看到的陈旧对象状态异常。

如果任何熟悉 Spring MVC 的人可以帮助我解决这个问题或提出解决方法,我将不胜感激。

编辑:
session 工厂代码。

private static final SessionFactory sessionFactory;
private static final Configuration configuration = new Configuration().configure();

static {
    try {
        // Create the SessionFactory from standard (hibernate.cfg.xml) 
        // config file.
        sessionFactory = new AnnotationConfiguration().configure().buildSessionFactory();
    } catch (Throwable ex) {
        // Log the exception. 
        System.err.println("Initial SessionFactory creation failed." + ex);
        throw new ExceptionInInitializerError(ex);
    }
}

public static SessionFactory getSessionFactory() {
    return sessionFactory;
}

最佳答案

使用 Spring MVC + hibernate 的主要缺陷之一是自然的方法是使用 hibernate 域对象作为表单的支持对象。默认情况下,Spring 将根据名称绑定(bind)请求中的任何内容。这无意中包含了 ID 或名称(通常是主键)或其他正在设置的 hibernate 管理属性。这也使您容易受到表单注入(inject)的攻击。<​​/p>

为了在这种情况下安全,您必须使用类似的东西:

protected void initBinder(HttpServletRequest request, ServletRequestDataBinder binder) 
throws Exception {
 String[] allowedFields = {"name", "birthday"}
 binder.setAllowedFields(allowedFields);
}

并明确地将允许的字段设置为仅在您的表单中的字段,并排除主键,否则您将一团糟!!!

关于java - Spring MVC,从请求生成表单支持对象?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/697778/

相关文章:

spring - 我无法在 spring mvc 项目中加载图像

java - 在 MySql 上映射一个可以增长到 400KB 的 byte[]

java - 如何使用 ZipOutputStream 压缩单个字符串并将其保存为可读字符串

java - 使用 clean() 方法在我的 build.gradle 中出错

java - RichFaces 中的服务器端数据表排序

java - 在 OneToMany 中识别子 null 并从数据库中删除的更好方法?

java - SQLFunctionTemplate 不应用查询参数的顺序

java - 如何提示用户执行操作

java - hibernate/JPA : how to handle behaviour for join

session - Spring Framework 3 和 session 属性