diff --git a/pom.xml b/pom.xml index 96e5744..61d82c9 100644 --- a/pom.xml +++ b/pom.xml @@ -6,12 +6,6 @@ spring-session-data-mongodb 2.0.0.BUILD-SNAPSHOT - - org.springframework.data - spring-data-mongodb-parent - 2.0.0.RC2 - - Spring Session MongoDB https://github.com/spring-projects/spring-session-data-mongodb @@ -77,9 +71,11 @@ 3.6.2 1.50.5 1.3 - 2.9.0.pr3 + 2.9.0 4.12 2.7.22 + 3.4.2 + 1.5.0 Bismuth-M3 5.0.0.RC3 Kay-RC2 @@ -310,10 +306,11 @@ html book + true true v${project.version} - ${basedir}/src/main/asciidoc - ${basedir}/src/main/asciidoc/java + ${basedir} + https://raw.githubusercontent.com/gregturn/spring-session-data-mongodb-examples/master ${spring-session.version} @@ -467,7 +464,8 @@ org.mongodb mongodb-driver - ${mongo} + ${mongo.version} + true @@ -487,11 +485,13 @@ org.springframework.security spring-security-core + test org.springframework spring-web + test @@ -541,24 +541,17 @@ test - - org.mongodb - mongodb-driver - ${mongo} - test - - org.mongodb mongodb-driver-async - ${mongo} + ${mongo.version} test org.mongodb mongodb-driver-reactivestreams - ${mongo.reactivestreams} + ${mongo-reactivestreams.version} test diff --git a/samples/boot/mongo/README.adoc b/samples/boot/mongo/README.adoc deleted file mode 100644 index d7203b5..0000000 --- a/samples/boot/mongo/README.adoc +++ /dev/null @@ -1 +0,0 @@ -Demonstrates using Spring Session with Spring Boot and Spring Security. You can log in with the username "user" and the password "password". \ No newline at end of file diff --git a/samples/boot/mongo/spring-session-sample-boot-mongo.gradle b/samples/boot/mongo/spring-session-sample-boot-mongo.gradle deleted file mode 100644 index fe83eae..0000000 --- a/samples/boot/mongo/spring-session-sample-boot-mongo.gradle +++ /dev/null @@ -1,19 +0,0 @@ -apply plugin: 'io.spring.convention.spring-sample-boot' - -dependencies { - compile project(':spring-session') - compile "org.springframework.data:spring-data-mongodb" - compile "org.springframework.boot:spring-boot-starter-web" - compile "org.springframework.boot:spring-boot-starter-security" - compile "org.springframework.boot:spring-boot-starter-thymeleaf" - compile "nz.net.ultraq.thymeleaf:thymeleaf-layout-dialect" - compile "org.webjars:bootstrap" - compile "org.webjars:html5shiv" - compile "org.webjars:webjars-locator" - compile "de.flapdoodle.embed:de.flapdoodle.embed.mongo" - - testCompile "org.springframework.boot:spring-boot-starter-test" - - integrationTestCompile seleniumDependencies - -} \ No newline at end of file diff --git a/samples/boot/mongo/src/integration-test/java/sample/BootTests.java b/samples/boot/mongo/src/integration-test/java/sample/BootTests.java deleted file mode 100644 index cd40559..0000000 --- a/samples/boot/mongo/src/integration-test/java/sample/BootTests.java +++ /dev/null @@ -1,104 +0,0 @@ -/* - * Copyright 2014-2017 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package sample; - -import java.util.Set; - -import org.junit.After; -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.openqa.selenium.By; -import org.openqa.selenium.Cookie; -import org.openqa.selenium.WebDriver; -import org.openqa.selenium.WebElement; -import sample.pages.HomePage; -import sample.pages.LoginPage; - -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; -import org.springframework.boot.test.context.SpringBootTest; -import org.springframework.boot.test.context.SpringBootTest.WebEnvironment; -import org.springframework.test.context.junit4.SpringRunner; -import org.springframework.test.web.servlet.MockMvc; -import org.springframework.test.web.servlet.htmlunit.webdriver.MockMvcHtmlUnitDriverBuilder; - -import static org.assertj.core.api.Assertions.assertThat; - -/** - * @author Pool Dolorier - */ -@RunWith(SpringRunner.class) -@AutoConfigureMockMvc -@SpringBootTest(webEnvironment = WebEnvironment.MOCK) -public class BootTests { - - @Autowired - private MockMvc mockMvc; - - private WebDriver driver; - - @Before - public void setUp() { - this.driver = MockMvcHtmlUnitDriverBuilder - .mockMvcSetup(this.mockMvc) - .build(); - } - - @After - public void tearDown() { - this.driver.quit(); - } - - @Test - public void unauthenticatedUserSentToLogInPage() { - HomePage homePage = HomePage.go(this.driver); - LoginPage loginPage = homePage.unauthenticated(); - loginPage.assertAt(); - } - - @Test - public void logInViewsHomePage() { - LoginPage loginPage = LoginPage.go(this.driver); - loginPage.assertAt(); - HomePage homePage = loginPage.login("user", "password"); - homePage.assertAt(); - WebElement username = homePage.getDriver().findElement(By.id("un")); - assertThat(username.getText()).isEqualTo("user"); - Set cookies = homePage.getDriver().manage().getCookies(); - assertThat(cookies).extracting("name").contains("SESSION"); - assertThat(cookies).extracting("name").doesNotContain("JSESSIONID"); - } - - @Test - public void logoutSuccess() { - LoginPage loginPage = LoginPage.go(this.driver); - HomePage homePage = loginPage.login("user", "password"); - LoginPage successLogoutPage = homePage.logout(); - successLogoutPage.assertAt(); - } - - @Test - public void loggedOutUserSentToLoginPage() { - LoginPage loginPage = LoginPage.go(this.driver); - HomePage homePage = loginPage.login("user", "password"); - homePage.logout(); - HomePage backHomePage = HomePage.go(this.driver); - LoginPage backLoginPage = backHomePage.unauthenticated(); - backLoginPage.assertAt(); - } -} diff --git a/samples/boot/mongo/src/integration-test/java/sample/pages/BasePage.java b/samples/boot/mongo/src/integration-test/java/sample/pages/BasePage.java deleted file mode 100644 index 3613a7f..0000000 --- a/samples/boot/mongo/src/integration-test/java/sample/pages/BasePage.java +++ /dev/null @@ -1,40 +0,0 @@ -/* - * Copyright 2014-2017 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package sample.pages; - -import org.openqa.selenium.WebDriver; - -/** - * @author Pool Dolorier - */ -public abstract class BasePage { - - private WebDriver driver; - - public BasePage(WebDriver driver) { - this.driver = driver; - } - - public WebDriver getDriver() { - return this.driver; - } - - public static void get(WebDriver driver, String get) { - String baseUrl = "http://localhost"; - driver.get(baseUrl + get); - } -} diff --git a/samples/boot/mongo/src/integration-test/java/sample/pages/HomePage.java b/samples/boot/mongo/src/integration-test/java/sample/pages/HomePage.java deleted file mode 100644 index 6a82ae2..0000000 --- a/samples/boot/mongo/src/integration-test/java/sample/pages/HomePage.java +++ /dev/null @@ -1,55 +0,0 @@ -/* - * Copyright 2014-2017 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package sample.pages; - -import org.openqa.selenium.WebDriver; -import org.openqa.selenium.WebElement; -import org.openqa.selenium.support.FindBy; -import org.openqa.selenium.support.PageFactory; - -import static org.assertj.core.api.Assertions.assertThat; - -/** - * @author Pool Dolorier - */ -public class HomePage extends BasePage { - - @FindBy(css = "input[type='submit']") - private WebElement submit; - - public HomePage(WebDriver driver) { - super(driver); - } - - public static HomePage go(WebDriver driver) { - get(driver, "/"); - return PageFactory.initElements(driver, HomePage.class); - } - - public LoginPage unauthenticated() { - return LoginPage.go(getDriver()); - } - - public LoginPage logout() { - this.submit.click(); - return LoginPage.go(getDriver()); - } - - public void assertAt() { - assertThat(getDriver().getTitle()).isEqualTo("Spring Session Sample - Secured Content"); - } -} diff --git a/samples/boot/mongo/src/integration-test/java/sample/pages/LoginPage.java b/samples/boot/mongo/src/integration-test/java/sample/pages/LoginPage.java deleted file mode 100644 index 5e8e102..0000000 --- a/samples/boot/mongo/src/integration-test/java/sample/pages/LoginPage.java +++ /dev/null @@ -1,59 +0,0 @@ -/* - * Copyright 2014-2017 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package sample.pages; - -import org.openqa.selenium.WebDriver; -import org.openqa.selenium.WebElement; -import org.openqa.selenium.support.FindBy; -import org.openqa.selenium.support.PageFactory; - -import static org.assertj.core.api.Assertions.assertThat; - -/** - * @author Pool Dolorier - */ -public class LoginPage extends BasePage { - - @FindBy(name = "username") - private WebElement username; - - @FindBy(name = "password") - private WebElement password; - - @FindBy(css = "input[name='submit']") - private WebElement submit; - - public LoginPage(WebDriver driver) { - super(driver); - } - - public static LoginPage go(WebDriver driver) { - get(driver, "/login"); - return PageFactory.initElements(driver, LoginPage.class); - } - - public void assertAt() { - assertThat(getDriver().getTitle()).isEqualTo("Login Page"); - } - - public HomePage login(String user, String password) { - this.username.sendKeys(user); - this.password.sendKeys(password); - this.submit.click(); - return HomePage.go(getDriver()); - } -} diff --git a/samples/boot/mongo/src/main/java/sample/Application.java b/samples/boot/mongo/src/main/java/sample/Application.java deleted file mode 100644 index c7fbb77..0000000 --- a/samples/boot/mongo/src/main/java/sample/Application.java +++ /dev/null @@ -1,30 +0,0 @@ -/* - * Copyright 2014-2016 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package sample; - -import org.springframework.boot.SpringApplication; -import org.springframework.boot.autoconfigure.SpringBootApplication; - -/** - * @author Rob Winch - */ -@SpringBootApplication -public class Application { - - public static void main(String[] args) { - SpringApplication.run(Application.class, args); - } -} diff --git a/samples/boot/mongo/src/main/java/sample/EmbeddedMongoPortLogger.java b/samples/boot/mongo/src/main/java/sample/EmbeddedMongoPortLogger.java deleted file mode 100644 index 9dbe1ed..0000000 --- a/samples/boot/mongo/src/main/java/sample/EmbeddedMongoPortLogger.java +++ /dev/null @@ -1,44 +0,0 @@ -/* - * Copyright 2014-2016 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package sample; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import org.springframework.boot.ApplicationArguments; -import org.springframework.boot.ApplicationRunner; -import org.springframework.context.EnvironmentAware; -import org.springframework.core.env.Environment; -import org.springframework.stereotype.Component; - -@Component -class EmbeddedMongoPortLogger implements ApplicationRunner, EnvironmentAware { - - private static final Logger logger = LoggerFactory.getLogger(EmbeddedMongoPortLogger.class); - - private Environment environment; - - public void run(ApplicationArguments args) throws Exception { - String port = this.environment.getProperty("local.mongo.port"); - logger.info("Embedded Mongo started on port " + port + - ", use 'mongo --port " + port + "' command to connect"); - } - - public void setEnvironment(Environment environment) { - this.environment = environment; - } - -} diff --git a/samples/boot/mongo/src/main/java/sample/config/HttpSessionConfig.java b/samples/boot/mongo/src/main/java/sample/config/HttpSessionConfig.java deleted file mode 100644 index 159ea18..0000000 --- a/samples/boot/mongo/src/main/java/sample/config/HttpSessionConfig.java +++ /dev/null @@ -1,31 +0,0 @@ -/* - * Copyright 2014-2016 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package sample.config; - -import org.springframework.context.annotation.Bean; -import org.springframework.session.data.mongo.JdkMongoSessionConverter; -import org.springframework.session.data.mongo.config.annotation.web.http.EnableMongoHttpSession; - -// tag::class[] -@EnableMongoHttpSession // <1> -public class HttpSessionConfig { - - @Bean - public JdkMongoSessionConverter jdkMongoSessionConverter() { - return new JdkMongoSessionConverter(); // <2> - } -} -// end::class[] diff --git a/samples/boot/mongo/src/main/java/sample/config/SecurityConfig.java b/samples/boot/mongo/src/main/java/sample/config/SecurityConfig.java deleted file mode 100644 index 72a89d3..0000000 --- a/samples/boot/mongo/src/main/java/sample/config/SecurityConfig.java +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Copyright 2014-2016 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package sample.config; - -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; -import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; -import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter; - -/** - * @author Rob Winch - */ -@EnableWebSecurity -public class SecurityConfig extends WebSecurityConfigurerAdapter { - - @Autowired - public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception { - auth.inMemoryAuthentication().withUser("user").password("password").roles("USER"); - } -} diff --git a/samples/boot/mongo/src/main/java/sample/mvc/IndexController.java b/samples/boot/mongo/src/main/java/sample/mvc/IndexController.java deleted file mode 100644 index 2647a1b..0000000 --- a/samples/boot/mongo/src/main/java/sample/mvc/IndexController.java +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Copyright 2014-2016 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package sample.mvc; - -import org.springframework.stereotype.Controller; -import org.springframework.web.bind.annotation.RequestMapping; - -/** - * Controller for sending the user to the login view. - * - * @author Rob Winch - * - */ -@Controller -public class IndexController { - @RequestMapping("/") - public String index() { - return "index"; - } -} diff --git a/samples/boot/mongo/src/main/resources/application.properties b/samples/boot/mongo/src/main/resources/application.properties deleted file mode 100644 index 51ab5db..0000000 --- a/samples/boot/mongo/src/main/resources/application.properties +++ /dev/null @@ -1,3 +0,0 @@ -spring.thymeleaf.cache=false -spring.template.cache=false -spring.data.mongodb.port=0 diff --git a/samples/boot/mongo/src/main/resources/static/resources/img/favicon.ico b/samples/boot/mongo/src/main/resources/static/resources/img/favicon.ico deleted file mode 100644 index bfb9974..0000000 Binary files a/samples/boot/mongo/src/main/resources/static/resources/img/favicon.ico and /dev/null differ diff --git a/samples/boot/mongo/src/main/resources/static/resources/img/logo.png b/samples/boot/mongo/src/main/resources/static/resources/img/logo.png deleted file mode 100644 index 3932308..0000000 Binary files a/samples/boot/mongo/src/main/resources/static/resources/img/logo.png and /dev/null differ diff --git a/samples/boot/mongo/src/main/resources/templates/index.html b/samples/boot/mongo/src/main/resources/templates/index.html deleted file mode 100644 index 1e2703e..0000000 --- a/samples/boot/mongo/src/main/resources/templates/index.html +++ /dev/null @@ -1,11 +0,0 @@ - - - Secured Content - - -
-

