JavaRush /Blogue Java /Random-PT /Introdução ao Maven, Spring, MySQL, Hibernate e a primeir...
Макс
Nível 41

Introdução ao Maven, Spring, MySQL, Hibernate e a primeira aplicação CRUD (parte 4)

Publicado no grupo Random-PT
Boa tarde. Neste artigo gostaria de compartilhar meu primeiro encontro com coisas como Maven, Spring, Hibernate, MySQL e Tomcat no processo de criação de uma aplicação CRUD simples. Esta é a parte final. O artigo é destinado principalmente àqueles que já completaram 30-40 níveis aqui, mas ainda não se aventuraram além do Java puro e estão apenas começando (ou prestes a começar) a entrar no mundo aberto com todas essas tecnologias, frameworks e outros desconhecidos palavras. Esta é a quarta parte final do artigo “Introdução ao Maven, Spring, MySQL, Hibernate e a primeira aplicação CRUD”. As partes anteriores podem ser vistas seguindo os links:

Contente:

Recursos de design e web

Nosso aplicativo funciona, mas você não consegue vê-lo sem lágrimas, inscrições chatas, links feios, fundo branco vazio. Precisamos consertar isso e adicionar belezas diferentes. Como vamos fazer isso? Bem, em primeiro lugar, você pode simplesmente brincar com as páginas e fazer todo tipo de coisa usando os recursos do HTML . Mas se você tentar alterar planos de fundo, cores, tamanhos, disposição dos elementos, etc. usando apenas HTML. e assim por diante. então, no final, você pode bagunçar tanto a página que não conseguirá distinguir nada mais tarde. Além disso, as opções de design do HTML são bastante limitadas. É melhor usar CSS (Cascading Style Sheets) para isso . Assim, tudo relacionado ao design pode ser reunido em um só lugar e depois aplicado ao elemento desejado da página. O código CSS pode ser escrito diretamente na página JSP em uma tag especial, mas é muito mais conveniente colocá-lo em um arquivo separado e simplesmente aplicá-lo às páginas necessárias. Para colocar arquivos com estilos e outros recursos estáticos da web, criaremos um diretório separado dentro de webapp . Para não confundir recursos da web com recursos regulares (onde temos db.properties ), vamos apenas chamar este diretório de res e colocar todos os arquivos CSS, imagens, etc.
Introdução ao Maven, Spring, MySQL, Hibernate e a primeira aplicação CRUD (parte 4) - 1
Para usar esses arquivos precisamos especificar sua localização na configuração. Vamos para nossa aula WebConfig. Anteriormente, usávamos a anotação @EnableWebMvcpara não configurar nada, mas simplesmente usar a configuração padrão. Mas agora há necessidade de configurar alguma coisa. Para fazer isso, usamos a interface WebMvcConfigurer, que permite substituir os métodos de configuração. Que. podemos usar a configuração padrão, mas ao mesmo tempo personalizar alguns aspectos para nós mesmos. Neste caso addResourceHandlers, precisamos de um método com o qual indiquemos a localização dos recursos estáticos da web. Por precaução, toda a turma acaba ficando assim:
package testgroup.filmography.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.ViewResolver;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import org.springframework.web.servlet.view.InternalResourceViewResolver;

