Kodowanie znaków UTF-8 JSP Tomcat Spring 4

Kodowanie znaków UTF-8 JSP Tomcat Spring 4
TE
  • Rejestracja:ponad 11 lat
  • Ostatnio:około 4 godziny
  • Postów:67
0

Cześć,

Jest wiele tematów na ten temat. Przejrzałem wszystkie, wypróbowałem różne konfiguracje i niestety nie udało się mi się uzyskać polskich znaków. Problem występuje przy przesłaniu formularza do bazy. Na stronach statyczny tekst się wyświetla prawidłowo. Niżej wrzucam konfiguracje.
Używam Springa, MySQL i Tomcata.

AppConfig.java

Kopiuj
 
@Configuration
@EnableWebMvc
@ComponentScan(basePackages = "pl.travel.tourist")
public class AppConfig extends WebMvcConfigurerAdapter {
    
    @Bean
    public ViewResolver viewResolver() {
        InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
        viewResolver.setViewClass(JstlView.class);
        viewResolver.setPrefix("/WEB-INF/views/");
        viewResolver.setSuffix(".jsp");
        return viewResolver;
    }


    /**
     * Configure ResourceHandlers to serve static resources like CSS/ Javascript etc...
     */
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/static/**").addResourceLocations("/static/");
    }

    @Bean
    public MessageSource messageSource() {
        ResourceBundleMessageSource messageSource = new ResourceBundleMessageSource();
        messageSource.setBasename("messages");
        return messageSource;
    }

    @Override
    public void addFormatters(FormatterRegistry registry) {
        registry.addConverter(idToRegionConverter);
        registry.addConverter(idToKategoriaConverter);
        registry.addConverter(roleToUserProfileConverter);
        registry.addConverter(idToWydarzenieConverter);
        registry.addConverter(idToUserConverter);
    }

    @Override
    public void configurePathMatch(PathMatchConfigurer matcher) {
        matcher.setUseRegisteredSuffixPatternMatch(true);
    }

    @Bean
    public MultipartResolver multipartResolver() throws IOException {
        return new StandardServletMultipartResolver();
    }

}

AppInitializer.class

Kopiuj
public class AppInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {

    @Override
    protected Class<?>[] getRootConfigClasses() {

        return null;
    }

    @Override
    protected Class<?>[] getServletConfigClasses() {
        return new Class[] { AppConfig.class };
    }

    @Override
    protected String[] getServletMappings() {
        return new String[] { "/" };
    }

    @Override
    protected void customizeRegistration(ServletRegistration.Dynamic registration) {
        registration.setMultipartConfig(new MultipartConfigElement("/home/tom/uploads/", 2097152, 4194304, 0));
    }

    @Override
    public void onStartup(ServletContext servletContext) throws ServletException {
        super.onStartup(servletContext);

        FilterRegistration.Dynamic encodingFilter = servletContext.addFilter("encoding-filter", new CharacterEncodingFilter());
        encodingFilter.setInitParameter("encoding", "UTF-8");
        encodingFilter.setInitParameter("forceEncoding", "true");
        encodingFilter.addMappingForUrlPatterns(null, true, "/*");
    }

}

SecurityConfiguration.java

Kopiuj
@Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
@Import({SecurityWebApplicationInitializer.class})
public class SecurityConfiguration extends WebSecurityConfigurerAdapter  {

    @Autowired
    @Qualifier("customUserDetailsService")
    UserDetailsService userDetailsService;

    @Autowired
    public void configureGlobalSecurity(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(userDetailsService);
        auth.authenticationProvider(authenticationProvider());
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }


    @Bean
    public DaoAuthenticationProvider authenticationProvider() {
        DaoAuthenticationProvider authenticationProvider = new DaoAuthenticationProvider();
        authenticationProvider.setUserDetailsService(userDetailsService);
        authenticationProvider.setPasswordEncoder(passwordEncoder());
        return authenticationProvider;
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
                .antMatchers("/").permitAll()
                .antMatchers("/admin/**").access("hasRole('ADMIN')")
                .and().formLogin().loginPage("/login")
                .usernameParameter("userLogin").passwordParameter("password")
                .and().csrf().disable();

    }
}

SecurityWebApplicationInitializer.java

Kopiuj
public class SecurityWebApplicationInitializer extends AbstractSecurityWebApplicationInitializer {

    @Override
    protected void beforeSpringSecurityFilterChain(ServletContext servletContext) {
        super.beforeSpringSecurityFilterChain(servletContext);
        FilterRegistration.Dynamic characterEncodingFilter = servletContext.addFilter("encodingFilter", new CharacterEncodingFilter());
        characterEncodingFilter.setInitParameter("encoding", "UTF-8");
        characterEncodingFilter.setInitParameter("forceEncoding", "true");
        characterEncodingFilter.addMappingForUrlPatterns(null, false, "/*");
    }

}

W pliku configuracyjnym tomcata server.xml ustawiłem tak:

Kopiuj
<Connector port="8080" protocol="HTTP/1.1"
               connectionTimeout="20000"
               redirectPort="8443" URIEncoding="UTF-8" />

Na widokach jsp na górze mam ustawione:

Kopiuj
<%@ page contentType="text/html;charset=UTF-8" language="java" %>

W formularzach dodaje parametr:
accept-charset="UTF-8"

Proszę o pomoc, jakiekolwiek wskazówki na pewno się przydadzą. Chciałbym się obejść bez konfiguracji w pliku web.xml, jeśli się da :)

Lectre
  • Rejestracja:ponad 10 lat
  • Ostatnio:ponad 6 lat
  • Lokalizacja:Warszawa
  • Postów:293
0

A spróbuj dodać w swoim ViewResolver

Kopiuj
resolver.setContentType("text/html;charset=UTF-8");
TE
Nie zadziałało :/ Sprawdziłem za pomocą Firebuga jak przesyłany jest request POST i w Content-Language mam "en-US". Ale w widoku ustawiam język polski za pomocą <html lang="pl"> . W czym może być problem?
Lectre
  • Rejestracja:ponad 10 lat
  • Ostatnio:ponad 6 lat
  • Lokalizacja:Warszawa
  • Postów:293
0

W security configu dodaj

Kopiuj
CharacterEncodingFilter filter = new CharacterEncodingFilter();
		filter.setEncoding("UTF-8");
		filter.setForceEncoding(true);
		http.addFilterBefore(filter, CsrfFilter.class);
TE
A w której metodzie dokładnie to zrobić?
TE
Nie zadziałało :/
Lectre
A wrzuć do configure()
TE
Też próbowałem i nie zadziałało :/
Lectre
Kiedyś klepałem w Springu polski projekt, wydawało mi się, że właśnie gdy dodałem to - zadziałało.
TE
Mam projekt na gicie, jakbyś miał czas to odpalibyś u siebie i sprawdził co może być nie tak? Ja dopiero zaczyna ze Springiem i możliwe, że ominąłem jakąś trywialną rzecz przy konfiguracji https://github.com/tdabrowski/tourist-travel
Lectre
Nie dam rady odpalić. Swój mam na prywatnym repo, zaraz go przejrzę. A w którym momencie 'tracisz' polskie ogonki? w formach z View przychodzą dobre?
TE
Z bazy danych ściągam poprawnie polskie znaki, wszystko się "krzaczy" jeśli wysyłam POSTem formularz do bazy
Lectre
No ale w momencie dodawania do bazy, czy jak w kontrolerze dostajesz foremkę? Sprawdź.
TE
Hmm a można to łatwo sprawdzić?
Lectre
debugger lub System.out.println w kontrolerze.
TE
Ok więc jak dostanę form to już dane są zepsute :/
Lectre
  • Rejestracja:ponad 10 lat
  • Ostatnio:ponad 6 lat
  • Lokalizacja:Warszawa
  • Postów:293
1

Może pokaż dowolny view z formularzem. Używasz JSP, a czy w nagłówku określasz format response?

Kopiuj
<%@ page language="java" contentType="text/html; charset=UTF-8"
	pageEncoding="UTF-8"%>
<%
	response.setCharacterEncoding("UTF-8");
	request.setCharacterEncoding("UTF-8");
%>
TE
Jest progress!! :D Nie miałem ustawionego response i request. Wiec teraz dane przychodzą dobre z formularza ale niestety do bazy zapisywane są wciąż "krzaki" :/
Lectre
Sprawdz w bazie jakie masz kodowanie
TE
  • Rejestracja:ponad 11 lat
  • Ostatnio:około 4 godziny
  • Postów:67
1

Działa!! :) Dzięki wielkie @Lectre ! Rozwiązaniem było dodanie do widoku JSP tego kodu.

Kopiuj
<%
    response.setCharacterEncoding("UTF-8");
    request.setCharacterEncoding("UTF-8");
%>
 

Oprócz tego trzeba upewnić się, że w bazie danych mamy ustawione kodowanie UTF-8 oraz odpowiednio łączymy się z nią przez JDBC.
jdbc:mysql://IP_BAZY_DANYCH/NAZWA_TABELI?useUnicode=true&amp;characterEncoding=utf8

Jak ustawić kodowanie w MySQL na utf-8?
W pliku (dla linuxa) /etc/mysql/my.conf dodajemy pod sekcją [mysqld] taki kod:

Kopiuj
character-set-server=utf8
default-character-set=utf8
default-collation=utf8_general_ci
init-connect='SET NAMES utf8'
character-set-client=utf8 

Aktualizujemy nasze tabele za pomocą:
ALTER TABLE nazwa_tabeli CONVERT TO CHARACTER SET utf8 COLLATE utf8_unicode_ci;

Dzięki zastosowaniu tych wskazówek i dodaniu filtrów w konfiguracji Spring Security, które już miałem dodane wszystko powinno śmigać :)

0

Podpinam się pod temat.

Na backendzie mam endpoint, który zwraca plik w takiej formie '%C5%9B%C5%9B%C5%9B' . Czy to poprawne czy w requescie powinien być widoczny normalny string 'śśś' ?

Chrome a nawet IE radzą sobie poprawnie. Tylko firefox nie ogarnia.

Zarejestruj się i dołącz do największej społeczności programistów w Polsce.

Otrzymaj wsparcie, dziel się wiedzą i rozwijaj swoje umiejętności z najlepszymi.