MongoDB
 sql >> база данни >  >> NoSQL >> MongoDB

Пролетна сесия с MongoDB

1. Прегледа

В този бърз урок ще проучим как да използваме Spring Session, подкрепен с MongoDB, както със, така и без Spring Boot.

Spring Session може да бъде подкрепен и с други магазини като Redis и JDBC.

2. Spring Boot Configuration

Първо, нека разгледаме зависимостите и конфигурацията, необходими за Spring Boot. Като начало, нека добавим най-новите версии на spring-session-data-mongodb и spring-boot-starter-data-mongodb към нашия проект:

<dependency>
    <groupId>org.springframework.session</groupId>
    <artifactId>spring-session-data-mongodb</artifactId>
    <version>2.2.6.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-mongodb</artifactId>
    <version>2.2.6.RELEASE</version>
</dependency>

След това, за да активираме автоматичното конфигуриране на Spring Boot, ще трябва да добавим типа магазин Spring Session като mongodb в application.properties :

spring.session.store-type=mongodb

3. Пружинна конфигурация без пружинно зареждане

Сега, нека да разгледаме зависимостите и конфигурацията, необходими за съхраняване на Spring сесията в MongoDB без Spring Boot.

Подобно на конфигурацията на Spring Boot, ще ни трябва spring-session-data-mongodb зависимост. Тук обаче ще използваме spring-data-mongodb зависимост за достъп до нашата база данни MongoDB:

<dependency>
    <groupId>org.springframework.session</groupId>
    <artifactId>spring-session-data-mongodb</artifactId>
    <version>2.2.6.RELEASE</version>
</dependency>
<dependency>
    <groupId>org.springframework.data</groupId>
    <artifactId>spring-data-mongodb</artifactId>
    <version>2.2.6.RELEASE</version>
</dependency>

И накрая, нека видим как да конфигурирате приложението:

@EnableMongoHttpSession
public class HttpSessionConfig {

    @Bean
    public JdkMongoSessionConverter jdkMongoSessionConverter() {
        return new JdkMongoSessionConverter(Duration.ofMinutes(30));
    }
}

Сесията @EnableMongoHttpSession анотацията позволява конфигурацията, необходима за съхраняване на данните за сесията в MongoDB .

Също така имайте предвид, че JdkMongoSessionConverter отговаря за сериализирането и десериализирането на данните за сесията.

4. Примерно приложение

Нека създадем приложение за тестване на конфигурациите. Ще използваме Spring Boot, тъй като е по-бърз и изисква по-малко конфигурация.

Ще започнем със създаване на контролера за обработка на заявки:

@RestController
public class SpringSessionMongoDBController {

    @GetMapping("/")
    public ResponseEntity<Integer> count(HttpSession session) {

        Integer counter = (Integer) session.getAttribute("count");

        if (counter == null) {
            counter = 1;
        } else {
            counter++;
        }

        session.setAttribute("count", counter);

        return ResponseEntity.ok(counter);
    }
}

Както можем да видим в този пример, ние увеличаваме counter при всяко посещение до крайната точка и съхраняване на стойността му в атрибут на сесия с име count .

5. Тестване на приложениетота

Нека тестваме приложението, за да видим дали всъщност можем да съхраняваме данните за сесията в MongoDB.

За да направим това, ще получим достъп до крайната точка и ще проверим бисквитката, която ще получим. Това ще съдържа идентификатор на сесията.

След това ще потърсим колекцията MongoDB, за да извлечем данните за сесията, използвайки идентификатора на сесията:

@Test
public void 
  givenEndpointIsCalledTwiceAndResponseIsReturned_whenMongoDBIsQueriedForCount_thenCountMustBeSame() {
    
    HttpEntity<String> response = restTemplate
      .exchange("http://localhost:" + 8080, HttpMethod.GET, null, String.class);
    HttpHeaders headers = response.getHeaders();
    String set_cookie = headers.getFirst(HttpHeaders.SET_COOKIE);

    Assert.assertEquals(response.getBody(),
      repository.findById(getSessionId(set_cookie)).getAttribute("count").toString());
}

private String getSessionId(String cookie) {
    return new String(Base64.getDecoder().decode(cookie.split(";")[0].split("=")[1]));
}

6. Как работи?

Нека да разгледаме какво се случва в пролетната сесия зад кулисите.

SessionRepositoryFilter отговаря за по-голямата част от работата:

  • преобразува HttpSession в MongoSession
  • проверява дали има бисквитка присъства и ако е така, зарежда данните за сесията от магазина
  • записва актуализираните данни за сесията в магазина
  • проверява валидността на сесията

Също така SessionRepositoryFilter създава бисквитка с името SESSION това е HttpOnly и е сигурно. Тази бисквитка съдържа идентификатора на сесията, който е кодирана от Base64 стойност.

За да персонализираме името или свойствата на бисквитката, ще трябва да създадем Spring bean от тип DefaultCookieSerializer.

Например, тук деактивираме httponly свойство на бисквитката:

@Bean
public DefaultCookieSerializer customCookieSerializer(){
    DefaultCookieSerializer cookieSerializer = new DefaultCookieSerializer();
        
    cookieSerializer.setUseHttpOnlyCookie(false);
        
    return cookieSerializer;
}

7. Подробности за сесията се съхраняват в MongoDBа

Нека да запитаме нашата колекция от сесии, като използваме следната команда в нашата конзола MongoDB:

db.sessions.findOne()

В резултат на това ще получим BSON документ, подобен на:

{
    "_id" : "5d985be4-217c-472c-ae02-d6fca454662b",
    "created" : ISODate("2019-05-14T16:45:41.021Z"),
    "accessed" : ISODate("2019-05-14T17:18:59.118Z"),
    "interval" : "PT30M",
    "principal" : null,
    "expireAt" : ISODate("2019-05-14T17:48:59.118Z"),
    "attr" : BinData(0,"rO0ABXNyABFqYXZhLnV0aWwuSGFzaE1hcAUH2sHDFmDRAwACRgAKbG9hZEZhY3RvckkACXRocmVzaG9sZHhwP0AAAAAAAAx3CAAAABAAAAABdAAFY291bnRzcgARamF2YS5sYW5nLkludGVnZXIS4qCk94GHOAIAAUkABXZhbHVleHIAEGphdmEubGFuZy5OdW1iZXKGrJUdC5TgiwIAAHhwAAAAC3g=")
}

_id е UUID, който ще бъде кодиран Base64 от DefaultCookieSerializer и задайте като стойност в SESSION бисквитка. Също така имайте предвид, че attr атрибутът съдържа действителната стойност на нашия брояч.


  1. Redis
  2.   
  3. MongoDB
  4.   
  5. Memcached
  6.   
  7. HBase
  8.   
  9. CouchDB
  1. Накарайте Spark, Python и MongoDB да работят заедно

  2. Заявката за агрегиране на Mongoose се проваля в теста на Jest/Mockgoose, работи другаде

  3. Как да направя заявка NOT IN в Mongo?

  4. Как да подобрим производителността на вмъкване на MongoDB

  5. Mongoose Model.find не е функция?