@Configuration
@EnableWebMvc
@ComponentScan(basePackages = "testgroup.filmography")
public class WebConfig implements WebMvcConfigurer {

    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/res/**").addResourceLocations("/res/");
    }

    @Bean
    ViewResolver viewResolver() {
        InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
        viewResolver.setPrefix("/WEB-INF/pages/");
        viewResolver.setSuffix(".jsp");
        return viewResolver;
    }
}
Agora para usar nosso CSS na página você precisa vincular ele dentro da tag head:
<head>
    <link href="<c:url value="/res/style.css"/>" rel="stylesheet" type="text/css"/>
</head>
Basta adicionar esta linha e criar, por exemplo, este arquivo CSS simples:
table {
    border-spacing: 0 10px;
    font:  bold 100% Georgia, serif;
    margin: 40px auto;
    text-shadow: 5px 5px 5px #3F3F7F;
    background: #B1B9D9;
    text-align: center;
    vertical-align: middle;
    width: 50%;
    border: 10px solid blue;
}
E isso vai mudar completamente a nossa tabela (parece bobagem, claro, mas é assim, por exemplo): Introdução ao Maven, Spring, MySQL, Hibernate e a primeira aplicação CRUD (parte 4) - 2Bom, acho que não há necessidade de falar detalhadamente sobre CSS, tudo é bem simples. Na Internet você encontra diversas opções prontas para desenho de tabelas e formulários. Mas é melhor, claro, você mesmo fazer o design, não precisa ser designer, afinal, este não é um site complicado. Mesmo algumas horas após o primeiro contato serão suficientes para criar um design bastante bonito e elegante para uma página tão simples. Além disso, a Internet está repleta de todos os tipos de lições, exemplos, existem sites especiais onde você pode editar simultaneamente HTML, CSS em uma tela e ver imediatamente como fica tudo. Com um pouco de prática você pode criar arte de verdade. É verdade que você também não deve se deixar levar por aqui (a menos, é claro, que você tenha planos de se tornar um designer), caso contrário, o design é uma coisa dessas, você pode ficar preso aqui por muito tempo. Quando comecei a entender CSS, fiquei preso. Queria experimentar de tudo, cada propriedade, distorcer alguma coisa, mexer, experimentar, pegar páginas de alguns sites e refez-las irreconhecíveis. Provavelmente me diverti com esse brinquedo por uma semana, sem fazer mais nada, até que ele me deixou ir :) Bem, em geral, é claro, você não deve exagerar e fazer um milagre colorido incompreensível, você precisa fazer isso de forma simples e com bom gosto. A única coisa digna de nota. Você precisa entender que CSS é uma descrição de design e HTML é uma marcação . Você não deve tentar fazer absolutamente tudo através de CSS; alguns aspectos serão muito difíceis de fazer, e alguns são simplesmente impossíveis, quando em HTML isso é feito com algumas linhas extras, ou mesmo apenas um atributo em uma tag. Você precisa combiná-los, criar todos os tipos de cores, planos de fundo, fontes em CSS e, se, por exemplo, precisar combinar algumas células de uma tabela, é mais fácil usar ferramentas HTML. Bem, por exemplo, aqui está o que consegui fazer com as páginas em algumas horas mexendo em CSS e HTML (não vou entrar em detalhes aqui sobre a bagunça que fiz para conseguir isso, no final haverá um link para o GitHub deste projeto onde você pode olhar): Знакомство с Maven, Spring, MySQL, Hibernate и первое CRUD приложение (часть 4) - 3Claro, não sei com que competência fiz tudo lá, mas considerando que vi CSS pela primeira vez uma semana antes, acho que deu muito certo.

Paginação

Agora tudo funciona, parece bom, mas até agora só existem alguns registros na tabela. E se houver cem ou mil filmes? Não é muito conveniente percorrer uma lista tão longa. É muito mais conveniente quando a lista é exibida em páginas de 10 entradas, por exemplo. Portanto, agora tentaremos implementar a divisão da lista em páginas (às vezes isso também é chamado de “paginação” ou “paginação” ( paginação em inglês )). Isso pode ser feito de diferentes maneiras. Por exemplo, você pode transferir a lista completa para uma página jsp e criar uma tabela para o número necessário de registros. Ou você pode, por exemplo, extrair os registros necessários da lista geral do serviço e, em seguida, enviar essa minilista para uma página jsp para exibição. Mas é melhor, claro, fazer isso no nível do banco de dados. A ideia não é pegar uma lista completa do banco de dados e depois dividi-la em partes, mas inicialmente obter a parte necessária do banco de dados sem mexer em todo o resto. Afinal, por que precisamos extrair todas as centenas ou milhares de registros do banco de dados de uma vez, se o que precisamos está entre os dez primeiros, é melhor retirar apenas este dez. Vamos ao DAO e adicionamos allFilmsum parâmetro ao método int page, que será responsável pelo número da página (no serviço, claro, fazemos o mesmo). E vamos mudar um pouco a implementação deste método; se antes retirámos a lista inteira, agora retiraremos apenas uma parte. setFirstResultOs métodos (com qual linha da tabela começar) e setMaxResults(quantos registros exibir) nos ajudarão com isso :
@SuppressWarnings("unchecked")
public List<Film> allFilms(int page) {
    Session session = sessionFactory.getCurrentSession();
    return session.createQuery("from Film").setFirstResult(10 * (page - 1)).setMaxResults(10).list();
}
Aqueles. se esta for a 1ª página, exibimos no máximo 10 registros, a partir do 0; se esta for a 5ª página, então 10 registros a partir da 40 (não esquecer que a numeração no banco de dados começa em 0). Também criaremos adicionalmente um método que retornará o número de registros na tabela. Precisaremos disso para saber o número de todas as páginas e criar links para elas em nossa página jsp:
public int filmsCount() {
     Session session = sessionFactory.getCurrentSession();
     return session.createQuery("select count(*) from Film", Number.class).getSingleResult().intValue();
 }
Usando essa consulta, obteremos o número de todos os registros da tabela (como intum valor) sem extrair os próprios registros. Agora vamos ao controlador e trabalhar no método que retorna a página principal com uma lista de filmes:
@RequestMapping(value = "/", method = RequestMethod.GET)
public ModelAndView allFilms(@RequestParam(defaultValue = "1") int page) {
    List&ltFilm> films = filmService.allFilms(page);
    int filmsCount = filmService.filmsCount();
    int pagesCount = (filmsCount + 9)/10;
    ModelAndView modelAndView = new ModelAndView();
    modelAndView.setViewName("films");
    modelAndView.addObject("page", page);
    modelAndView.addObject("filmsList", films);
    modelAndView.addObject("filmsCount", filmsCount);
    modelAndView.addObject("pagesCount", pagesCount);
    return modelAndView;
}
Uma nova anotação apareceu aqui @RequestParam, indicando que estamos obtendo esse valor de um parâmetro de solicitação. Agora, se formos para um endereço com um parâmetro, por exemplo http://localhost:8080/ ?page=4 , obteremos, respectivamente, a 4ª página. Definimos o valor padrão como " 1 " para que quando a aplicação for iniciada, quando formos para um endereço sem o parâmetro http://localhost:8080/ , obtenhamos a primeira página. No método obtemos o número de todos os registros, então desta forma simples calculamos o número de páginas. Aqueles. se tivermos 10 registros, isso é 1 página, e se houver 11, então já são 2. Bom, transferimos tudo isso para o modelo. Você precisa saber a quantidade de páginas para criar links para todas elas em um ciclo, e deixar a quantidade de filmes lá para o caso, por exemplo, se você quiser exibir essa informação em algum lugar da página. Agora só falta acessar films.jsp e adicionar links para cada página usando esta construção:
<c:forEach begin="1" end="${pagesCount}" step="1" varStatus="i">
    <c:url value="/" var="url">
        <c:param name="page" value="${i.index}"/>
    </c:url>
    <a href="${url}">${i.index}</a>
</c:forEach>
Criamos links pelos contadores 1, 2, 3, ... e definimos o parâmetro pelo valor do índice.

A propósito, da mesma forma que na paginação, você pode adicionar outros recursos, como classificação, filtragem e pesquisa. Simplesmente passamos vários parâmetros para o método DAO e os usamos para formar uma consulta apropriada ao banco de dados a fim de extrair os registros necessários na ordem exigida.

Vamos adicionar mais um pequeno toque. Voltamos ao controlador. Nos métodos add, edit e delete, após a conclusão da operação, redirecionamos para a página principal "redirect:/" . Que. se estivermos em algum lugar na 50ª página e clicarmos em editar entrada, após a execução iremos para o endereço " / ", ou seja, Voltemos à página 1. Isto não é muito conveniente; gostaria de voltar ao lugar de onde viemos. Vamos resolver isso de forma muito simples. FilmControllerVamos criar uma variável de instância na classeint page
private int page;
Dentro do método allFilmsiremos atribuir o valor do parâmetro a esta variável page:
this.page = page;
Que. Cada vez que este método for executado (ou seja, quando navegarmos pelas páginas), o valor da página atual será escrito na variável. E então usamos esse valor em nossos métodos para redirecionar de volta para a mesma página.
modelAndView.setViewName("redirect:/?page=" + this.page);

Conclusão

Provavelmente terminaremos aqui. O resultado é um aplicativo CRUD completo. Certamente está longe do ideal (muito longe), mas pode ser otimizado e melhorado, bugs corrigidos e funcionalidades adicionadas. Você pode usar métodos integrados para operações brutas; adicione filtragem, pesquisa, classificação; adicione outras tabelas relacionadas; implementar suporte para diferentes usuários com autorização e autenticação, etc. e assim por diante. O espaço para a imaginação é ilimitado, então vá em frente. Link para o github deste projeto . Obrigado pela sua atenção. PS Esta é minha primeira tentativa na vida de escrever um artigo, então não julgue estritamente :). Peço desculpas por não adicionar links diferentes para recursos úteis; infelizmente, ainda não consigo desenvolver o hábito de salvar links para as fontes de onde obtenho informações. E, claro, peço desculpas pelas muitas cartas, brevidade não é meu talento, espero que alguém dê conta. Links para todas as partes
Comentários
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION