Задать вопрос
Ответы пользователя по тегу Spring
  • Как работать с файловой системой в Spring Boot?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Но потом, когда я загружу проект на сервер, то там же другая файловая система, другие директории и т.д. - как с этим быть?

    Ну во-первых, как отметил коллега Dmitry Roo нужно использовать относительные пути.
    Во-вторых, у вас должны быть несколько файлов конфигурации (с разными профилями). Например, для dev upload.path будет /home/Desktop/uploads, а для prod профиля будет uploads/ и т.д.

    Во-вторых - а как быть с безопасностью? Как-то же надо фильтровать то, что мне загружают? А то скрипт какой-нибудь загрузят или ещё что-то. Как это вообще отслеживать?

    Обычно, делают проверку MIME type, как на клиентской стороне, так и на стороне сервера.

    Например, средствами js можно запретить загрузку других файлов, кроме image/* и т.д.
    Тоже самое делаю на сервере. Проверяют формат загруженного файла и если он не соответствует ожидаемому MIME type, то выбрасывают исключение и удаляют файл.

    Как отслеживать оставшееся место на диске?

    Смотря, что подразумевается в данном случае. Если хостинг, то java.nio подойдет. А если это amazon s3 или другой сервис, то смотрите документацию к REST API.
    Ответ написан
    2 комментария
  • Как запретить десериализацию поля в jackson?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    нужно , чтобы в поле result попадал json как строка. Менять ответ контроллера (например обернуть в кавычки) я не могу.

    Можно написать свой кастомный конвертер для контроллера.
    https://stackoverflow.com/questions/57536693/how-t...

    Или вы имеете ввиду:

    аннотацию JsonIgnore?
    https://www.tutorialspoint.com/jackson_annotations...
    https://stackoverflow.com/questions/12505141/only-...

    Есть еще аннотации
    https://www.baeldung.com/jackson-bidirectional-rel...
    Ответ написан
    Комментировать
  • Можно ли так использовать спринг?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день
    имеет ли смысл только для работы с бд подключать springframework

    Может быть для работы с БД стоит подключать ORM фреймворки. Например, Hibernate, EclipseLink, MyBatis, ormlite.

    По факту spring это контейнер бинов (реализация IOC & DI). Соответственно, если вы хотите использовать DI в своем приложении, то можете использовать спринг. Ну или другую либу для DI (guice, dagger etc.)

    Например, если вы пишете JavaFX приложение, то есть хорошая либа для ьыстрой интеграции спринга
    https://github.com/rgielen/javafx-weaver/

    А просто для работы с БД используйте связку hibernate + hikaricp
    Ответ написан
    6 комментариев
  • Не обогащаются таблицы при создании Entity?

    azerphoenix
    @azerphoenix Куратор тега Spring
    Java Software Engineer
    Добрый день!
    Да, конечно же сперва выполняется sql файл.
    Можно реализовать по разному:

    1) Попробуйте вынести DDL запросы в sql файл. (schema.sql)
    2) Либо наоборот содержимое data.sql инициализируйте при помощи java кода. Например, имплементируйте интерфейс CommandLineRunner
    3) Попробуйте использовать либу FlyWay для миграций

    spring.jpa.hibernate.ddl-auto=create-drop
    Это означает, что все созданные таблицы будут дропнуты и на момент старта в БД нет таблиц, куда ваши инсерты должны быть добавлены.

    Полезная информация - https://www.baeldung.com/spring-boot-data-sql-and-...
    Ответ написан
    2 комментария
  • Как корректно создавать Spring Beans динамически?

    azerphoenix
    @azerphoenix Автор вопроса, куратор тега Java
    Java Software Engineer
    Применительно к данной задаче, которую я описал выше не пришлось созадвать бины динамически.
    Вместо этого было принято решение написать микросервисное приложение, в котором каждый из стран / городов для грапхоппера является отдельным микросервисом работающим внутри докера.
    Таким образом надобность в создании бинов в runtime отпала.

    Если вдруг кому-то все же понадобится создавать бины динамически, то можете глянуть на это решение:
    https://stackoverflow.com/questions/57157396/how-t...
    Ответ написан
    Комментировать
  • Почему страница .html перестаёт видеть style.css?

    azerphoenix
    @azerphoenix Куратор тега Spring
    Java Software Engineer
    Рекомедую прочитать документацию thymeleaf.

    Убедитесь, что файл css лежит в resources/static/css/style.css

    Вы стили подключаете неправильно.
    <link href="css/style.css" type="text/css"  rel="stylesheet"/>.


    Должно быть так:
    <link th:href="@{/css/style.css}" type="text/css"  rel="stylesheet"/>.

    При таком синтаксисе учитывается context path.

    Ну и как отметил коллега Сергей Горностаев изучите основые HTML / CSS.
    Ответ написан
    Комментировать
  • Как правильно работать с ManyToMany в Spring?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день.
    Читали ли вы лог ошибок?
    ClassCastException: java.lang.String cannot be cast to com.example.deeplom.domain.TableGames

    Ошибка приведения типов. Тип String не может быть приведен к типу TableGames.
    Притом исключение выбрасывается в методе: addGameRoom()
    Поставьте точки остановки и проведите дебаг проекта
    Ответ написан
    Комментировать
  • Как правильно вставлять картинки в html в Spring?

    azerphoenix
    @azerphoenix Куратор тега Spring
    Java Software Engineer
    Добрый день.
    Прежде всего настоятельно рекомендую провести поиск по этому сайту, а также погуглить, так как ответ на ваш вопрос легко ищется поисковиком и в общем-то найдете кучу ответов. Помню, как буквально пару месяцев назад здесь же отвечал на аналогичный вопрос.

    Теперь, что касается вашего вопроса:

    Я так понимаю так же нужно настраивать Thymeleaf?

    Шаблонизатор вам нужен в любом случае. Будь то thymeleaf или freemarker, mustache и др. Можете взять thymeleaf.

    Предположу, что ожидается некое динамическое добавление картинок в шаблон. Т.е. художники загружают свои работы, а далее они отображаются в шаблоне.
    Если так, то разделим вашу задачу на несколько частей:
    1) Реализовать загрузку картинок, хранение данных о картинках в БД (например, путь к картинке)
    https://spring.io/guides/gs/uploading-files/
    https://stackabuse.com/uploading-files-with-spring-boot
    https://www.baeldung.com/spring-file-upload
    2) Реализовать вывод картинки в шаблоне.
    В данном вашем примере у вас выводится изображение в формате svg (placeholder)
    Вам нужно вместо нее добавить img тег
    Примерно так:
    <img th:src="${image}" alt="Картинка"/>
    Конечно же вместо переменной image вам нужно подставить свою переменную.
    Если нужно вывести блок со всеми работами художника, то вам нужно будет вывести цикл с его работами.
    Итерируем по списку работ художника - https://habr.com/ru/post/351132/
    Ответ написан
    7 комментариев
  • Где нужно реализовывать HQL запросы?

    azerphoenix
    @azerphoenix Куратор тега Spring
    Java Software Engineer
    Ссылка на полезный источник: https://www.baeldung.com/hibernate-named-query

    Вот эту часть кода по логике надо писать в модели прям над названием класса?

    Да

    Теперь когда я хочу найти компании с паспортом работника, по логике я могу вызвать этот query и вызывать я его должен в классе Cервиса верно?

    Как вариант можно в сервисе. Обычно, да это делается в сервисном слое, но никто не запрещает проделывать вам это внутри контроллера или еще где-то.

    Так же возникает вопрос, если мы используем HQL и нам нужно написать какой то один непопулярный запрос, который допустим будет использован всего один раз во всем проекте.

    В Spring, используется не только HQL, но и Spring Data или Criteria API или же JPQL.
    Ответ написан
    Комментировать
  • Почему вылетает ошибка при ленивой инициализации при работе с БД?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день!
    Если не ошибаюсь, то вы столкнулись с этой проблемой:
    https://www.baeldung.com/spring-open-session-in-view

    Говоря проще, если у вас включен open-session-in-view, то вам не нужно использовать аннотацию Transactional, но при этом это является антипаттерном

    Because OSIV creates a Session at the beginning of the request, the transactional proxy uses the current available Session instead of creating a brand new one.
    Ответ написан
    Комментировать
  • Почему при сохранении объекта через связь OneToMany - ManyToOne получаю ошибку?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день!
    Предположу, что у вас возникла проблема с тем, что в SQL есть зарезервированные слова и при создании таблиц и колонок у вас эти столбцы не создаются.

    not-null property references a null or transient value : com.SchoolJournal.SpringHibernate.model.Pupil.name

    В данном случае это название переменной Pupil.name
    (433 строка) - Список зарезервированных слов в SQL
    И если вы глянете в БД, то в таблице pupil не найдете колонку name. Отсюда и ошибка.

    Решение: в Column укажите name, экранируйте при помощи обратной одинарной кавычки
    @Column(name = '"`name`", nullable = false)
            @Getter
            @Setter
            private String name;


    Полезный ресурс - https://vladmihalcea.com/escape-sql-reserved-keywo...

    Что касается OneToMany & ManyToOne, то рекомендую прочитать эту статью.
    https://vladmihalcea.com/the-best-way-to-map-a-one...
    Ответ написан
  • Аутентификация Spring Security через метод Post?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день.
    Если подразумевается, что будет авторизация через андроид или js-фреймворк, то нужно разработать REST сервис.
    В данном случае POST запросом из клиента отправляем логин и пароль пользователя в бекэнд. Там генерируем jwt и возвращаем его на клиент. Далее другой эндпоинт будет каждый раз проверять jwt на корректность и выдавать нужные данные.
    Вот, неплохой пример реализации jwt auth - https://github.com/hantsy/spring-webmvc-jwt-sample
    Ответ написан
    2 комментария
  • Как вывести картинку из бд в Spring?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день.
    У меня есть бд блога на локалхосте я туда успешно гружу всю информацию для поста (название, дату , текст и картинку)

    Картинка не должна хранится в БД. Вы конечно можете хранить картинку в БД в blob, но не нужно! Лучше в БД храните например, путь до картинки, а еще лучше путь можно сохранить в properties или yml, а в БД хранить название картинки.

    Далее небольшой совет:
    postAddArticle(@AuthenticationPrincipal User user, Date timeArticle, @RequestParam String title, String author,
                                     @RequestParam String anons, @RequestParam String text,
                                     @RequestParam("file") MultipartFile file, Model model)

    Если у вас более 4-х аргументов, то лучше собрать его в Dto. Это также позволит вам проводить валидацию через javax validation.

    А теперь, ответ на ваш вопрос: чтобы вывести картинку хранимую в БД необходимо массив байт, который вы сохранили в БД конвертировать в base64 и закинуть в тег img.

    <img src="data:image/jpeg;base64,[тут_код_картинки_в_base64]">


    Вот, тут дан похожий ответ: https://stackoverflow.com/questions/26400994/how-t...

    Через контроллер добавляем
    byte[] encodeBase64 = Base64.encode(repository.getImage());
    String base64Encoded = new String(encodeBase64, "UTF-8");
    model.addObject("image", base64Encoded );


    Выводим в шаблонизаторе
    <img src="data:image/jpeg;base64,${image}" />

    Если решите реализовать загрузку файла, как я указал в самом начале своего ответа, то для начала можете прочитать эту статью - https://www.callicoder.com/spring-boot-file-upload...
    Ответ написан
    7 комментариев
  • Как передать объект из одного репозитория в другой в Spring?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день!
    Как отметил коллега Dmitry Roo :
    Вообще мне кажется у вас архитектурно не очень придумано.
    Лучше бы сделать отдельно пользователей и отдельно роли.


    В данном случае я соглашусь с ним. Лучше конечно же просто иметь сущность User, но при этом завести enum Role (например, candidate_trainer, trainer). А дальше при нажатии на кнопку в админке просто заменяете роль пользователя с candidate_trainer -> trainer и все.

    Возможно, что есть причины, из-за которых вы решили разделить данные сущности. Тогда просто удаляете старую запись и создаете новую.
    Например,
    при клике берем Id кандидата.
    Находим его по id.
    Создаем новую сущность (можно даже написать некий Converter<S, T>)
    Сохраняем новую запись
    Удаляем старую запись
    Ответ написан
    1 комментарий
  • Как отправить файл методом POST через JSON?

    azerphoenix
    @azerphoenix Куратор тега Spring
    Java Software Engineer
    Добрый день!
    Для приема файла в контроллере используйте интерфейс MultiPartFile
    https://docs.spring.io/spring-framework/docs/curre...

    А через клиент пересылается массив байтов. Например, если под клиентом подразумевается некий js-фреймворк или просто html форма, то обратите внимание на:
    enctype="multipart/form-data"

    https://developer.mozilla.org/ru/docs/Learn/Forms/...
    Ответ написан
    2 комментария
  • Spring boot не видит css и js. Пути к файлам прописывал по советам всех форумов. Может не правильный конфиг?

    azerphoenix
    @azerphoenix Куратор тега Spring
    Java Software Engineer
    Добрый день.
    Используете ли вы шаблонизатор thymeleaf?

    Если да, то это не совсем корректно:
    <link href="${pageContext.request.contextPath}/templates/bootstrap/plugins/fontawesome-free/css/all.min.css" rel="stylesheet">


    Попробуйте так:


    То же самое проделайте с js
    Например,
    <script th:src="@{/bootstrap/plugins/bootstrap/js/bootstrap.bundle.min.js}"></script>


    Все остальное замените таким же образом. Должно сработать.

    И еще что в консоли браузера отображается во вкладке Сеть (Network) ?
    Ответ написан
    4 комментария
  • Как сделать что бы имя пользователя выводило на каждой странице сайта, а не только на главной?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Добрый день!
    Возможно, что это не самое лучшее решение, но я бы сделал это следующим образом:
    Я бы использовал @ControllerAdvice

    @ControllerAdvice
    public class GlobalControllerAdvice {
    
        // Текущий авторизованный пользователь
        @ModelAttribute("user")
        public User getUserProfile(
                @AuthenticationPrincipal UserDetails currentUser
        ) {
            if(
                    SecurityContextHolder.getContext().getAuthentication() != null &&
                    SecurityContextHolder.getContext().getAuthentication().isAuthenticated() &&
                    !(SecurityContextHolder.getContext().getAuthentication() instanceof AnonymousAuthenticationToken)
    
            ) {
                return (User) userService.findUserByEmail(currentUser.getUsername());
            } else {
                return null;
            }
    
        }
    
    }


    Соответственно, если пользователь авторизован, то вы получите user, а если нет, то null.
    Ну и дальше в любом шаблоне можете выводить информацию о пользователе БЕЗ использование этого кода для каждого контроллера:
    if(user != null){
                model.addAttribute("user", user.getUsername());
                return "/index";
            } else {
                model.addAttribute("user", "Аноним");
                return "/index";
            }
    Ответ написан
  • Как сделать два метода на один эндпоинт в REST-контроллере Spring?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    А почему бы вместо этого:
    @PostMapping("/order")
    public void pay(@AuthenticationPrincipal AuthorizedUser user) {
        ...
    }
    
    @PostMapping("/order")
    public void pay(@RequestParam(value = "consumer-id") Integer consumerId,
                             @RequestParam(value = "consumer-region-code") Integer regionCode) {
        ...
    }


    не использовать:

    @PostMapping("/order")
    public void pay(
    @AuthenticationPrincipal AuthorizedUser user,
    @RequestParam(value = "consumer-id", required = false) Integer consumerId,
    @RequestParam(value = "consumer-region-code", required = false) Integer regionCode
    ) {
        ...
    }
    Ответ написан
    6 комментариев
  • Как работает security в микросервисной архитектуре?

    azerphoenix
    @azerphoenix Куратор тега Java
    Java Software Engineer
    Spring Security работает в сервисе Gateway.
    60a04e47abf73734501583.png
    Для каждого из микросервисов, для которых нужно обеспечить безопасность, подключается Spring Security. Также Spring Security добавляется к gateway. Т.е. нет обращения к отдельному микросервису security.
    Ответ написан
    Комментировать