2017-11-04 1 views
0

사용자 및 주소가 2 개 있습니다. 다음과 같은 관계가 설정됩니다이스프링 데이터 REST + 최대 절전 모드 5 + 잭슨 LAZY 직렬화 실패

@Entity 
@Table(name = "addresses") 
@JsonIgnoreProperties({"hibernateLazyInitializer", "handler"}) 
public class Address { 
    private static final long serialVersionUID = 1L; 
    @Id 
    @JsonIgnore 
    @GeneratedValue(strategy = GenerationType.IDENTITY) 
    private Long id; 

    @ManyToOne(fetch = FetchType.LAZY) 
    @JoinColumn(name = "username") 
    private User user; 

사용자가 내가 하나 개 이상의 주소 기관과 사용자의 사용자 이름 GET http://localhost:8080/api/data/users/{USERNAME}/addresses를 호출 할 때마다

@Entity 
@Table(name = "users") 
public class User { 
    @Id 
    private String username; 

    (...) 

    @OneToMany(mappedBy = "user", cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY) 
    private List<Address> addresses; 

, 결과가

주소를 :

,210

또한 언급 할만큼 가치가 사실은 그 봄의 데이터 REST 링크를 생성하더라도 다음 http://localhost:8080/api/data/addresses/33/user 링크가 전혀 작동하지 않는

"_links": { "self": { "href": "http://localhost:8080/api/data/addresses/33" }, "address": { "href": "http://localhost:8080/api/data/addresses/33" }, "user": [ { "href": "http://localhost:8080/api/data/users" }, { "href": "http://localhost:8080/api/data/addresses/33/user" } ] }

. (던지는 java.lang.NoClassDefFoundError가 : javax의/서블릿/JSP/JSTL/코어/구성)

지금까지 내가 주소 엔티티에 EAGER FetchingType에 LAZY를 변경하고 다음과 같이 동작 후 변경 시도 :

  • 내가 할 수없는 GET http://localhost:8080/api/data/addresses (오류 메시지 "이드 직렬화! : to.wysylam.couriersystem.api.entities.User에 할당 할 수 있어야합니다"로 500)

