programing

스프링 3.0.5에서 매개 변수 바인딩이 쉼표를 해석하지 못하도록 방지하는 방법은 무엇입니까?

subpage 2023. 8. 12. 10:20
반응형

스프링 3.0.5에서 매개 변수 바인딩이 쉼표를 해석하지 못하도록 방지하는 방법은 무엇입니까?

다음 컨트롤러 방법을 고려합니다.

@RequestMapping(value = "/test", method = RequestMethod.GET)
public void test(@RequestParam(value = "fq", required = false) String[] filterQuery) {
    logger.debug(fq = " + StringUtils.join(filterQuery, "|"));
}

은 다양한 다은다기출다니력입대에 출력입니다.fq조합:

  1. /test?fq=foo으로 의결과가 됩니다.fq = foo
  2. /test?fq=foo&fq=bar으로 의결과가 됩니다.fq = foo|bar
  3. /test?fq=foo,bar으로 의결과가 됩니다.fq = foo|bar
  4. /test?fq=foo,bar&fq=bash으로 의결과가 됩니다.fq = foo,bar|bash
  5. /test?fq=foo,bar&fq=으로 의결과가 됩니다.fq = foo,bar|

예 3이 문제입니다.이 ( 출력될 합니다.fq = foo,bar.

나는 쉼표를 벗어나려고 노력했습니다.\ 및사용을 사용합니다.%3C하지만 그녀의 작품.

가 봤때을는제를 요.HttpServletRequest개체의 버전:

String[] fqs = request.getParameterValues("fq");
logger.debug(fqs = " + StringUtils.join(fqs, "|"));

은 예상합니다: 예상출출니다합력을력다▁the▁it니.fqs = foo,bar그래서 "문제"는 스프링 데이터 바인딩에 있습니다.

할 수 있었습니다.HttpServletRequest하지만 실제 코드에서 백을 사용하고 있기 때문에(같은 일이 일어나고 있음) 바인딩 기능을 다시 구현하고 싶지 않습니다.저는 누군가 탈출이나 다른 메커니즘을 통해 이러한 행동을 예방할 수 있는 간단한 방법을 제공할 수 있기를 바랍니다.

TIA

업데이트: Twitter에 이 Q를 게시하고 예상 출력이 Spring 3.0.4와 함께 표시된다는 답변을 받았습니다.해제합니다.저는 이제 이것이 사실이고 따라서 일시적인 해결책이라는 것을 확인했습니다.Spring JIRA 시스템에 버그로 기록하겠습니다.3.0.5에 대한 해결책이나 해결책을 제공할 수 있는 사람이 있다면 그들의 답변을 받아들이겠습니다.

저는 당신의 코드를 테스트했습니다. 믿을 수 없지만, 당신의 문제를 재현할 수 없습니다.스프링의 최신 버전(3.0.5)을 다운로드했습니다. 컨트롤러는 다음과 같습니다.

package test;

import org.apache.commons.lang.StringUtils;
import org.apache.log4j.Logger;
import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
@RequestMapping("/test/**")
public class MyController {

    private static final Logger logger = Logger.getLogger(MyController.class);

    @RequestMapping(value = "/test/params", method = RequestMethod.GET)
    public void test(SearchRequestParams requestParams, BindingResult result) {
    logger.debug("fq = " + StringUtils.join(requestParams.getFq(), "|"));
    }
}

SearchRequestParams 클래스입니다.

package test;

public class SearchRequestParams {
    private String[] fq;

    public String[] getFq() {
    return fq;
    }

    public void setFq(String[] fq) {
    this.fq = fq;
    }
}

이것이 제 간단한 스프링 구성입니다.

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

<bean class="test.MyController" />

<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
    <property name="prefix">
        <value>/WEB-INF/jsp/</value>
    </property>
    <property name="suffix">
        <value>.jsp</value>
    </property>
</bean>

tomcat 7때 7.0.8 내에서 http://localhost:8080/testweb/test/params.htm?fq=foo,bar는 로그 수 있습니다.DEBUG fq = foo,bar제 코드와 당신 코드의 차이점은 무엇입니까?내가 뭘 잘못하고 있나요?저는 당신을 돕고 싶기 때문에, 만약 당신이 어떤 의심이 있거나 제가 당신을 위해 다른 검사를 할 수 있다면, 그것은 기쁨이 될 것입니다.

/ / 업데이트
은 코로문재현습니다했제라는 를 가지고 있습니다. 태그가 있습니다.<mvc:annotation-driven />서비스인 " " " 를 합니다.FormattingConversionService 변가포있다습니함어의 기본 합니다.StringString[]쉼표를 구분 기호로 사용합니다.사용자 자신의 변환기가 포함된 다른 변환 서비스 빈을 사용해야 합니다.StringString[]다른 구분 기호를 사용해야 합니다. 쿼리 문자열("?first=1;second=2;second=3")에 일반적으로 사용되는 구분 기호이기 때문에 ";"를 사용하기로 선택했습니다.

import org.springframework.core.convert.converter.Converter;
import org.springframework.util.StringUtils;

public class CustomStringToArrayConverter implements Converter<String, String[]>{
   @Override
    public String[] convert(String source) {
        return StringUtils.delimitedListToStringArray(source, ";");
    }
}

그런 다음 구성에서 이 변환 서비스 빈을 지정해야 합니다.

<mvc:annotation-driven conversion-service="conversionService" />

<bean id="conversionService" class="org.springframework.context.support.ConversionServiceFactoryBean">
    <property name="converters">
        <list>
            <bean class="au.org.ala.testspringbinding.CustomStringToArrayConverter" />
        </list>
    </property>
</bean>

문제가 해결되었으니 부작용이 없는지 확인해야 합니다.애플리케이션에서 원본 변환이 필요하지 않기를 바랍니다.StringString[](쉼표를 구분 기호로 사용) ;-)

제게 - 합니다 - 는나나위가우아고짧하은길찾다니을았습추 - 가를한장.@InitBinder@Controller:

@InitBinder
public void initBinder(WebDataBinder binder) {
    binder.registerCustomEditor(String[].class, new StringArrayPropertyEditor(null));
}

하지 않고 String을 String합니다.null클래스 springframework.param), 스링클스래 org.파일 이름은 .propertyeditors.", ", "입니다.StringArrayPropertyEditor가 있습니다.같은 프로젝트의 다른 사용자가 새 기본 변환 방법을 사용하는 경우에는 문제가 없습니다.

루거우의 코멘트는 제가 사용하고 있었기 때문에 저에게 효과가 있었던 유일한 해결책이었습니다.List<String>String[].

이 값을 컨트롤러에 추가하여 쉼표로 구분된 값 구문 분석을 제거합니다.

    @InitBinder
    public void initBinder(WebDataBinder binder) {
        binder.registerCustomEditor(List.class, new CustomCollectionEditor(List.class));
    }

필립 포터가 제안한 것처럼, 저는 제 질문에 대한 "업데이트"를 답으로 게시합니다. 놓치기 쉬웠을 수도 있지만...

Spring 3.0.5부터 다운그레이드.3.0.4로 릴리스.릴리스를 사용하여 문제를 해결했습니다).@RequestParam하는 주석. 3.0.5의 버그입니다.

그러나 양식 지원 빈에 바인딩할 때 관련 문제는 해결되지 않습니다. 이것은 제 웹 앱에 있는 것입니다.모든 버전을 3.0.0으로 다시 테스트했습니다.해제하고 동일한 결과를 얻습니다(/test?fq=foo,barfq = foo|bar).

예.

@RequestMapping(value = "/test", method = RequestMethod.GET)
public void test(SearchRequestParams requestParams, BindingResult result) {
    logger.debug("fq = " + StringUtils.join(requestParams.getFq(), "|"));
}

SearchRequestParams " " 를 합니다.String[] fq.

이에 대한 해결책이 있는 사람이 있다면 기꺼이 그들의 답변을 받아들이겠습니다.

자바나는 이미 올바른 근본 원인을 지적했습니다.여기와 여기에 표시된 것처럼 StringToArrayConverter도 함께 제거할 수 있다는 점을 추가로 지적하고 싶습니다.

다음은 MVC 요청에서 쉼표 구분을 우회하는 나의 여정입니다.

이는 다음과 같은 솔루션 유형의 Springs 진화에 대한 저의 이해입니다.문서는 최신 솔루션이 무엇인지에 대해 매우 모호합니다.

먼저 WebMvcConfigAdapter는 인터페이스 WebMvcConfig를 구현했습니다.이것은 결국 더 이상 사용되지 않습니다.

이 버전은 WebMvcConfigSupport로 대체되었습니다.이것은 결국 더 이상 사용되지 않았지만 첫 번째 해결책보다 더 좋았습니다.주요 문제는 MVC 자동 구성을 해제하고 swagger.html이 작동하지 않고 액추에이터 정보가 누락되어 날짜가 큰 소수점이 되었다는 것입니다.

최신 버전은 Java 8 기능을 사용하여 기본 메서드를 구현하는 수정된 인터페이스 WebMvcConfig입니다.

내 경우 WebConfigUUID가 최신 버전의 WebMvcConfig를 구현하는 AnyClass일 수 있는 클래스를 만듭니다.

이를 통해 다른 변환기에 영향을 주거나 다른 변환기를 오버라이드하여 작동하거나 액추에이터 정보 출력을 처리하지 않고도 필요한 것을 변경할 수 있습니다.

다음은 MVC 요청을 처리할 때 문자열의 쉼표 구분을 목록으로 우회하는 변경 사항을 구현한 두 클래스입니다.
문자열 목록은 계속 생성되지만 값은 하나뿐입니다.

import java.util.Collection;
import org.springframework.context.annotation.Configuration;
import org.springframework.format.FormatterRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
@Configuration
public class WebConfigUUID implements WebMvcConfigurer {
  @Override
  public void addFormatters(FormatterRegistry registry)  {
    registry.removeConvertible(String.class,Collection.class);
    registry.addConverter(String.class,Collection.class,BypassCommaDelimiterConfiguration.commaDelimiterBypassedParsingConverter());
  }
}

import java.util.ArrayList;
import java.util.List;
import org.springframework.core.convert.converter.Converter;

public class BypassCommaDelimiterConfiguration  {
    public static Converter<String, List<String>> commaDelimiterBypassedParsingConverter() {
        return new Converter<String, List<String>>() {
            @Override
            public List<String> convert(final String source) {
                final List<String> classes = new ArrayList<String>();
                classes.add(source);
                return classes;
            }
        };
    }
}

해킹이지만 '-'로 구분된 매개 변수를 전달하는 것을 고려해 본 적이 있습니까?

/test?fq=foo-bar results in fq = foo-bar
/test?fq=foo-bar&fq=bash results in fq = foo-bar|bash 

또는 다른 구분 기호는 ~, 또는 !, 또는 ^, 또는 ?일 수 있습니다.

언급URL : https://stackoverflow.com/questions/4998748/how-to-prevent-parameter-binding-from-interpreting-commas-in-spring-3-0-5

반응형