6

単一のスプリング mvc メソッドでコンテンツ タイプ application/x-www-form-urlencoded および application/json を処理する必要があります。

残りのサービスでは、入力をフォーム パラメーターまたは json として受け入れる必要があります。これを実現するには、2 つのメソッドを記述します。フォーム params または json のいずれかで、応答は常に json になります。

@RequestMapping (method = RequestMethod.POST, produces = {"application/json"},
        consumes = {"application/x-www-form-urlencoded"})
public @ResponseBody Book createBook(Book book)
        throws Exception {
    return book;
}

@RequestMapping (method = RequestMethod.POST, produces = {"application/json"},
        consumes = {"application/json"})
public @ResponseBody Book createBookJSON(@RequestBody Book book)
        throws Exception {
    return book;
} 

これら2つの方法を1つにまとめて機能させることは可能ですか? どんな助けでも大歓迎です。

編集

同じことを実装しました。コントローラーと構成を以下に示しますが、json リクエストを送信すると、応答として null 値が返されます。

フォームパラメーターを送信すると、正常に機能しています。問題を見つけるのを手伝ってください。

コントローラー方式

 @RequestMapping (method = RequestMethod.POST, produces = {"application/json", "application/xml"}, consumes = {"application/x-www-form-urlencoded", "application/json"})                   
    public @ResponseBody Book createBook(Book book)
            throws Exception {
        return book;
    }

サーブレット コンテキスト

<mvc:view-controller path="/" view-name="index"/>

<context:annotation-config />

<bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping"/>

<bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter"/>

<bean class="org.springframework.web.servlet.view.ContentNegotiatingViewResolver">
    <property name="order" value="1" />
    <property name="mediaTypes">
        <map>
            <entry key="xml" value="application/xml" />
            <entry key="json" value="application/json" />
        </map>
    </property>
    <property name="defaultViews">
        <list>
            <!-- JSON View -->
            <bean class="org.springframework.web.servlet.view.json.MappingJacksonJsonView" />

            <!-- JAXB XML View -->
            <bean class="org.springframework.web.servlet.view.xml.MarshallingView">
                <constructor-arg>
                    <ref bean="jaxb2Marshaller" />
                </constructor-arg>
            </bean>

        </list>
    </property>
    <property name="ignoreAcceptHeader" value="true" />
</bean>

<bean class="org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter" >
    <property name="order" value="1" />
    <property name="messageConverters">
        <list>
            <bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter" >
                <property name="supportedMediaTypes" value="application/json"/>
            </bean>

            <bean id="marshallingHttpMessageConverter" class="org.springframework.http.converter.xml.MarshallingHttpMessageConverter">
                <property name="marshaller" ref="jaxb2Marshaller" />
                <property name="unmarshaller" ref="jaxb2Marshaller" />
                <property name="supportedMediaTypes" value="application/xml"/>
            </bean>

            <bean class = "org.springframework.http.converter.FormHttpMessageConverter">
                <property name="supportedMediaTypes" value = "application/x-www-form-urlencoded" />
            </bean>

            <bean class = "org.springframework.http.converter.StringHttpMessageConverter">
                <property name="supportedMediaTypes" value = "text/plain;charset=UTF-8" />
            </bean>
        </list>
    </property>
</bean>

<bean id="jaxb2Marshaller" class="org.springframework.oxm.jaxb.Jaxb2Marshaller" >
    <property name="classesToBeBound">
        <list>
            <value>com.lt.domain.Book</value>
        </list>
    </property>
</bean>

<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
    <property name="order" value="2" />
    <property name="prefix" value="/WEB-INF/views/"/>
    <property name="suffix" value=".jsp"/>
</bean>
4

2 に答える 2

3
@RequestMapping (method = RequestMethod.POST)
public Book createBook(Book book)
        throws Exception {
    return book;
}

consumers は、消費できるものすべての文字列配列を取り、Spring Bean バインディングが残りを処理する必要があります。問題は、json を自動的にマーシャリングおよびアンマーシャリングするために、Bean バインディングを正しく設定していない可能性があります。@RequestBody と @RepsonseBody を使用することは、最善の選択肢ではありません。

依存関係にjacksonが追加されていることを確認してください

<dependency>
<groupId>org.codehaus.jackson</groupId>
<artifactId>jackson-mapper-asl</artifactId>
<version>latest</version>
</dependency>

contentnegotiatingviewresolver を使用する

<bean class="org.springframework.web.servlet.view.ContentNegotiatingViewResolver">
    <property name="mediaTypes">
        <map>
            <entry key="htm" value="text/htm"/>
            <entry key="html" value="text/html"/>
            <entry key="json" value="application/json"/>
        </map>
    </property>
    <property name="viewResolvers">
        <list>
            <bean class="org.springframework.web.servlet.view.BeanNameViewResolver"/>
            <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
                <property name="prefix" value="/WEB-INF/jsp/"/>
                <property name="suffix" value=".jsp"/>
            </bean>
        </list>
    </property>

    <property name="defaultViews">
        <list>
            <bean class="org.springframework.web.servlet.view.json.MappingJacksonJsonView"/>

        </list>
    </property>
</bean>

クライアント アプリケーションで Accept ヘッダーが必要な値に設定されていることを確認してください。また、requestmethod アノテーションですべての生成および消費データをドロップできる必要があります。

于 2012-12-13T10:38:22.973 に答える
3

Spring で JSON からオブジェクトに自動的に変換する場合は、@RequestBody. 使用しない場合、JSON で送信するときに説明したように、値はバインドされず、すべてのパラメーターは null になります。

使用する場合@RequestBody: 春のドキュメントで説明されているように、バックグラウンドで MessageConverters を使用して変換が行われます: http://static.springsource.org/spring/docs/3.1.x/spring-framework-reference/html/mvc.html #mvc-ann-requestbody

MappingJacksonHttpMessageConverterJSON からオブジェクトへの変換を行う を正しく構成しています。

欠けているのは、フォーム データからオブジェクトへの変換FormHttpMessageConverterです。x-www-form-urlencode を使用したリクエストをMultiValueMap<String, String>、カスタム オブジェクトではなく に変換します。

私の現在の理解では、に似たものを作成する必要がありますが、MappingJacksonHttpMessageConverterフォームデータのみを処理できます。

于 2013-03-19T16:20:34.940 に答える