  • 내가 할 수 GET http://localhost:8080/api/data/users/{USERNAME}/addresses

,

솔직히 나는 지금 아이디어가 없습니다. 다음과 같이

구성 파일이 정의됩니다

@Configuration 
@ComponentScan(basePackages = { "to.wysylam.couriersystem.api.controllers", 
          "to.wysylam.couriersystem.api.services", 
          "to.wysylam.couriersystem.api.hateoas" 
          }) 
@Import({JpaConfig.class, 
    SecurityConfig.class, 
    DataRestConfig.class, 
    RepositoryRestMvcConfiguration.class 
}) 
public class AppConfig { 

} 

@Configuration 
public class DataRestConfig extends RepositoryRestConfigurerAdapter { 
    @Override 
    public void configureRepositoryRestConfiguration(RepositoryRestConfiguration config){ 
    config.setRepositoryDetectionStrategy(
       RepositoryDetectionStrategy.RepositoryDetectionStrategies.ANNOTATED 
    ); 
    config.exposeIdsFor(User.class); 
    config.setBasePath("/data"); 
} 

@Bean 
protected Module module(){ 
    return new Hibernate5Module(); 
} 

@Override 
public void configureConversionService(ConfigurableConversionService configurableConversionService){ 
    configurableConversionService.addConverter(String.class, String[].class, stringToStringArrayConverter()); 
} 

private Converter<String, String[]> stringToStringArrayConverter(){ 
    return (source) -> StringUtils.delimitedListToStringArray(source, ";"); 

} 
} 

@Configuration 
@EnableJpaRepositories(basePackages = "to.wysylam.couriersystem.api.repositories") 
public class JpaConfig { 
private static Properties getJpaProperties(){ 
    Properties jpaProperties = new Properties(); 
    jpaProperties.put("hibernate.hbm2ddl.auto", "validate"); 
    jpaProperties.put("hibernate.default_schema", "couriersystem"); 
    jpaProperties.put("hibernate.dialect", "org.hibernate.dialect.PostgreSQL82Dialect"); 
    jpaProperties.put("hibernate.enable_lazy_load_no_trans","true"); 
    return jpaProperties; 
} 

@Bean 
public static LocalContainerEntityManagerFactoryBean entityManagerFactory(){ 
    LocalContainerEntityManagerFactoryBean asBean = new LocalContainerEntityManagerFactoryBean(); 
    asBean.setDataSource(dataSource()); 
    asBean.setPackagesToScan("to.wysylam.couriersystem.api.entities"); 
    asBean.setJpaVendorAdapter(new HibernateJpaVendorAdapter()); 
    asBean.setJpaProperties(getJpaProperties()); 

    return asBean; 
} 

@Bean(name = "dataSource") 
public static DriverManagerDataSource dataSource(){ 
    DriverManagerDataSource bean = new DriverManagerDataSource(); 
    bean.setDriverClassName("org.postgresql.Driver"); 
    bean.setUrl("jdbc:postgresql://localhost:5432/postgres"); 
    bean.setUsername("dev"); 
    bean.setPassword("pwd"); 
    return bean; 
} 

@Bean 
public static JpaTransactionManager transactionManager(){ 
    JpaTransactionManager asBean = new JpaTransactionManager(); 
    asBean.setEntityManagerFactory(entityManagerFactory().getObject()); 
    return asBean; 
} 

@Bean 
public static PersistenceExceptionTranslationPostProcessor persistenceExceptionTranslationPostProcessor(){ 
    return new PersistenceExceptionTranslationPostProcessor(); 
} 

@Bean 
public static HibernateExceptionTranslator hibernateExceptionTranslator(){ 
    return new HibernateExceptionTranslator(); 
} 
} 

@Configuration 
@EnableWebMvc 
@ComponentScan(basePackages = "to.wysylam.couriersystem.api.controllers") 
@EnableGlobalMethodSecurity(prePostEnabled = true) 
@Import(AppConfig.class) 
public class WebConfig implements WebMvcConfigurer { 

@Bean 
public InternalResourceViewResolver viewResolver(){ 
    InternalResourceViewResolver viewResolver = new InternalResourceViewResolver(); 
    viewResolver.setViewClass(JstlView.class); 
    viewResolver.setPrefix("/WEB-INF/pages/"); 
    viewResolver.setSuffix(".jsp"); 

    return viewResolver; 
} 

@Override 
public void addFormatters(FormatterRegistry registry){ 
    registry.removeConvertible(String.class, String[].class); 
    registry.addConverter(String.class, String[].class, stringToStringArrayConverter()); 
} 

private Converter<String, String[]> stringToStringArrayConverter(){ 
    return (source) -> StringUtils.delimitedListToStringArray(source, ";"); 
} 
} 

이 어떤 도움이 기간 동안

UPDATE

감사, 나는 길이 긴 문자열에서 사용자 클래스 ID를 변경했습니다.

[DEBUG] 2017-11-06 18:25:01.053 [http-nio-8080-exec-39] ExceptionHandlerExceptionResolver - Resolving exception from handler [public org.springframework.hateoas.Resources<?> org.springframework.data.rest.webmvc.RepositoryEntityController.getCollectionResource(org.springframework.data.rest.webmvc.RootResourceInformation,org.springframework.data.rest.webmvc.support.DefaultedPageable,org.springframework.data.domain.Sort,org.springframework.data.rest.webmvc.PersistentEntityResourceAssembler) throws org.springframework.data.rest.webmvc.ResourceNotFoundException,org.springframework.web.HttpRequestMethodNotSupportedException]: java.lang.IllegalArgumentException: Id must be assignable to Serializable!: to.wysylam.couriersystem.api.entities.User 

[DEBUG] 2017-11-06 18:25:01.055 [http-nio-8080-exec-39] ExceptionHandlerExceptionResolver - Resolving exception from handler [public org.springframework.hateoas.Resources<?> org.springframework.data.rest.webmvc.RepositoryEntityController.getCollectionResource(org.springframework.data.rest.webmvc.RootResourceInformation,org.springframework.data.rest.webmvc.support.DefaultedPageable,org.springframework.data.domain.Sort,org.springframework.data.rest.webmvc.PersistentEntityResourceAssembler) throws org.springframework.data.rest.webmvc.ResourceNotFoundException,org.springframework.web.HttpRequestMethodNotSupportedException]: java.lang.IllegalArgumentException: Id must be assignable to Serializable!: to.wysylam.couriersystem.api.entities.User 

답변

0

물론 내 코드에는 실수가있었습니다.

내가 ResourceProcessor<Resource<Address>>을 정의했고 이 내 데이터베이스에 사용자 정의가없는 주소 행이있는 동안이라는 사용자 속성을 부여 받았습니다.

간단한 null 확인을 통해 해결되었습니다.

케이스가 닫혔습니다.

1

여러 대에 @JsonSerialize(as = Address.class) 설정 : 문제는, 그러나,

업데이트 2

일부 흥미로운 로그 덤프 (GET <host>/api/data/addresses을 처리하는 동안) ... there.Obviously 여전히 한 클래스가 제 경우에 도움이되었습니다 ...

+0

불행히도 나에게 도움이되지 않았다. 내가 뭘 잘못 할 수 있을까? –

관련 문제