Secured Page

-

This page is secured using Spring Boot, Spring Session, and Spring Security.

-
- - diff --git a/samples/boot/mongo/src/main/resources/templates/layout.html b/samples/boot/mongo/src/main/resources/templates/layout.html deleted file mode 100644 index 7a66980..0000000 --- a/samples/boot/mongo/src/main/resources/templates/layout.html +++ /dev/null @@ -1,122 +0,0 @@ - - - - Spring Session Sample - - - - - - - - - - - -
- - -
-
- Some Success message -
-
- Fake content -
-
- -
-
- - - - diff --git a/src/main/asciidoc/guides/boot-mongo.adoc b/src/main/asciidoc/guides/boot-mongo.adoc index b9a63c5..ac63ee0 100644 --- a/src/main/asciidoc/guides/boot-mongo.adoc +++ b/src/main/asciidoc/guides/boot-mongo.adoc @@ -1,5 +1,5 @@ = Spring Session - Mongo Repositories -Jakub Kubrynski +Jakub Kubrynski, Greg Turnquist :toc: This guide describes how to use Spring Session backed by Mongo. @@ -74,7 +74,7 @@ All you have to do is to add the following Spring Configuration: [source,java] ---- -include::{samples-dir}boot/mongo/src/main/java/sample/config/HttpSessionConfig.java[tags=class] +include::{samples-dir}/spring-session-data-mongodb-traditional-boot/src/main/java/sample/config/HttpSessionConfig.java[tag=class] ---- <1> The `@EnableMongoHttpSession` annotation creates a Spring Bean with the name of `springSessionRepositoryFilter` that implements Filter. diff --git a/src/main/asciidoc/index.adoc b/src/main/asciidoc/index.adoc index f1dba5b..edb4542 100644 --- a/src/main/asciidoc/index.adoc +++ b/src/main/asciidoc/index.adoc @@ -56,7 +56,7 @@ If you would like to provide custom Jackson modules you can do it by explicitly [source,java,indent=0] ---- -include::{docs-test-dir}/docs/http/MongoJacksonSessionConfiguration.java[tags=config] +include::{code-dir}/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJacksonITest.java[tag=sample] ---- ==== JdkMongoSessionConverter @@ -68,7 +68,7 @@ You can explicitly register `JdkMongoSessionConverter` by defining it as a Bean. [source,java,indent=0] ---- -include::{docs-test-dir}/docs/http/MongoJdkSessionConfiguration.java[tags=config] +include::{code-dir}/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJdkSerializationITest.java[tag=sample] ---- There is also a constructor taking `Serializer` and `Deserializer` objects, allowing you to pass custom implementations, which is especially important when you want to use non-default classloader. diff --git a/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJacksonITest.java b/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJacksonITest.java index ddeb3df..ebd8499 100644 --- a/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJacksonITest.java +++ b/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJacksonITest.java @@ -61,6 +61,7 @@ public class MongoRepositoryJacksonITest extends AbstractMongoRepositoryITest { assertThat(findByCartId.keySet()).containsOnly(toSave.getId()); } + // tag::sample[] @Configuration @EnableMongoHttpSession static class Config extends BaseConfig { @@ -69,6 +70,6 @@ public class MongoRepositoryJacksonITest extends AbstractMongoRepositoryITest { public AbstractMongoSessionConverter mongoSessionConverter() { return new JacksonMongoSessionConverter(Collections.singletonList(new GeoModule())); } - } + // end::sample[] } diff --git a/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJdkSerializationITest.java b/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJdkSerializationITest.java index 507fad8..7ccfd2d 100644 --- a/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJdkSerializationITest.java +++ b/src/test/java/org/springframework/session/data/mongo/integration/MongoRepositoryJdkSerializationITest.java @@ -78,6 +78,7 @@ public class MongoRepositoryJdkSerializationITest extends AbstractMongoRepositor assertThat(findByPrincipalName.keySet()).containsOnly(toSave.getId()); } + // tag::sample[] @Configuration @EnableMongoHttpSession static class Config extends BaseConfig { @@ -86,6 +87,6 @@ public class MongoRepositoryJdkSerializationITest extends AbstractMongoRepositor public AbstractMongoSessionConverter mongoSessionConverter() { return new JdkMongoSessionConverter(); } - } + // end::sample[] }