From 65183f082ddc79b9b41928feabcd259eba98e982 Mon Sep 17 00:00:00 2001 From: Steven van Beelen Date: Wed, 10 Jul 2019 13:26:48 +0200 Subject: [PATCH 001/107] Update Axon dependency Update the Axon Framework version to 4.1.1. Additionally, drop the exclusion on axon-server-connector, as the page will be adjusted to use Axon Server SE. BAEL-2345 --- axon/pom.xml | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/axon/pom.xml b/axon/pom.xml index 2b9ac1fcdd..002701373f 100644 --- a/axon/pom.xml +++ b/axon/pom.xml @@ -18,12 +18,6 @@ org.axonframework axon-spring-boot-starter ${axon.version} - - - org.axonframework - axon-server-connector - - @@ -58,7 +52,7 @@ - 4.0.3 + 4.1.1 \ No newline at end of file From 97ab7130240d8995a9710ce53c611d4e51044627 Mon Sep 17 00:00:00 2001 From: Steven van Beelen Date: Wed, 10 Jul 2019 13:27:50 +0200 Subject: [PATCH 002/107] Create dedicated UnconfirmedOrderException Create a dedicated UnconfirmedOrderException and use it from the OrderAggregate instead of the IllegalStateException BAEL-2435 --- .../com/baeldung/axon/commandmodel/OrderAggregate.java | 7 ++++--- .../coreapi/exceptions/UnconfirmedOrderException.java | 8 ++++++++ 2 files changed, 12 insertions(+), 3 deletions(-) create mode 100644 axon/src/main/java/com/baeldung/axon/coreapi/exceptions/UnconfirmedOrderException.java diff --git a/axon/src/main/java/com/baeldung/axon/commandmodel/OrderAggregate.java b/axon/src/main/java/com/baeldung/axon/commandmodel/OrderAggregate.java index b37b2fdd66..4ef02e6b54 100644 --- a/axon/src/main/java/com/baeldung/axon/commandmodel/OrderAggregate.java +++ b/axon/src/main/java/com/baeldung/axon/commandmodel/OrderAggregate.java @@ -13,6 +13,7 @@ import com.baeldung.axon.coreapi.commands.ShipOrderCommand; import com.baeldung.axon.coreapi.events.OrderConfirmedEvent; import com.baeldung.axon.coreapi.events.OrderPlacedEvent; import com.baeldung.axon.coreapi.events.OrderShippedEvent; +import com.baeldung.axon.coreapi.exceptions.UnconfirmedOrderException; @Aggregate public class OrderAggregate { @@ -34,7 +35,7 @@ public class OrderAggregate { @CommandHandler public void handle(ShipOrderCommand command) { if (!orderConfirmed) { - throw new IllegalStateException("Cannot ship an order which has not been confirmed yet."); + throw new UnconfirmedOrderException(); } apply(new OrderShippedEvent(orderId)); @@ -43,12 +44,12 @@ public class OrderAggregate { @EventSourcingHandler public void on(OrderPlacedEvent event) { this.orderId = event.getOrderId(); - orderConfirmed = false; + this.orderConfirmed = false; } @EventSourcingHandler public void on(OrderConfirmedEvent event) { - orderConfirmed = true; + this.orderConfirmed = true; } protected OrderAggregate() { diff --git a/axon/src/main/java/com/baeldung/axon/coreapi/exceptions/UnconfirmedOrderException.java b/axon/src/main/java/com/baeldung/axon/coreapi/exceptions/UnconfirmedOrderException.java new file mode 100644 index 0000000000..1873bc6893 --- /dev/null +++ b/axon/src/main/java/com/baeldung/axon/coreapi/exceptions/UnconfirmedOrderException.java @@ -0,0 +1,8 @@ +package com.baeldung.axon.coreapi.exceptions; + +public class UnconfirmedOrderException extends IllegalStateException { + + public UnconfirmedOrderException() { + super("Cannot ship an order which has not been confirmed yet."); + } +} From 496c2b173760e6f6a8047ac0ff8627615b2cd366 Mon Sep 17 00:00:00 2001 From: Steven van Beelen Date: Wed, 10 Jul 2019 13:37:28 +0200 Subject: [PATCH 003/107] Add ProcessingGroup annotation to OrderedProductsEventHandler Add the ProcessingGroup annotation to OrderedProductsEventHandler so that this event handler is grouped in a nicely named Event Processor. If the app is started in conjunction with Axon Server, this will make the set up more evident from the dashboard BAEL-2435 --- .../baeldung/axon/querymodel/OrderedProductsEventHandler.java | 2 ++ axon/src/main/resources/application.properties | 1 + 2 files changed, 3 insertions(+) create mode 100644 axon/src/main/resources/application.properties diff --git a/axon/src/main/java/com/baeldung/axon/querymodel/OrderedProductsEventHandler.java b/axon/src/main/java/com/baeldung/axon/querymodel/OrderedProductsEventHandler.java index d4cf3d999b..a37f0111ed 100644 --- a/axon/src/main/java/com/baeldung/axon/querymodel/OrderedProductsEventHandler.java +++ b/axon/src/main/java/com/baeldung/axon/querymodel/OrderedProductsEventHandler.java @@ -5,6 +5,7 @@ import java.util.HashMap; import java.util.List; import java.util.Map; +import org.axonframework.config.ProcessingGroup; import org.axonframework.eventhandling.EventHandler; import org.axonframework.queryhandling.QueryHandler; import org.springframework.stereotype.Service; @@ -16,6 +17,7 @@ import com.baeldung.axon.coreapi.queries.FindAllOrderedProductsQuery; import com.baeldung.axon.coreapi.queries.OrderedProduct; @Service +@ProcessingGroup("ordered-products") public class OrderedProductsEventHandler { private final Map orderedProducts = new HashMap<>(); diff --git a/axon/src/main/resources/application.properties b/axon/src/main/resources/application.properties new file mode 100644 index 0000000000..7c51eb8e1e --- /dev/null +++ b/axon/src/main/resources/application.properties @@ -0,0 +1 @@ +spring.application.name=Order Management Service \ No newline at end of file From 6c6392a797a8039db7a95f93a2ee4f87707dd898 Mon Sep 17 00:00:00 2001 From: jemgiordano Date: Fri, 12 Jul 2019 21:02:52 +1000 Subject: [PATCH 004/107] BAEL-2798 Update to 'Scheduling in Spring with Quartz' article to add JDBC examples. --- spring-quartz/pom.xml | 13 ++++- .../basics/scheduler/QrtzScheduler.java | 55 +++++++++++++------ .../basics/scheduler/SampleJob.java | 2 +- .../basics/scheduler/SpringQrtzScheduler.java | 27 +++++++-- .../basics/service/SampleJobService.java | 15 ++++- .../src/main/resources/application.properties | 11 +++- .../src/main/resources/quartz.properties | 18 +++++- .../SpringContextIntegrationTest.java | 14 +++++ 8 files changed, 125 insertions(+), 30 deletions(-) diff --git a/spring-quartz/pom.xml b/spring-quartz/pom.xml index 58e72c1d51..4c7ac6eee9 100644 --- a/spring-quartz/pom.xml +++ b/spring-quartz/pom.xml @@ -32,6 +32,16 @@ quartz ${quartz.version} + + com.mchange + c3p0 + ${c3p0.version} + + + + com.h2database + h2 + @@ -44,7 +54,8 @@ - 2.2.3 + 2.3.0 + 0.9.5.2 \ No newline at end of file diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java index 6601df6c94..73416262ce 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java @@ -1,31 +1,32 @@ package org.baeldung.springquartz.basics.scheduler; -import static org.quartz.JobBuilder.newJob; -import static org.quartz.SimpleScheduleBuilder.simpleSchedule; -import static org.quartz.TriggerBuilder.newTrigger; - -import java.io.IOException; - -import javax.annotation.PostConstruct; - import org.baeldung.springquartz.config.AutoWiringSpringBeanJobFactory; import org.quartz.*; -import org.quartz.impl.StdSchedulerFactory; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.config.PropertiesFactoryBean; import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.core.io.ClassPathResource; +import org.springframework.scheduling.quartz.SchedulerFactoryBean; import org.springframework.scheduling.quartz.SpringBeanJobFactory; +import javax.annotation.PostConstruct; +import java.io.IOException; +import java.util.Properties; + +import static org.quartz.JobBuilder.newJob; +import static org.quartz.SimpleScheduleBuilder.simpleSchedule; +import static org.quartz.TriggerBuilder.newTrigger; + @Configuration @ConditionalOnExpression("'${using.spring.schedulerFactory}'=='false'") public class QrtzScheduler { - Logger logger = LoggerFactory.getLogger(getClass()); + private static final Logger logger = LoggerFactory.getLogger(QrtzScheduler.class); @Autowired private ApplicationContext applicationContext; @@ -45,14 +46,9 @@ public class QrtzScheduler { } @Bean - public Scheduler scheduler(Trigger trigger, JobDetail job) throws SchedulerException, IOException { - - StdSchedulerFactory factory = new StdSchedulerFactory(); - factory.initialize(new ClassPathResource("quartz.properties").getInputStream()); - + public Scheduler scheduler(Trigger trigger, JobDetail job, SchedulerFactoryBean factory) throws SchedulerException { logger.debug("Getting a handle to the Scheduler"); Scheduler scheduler = factory.getScheduler(); - scheduler.setJobFactory(springBeanJobFactory()); scheduler.scheduleJob(job, trigger); logger.debug("Starting Scheduler threads"); @@ -60,10 +56,29 @@ public class QrtzScheduler { return scheduler; } + @Bean + public SchedulerFactoryBean schedulerFactoryBean() throws IOException { + SchedulerFactoryBean factory = new SchedulerFactoryBean(); + factory.setJobFactory(springBeanJobFactory()); + factory.setQuartzProperties(quartzProperties()); + return factory; + } + + public Properties quartzProperties() throws IOException { + PropertiesFactoryBean propertiesFactoryBean = new PropertiesFactoryBean(); + propertiesFactoryBean.setLocation(new ClassPathResource("/quartz.properties")); + propertiesFactoryBean.afterPropertiesSet(); + return propertiesFactoryBean.getObject(); + } + @Bean public JobDetail jobDetail() { - return newJob().ofType(SampleJob.class).storeDurably().withIdentity(JobKey.jobKey("Qrtz_Job_Detail")).withDescription("Invoke Sample Job service...").build(); + return newJob().ofType(SampleJob.class) + .storeDurably() + .withIdentity(JobKey.jobKey("Qrtz_Job_Detail")) + .withDescription("Invoke Sample Job service...") + .build(); } @Bean @@ -72,6 +87,10 @@ public class QrtzScheduler { int frequencyInSec = 10; logger.info("Configuring trigger to fire every {} seconds", frequencyInSec); - return newTrigger().forJob(job).withIdentity(TriggerKey.triggerKey("Qrtz_Trigger")).withDescription("Sample trigger").withSchedule(simpleSchedule().withIntervalInSeconds(frequencyInSec).repeatForever()).build(); + return newTrigger().forJob(job) + .withIdentity(TriggerKey.triggerKey("Qrtz_Trigger")) + .withDescription("Sample trigger") + .withSchedule(simpleSchedule().withIntervalInSeconds(frequencyInSec).repeatForever()) + .build(); } } diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java index 7c50f9a231..8bfd856b86 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java @@ -12,7 +12,7 @@ import org.springframework.stereotype.Component; @Component public class SampleJob implements Job { - Logger logger = LoggerFactory.getLogger(getClass()); + private static final Logger logger = LoggerFactory.getLogger(SampleJob.class); @Autowired private SampleJobService jobService; diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java index 9978f61522..40234df1c9 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java @@ -1,7 +1,5 @@ package org.baeldung.springquartz.basics.scheduler; -import javax.annotation.PostConstruct; - import org.baeldung.springquartz.config.AutoWiringSpringBeanJobFactory; import org.quartz.JobDetail; import org.quartz.SimpleTrigger; @@ -9,7 +7,11 @@ import org.quartz.Trigger; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression; +import org.springframework.boot.autoconfigure.quartz.QuartzDataSource; +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.boot.jdbc.DataSourceBuilder; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; @@ -19,11 +21,15 @@ import org.springframework.scheduling.quartz.SchedulerFactoryBean; import org.springframework.scheduling.quartz.SimpleTriggerFactoryBean; import org.springframework.scheduling.quartz.SpringBeanJobFactory; +import javax.annotation.PostConstruct; +import javax.sql.DataSource; + @Configuration +@EnableAutoConfiguration @ConditionalOnExpression("'${using.spring.schedulerFactory}'=='true'") public class SpringQrtzScheduler { - Logger logger = LoggerFactory.getLogger(getClass()); + private static final Logger logger = LoggerFactory.getLogger(SpringQrtzScheduler.class); @Autowired private ApplicationContext applicationContext; @@ -43,7 +49,9 @@ public class SpringQrtzScheduler { } @Bean - public SchedulerFactoryBean scheduler(Trigger trigger, JobDetail job) { + public SchedulerFactoryBean scheduler(Trigger trigger, + JobDetail job, + DataSource quartzDataSource) { SchedulerFactoryBean schedulerFactory = new SchedulerFactoryBean(); schedulerFactory.setConfigLocation(new ClassPathResource("quartz.properties")); @@ -53,6 +61,9 @@ public class SpringQrtzScheduler { schedulerFactory.setJobDetails(job); schedulerFactory.setTriggers(trigger); + // Comment the following line to use the default Quartz job store. + schedulerFactory.setDataSource(quartzDataSource); + return schedulerFactory; } @@ -81,4 +92,12 @@ public class SpringQrtzScheduler { trigger.setName("Qrtz_Trigger"); return trigger; } + + @Bean + @QuartzDataSource + @ConfigurationProperties(prefix = "spring.datasource") + public DataSource quartzDataSource() { + return DataSourceBuilder.create().build(); + } + } diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java index ddf4efc2c5..4b976d37b0 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java @@ -4,20 +4,31 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Service; +import java.util.concurrent.atomic.AtomicInteger; + @Service public class SampleJobService { - private Logger logger = LoggerFactory.getLogger(getClass()); + public static final long EXECUTION_TIME = 5000L; + + private static final Logger logger = LoggerFactory.getLogger(SampleJobService.class); + + private AtomicInteger count = new AtomicInteger(); public void executeSampleJob() { logger.info("The sample job has begun..."); try { - Thread.sleep(5000); + Thread.sleep(EXECUTION_TIME); } catch (InterruptedException e) { logger.error("Error while executing sample job", e); } finally { + count.incrementAndGet(); logger.info("Sample job has finished..."); } } + + public int getNumberOfInvocations() { + return count.get(); + } } diff --git a/spring-quartz/src/main/resources/application.properties b/spring-quartz/src/main/resources/application.properties index 7bdd647e25..557349af2e 100644 --- a/spring-quartz/src/main/resources/application.properties +++ b/spring-quartz/src/main/resources/application.properties @@ -1 +1,10 @@ -using.spring.schedulerFactory=true \ No newline at end of file +using.spring.schedulerFactory=true + +spring.quartz.job-store-type=jdbc +# Always create the Quartz database on startup +spring.quartz.jdbc.initialize-schema=always + +spring.datasource.jdbc-url=jdbc:h2:mem:spring-quartz;DB_CLOSE_ON_EXIT=FALSE +spring.datasource.driverClassName=org.h2.Driver +spring.datasource.username=sa +spring.datasource.password= diff --git a/spring-quartz/src/main/resources/quartz.properties b/spring-quartz/src/main/resources/quartz.properties index cefaaef8e4..662bb83eb0 100644 --- a/spring-quartz/src/main/resources/quartz.properties +++ b/spring-quartz/src/main/resources/quartz.properties @@ -4,7 +4,19 @@ org.quartz.threadPool.threadCount=2 org.quartz.threadPool.threadsInheritContextClassLoaderOfInitializingThread=true # job-store -org.quartz.jobStore.class = org.quartz.simpl.RAMJobStore +# Enable this property for RAMJobStore +#org.quartz.jobStore.class=org.quartz.simpl.RAMJobStore -# others -org.quartz.jobStore.misfireThreshold = 60000 \ No newline at end of file +# Enable these properties for a JDBCJobStore using JobStoreTX +org.quartz.jobStore.class=org.quartz.impl.jdbcjobstore.JobStoreTX +org.quartz.jobStore.driverDelegateClass=org.quartz.impl.jdbcjobstore.StdJDBCDelegate +org.quartz.jobStore.dataSource=quartzDataSource +# Enable this property for JobStoreCMT +#org.quartz.jobStore.nonManagedTXDataSource=quartzDataSource + +# H2 database +# use an in-memory database & initialise Quartz using their standard SQL script +org.quartz.dataSource.quartzDataSource.URL=jdbc:h2:mem:spring-quartz;INIT=RUNSCRIPT FROM 'classpath:/org/quartz/impl/jdbcjobstore/tables_h2.sql' +org.quartz.dataSource.quartzDataSource.driver=org.h2.Driver +org.quartz.dataSource.quartzDataSource.user=sa +org.quartz.dataSource.quartzDataSource.password= diff --git a/spring-quartz/src/test/java/org/baeldung/SpringContextIntegrationTest.java b/spring-quartz/src/test/java/org/baeldung/SpringContextIntegrationTest.java index 516cc587a7..fec47f045c 100644 --- a/spring-quartz/src/test/java/org/baeldung/SpringContextIntegrationTest.java +++ b/spring-quartz/src/test/java/org/baeldung/SpringContextIntegrationTest.java @@ -1,16 +1,30 @@ package org.baeldung; import org.baeldung.springquartz.SpringQuartzApp; +import org.baeldung.springquartz.basics.service.SampleJobService; import org.junit.Test; import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.context.junit4.SpringRunner; +import static org.assertj.core.api.Assertions.assertThat; + @RunWith(SpringRunner.class) @SpringBootTest(classes = SpringQuartzApp.class) public class SpringContextIntegrationTest { + @Autowired + private SampleJobService sampleJobService; + @Test public void whenSpringContextIsBootstrapped_thenNoExceptions() { } + + @Test + public void whenSchedulerStarts_thenJobsRun() throws InterruptedException { + assertThat(sampleJobService.getNumberOfInvocations()).isEqualTo(0); + Thread.sleep(SampleJobService.EXECUTION_TIME); + assertThat(sampleJobService.getNumberOfInvocations()).isEqualTo(1); + } } From 6b4e6a11764dd5246e5e47967dedd52e903db844 Mon Sep 17 00:00:00 2001 From: jemgiordano Date: Sat, 13 Jul 2019 17:52:10 +1000 Subject: [PATCH 005/107] BAEL-2798 Update to 'Scheduling in Spring with Quartz' article to add JDBC examples. --- .../basics/scheduler/QrtzScheduler.java | 28 ++++++++----------- .../basics/scheduler/SampleJob.java | 2 +- .../basics/scheduler/SpringQrtzScheduler.java | 12 ++++---- .../basics/service/SampleJobService.java | 2 +- 4 files changed, 18 insertions(+), 26 deletions(-) diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java index 73416262ce..ccf9fca8c1 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/QrtzScheduler.java @@ -1,5 +1,13 @@ package org.baeldung.springquartz.basics.scheduler; +import static org.quartz.JobBuilder.newJob; +import static org.quartz.SimpleScheduleBuilder.simpleSchedule; +import static org.quartz.TriggerBuilder.newTrigger; + +import java.io.IOException; + +import javax.annotation.PostConstruct; + import org.baeldung.springquartz.config.AutoWiringSpringBeanJobFactory; import org.quartz.*; import org.slf4j.Logger; @@ -14,19 +22,13 @@ import org.springframework.core.io.ClassPathResource; import org.springframework.scheduling.quartz.SchedulerFactoryBean; import org.springframework.scheduling.quartz.SpringBeanJobFactory; -import javax.annotation.PostConstruct; -import java.io.IOException; import java.util.Properties; -import static org.quartz.JobBuilder.newJob; -import static org.quartz.SimpleScheduleBuilder.simpleSchedule; -import static org.quartz.TriggerBuilder.newTrigger; - @Configuration @ConditionalOnExpression("'${using.spring.schedulerFactory}'=='false'") public class QrtzScheduler { - private static final Logger logger = LoggerFactory.getLogger(QrtzScheduler.class); + Logger logger = LoggerFactory.getLogger(getClass()); @Autowired private ApplicationContext applicationContext; @@ -74,11 +76,7 @@ public class QrtzScheduler { @Bean public JobDetail jobDetail() { - return newJob().ofType(SampleJob.class) - .storeDurably() - .withIdentity(JobKey.jobKey("Qrtz_Job_Detail")) - .withDescription("Invoke Sample Job service...") - .build(); + return newJob().ofType(SampleJob.class).storeDurably().withIdentity(JobKey.jobKey("Qrtz_Job_Detail")).withDescription("Invoke Sample Job service...").build(); } @Bean @@ -87,10 +85,6 @@ public class QrtzScheduler { int frequencyInSec = 10; logger.info("Configuring trigger to fire every {} seconds", frequencyInSec); - return newTrigger().forJob(job) - .withIdentity(TriggerKey.triggerKey("Qrtz_Trigger")) - .withDescription("Sample trigger") - .withSchedule(simpleSchedule().withIntervalInSeconds(frequencyInSec).repeatForever()) - .build(); + return newTrigger().forJob(job).withIdentity(TriggerKey.triggerKey("Qrtz_Trigger")).withDescription("Sample trigger").withSchedule(simpleSchedule().withIntervalInSeconds(frequencyInSec).repeatForever()).build(); } } diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java index 8bfd856b86..7c50f9a231 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SampleJob.java @@ -12,7 +12,7 @@ import org.springframework.stereotype.Component; @Component public class SampleJob implements Job { - private static final Logger logger = LoggerFactory.getLogger(SampleJob.class); + Logger logger = LoggerFactory.getLogger(getClass()); @Autowired private SampleJobService jobService; diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java index 40234df1c9..f824765efe 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/scheduler/SpringQrtzScheduler.java @@ -1,5 +1,8 @@ package org.baeldung.springquartz.basics.scheduler; +import javax.annotation.PostConstruct; +import javax.sql.DataSource; + import org.baeldung.springquartz.config.AutoWiringSpringBeanJobFactory; import org.quartz.JobDetail; import org.quartz.SimpleTrigger; @@ -21,15 +24,12 @@ import org.springframework.scheduling.quartz.SchedulerFactoryBean; import org.springframework.scheduling.quartz.SimpleTriggerFactoryBean; import org.springframework.scheduling.quartz.SpringBeanJobFactory; -import javax.annotation.PostConstruct; -import javax.sql.DataSource; - @Configuration @EnableAutoConfiguration @ConditionalOnExpression("'${using.spring.schedulerFactory}'=='true'") public class SpringQrtzScheduler { - private static final Logger logger = LoggerFactory.getLogger(SpringQrtzScheduler.class); + Logger logger = LoggerFactory.getLogger(getClass()); @Autowired private ApplicationContext applicationContext; @@ -49,9 +49,7 @@ public class SpringQrtzScheduler { } @Bean - public SchedulerFactoryBean scheduler(Trigger trigger, - JobDetail job, - DataSource quartzDataSource) { + public SchedulerFactoryBean scheduler(Trigger trigger, JobDetail job, DataSource quartzDataSource) { SchedulerFactoryBean schedulerFactory = new SchedulerFactoryBean(); schedulerFactory.setConfigLocation(new ClassPathResource("quartz.properties")); diff --git a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java index 4b976d37b0..6f66352616 100644 --- a/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java +++ b/spring-quartz/src/main/java/org/baeldung/springquartz/basics/service/SampleJobService.java @@ -11,7 +11,7 @@ public class SampleJobService { public static final long EXECUTION_TIME = 5000L; - private static final Logger logger = LoggerFactory.getLogger(SampleJobService.class); + private Logger logger = LoggerFactory.getLogger(getClass()); private AtomicInteger count = new AtomicInteger(); From ecfb5a2b944a847432b9d53e507a088a3486aabc Mon Sep 17 00:00:00 2001 From: eelhazati Date: Mon, 15 Jul 2019 10:25:50 +0100 Subject: [PATCH 006/107] add module to the main pom, in the profiles default-first and integration-lite-first. --- pom.xml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 35a7b95095..f9ee6e74c2 100644 --- a/pom.xml +++ b/pom.xml @@ -559,7 +559,7 @@ spring-boot-flowable spring-security-kerberos morphia - + oauth2-framework-impl @@ -1236,6 +1236,7 @@ rsocket rxjava rxjava-2 + oauth2-framework-impl From aba05a929c0d5084d88bf192f15055ac34127825 Mon Sep 17 00:00:00 2001 From: eelhazati Date: Mon, 15 Jul 2019 10:32:04 +0100 Subject: [PATCH 007/107] Replace the 'approbation' term with 'approval'. --- .../authorization/server/api/AuthorizationEndpoint.java | 4 ++-- .../oauth2-authorization-server/src/main/webapp/authorize.jsp | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/AuthorizationEndpoint.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/AuthorizationEndpoint.java index 10e78a2dfd..ba5e1ec359 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/AuthorizationEndpoint.java +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/AuthorizationEndpoint.java @@ -121,8 +121,8 @@ public class AuthorizationEndpoint { String redirectUri = originalParams.getFirst("resolved_redirect_uri"); StringBuilder sb = new StringBuilder(redirectUri); - String approbationStatus = params.getFirst("approbation_status"); - if ("NO".equals(approbationStatus)) { + String approvalStatus = params.getFirst("approval_status"); + if ("NO".equals(approvalStatus)) { URI location = UriBuilder.fromUri(sb.toString()) .queryParam("error", "User doesn't approved the request.") .queryParam("error_description", "User doesn't approved the request.") diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/webapp/authorize.jsp b/oauth2-framework-impl/oauth2-authorization-server/src/main/webapp/authorize.jsp index 1004b5b8b7..41b0582c03 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/webapp/authorize.jsp +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/webapp/authorize.jsp @@ -41,8 +41,8 @@ - - + + From ee6012a4decab36c07f4e16bd2e981c559faa528 Mon Sep 17 00:00:00 2001 From: Krzysztof Majewski Date: Wed, 17 Jul 2019 16:34:38 +0200 Subject: [PATCH 008/107] BAEL-2825 --- .../main/java/com/baeldung/jpa/entity/Article.java | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 persistence-modules/java-jpa/src/main/java/com/baeldung/jpa/entity/Article.java diff --git a/persistence-modules/java-jpa/src/main/java/com/baeldung/jpa/entity/Article.java b/persistence-modules/java-jpa/src/main/java/com/baeldung/jpa/entity/Article.java new file mode 100644 index 0000000000..02082c3d92 --- /dev/null +++ b/persistence-modules/java-jpa/src/main/java/com/baeldung/jpa/entity/Article.java @@ -0,0 +1,12 @@ +package com.baeldung.jpa.entity; + +import javax.persistence.Entity; +import javax.persistence.Table; + +@Entity(name = "MyArticle") +@Table(name = Article.TABLE_NAME) +public class Article { + + public static final String TABLE_NAME = "ARTICLES"; + +} From 82f1efaabe55577d9f1df64851213a16e346df9d Mon Sep 17 00:00:00 2001 From: Loredana Crusoveanu Date: Thu, 18 Jul 2019 18:50:31 +0300 Subject: [PATCH 009/107] Update pom.xml --- pom.xml | 1 - 1 file changed, 1 deletion(-) diff --git a/pom.xml b/pom.xml index e04d9f7bba..9be2971be4 100644 --- a/pom.xml +++ b/pom.xml @@ -556,7 +556,6 @@ tensorflow-java spring-boot-flowable spring-security-kerberos - morphia oauth2-framework-impl From 04e9fdafa45f92d172f0423c17fe7148fcd176f3 Mon Sep 17 00:00:00 2001 From: drazen Date: Thu, 18 Jul 2019 20:23:15 +0200 Subject: [PATCH 010/107] BAEL-3007: WebClient vs RestTemplate example. --- pom.xml | 3 + spring-5-reactive-2/.gitignore | 12 ++++ spring-5-reactive-2/README.md | 1 + spring-5-reactive-2/pom.xml | 50 ++++++++++++++++ .../java/com/baeldung/webclient/Tweet.java | 13 ++++ .../TweetsSlowServiceController.java | 20 +++++++ .../webclient/WebClientApplication.java | 11 ++++ .../com/baeldung/webclient/WebController.java | 60 +++++++++++++++++++ .../WebControllerIntegrationTest.java | 51 ++++++++++++++++ 9 files changed, 221 insertions(+) create mode 100644 spring-5-reactive-2/.gitignore create mode 100644 spring-5-reactive-2/README.md create mode 100644 spring-5-reactive-2/pom.xml create mode 100644 spring-5-reactive-2/src/main/java/com/baeldung/webclient/Tweet.java create mode 100644 spring-5-reactive-2/src/main/java/com/baeldung/webclient/TweetsSlowServiceController.java create mode 100644 spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebClientApplication.java create mode 100644 spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebController.java create mode 100644 spring-5-reactive-2/src/test/java/com/baeldung/webclient/WebControllerIntegrationTest.java diff --git a/pom.xml b/pom.xml index 2e34254bf5..179f7844ee 100644 --- a/pom.xml +++ b/pom.xml @@ -606,6 +606,7 @@ spring-5-data-reactive spring-5-mvc spring-5-reactive + spring-5-reactive-2 spring-5-reactive-client spring-5-reactive-oauth spring-5-reactive-security @@ -820,6 +821,7 @@ spring-5 spring-5-data-reactive spring-5-reactive + spring-5-reactive-2 spring-5-reactive-client spring-5-reactive-security spring-5-security @@ -1277,6 +1279,7 @@ spring-5-data-reactive spring-5-mvc spring-5-reactive + spring-5-reactive-2 spring-5-reactive-client spring-5-reactive-oauth spring-5-reactive-security diff --git a/spring-5-reactive-2/.gitignore b/spring-5-reactive-2/.gitignore new file mode 100644 index 0000000000..dec013dfa4 --- /dev/null +++ b/spring-5-reactive-2/.gitignore @@ -0,0 +1,12 @@ +#folders# +.idea +/target +/neoDb* +/data +/src/main/webapp/WEB-INF/classes +*/META-INF/* + +# Packaged files # +*.jar +*.war +*.ear \ No newline at end of file diff --git a/spring-5-reactive-2/README.md b/spring-5-reactive-2/README.md new file mode 100644 index 0000000000..bbb45e9f8c --- /dev/null +++ b/spring-5-reactive-2/README.md @@ -0,0 +1 @@ +## Spring 5 Reactive Project diff --git a/spring-5-reactive-2/pom.xml b/spring-5-reactive-2/pom.xml new file mode 100644 index 0000000000..668e0e5cf9 --- /dev/null +++ b/spring-5-reactive-2/pom.xml @@ -0,0 +1,50 @@ + + + 4.0.0 + com.baeldung + spring-5-reactive-2 + 0.0.1-SNAPSHOT + spring-5-reactive-2 + jar + spring 5 sample project about new features + + + com.baeldung + parent-boot-2 + 0.0.1-SNAPSHOT + ../parent-boot-2 + + + + + org.springframework.boot + spring-boot-starter-webflux + + + org.springframework.boot + spring-boot-starter-test + test + + + org.projectlombok + lombok + ${lombok.version} + provided + + + + + + + org.springframework.boot + spring-boot-maven-plugin + + com.baeldung.webclient.WebClientApplication + JAR + + + + + + diff --git a/spring-5-reactive-2/src/main/java/com/baeldung/webclient/Tweet.java b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/Tweet.java new file mode 100644 index 0000000000..8d294955f3 --- /dev/null +++ b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/Tweet.java @@ -0,0 +1,13 @@ +package com.baeldung.webclient; + +import lombok.AllArgsConstructor; +import lombok.Data; +import lombok.NoArgsConstructor; + +@Data +@NoArgsConstructor +@AllArgsConstructor +public class Tweet { + private String text; + private String username; +} diff --git a/spring-5-reactive-2/src/main/java/com/baeldung/webclient/TweetsSlowServiceController.java b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/TweetsSlowServiceController.java new file mode 100644 index 0000000000..fecaca25ef --- /dev/null +++ b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/TweetsSlowServiceController.java @@ -0,0 +1,20 @@ +package com.baeldung.webclient; + +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RestController; + +import java.util.Arrays; +import java.util.List; + +@RestController +public class TweetsSlowServiceController { + + @GetMapping("/slow-service-tweets") + private List getAllTweets() throws Exception { + Thread.sleep(2000L); // delay + return Arrays.asList( + new Tweet("RestTemplate rules", "@user1"), + new Tweet("WebClient is better", "@user2"), + new Tweet("OK, both are useful", "@user1")); + } +} diff --git a/spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebClientApplication.java b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebClientApplication.java new file mode 100644 index 0000000000..751e3a9487 --- /dev/null +++ b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebClientApplication.java @@ -0,0 +1,11 @@ +package com.baeldung.webclient; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +@SpringBootApplication +public class WebClientApplication { + public static void main(String[] args) { + SpringApplication.run(WebClientApplication.class, args); + } +} diff --git a/spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebController.java b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebController.java new file mode 100644 index 0000000000..73f5724819 --- /dev/null +++ b/spring-5-reactive-2/src/main/java/com/baeldung/webclient/WebController.java @@ -0,0 +1,60 @@ +package com.baeldung.webclient; + +import lombok.Setter; +import lombok.extern.slf4j.Slf4j; +import org.springframework.core.ParameterizedTypeReference; +import org.springframework.http.HttpMethod; +import org.springframework.http.MediaType; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RestController; +import org.springframework.web.client.RestTemplate; +import org.springframework.web.reactive.function.client.WebClient; +import reactor.core.publisher.Flux; + +import java.util.List; + +@Slf4j +@RestController +public class WebController { + + private static final int DEFAULT_PORT = 8080; + + @Setter + private int serverPort = DEFAULT_PORT; + + @GetMapping("/tweets-blocking") + public List getTweetsBlocking() { + log.info("Starting BLOCKING Controller!"); + final String uri = getSlowServiceUri(); + + RestTemplate restTemplate = new RestTemplate(); + ResponseEntity> response = restTemplate.exchange( + uri, HttpMethod.GET, null, + new ParameterizedTypeReference>(){}); + + List result = response.getBody(); + result.forEach(tweet -> log.info(tweet.toString())); + log.info("Exiting BLOCKING Controller!"); + return result; + } + + @GetMapping(value = "/tweets-non-blocking", produces = MediaType.TEXT_EVENT_STREAM_VALUE) + public Flux getTweetsNonBlocking() { + log.info("Starting NON-BLOCKING Controller!"); + Flux tweetFlux = WebClient.create() + .get() + .uri(getSlowServiceUri()) + .retrieve() + .bodyToFlux(Tweet.class); + + tweetFlux.subscribe(tweet -> log.info(tweet.toString())); + log.info("Exiting NON-BLOCKING Controller!"); + return tweetFlux; + } + + private String getSlowServiceUri() { + return "http://localhost:" + serverPort + "/slow-service-tweets"; + } + +} diff --git a/spring-5-reactive-2/src/test/java/com/baeldung/webclient/WebControllerIntegrationTest.java b/spring-5-reactive-2/src/test/java/com/baeldung/webclient/WebControllerIntegrationTest.java new file mode 100644 index 0000000000..09c3a5fb84 --- /dev/null +++ b/spring-5-reactive-2/src/test/java/com/baeldung/webclient/WebControllerIntegrationTest.java @@ -0,0 +1,51 @@ +package com.baeldung.webclient; + +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.web.server.LocalServerPort; +import org.springframework.test.context.junit4.SpringRunner; +import org.springframework.test.web.reactive.server.WebTestClient; + +@RunWith(SpringRunner.class) +@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT, classes = WebClientApplication.class) +public class WebControllerIntegrationTest { + + @LocalServerPort + int randomServerPort; + + @Autowired + private WebTestClient testClient; + + @Autowired + private WebController webController; + + @Before + public void setup() { + webController.setServerPort(randomServerPort); + } + + @Test + public void whenEndpointWithBlockingClientIsCalled_thenThreeTweetsAreReceived() { + testClient.get() + .uri("/tweets-blocking") + .exchange() + .expectStatus() + .isOk() + .expectBodyList(Tweet.class) + .hasSize(3); + } + + @Test + public void whenEndpointWithNonBlockingClientIsCalled_thenThreeTweetsAreReceived() { + testClient.get() + .uri("/tweets-non-blocking") + .exchange() + .expectStatus() + .isOk() + .expectBodyList(Tweet.class) + .hasSize(3); + } +} \ No newline at end of file From e12749abcd76f7e66b93393b2a3f84a5222b0e5e Mon Sep 17 00:00:00 2001 From: Thabo Ntsoko Date: Thu, 18 Jul 2019 20:23:31 +0200 Subject: [PATCH 011/107] Demo code for looping diagonally through a square 2D array --- .../array/looping/LoopDiagonally.java | 45 +++++++++++++++++++ .../array/looping/LoopDiagonallyTest.java | 20 +++++++++ 2 files changed, 65 insertions(+) create mode 100644 core-java-arrays/src/main/java/com/baeldung/array/looping/LoopDiagonally.java create mode 100644 core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java diff --git a/core-java-arrays/src/main/java/com/baeldung/array/looping/LoopDiagonally.java b/core-java-arrays/src/main/java/com/baeldung/array/looping/LoopDiagonally.java new file mode 100644 index 0000000000..71e2840f45 --- /dev/null +++ b/core-java-arrays/src/main/java/com/baeldung/array/looping/LoopDiagonally.java @@ -0,0 +1,45 @@ +package com.baeldung.array.looping; + +public class LoopDiagonally { + + + public String loopDiagonally(String[][] twoDArray) { + + int length = twoDArray.length; + int diagonalLines = (length + length) - 1; + int itemsInDiagonal = 0; + int midPoint = (diagonalLines / 2) + 1; + StringBuilder output = new StringBuilder(); + + for (int i = 1; i <= diagonalLines; i++) { + + StringBuilder items = new StringBuilder(); + int rowIndex; + int columnIndex; + + if (i <= midPoint) { + itemsInDiagonal++; + for (int j = 0; j < itemsInDiagonal; j++) { + rowIndex = (i - j) - 1; + columnIndex = j; + items.append(twoDArray[rowIndex][columnIndex]); + } + } else { + itemsInDiagonal--; + for (int j = 0; j < itemsInDiagonal; j++) { + rowIndex = (length - 1) - j; + columnIndex = (i - length) + j; + items.append(twoDArray[rowIndex][columnIndex]); + } + } + + if (i != diagonalLines) { + output.append(items).append(" "); + } else { + output.append(items); + } + } + + return output.toString(); + } +} diff --git a/core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java b/core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java new file mode 100644 index 0000000000..df6079270b --- /dev/null +++ b/core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java @@ -0,0 +1,20 @@ +package com.baeldung.array.looping; + +import org.junit.Test; + +import static org.junit.Assert.assertEquals; + +public class LoopDiagonallyTest { + + @Test + public void twoArrayIsLoopedDiagonallyAsExpected() { + + LoopDiagonally loopDiagonally = new LoopDiagonally(); + String[][] twoDArray = {{"a", "b", "c"}, + {"d", "e", "f"}, + {"g", "h", "i"}}; + + String output = loopDiagonally.loopDiagonally(twoDArray); + assertEquals("a db gec hf i", output); + } +} \ No newline at end of file From 62d1391db542de03cedb5cc427c933a657336429 Mon Sep 17 00:00:00 2001 From: Steven van Beelen Date: Fri, 19 Jul 2019 16:05:12 +0200 Subject: [PATCH 012/107] Update Axon version Update Axon version to 4.1.2 BAEL-3099 --- axon/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/axon/pom.xml b/axon/pom.xml index 002701373f..3d30cceb83 100644 --- a/axon/pom.xml +++ b/axon/pom.xml @@ -52,7 +52,7 @@ - 4.1.1 + 4.1.2 \ No newline at end of file From ce364f6b2ebfb4ae3c443382497f2ee4b7d024ae Mon Sep 17 00:00:00 2001 From: Steven van Beelen Date: Fri, 19 Jul 2019 16:05:39 +0200 Subject: [PATCH 013/107] Adjust expected exception Adjust expected exception from IllegalArgumentException to UnconfirmedOrderException BAEL-3099 --- .../baeldung/axon/commandmodel/OrderAggregateUnitTest.java | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/axon/src/test/java/com/baeldung/axon/commandmodel/OrderAggregateUnitTest.java b/axon/src/test/java/com/baeldung/axon/commandmodel/OrderAggregateUnitTest.java index 9beedbaa19..aaefe49fb1 100644 --- a/axon/src/test/java/com/baeldung/axon/commandmodel/OrderAggregateUnitTest.java +++ b/axon/src/test/java/com/baeldung/axon/commandmodel/OrderAggregateUnitTest.java @@ -2,6 +2,7 @@ package com.baeldung.axon.commandmodel; import java.util.UUID; +import com.baeldung.axon.coreapi.exceptions.UnconfirmedOrderException; import org.axonframework.test.aggregate.AggregateTestFixture; import org.axonframework.test.aggregate.FixtureConfiguration; import org.junit.*; @@ -41,12 +42,12 @@ public class OrderAggregateUnitTest { } @Test - public void givenOrderPlacedEvent_whenShipOrderCommand_thenShouldThrowIllegalStateException() { + public void givenOrderPlacedEvent_whenShipOrderCommand_thenShouldThrowUnconfirmedOrderException() { String orderId = UUID.randomUUID().toString(); String product = "Deluxe Chair"; fixture.given(new OrderPlacedEvent(orderId, product)) .when(new ShipOrderCommand(orderId)) - .expectException(IllegalStateException.class); + .expectException(UnconfirmedOrderException.class); } @Test From 9978d337fcededcc0fa6e51ba4819dcccde25e8f Mon Sep 17 00:00:00 2001 From: Loredana Date: Sat, 20 Jul 2019 12:09:38 +0300 Subject: [PATCH 014/107] fix envers test --- .../src/main/java/com/baeldung/spring/PersistenceConfig.java | 2 +- .../persistence/audit/EnversFooBarAuditIntegrationTest.java | 5 ++++- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/persistence-modules/spring-hibernate4/src/main/java/com/baeldung/spring/PersistenceConfig.java b/persistence-modules/spring-hibernate4/src/main/java/com/baeldung/spring/PersistenceConfig.java index 35e80b81a5..b7cf0fadf2 100644 --- a/persistence-modules/spring-hibernate4/src/main/java/com/baeldung/spring/PersistenceConfig.java +++ b/persistence-modules/spring-hibernate4/src/main/java/com/baeldung/spring/PersistenceConfig.java @@ -47,7 +47,7 @@ import com.google.common.base.Preconditions; @EnableTransactionManagement @EnableJpaRepositories(basePackages = { "com.baeldung.persistence" }, transactionManagerRef = "jpaTransactionManager") @EnableJpaAuditing -@PropertySource({ "classpath:persistence-mysql.properties" }) +@PropertySource({ "classpath:persistence-h2.properties" }) @ComponentScan({ "com.baeldung.persistence" }) public class PersistenceConfig { diff --git a/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java b/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java index 2f23a9a532..0530c2a70f 100644 --- a/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java +++ b/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java @@ -2,6 +2,7 @@ package com.baeldung.persistence.audit; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertTrue; import java.util.List; @@ -17,6 +18,7 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; +import org.springframework.test.annotation.DirtiesContext; import org.springframework.test.context.ContextConfiguration; import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; import org.springframework.test.context.support.AnnotationConfigContextLoader; @@ -29,6 +31,7 @@ import com.baeldung.spring.config.PersistenceTestConfig; @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(classes = { PersistenceTestConfig.class }, loader = AnnotationConfigContextLoader.class) +@DirtiesContext(classMode = DirtiesContext.ClassMode.BEFORE_CLASS) public class EnversFooBarAuditIntegrationTest { private static Logger logger = LoggerFactory.getLogger(EnversFooBarAuditIntegrationTest.class); @@ -118,7 +121,7 @@ public class EnversFooBarAuditIntegrationTest { barRevisionList = barService.getRevisions(); assertNotNull(barRevisionList); - assertEquals(4, barRevisionList.size()); + assertTrue(barRevisionList.size()>=4); assertEquals("BAR", barRevisionList.get(0).getName()); assertEquals("BAR", barRevisionList.get(1).getName()); From 98c537f20f49a720909ca44ea055a64cc44e9050 Mon Sep 17 00:00:00 2001 From: Loredana Date: Sat, 20 Jul 2019 12:11:16 +0300 Subject: [PATCH 015/107] update links --- persistence-modules/spring-data-jpa/README.md | 1 - persistence-modules/spring-hibernate4/README.md | 1 + 2 files changed, 1 insertion(+), 1 deletion(-) diff --git a/persistence-modules/spring-data-jpa/README.md b/persistence-modules/spring-data-jpa/README.md index e85d8a8487..4b4a590e10 100644 --- a/persistence-modules/spring-data-jpa/README.md +++ b/persistence-modules/spring-data-jpa/README.md @@ -10,7 +10,6 @@ - [Spring Data Java 8 Support](http://www.baeldung.com/spring-data-java-8) - [A Simple Tagging Implementation with JPA](http://www.baeldung.com/jpa-tagging) - [Spring Data Composable Repositories](https://www.baeldung.com/spring-data-composable-repositories) -- [Auditing with JPA, Hibernate, and Spring Data JPA](https://www.baeldung.com/database-auditing-jpa) - [Query Entities by Dates and Times with Spring Data JPA](https://www.baeldung.com/spring-data-jpa-query-by-date) - [DDD Aggregates and @DomainEvents](https://www.baeldung.com/spring-data-ddd) - [Spring Data – CrudRepository save() Method](https://www.baeldung.com/spring-data-crud-repository-save) diff --git a/persistence-modules/spring-hibernate4/README.md b/persistence-modules/spring-hibernate4/README.md index 426944c149..020e867c82 100644 --- a/persistence-modules/spring-hibernate4/README.md +++ b/persistence-modules/spring-hibernate4/README.md @@ -10,6 +10,7 @@ - [Hibernate: save, persist, update, merge, saveOrUpdate](http://www.baeldung.com/hibernate-save-persist-update-merge-saveorupdate) - [Eager/Lazy Loading In Hibernate](http://www.baeldung.com/hibernate-lazy-eager-loading) - [The DAO with Spring and Hibernate](http://www.baeldung.com/persistence-layer-with-spring-and-hibernate) +- [Auditing with JPA, Hibernate, and Spring Data JPA](https://www.baeldung.com/database-auditing-jpa) ### Quick Start From c10619ea207c50d8ac638622a7ad50cedc20873f Mon Sep 17 00:00:00 2001 From: Loredana Date: Sat, 20 Jul 2019 12:13:01 +0300 Subject: [PATCH 016/107] update test --- .../persistence/audit/EnversFooBarAuditIntegrationTest.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java b/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java index 0530c2a70f..444324dafc 100644 --- a/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java +++ b/persistence-modules/spring-hibernate4/src/test/java/com/baeldung/persistence/audit/EnversFooBarAuditIntegrationTest.java @@ -121,7 +121,7 @@ public class EnversFooBarAuditIntegrationTest { barRevisionList = barService.getRevisions(); assertNotNull(barRevisionList); - assertTrue(barRevisionList.size()>=4); + assertEquals(4, barRevisionList.size()); assertEquals("BAR", barRevisionList.get(0).getName()); assertEquals("BAR", barRevisionList.get(1).getName()); From e81753727d534f8121de19a9008d1c11cebeb90d Mon Sep 17 00:00:00 2001 From: amit2103 Date: Sun, 21 Jul 2019 00:57:41 +0530 Subject: [PATCH 017/107] [BAEL-15959] - Moved article to spring-security-core --- spring-5-mvc/README.md | 1 - .../java/com/baeldung/Spring5Application.java | 32 ------------------- spring-5-mvc/src/main/webapp/WEB-INF/web.xml | 9 ------ spring-security-core/README.md | 1 + .../src/main/java/org/baeldung/app/App.java | 32 +++++++++++++++++++ .../org/baeldung}/filter/CustomFilter.java | 2 +- .../src/main/webapp/WEB-INF/web.xml | 17 ++++++++++ 7 files changed, 51 insertions(+), 43 deletions(-) rename {spring-5-mvc/src/main/java/com/baeldung/spring => spring-security-core/src/main/java/org/baeldung}/filter/CustomFilter.java (96%) create mode 100644 spring-security-core/src/main/webapp/WEB-INF/web.xml diff --git a/spring-5-mvc/README.md b/spring-5-mvc/README.md index 7e83077f54..063945281f 100644 --- a/spring-5-mvc/README.md +++ b/spring-5-mvc/README.md @@ -1,4 +1,3 @@ ### Relevant Articles: - [Spring Boot and Kotlin](http://www.baeldung.com/spring-boot-kotlin) - [Spring MVC Streaming and SSE Request Processing](https://www.baeldung.com/spring-mvc-sse-streams) -- [Overview and Need for DelegatingFilterProxy in Spring](https://www.baeldung.com/spring-delegating-filter-proxy) diff --git a/spring-5-mvc/src/main/java/com/baeldung/Spring5Application.java b/spring-5-mvc/src/main/java/com/baeldung/Spring5Application.java index 74a348dea6..38b2d943f8 100644 --- a/spring-5-mvc/src/main/java/com/baeldung/Spring5Application.java +++ b/spring-5-mvc/src/main/java/com/baeldung/Spring5Application.java @@ -1,12 +1,8 @@ package com.baeldung; -import javax.servlet.Filter; - import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.autoconfigure.security.servlet.SecurityAutoConfiguration; -import org.springframework.web.filter.DelegatingFilterProxy; -import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer; @SpringBootApplication( exclude = SecurityAutoConfiguration.class) public class Spring5Application { @@ -14,32 +10,4 @@ public class Spring5Application { public static void main(String[] args) { SpringApplication.run(Spring5Application.class, args); } - - public static class ApplicationInitializer extends AbstractAnnotationConfigDispatcherServletInitializer { - - @Override - protected Class[] getRootConfigClasses() { - return null; - } - - @Override - protected Class[] getServletConfigClasses() { - // TODO Auto-generated method stub - return null; - } - - @Override - protected String[] getServletMappings() { - // TODO Auto-generated method stub - return null; - } - - @Override - protected javax.servlet.Filter[] getServletFilters() { - DelegatingFilterProxy delegateFilterProxy = new DelegatingFilterProxy(); - delegateFilterProxy.setTargetBeanName("loggingFilter"); - return new Filter[] { delegateFilterProxy }; - } - } - } diff --git a/spring-5-mvc/src/main/webapp/WEB-INF/web.xml b/spring-5-mvc/src/main/webapp/WEB-INF/web.xml index 43c7143e5b..ab4d38ce1c 100644 --- a/spring-5-mvc/src/main/webapp/WEB-INF/web.xml +++ b/spring-5-mvc/src/main/webapp/WEB-INF/web.xml @@ -16,14 +16,5 @@ functional / - - loggingFilter - org.springframework.web.filter.DelegatingFilterProxy - - - - loggingFilter - /* - \ No newline at end of file diff --git a/spring-security-core/README.md b/spring-security-core/README.md index b38dc061b4..bc9a8afed7 100644 --- a/spring-security-core/README.md +++ b/spring-security-core/README.md @@ -10,3 +10,4 @@ mvn clean install - [Spring Security – @PreFilter and @PostFilter](http://www.baeldung.com/spring-security-prefilter-postfilter) - [Spring Boot Authentication Auditing Support](http://www.baeldung.com/spring-boot-authentication-audit) - [Introduction to Spring Method Security](http://www.baeldung.com/spring-security-method-security) +- [Overview and Need for DelegatingFilterProxy in Spring](https://www.baeldung.com/spring-delegating-filter-proxy) \ No newline at end of file diff --git a/spring-security-core/src/main/java/org/baeldung/app/App.java b/spring-security-core/src/main/java/org/baeldung/app/App.java index 37d8c34c5a..db0c9135c4 100644 --- a/spring-security-core/src/main/java/org/baeldung/app/App.java +++ b/spring-security-core/src/main/java/org/baeldung/app/App.java @@ -1,11 +1,15 @@ package org.baeldung.app; +import javax.servlet.Filter; + import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.autoconfigure.domain.EntityScan; import org.springframework.boot.web.support.SpringBootServletInitializer; import org.springframework.context.annotation.ComponentScan; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; +import org.springframework.web.filter.DelegatingFilterProxy; +import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer; @SpringBootApplication @EnableJpaRepositories("org.baeldung.repository") @@ -15,4 +19,32 @@ public class App extends SpringBootServletInitializer { public static void main(String[] args) { SpringApplication.run(App.class, args); } + + public static class ApplicationInitializer extends AbstractAnnotationConfigDispatcherServletInitializer { + + @Override + protected javax.servlet.Filter[] getServletFilters() { + DelegatingFilterProxy delegateFilterProxy = new DelegatingFilterProxy(); + delegateFilterProxy.setTargetBeanName("loggingFilter"); + return new Filter[] { delegateFilterProxy }; + } + + @Override + protected Class[] getRootConfigClasses() { + // TODO Auto-generated method stub + return null; + } + + @Override + protected Class[] getServletConfigClasses() { + // TODO Auto-generated method stub + return null; + } + + @Override + protected String[] getServletMappings() { + // TODO Auto-generated method stub + return null; + } + } } diff --git a/spring-5-mvc/src/main/java/com/baeldung/spring/filter/CustomFilter.java b/spring-security-core/src/main/java/org/baeldung/filter/CustomFilter.java similarity index 96% rename from spring-5-mvc/src/main/java/com/baeldung/spring/filter/CustomFilter.java rename to spring-security-core/src/main/java/org/baeldung/filter/CustomFilter.java index 4aa33cd749..35596eae16 100644 --- a/spring-5-mvc/src/main/java/com/baeldung/spring/filter/CustomFilter.java +++ b/spring-security-core/src/main/java/org/baeldung/filter/CustomFilter.java @@ -1,4 +1,4 @@ -package com.baeldung.spring.filter; +package org.baeldung.filter; import java.io.IOException; diff --git a/spring-security-core/src/main/webapp/WEB-INF/web.xml b/spring-security-core/src/main/webapp/WEB-INF/web.xml new file mode 100644 index 0000000000..e4954338a9 --- /dev/null +++ b/spring-security-core/src/main/webapp/WEB-INF/web.xml @@ -0,0 +1,17 @@ + + + + + loggingFilter + org.springframework.web.filter.DelegatingFilterProxy + + + + loggingFilter + /* + + + \ No newline at end of file From 9fe7b80348854fe6011bb8cffa4c323689d5520e Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 15:54:32 +0800 Subject: [PATCH 018/107] Update README.md --- spring-5-reactive-client/README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/spring-5-reactive-client/README.md b/spring-5-reactive-client/README.md index f94bd0b0c1..f03ed7237d 100644 --- a/spring-5-reactive-client/README.md +++ b/spring-5-reactive-client/README.md @@ -4,3 +4,5 @@ The "REST With Spring" Classes: http://bit.ly/restwithspring ### Relevant Articles + +- [Spring Security 5 for Reactive Applications](https://www.baeldung.com/spring-security-5-reactive) From e4f1ddd488a420dc16d6b9f2a844cabd67509822 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 15:56:00 +0800 Subject: [PATCH 019/107] Update README.md --- spring-groovy/README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/spring-groovy/README.md b/spring-groovy/README.md index ff12555376..2aab1b2e18 100644 --- a/spring-groovy/README.md +++ b/spring-groovy/README.md @@ -1 +1,3 @@ ## Relevant articles: + +- [Groovy Bean Definitions](https://www.baeldung.com/spring-groovy-beans) From 01b8b344116403d4b1c9370d32b22afca6612177 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 15:57:07 +0800 Subject: [PATCH 020/107] Delete README.md --- resteasy/bin/README.md | 6 ------ 1 file changed, 6 deletions(-) delete mode 100644 resteasy/bin/README.md diff --git a/resteasy/bin/README.md b/resteasy/bin/README.md deleted file mode 100644 index f4dba1493a..0000000000 --- a/resteasy/bin/README.md +++ /dev/null @@ -1,6 +0,0 @@ -========= - -## A Guide to RESTEasy - - -### Relevant Articles: From 1d4c353cf646b7fcb8bd86187c6f6cb8d5094f5d Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:00:24 +0800 Subject: [PATCH 021/107] Create README.md --- core-java-modules/multimodulemavenproject/README.md | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 core-java-modules/multimodulemavenproject/README.md diff --git a/core-java-modules/multimodulemavenproject/README.md b/core-java-modules/multimodulemavenproject/README.md new file mode 100644 index 0000000000..fc4ca60b6b --- /dev/null +++ b/core-java-modules/multimodulemavenproject/README.md @@ -0,0 +1,3 @@ +## Relevant Articles + +- [Multi-Module Maven Application with Java Modules](https://www.baeldung.com/maven-multi-module-project-java-jpms) From 6780457b188610101a609386a4142d3539fd3b74 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:01:53 +0800 Subject: [PATCH 022/107] Create README.md --- spring-security-cors/README.md | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 spring-security-cors/README.md diff --git a/spring-security-cors/README.md b/spring-security-cors/README.md new file mode 100644 index 0000000000..2ab5e33ee3 --- /dev/null +++ b/spring-security-cors/README.md @@ -0,0 +1,3 @@ +## Relevant Articles + +- [Fixing 401s with CORS Preflights and Spring Security](https://www.baeldung.com/spring-security-cors-preflight) From 2f04bde63ec5cb901fbe655145f2937ce34e0312 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:03:46 +0800 Subject: [PATCH 023/107] Create README.md --- testing-modules/load-testing-comparison/README.md | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 testing-modules/load-testing-comparison/README.md diff --git a/testing-modules/load-testing-comparison/README.md b/testing-modules/load-testing-comparison/README.md new file mode 100644 index 0000000000..bad22e7a49 --- /dev/null +++ b/testing-modules/load-testing-comparison/README.md @@ -0,0 +1,3 @@ +## Relevant Articles + +-[Gatling vs JMeter vs The Grinder: Comparing Load Test Tools](https://www.baeldung.com/gatling-jmeter-grinder-comparison) From f76d67c2489b4db663fce54012c3ca03bcba1714 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:04:00 +0800 Subject: [PATCH 024/107] Update README.md --- testing-modules/load-testing-comparison/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/testing-modules/load-testing-comparison/README.md b/testing-modules/load-testing-comparison/README.md index bad22e7a49..9823be5369 100644 --- a/testing-modules/load-testing-comparison/README.md +++ b/testing-modules/load-testing-comparison/README.md @@ -1,3 +1,3 @@ ## Relevant Articles --[Gatling vs JMeter vs The Grinder: Comparing Load Test Tools](https://www.baeldung.com/gatling-jmeter-grinder-comparison) +- [Gatling vs JMeter vs The Grinder: Comparing Load Test Tools](https://www.baeldung.com/gatling-jmeter-grinder-comparison) From f574a14badd7cd577a3775e6125a080b6871be36 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:05:12 +0800 Subject: [PATCH 025/107] Create README.md --- testing-modules/parallel-tests-junit/README.md | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 testing-modules/parallel-tests-junit/README.md diff --git a/testing-modules/parallel-tests-junit/README.md b/testing-modules/parallel-tests-junit/README.md new file mode 100644 index 0000000000..0b7834c5e7 --- /dev/null +++ b/testing-modules/parallel-tests-junit/README.md @@ -0,0 +1,3 @@ +## Relevant Articles + +- [Running JUnit Tests in Parallel with Maven](https://www.baeldung.com/maven-junit-parallel-tests) From 8b39d2ab37aa6318992a9cff0758529c2a212a10 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:09:53 +0800 Subject: [PATCH 026/107] Create README.md --- jhipster/jhipster-uaa/README.md | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 jhipster/jhipster-uaa/README.md diff --git a/jhipster/jhipster-uaa/README.md b/jhipster/jhipster-uaa/README.md new file mode 100644 index 0000000000..3971e3c8c6 --- /dev/null +++ b/jhipster/jhipster-uaa/README.md @@ -0,0 +1,3 @@ +## Relevant Articles + +- [Building a Basic UAA-Secured JHipster Microservice](https://www.baeldung.com/jhipster-uaa-secured-micro-service) From 196289923e97200f10974d5c0b8ab31f219207b0 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:11:32 +0800 Subject: [PATCH 027/107] Update README.md --- jhipster/jhipster-monolithic/README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/jhipster/jhipster-monolithic/README.md b/jhipster/jhipster-monolithic/README.md index a2c267b74d..3a44f3f120 100644 --- a/jhipster/jhipster-monolithic/README.md +++ b/jhipster/jhipster-monolithic/README.md @@ -1,5 +1,7 @@ ### Relevant articles +- [Intro to JHipster](https://www.baeldung.com/jhipster) + # baeldung This application was generated using JHipster 4.0.8, you can find documentation and help at [https://jhipster.github.io/documentation-archive/v4.0.8](https://jhipster.github.io/documentation-archive/v4.0.8). From db63ca45ca61c89fe097c98ac4f9cebd1d5a1428 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:11:46 +0800 Subject: [PATCH 028/107] Update README.md --- jhipster/jhipster-monolithic/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/jhipster/jhipster-monolithic/README.md b/jhipster/jhipster-monolithic/README.md index 3a44f3f120..15c55118ee 100644 --- a/jhipster/jhipster-monolithic/README.md +++ b/jhipster/jhipster-monolithic/README.md @@ -1,4 +1,4 @@ -### Relevant articles +### Relevant Articles - [Intro to JHipster](https://www.baeldung.com/jhipster) From 51cd7667a59760cdfb5bc144d585a5f552bc63df Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:12:02 +0800 Subject: [PATCH 029/107] Update README.md --- jhipster/jhipster-monolithic/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/jhipster/jhipster-monolithic/README.md b/jhipster/jhipster-monolithic/README.md index 15c55118ee..65cc51ad88 100644 --- a/jhipster/jhipster-monolithic/README.md +++ b/jhipster/jhipster-monolithic/README.md @@ -1,4 +1,4 @@ -### Relevant Articles +## Relevant Articles - [Intro to JHipster](https://www.baeldung.com/jhipster) From f9b26474ce4f84cacba083e0ed77136b26e75ea4 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:13:15 +0800 Subject: [PATCH 030/107] Create README.md --- jhipster/jhipster-microservice/README.md | 3 +++ 1 file changed, 3 insertions(+) create mode 100644 jhipster/jhipster-microservice/README.md diff --git a/jhipster/jhipster-microservice/README.md b/jhipster/jhipster-microservice/README.md new file mode 100644 index 0000000000..7abe3204c4 --- /dev/null +++ b/jhipster/jhipster-microservice/README.md @@ -0,0 +1,3 @@ +## Relevant Articles + +- [JHipster with a Microservice Architecture](https://www.baeldung.com/jhipster-microservices) From c8ea0b65a90b5f30b4e8d78627d263150574a5e3 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:17:57 +0800 Subject: [PATCH 031/107] Update README.md --- quarkus/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/quarkus/README.md b/quarkus/README.md index 8116d16cb7..3ff08c6f9e 100644 --- a/quarkus/README.md +++ b/quarkus/README.md @@ -1,3 +1,3 @@ -## Relevant articles: +## Relevant Articles: - [Guide to QuarkusIO](https://www.baeldung.com/quarkus-io) From dc65ed87f68de3614a087b4aaa92cebd2835517c Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:20:20 +0800 Subject: [PATCH 032/107] Update README.md --- spring-groovy/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spring-groovy/README.md b/spring-groovy/README.md index 2aab1b2e18..36404230a9 100644 --- a/spring-groovy/README.md +++ b/spring-groovy/README.md @@ -1,3 +1,3 @@ -## Relevant articles: +## Relevant Articles: - [Groovy Bean Definitions](https://www.baeldung.com/spring-groovy-beans) From 0fa09cf5ae0ff47d566f6aee6172149311d3419f Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:22:09 +0800 Subject: [PATCH 033/107] Update README.md --- core-java-modules/core-java-exceptions/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core-java-modules/core-java-exceptions/README.md b/core-java-modules/core-java-exceptions/README.md index 5338789a2f..79e5bad23a 100644 --- a/core-java-modules/core-java-exceptions/README.md +++ b/core-java-modules/core-java-exceptions/README.md @@ -1,3 +1,3 @@ -## Relevant articles: +## Relevant Articles: - [Will an Error Be Caught by Catch Block in Java?](https://www.baeldung.com/java-error-catch) From 9bdd157a48c3565f59e1dce0e75ef83fdea499ed Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:22:48 +0800 Subject: [PATCH 034/107] Update README.md --- core-java-modules/core-java-exceptions/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core-java-modules/core-java-exceptions/README.md b/core-java-modules/core-java-exceptions/README.md index 79e5bad23a..4fda36bb44 100644 --- a/core-java-modules/core-java-exceptions/README.md +++ b/core-java-modules/core-java-exceptions/README.md @@ -1,3 +1,3 @@ ## Relevant Articles: -- [Will an Error Be Caught by Catch Block in Java?](https://www.baeldung.com/java-error-catch) + From f66288d9b53e4b33f195652ee48073d6aef1339e Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:23:10 +0800 Subject: [PATCH 035/107] Update README.md --- core-java-modules/core-java-12/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/core-java-modules/core-java-12/README.md b/core-java-modules/core-java-12/README.md index 4514fd1a2b..4fda36bb44 100644 --- a/core-java-modules/core-java-12/README.md +++ b/core-java-modules/core-java-12/README.md @@ -1,3 +1,3 @@ -## Relevant articles: +## Relevant Articles: + -- [String API Updates in Java 12](https://www.baeldung.com/java12-string-api) From 340f9656659cea31151b439aba7267b2d5f65c14 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:24:41 +0800 Subject: [PATCH 036/107] Update README.md --- parent-java/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/parent-java/README.md b/parent-java/README.md index ff12555376..729105e3fd 100644 --- a/parent-java/README.md +++ b/parent-java/README.md @@ -1 +1 @@ -## Relevant articles: +## Relevant Articles: From a672639976e1dc5ff815fad63f2cd227216c175a Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:26:13 +0800 Subject: [PATCH 037/107] Update README.md --- video-tutorials/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/video-tutorials/README.md b/video-tutorials/README.md index ff12555376..729105e3fd 100644 --- a/video-tutorials/README.md +++ b/video-tutorials/README.md @@ -1 +1 @@ -## Relevant articles: +## Relevant Articles: From 21c12dcef58a0eb21339af283218d046825feda1 Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:26:37 +0800 Subject: [PATCH 038/107] Update README.md --- parent-spring-4/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/parent-spring-4/README.md b/parent-spring-4/README.md index ff12555376..729105e3fd 100644 --- a/parent-spring-4/README.md +++ b/parent-spring-4/README.md @@ -1 +1 @@ -## Relevant articles: +## Relevant Articles: From 474aa7a5eef9d696037443ca152512e8677931cb Mon Sep 17 00:00:00 2001 From: johnA1331 <53036378+johnA1331@users.noreply.github.com> Date: Sun, 21 Jul 2019 16:26:53 +0800 Subject: [PATCH 039/107] Update README.md --- parent-spring-5/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/parent-spring-5/README.md b/parent-spring-5/README.md index ff12555376..729105e3fd 100644 --- a/parent-spring-5/README.md +++ b/parent-spring-5/README.md @@ -1 +1 @@ -## Relevant articles: +## Relevant Articles: From ca10190f5b3174a22ff2dec43a21225c9fa85ce9 Mon Sep 17 00:00:00 2001 From: Loredana Crusoveanu Date: Sun, 21 Jul 2019 11:46:51 +0300 Subject: [PATCH 040/107] Update README.md --- core-java-modules/core-java-12/README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/core-java-modules/core-java-12/README.md b/core-java-modules/core-java-12/README.md index 4fda36bb44..6c603e4dea 100644 --- a/core-java-modules/core-java-12/README.md +++ b/core-java-modules/core-java-12/README.md @@ -1,3 +1,4 @@ ## Relevant Articles: +- [String API Updates in Java 12](https://www.baeldung.com/java12-string-api) From 006bb85ca23661a5ef718be368bc8bc7b925b0a8 Mon Sep 17 00:00:00 2001 From: Loredana Crusoveanu Date: Sun, 21 Jul 2019 11:47:08 +0300 Subject: [PATCH 041/107] Update README.md --- core-java-modules/core-java-exceptions/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/core-java-modules/core-java-exceptions/README.md b/core-java-modules/core-java-exceptions/README.md index 4fda36bb44..79e5bad23a 100644 --- a/core-java-modules/core-java-exceptions/README.md +++ b/core-java-modules/core-java-exceptions/README.md @@ -1,3 +1,3 @@ ## Relevant Articles: - +- [Will an Error Be Caught by Catch Block in Java?](https://www.baeldung.com/java-error-catch) From 11836c0626b6a795e790aad88666523b4c8c15dd Mon Sep 17 00:00:00 2001 From: Loredana Crusoveanu Date: Sun, 21 Jul 2019 11:47:24 +0300 Subject: [PATCH 042/107] Update README.md --- spring-5-reactive-client/README.md | 1 - 1 file changed, 1 deletion(-) diff --git a/spring-5-reactive-client/README.md b/spring-5-reactive-client/README.md index f03ed7237d..0df2bdd339 100644 --- a/spring-5-reactive-client/README.md +++ b/spring-5-reactive-client/README.md @@ -5,4 +5,3 @@ The "REST With Spring" Classes: http://bit.ly/restwithspring ### Relevant Articles -- [Spring Security 5 for Reactive Applications](https://www.baeldung.com/spring-security-5-reactive) From 85d3960cf8612c54435f8e441f5f78f8ddb6633f Mon Sep 17 00:00:00 2001 From: Lukasz Rys Date: Sun, 21 Jul 2019 14:52:37 +0200 Subject: [PATCH 043/107] [BAEL-3079]: Embedded Redis Server Article (#7368) --- spring-boot-testing/pom.xml | 11 +++++++ .../configuration/RedisConfiguration.java | 24 ++++++++++++++ .../configuration/RedisProperties.java | 23 ++++++++++++++ .../boot/embeddedRedis/domain/User.java | 25 +++++++++++++++ .../domain/repository/UserRepository.java | 10 ++++++ .../src/main/resources/application.properties | 3 ++ .../embeddedRedis/TestRedisConfiguration.java | 28 +++++++++++++++++ .../UserRepositoryIntegrationTest.java | 31 +++++++++++++++++++ .../src/test/resources/application.properties | 3 ++ 9 files changed, 158 insertions(+) create mode 100644 spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisConfiguration.java create mode 100644 spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisProperties.java create mode 100644 spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/User.java create mode 100644 spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepository.java create mode 100644 spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/TestRedisConfiguration.java create mode 100644 spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepositoryIntegrationTest.java diff --git a/spring-boot-testing/pom.xml b/spring-boot-testing/pom.xml index 84107070bd..12fb14b366 100644 --- a/spring-boot-testing/pom.xml +++ b/spring-boot-testing/pom.xml @@ -15,6 +15,10 @@ + + org.springframework.boot + spring-boot-starter-data-redis + org.springframework.boot spring-boot-starter-web @@ -33,6 +37,13 @@ test + + + it.ozimov + embedded-redis + 0.7.2 + test + org.spockframework diff --git a/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisConfiguration.java b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisConfiguration.java new file mode 100644 index 0000000000..6b5b20892f --- /dev/null +++ b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisConfiguration.java @@ -0,0 +1,24 @@ +package com.baeldung.boot.embeddedRedis.configuration; + +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory; +import org.springframework.data.redis.core.RedisTemplate; +import org.springframework.data.redis.repository.configuration.EnableRedisRepositories; + +@Configuration +@EnableRedisRepositories +public class RedisConfiguration { + + @Bean + public LettuceConnectionFactory redisConnectionFactory(final RedisProperties redisProperties) { + return new LettuceConnectionFactory(redisProperties.getRedisHost(), redisProperties.getRedisPort()); + } + + @Bean + public RedisTemplate redisTemplate(final LettuceConnectionFactory connectionFactory) { + RedisTemplate template = new RedisTemplate<>(); + template.setConnectionFactory(connectionFactory); + return template; + } +} diff --git a/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisProperties.java b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisProperties.java new file mode 100644 index 0000000000..76f2e1bbfe --- /dev/null +++ b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/configuration/RedisProperties.java @@ -0,0 +1,23 @@ +package com.baeldung.boot.embeddedRedis.configuration; + +import org.springframework.beans.factory.annotation.Value; +import org.springframework.context.annotation.Configuration; + +@Configuration +public class RedisProperties { + private final int redisPort; + private final String redisHost; + + public RedisProperties(@Value("${spring.redis.port}") final int redisPort, @Value("${spring.redis.host}") final String redisHost) { + this.redisPort = redisPort; + this.redisHost = redisHost; + } + + public int getRedisPort() { + return redisPort; + } + + public String getRedisHost() { + return redisHost; + } +} diff --git a/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/User.java b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/User.java new file mode 100644 index 0000000000..41657aaa66 --- /dev/null +++ b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/User.java @@ -0,0 +1,25 @@ +package com.baeldung.boot.embeddedRedis.domain; + +import org.springframework.data.annotation.Id; +import org.springframework.data.redis.core.RedisHash; + +import java.util.UUID; + +@RedisHash("user") +public class User { + @Id private UUID id; + private String name; + + public User(UUID id, String name) { + this.id = id; + this.name = name; + } + + public UUID getId() { + return id; + } + + public String getName() { + return name; + } +} diff --git a/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepository.java b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepository.java new file mode 100644 index 0000000000..0558bb8482 --- /dev/null +++ b/spring-boot-testing/src/main/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepository.java @@ -0,0 +1,10 @@ +package com.baeldung.boot.embeddedRedis.domain.repository; + +import com.baeldung.boot.embeddedRedis.domain.User; +import org.springframework.data.repository.CrudRepository; + +import java.util.UUID; + +public interface UserRepository extends CrudRepository { + +} diff --git a/spring-boot-testing/src/main/resources/application.properties b/spring-boot-testing/src/main/resources/application.properties index e378aacdd5..8dc7f6e3c3 100644 --- a/spring-boot-testing/src/main/resources/application.properties +++ b/spring-boot-testing/src/main/resources/application.properties @@ -1,3 +1,6 @@ +# embedded redis +spring.redis.host= localhost +spring.redis.port= 6379 # security spring.security.user.name=john diff --git a/spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/TestRedisConfiguration.java b/spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/TestRedisConfiguration.java new file mode 100644 index 0000000000..b4748bcd38 --- /dev/null +++ b/spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/TestRedisConfiguration.java @@ -0,0 +1,28 @@ +package com.baeldung.boot.embeddedRedis; + +import com.baeldung.boot.embeddedRedis.configuration.RedisProperties; +import org.springframework.boot.test.context.TestConfiguration; +import redis.embedded.RedisServer; + +import javax.annotation.PostConstruct; +import javax.annotation.PreDestroy; + +@TestConfiguration +public class TestRedisConfiguration { + + private final RedisServer redisServer; + + public TestRedisConfiguration(final RedisProperties redisProperties) { + this.redisServer = new RedisServer(redisProperties.getRedisPort()); + } + + @PostConstruct + public void postConstruct() { + redisServer.start(); + } + + @PreDestroy + public void preDestroy() { + redisServer.stop(); + } +} diff --git a/spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepositoryIntegrationTest.java b/spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepositoryIntegrationTest.java new file mode 100644 index 0000000000..9577ccf0e8 --- /dev/null +++ b/spring-boot-testing/src/test/java/com/baeldung/boot/embeddedRedis/domain/repository/UserRepositoryIntegrationTest.java @@ -0,0 +1,31 @@ +package com.baeldung.boot.embeddedRedis.domain.repository; + +import com.baeldung.boot.embeddedRedis.TestRedisConfiguration; +import com.baeldung.boot.embeddedRedis.domain.User; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.test.context.junit4.SpringRunner; + +import java.util.UUID; + +import static org.junit.Assert.assertNotNull; + +@RunWith(SpringRunner.class) +@SpringBootTest(classes = TestRedisConfiguration.class) +public class UserRepositoryIntegrationTest { + + @Autowired + private UserRepository userRepository; + + @Test + public void shouldSaveUser_toRedis() { + final UUID id = UUID.randomUUID(); + final User user = new User(id, "name"); + + final User saved = userRepository.save(user); + + assertNotNull(saved); + } +} \ No newline at end of file diff --git a/spring-boot-testing/src/test/resources/application.properties b/spring-boot-testing/src/test/resources/application.properties index 9a8b496a8b..0c5b0e13e6 100644 --- a/spring-boot-testing/src/test/resources/application.properties +++ b/spring-boot-testing/src/test/resources/application.properties @@ -1,3 +1,6 @@ +#embedded redis +spring.redis.host= localhost +spring.redis.port= 6370 # security spring.security.user.name=john spring.security.user.password=123 \ No newline at end of file From 968710433aebdead914b595f4194b7aa2e8e3c82 Mon Sep 17 00:00:00 2001 From: Denis Date: Sun, 21 Jul 2019 18:56:35 +0200 Subject: [PATCH 044/107] BAEL-3084 remove xmlunit-2 ref from 'integration-lite-second' profile (#7372) --- pom.xml | 1 - 1 file changed, 1 deletion(-) diff --git a/pom.xml b/pom.xml index b888994a43..21a42f89d6 100644 --- a/pom.xml +++ b/pom.xml @@ -1456,7 +1456,6 @@ wicket xml - xmlunit-2 xstream From f5142320bf4809d6dabe6c03fc3108286fd7228e Mon Sep 17 00:00:00 2001 From: priyank-sriv Date: Mon, 22 Jul 2019 00:54:49 +0530 Subject: [PATCH 045/107] first commit - basic test --- patterns/backoff-jitter/pom.xml | 61 ++++++++++++++ .../backoff/jitter/BackoffWithJitterTest.java | 81 +++++++++++++++++++ patterns/pom.xml | 3 +- 3 files changed, 144 insertions(+), 1 deletion(-) create mode 100644 patterns/backoff-jitter/pom.xml create mode 100644 patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java diff --git a/patterns/backoff-jitter/pom.xml b/patterns/backoff-jitter/pom.xml new file mode 100644 index 0000000000..0a48a18abb --- /dev/null +++ b/patterns/backoff-jitter/pom.xml @@ -0,0 +1,61 @@ + + + 4.0.0 + com.baeldung + backoff-jitter + 1.0.0-SNAPSHOT + pom + + + + + + + + + + + junit + junit + ${junit.version} + test + + + org.mockito + mockito-core + ${mockito-core.version} + test + + + io.github.resilience4j + resilience4j-retry + ${resilience4j.version} + test + + + org.slf4j + slf4j-api + ${slf4j.version} + test + + + org.slf4j + slf4j-simple + ${slf4j.version} + test + + + + + UTF-8 + 1.8 + 1.8 + 4.12 + 2.27.0 + 1.7.26 + 0.16.0 + + + \ No newline at end of file diff --git a/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java new file mode 100644 index 0000000000..aef9f7fab7 --- /dev/null +++ b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java @@ -0,0 +1,81 @@ +package com.baeldung.backoff.jitter; + +import io.github.resilience4j.retry.IntervalFunction; +import io.github.resilience4j.retry.Retry; +import io.github.resilience4j.retry.RetryConfig; +import org.junit.Before; +import org.junit.Test; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.time.LocalDateTime; +import java.util.List; +import java.util.concurrent.Callable; +import java.util.concurrent.ExecutorService; +import java.util.function.Function; + +import static com.baeldung.backoff.jitter.BackoffWithJitterTest.RetryProperties.*; +import static io.github.resilience4j.retry.IntervalFunction.ofExponentialBackoff; +import static io.github.resilience4j.retry.IntervalFunction.ofExponentialRandomBackoff; +import static java.util.Collections.nCopies; +import static java.util.concurrent.Executors.newFixedThreadPool; +import static org.mockito.ArgumentMatchers.anyString; +import static org.mockito.Mockito.*; + +public class BackoffWithJitterTest { + + static Logger log = LoggerFactory.getLogger(BackoffWithJitterTest.class); + + interface PingPongService { + + String call(String ping) throws PingPongServiceException; + } + + class PingPongServiceException extends RuntimeException { + + public PingPongServiceException(String reason) { + super(reason); + } + } + + private PingPongService service; + private static final int NUM_TASKS = 8; + + @Before + public void setUp() { + service = mock(PingPongService.class); + } + + @Test + public void whenRetryExponentialBackoff_thenRetriedConfiguredNoOfTimes() { + IntervalFunction intervalFn = ofExponentialBackoff(INITIAL_INTERVAL, MULTIPLIER); + Function pingPongFn = getRetryablePingPongFn(intervalFn); + + when(service.call(anyString())).thenThrow(PingPongServiceException.class); + try { + pingPongFn.apply("Hello"); + } catch (PingPongServiceException e) { + verify(service, times(MAX_TRIES)).call(anyString()); + } + } + + private Function getRetryablePingPongFn(IntervalFunction intervalFn) { + RetryConfig retryConfig = RetryConfig.custom() + .maxAttempts(MAX_TRIES) + .intervalFunction(intervalFn) + .retryExceptions(PingPongServiceException.class) + .build(); + Retry retry = Retry.of("pingpong", retryConfig); + return Retry.decorateFunction(retry, ping -> { + log.info("Invoked at {}", LocalDateTime.now()); + return service.call(ping); + }); + } + + static class RetryProperties { + static final Long INITIAL_INTERVAL = 1000L; + static final Double MULTIPLIER = 2.0D; + static final Double RANDOMIZATION_FACTOR = 0.6D; + static final Integer MAX_TRIES = 4; + } +} diff --git a/patterns/pom.xml b/patterns/pom.xml index 2be9d2519e..7f7368ca07 100644 --- a/patterns/pom.xml +++ b/patterns/pom.xml @@ -19,7 +19,8 @@ design-patterns design-patterns-2 solid - dip + dip + backoff-jitter From 412e8b7634df712ad966d4ddce22f3ecc76d488b Mon Sep 17 00:00:00 2001 From: priyank-sriv Date: Mon, 22 Jul 2019 00:55:25 +0530 Subject: [PATCH 046/107] simple exponential backoff --- .../backoff/jitter/BackoffWithJitterTest.java | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java index aef9f7fab7..966207f430 100644 --- a/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java +++ b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java @@ -59,6 +59,22 @@ public class BackoffWithJitterTest { } } + @Test + public void whenRetryExponentialBackoffWithoutJitter_thenThunderingHerdProblemOccurs() throws InterruptedException { + IntervalFunction intervalFn = ofExponentialBackoff(INITIAL_INTERVAL, MULTIPLIER); + test(intervalFn); + } + + private void test(IntervalFunction intervalFn) throws InterruptedException { + Function pingPongFn = getRetryablePingPongFn(intervalFn); + ExecutorService executors = newFixedThreadPool(NUM_TASKS); + List> tasks = nCopies(NUM_TASKS, () -> pingPongFn.apply("Hello")); + + when(service.call(anyString())).thenThrow(PingPongServiceException.class); + + executors.invokeAll(tasks); + } + private Function getRetryablePingPongFn(IntervalFunction intervalFn) { RetryConfig retryConfig = RetryConfig.custom() .maxAttempts(MAX_TRIES) From ae1807fca2a9170abd547f6caf22017974aa3ac7 Mon Sep 17 00:00:00 2001 From: priyank-sriv Date: Mon, 22 Jul 2019 00:55:41 +0530 Subject: [PATCH 047/107] backoff with jitter --- .../com/baeldung/backoff/jitter/BackoffWithJitterTest.java | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java index 966207f430..0f0e652596 100644 --- a/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java +++ b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java @@ -65,6 +65,12 @@ public class BackoffWithJitterTest { test(intervalFn); } + @Test + public void whenRetryExponentialBackoffWithJitter_thenRetriesAreSpread() throws InterruptedException { + IntervalFunction intervalFn = ofExponentialRandomBackoff(INITIAL_INTERVAL, MULTIPLIER, RANDOMIZATION_FACTOR); + test(intervalFn); + } + private void test(IntervalFunction intervalFn) throws InterruptedException { Function pingPongFn = getRetryablePingPongFn(intervalFn); ExecutorService executors = newFixedThreadPool(NUM_TASKS); From 8b2b894bbd37b10e504a1131bd4d40f09c5cbdf9 Mon Sep 17 00:00:00 2001 From: Paul Latzelsperger <43503240+beardyinc@users.noreply.github.com> Date: Mon, 22 Jul 2019 08:18:49 +0200 Subject: [PATCH 048/107] added example code for BAEL-3082 (#7374) --- .../failure_vs_error/SimpleCalculator.java | 15 +++++++++ .../SimpleCalculatorUnitTest.java | 32 +++++++++++++++++++ 2 files changed, 47 insertions(+) create mode 100644 testing-modules/junit-5-advanced/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java create mode 100644 testing-modules/junit-5-advanced/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java diff --git a/testing-modules/junit-5-advanced/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java b/testing-modules/junit-5-advanced/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java new file mode 100644 index 0000000000..d018aa939f --- /dev/null +++ b/testing-modules/junit-5-advanced/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java @@ -0,0 +1,15 @@ +package com.baeldung.failure_vs_error; + +/** + * @author paullatzelsperger + * @since 2019-07-17 + */ +public class SimpleCalculator { + + public static double divideNumbers(double dividend, double divisor) { + if (divisor == 0) { + throw new ArithmeticException("Division by zero!"); + } + return dividend / divisor; + } +} diff --git a/testing-modules/junit-5-advanced/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java b/testing-modules/junit-5-advanced/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java new file mode 100644 index 0000000000..9b1777258c --- /dev/null +++ b/testing-modules/junit-5-advanced/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java @@ -0,0 +1,32 @@ +package com.baeldung.failure_vs_error; + +import org.junit.jupiter.api.Disabled; +import org.junit.jupiter.api.Test; + +import static org.junit.jupiter.api.Assertions.assertEquals; + +/** + * @author paullatzelsperger + * @since 2019-07-17 + */ +class SimpleCalculatorUnitTest { + + @Test + void divideNumbers() { + double result = SimpleCalculator.divideNumbers(6, 3); + assertEquals(2, result); + } + + @Test + @Disabled("test is expected to fail, disabled so that CI build still goes through") + void divideNumbers_failure() { + double result = SimpleCalculator.divideNumbers(6, 3); + assertEquals(15, result); + } + + @Test + @Disabled("test is expected to raise an error, disabled so that CI build still goes through") + void divideNumbers_error() { + SimpleCalculator.divideNumbers(10, 0); + } +} From da152e53a1794e7d6f51a665c8cf827d1293717f Mon Sep 17 00:00:00 2001 From: dionisPrifti Date: Mon, 22 Jul 2019 19:53:15 +0200 Subject: [PATCH 049/107] Bael 2997 spring boot configuration processor (#7376) * BAEL-2997: Adding spring boot configuration processor dependency. * BAEL-2997: Added examples for spring boot configuration processor, simple and nested properties. * BAEL-2997: Fixed the identation * BAEL-2997: Formatted the added dependencies * BAEL-2997: Added version for configuration-processor dependency. --- spring-boot-autoconfiguration/pom.xml | 15 +++- .../AnnotationProcessorApplication.java | 15 ++++ .../DatabaseProperties.java | 73 +++++++++++++++++++ .../DatabasePropertiesIntegrationTest.java | 31 ++++++++ .../databaseproperties-test.properties | 7 ++ 5 files changed, 139 insertions(+), 2 deletions(-) create mode 100644 spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/AnnotationProcessorApplication.java create mode 100644 spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/DatabaseProperties.java create mode 100644 spring-boot-autoconfiguration/src/test/java/com/baeldung/autoconfiguration/annotationprocessor/DatabasePropertiesIntegrationTest.java create mode 100644 spring-boot-autoconfiguration/src/test/resources/databaseproperties-test.properties diff --git a/spring-boot-autoconfiguration/pom.xml b/spring-boot-autoconfiguration/pom.xml index 91692ebfff..5b3b0eb86c 100644 --- a/spring-boot-autoconfiguration/pom.xml +++ b/spring-boot-autoconfiguration/pom.xml @@ -38,6 +38,19 @@ mysql mysql-connector-java + + + org.springframework.boot + spring-boot-configuration-processor + 2.1.6.RELEASE + true + + + + org.hsqldb + hsqldb + runtime + @@ -50,12 +63,10 @@ - org.apache.maven.plugins maven-war-plugin - diff --git a/spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/AnnotationProcessorApplication.java b/spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/AnnotationProcessorApplication.java new file mode 100644 index 0000000000..91ea94e43e --- /dev/null +++ b/spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/AnnotationProcessorApplication.java @@ -0,0 +1,15 @@ +package com.baeldung.autoconfiguration.annotationprocessor; + +import org.springframework.boot.autoconfigure.EnableAutoConfiguration; +import org.springframework.boot.builder.SpringApplicationBuilder; +import org.springframework.context.annotation.ComponentScan; + +import com.baeldung.autoconfiguration.MySQLAutoconfiguration; + +@EnableAutoConfiguration(exclude = { MySQLAutoconfiguration.class}) +@ComponentScan(basePackageClasses = {DatabaseProperties.class}) +public class AnnotationProcessorApplication { + public static void main(String[] args) { + new SpringApplicationBuilder(AnnotationProcessorApplication.class).run(); + } +} diff --git a/spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/DatabaseProperties.java b/spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/DatabaseProperties.java new file mode 100644 index 0000000000..4fb5b408a2 --- /dev/null +++ b/spring-boot-autoconfiguration/src/main/java/com/baeldung/autoconfiguration/annotationprocessor/DatabaseProperties.java @@ -0,0 +1,73 @@ +package com.baeldung.autoconfiguration.annotationprocessor; + +import javax.validation.constraints.Max; +import javax.validation.constraints.Min; + +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.context.annotation.Configuration; + +@Configuration +@ConfigurationProperties(prefix = "database") +public class DatabaseProperties { + + public static class Server { + + /** + * The IP of the database server + */ + private String ip; + + /** + * The Port of the database server. + * The Default value is 443. + * The allowed values are in the range 400-4000. + */ + @Min(400) + @Max(800) + private int port = 443; + + public String getIp() { + return ip; + } + + public void setIp(String ip) { + this.ip = ip; + } + + public int getPort() { + return port; + } + + public void setPort(int port) { + this.port = port; + } + } + + private String username; + private String password; + private Server server; + + public String getUsername() { + return username; + } + + public void setUsername(String username) { + this.username = username; + } + + public String getPassword() { + return password; + } + + public void setPassword(String password) { + this.password = password; + } + + public Server getServer() { + return server; + } + + public void setServer(Server server) { + this.server = server; + } +} \ No newline at end of file diff --git a/spring-boot-autoconfiguration/src/test/java/com/baeldung/autoconfiguration/annotationprocessor/DatabasePropertiesIntegrationTest.java b/spring-boot-autoconfiguration/src/test/java/com/baeldung/autoconfiguration/annotationprocessor/DatabasePropertiesIntegrationTest.java new file mode 100644 index 0000000000..350e65b465 --- /dev/null +++ b/spring-boot-autoconfiguration/src/test/java/com/baeldung/autoconfiguration/annotationprocessor/DatabasePropertiesIntegrationTest.java @@ -0,0 +1,31 @@ +package com.baeldung.autoconfiguration.annotationprocessor; + +import org.junit.Assert; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.test.context.TestPropertySource; +import org.springframework.test.context.junit4.SpringRunner; + +@RunWith(SpringRunner.class) +@SpringBootTest(classes = AnnotationProcessorApplication.class) +@TestPropertySource("classpath:databaseproperties-test.properties") +public class DatabasePropertiesIntegrationTest { + + @Autowired + private DatabaseProperties databaseProperties; + + @Test + public void whenSimplePropertyQueriedThenReturnsPropertyValue() throws Exception { + Assert.assertEquals("Incorrectly bound Username property", "baeldung", databaseProperties.getUsername()); + Assert.assertEquals("Incorrectly bound Password property", "password", databaseProperties.getPassword()); + } + + @Test + public void whenNestedPropertyQueriedThenReturnsPropertyValue() throws Exception { + Assert.assertEquals("Incorrectly bound Server IP nested property", "127.0.0.1", databaseProperties.getServer().getIp()); + Assert.assertEquals("Incorrectly bound Server Port nested property", 3306, databaseProperties.getServer().getPort()); + } + +} diff --git a/spring-boot-autoconfiguration/src/test/resources/databaseproperties-test.properties b/spring-boot-autoconfiguration/src/test/resources/databaseproperties-test.properties new file mode 100644 index 0000000000..c0d1d1f158 --- /dev/null +++ b/spring-boot-autoconfiguration/src/test/resources/databaseproperties-test.properties @@ -0,0 +1,7 @@ +#Simple Properties +database.username=baeldung +database.password=password + +#Nested Properties +database.server.ip=127.0.0.1 +database.server.port=3306 \ No newline at end of file From cb686cf9c4f1587d729e66668ec9387631b4a1f9 Mon Sep 17 00:00:00 2001 From: priyank-sriv Date: Tue, 23 Jul 2019 01:52:22 +0530 Subject: [PATCH 050/107] minor modifications --- patterns/backoff-jitter/README.md | 2 ++ patterns/backoff-jitter/pom.xml | 7 ------- .../backoff/jitter/BackoffWithJitterTest.java | 12 ++++++------ 3 files changed, 8 insertions(+), 13 deletions(-) create mode 100644 patterns/backoff-jitter/README.md diff --git a/patterns/backoff-jitter/README.md b/patterns/backoff-jitter/README.md new file mode 100644 index 0000000000..6459e4c8e0 --- /dev/null +++ b/patterns/backoff-jitter/README.md @@ -0,0 +1,2 @@ +### Relevant Articles: +- [Better Retries with Exponential Backoff and Jitter](https://baeldung.com/retries-with-exponential-backoff-and-jitter) diff --git a/patterns/backoff-jitter/pom.xml b/patterns/backoff-jitter/pom.xml index 0a48a18abb..6b0d016609 100644 --- a/patterns/backoff-jitter/pom.xml +++ b/patterns/backoff-jitter/pom.xml @@ -8,13 +8,6 @@ 1.0.0-SNAPSHOT pom - - - - - - - junit diff --git a/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java index 0f0e652596..f6b3ebbe45 100644 --- a/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java +++ b/patterns/backoff-jitter/src/test/java/com/baeldung/backoff/jitter/BackoffWithJitterTest.java @@ -39,7 +39,7 @@ public class BackoffWithJitterTest { } private PingPongService service; - private static final int NUM_TASKS = 8; + private static final int NUM_CONCURRENT_CLIENTS = 8; @Before public void setUp() { @@ -55,7 +55,7 @@ public class BackoffWithJitterTest { try { pingPongFn.apply("Hello"); } catch (PingPongServiceException e) { - verify(service, times(MAX_TRIES)).call(anyString()); + verify(service, times(MAX_RETRIES)).call(anyString()); } } @@ -73,8 +73,8 @@ public class BackoffWithJitterTest { private void test(IntervalFunction intervalFn) throws InterruptedException { Function pingPongFn = getRetryablePingPongFn(intervalFn); - ExecutorService executors = newFixedThreadPool(NUM_TASKS); - List> tasks = nCopies(NUM_TASKS, () -> pingPongFn.apply("Hello")); + ExecutorService executors = newFixedThreadPool(NUM_CONCURRENT_CLIENTS); + List> tasks = nCopies(NUM_CONCURRENT_CLIENTS, () -> pingPongFn.apply("Hello")); when(service.call(anyString())).thenThrow(PingPongServiceException.class); @@ -83,7 +83,7 @@ public class BackoffWithJitterTest { private Function getRetryablePingPongFn(IntervalFunction intervalFn) { RetryConfig retryConfig = RetryConfig.custom() - .maxAttempts(MAX_TRIES) + .maxAttempts(MAX_RETRIES) .intervalFunction(intervalFn) .retryExceptions(PingPongServiceException.class) .build(); @@ -98,6 +98,6 @@ public class BackoffWithJitterTest { static final Long INITIAL_INTERVAL = 1000L; static final Double MULTIPLIER = 2.0D; static final Double RANDOMIZATION_FACTOR = 0.6D; - static final Integer MAX_TRIES = 4; + static final Integer MAX_RETRIES = 4; } } From 4bf6b77067b91fa8a53be84b0a2973e4a61165e6 Mon Sep 17 00:00:00 2001 From: Juan Moreno Date: Tue, 23 Jul 2019 00:16:48 -0300 Subject: [PATCH 051/107] Sample code for BAEL-2539 (#7238) * UPDATE Added junit5 & assertJ configuration in order to run tests * FEAT Added JaxpTransformer basic implementation * UPDATE Added JAXP polish version * UPDATE Polish jaxp implementation * FEAT Added complete JAXP Sample * FIX typo * Added additional samples and JMH benchmark * FIX indent in Joox sample --- xml/pom.xml | 100 +++++++++++++++--- .../xml/attribute/Dom4jTransformer.java | 45 ++++++++ .../xml/attribute/JaxpTransformer.java | 63 +++++++++++ .../xml/attribute/JooxTransformer.java | 38 +++++++ .../xml/attribute/jmh/AttributeBenchMark.java | 72 +++++++++++++ xml/src/main/resources/xml/attribute.xml | 5 + .../main/resources/xml/attribute_expected.xml | 5 + .../xml/attribute/Dom4jProcessorUnitTest.java | 55 ++++++++++ .../xml/attribute/JaxpProcessorUnitTest.java | 34 ++++++ .../xml/attribute/JooxProcessorUnitTest.java | 54 ++++++++++ xml/src/test/resources/xml/attribute.xml | 5 + .../test/resources/xml/attribute_expected.xml | 5 + 12 files changed, 469 insertions(+), 12 deletions(-) create mode 100644 xml/src/main/java/com/baeldung/xml/attribute/Dom4jTransformer.java create mode 100644 xml/src/main/java/com/baeldung/xml/attribute/JaxpTransformer.java create mode 100644 xml/src/main/java/com/baeldung/xml/attribute/JooxTransformer.java create mode 100644 xml/src/main/java/com/baeldung/xml/attribute/jmh/AttributeBenchMark.java create mode 100644 xml/src/main/resources/xml/attribute.xml create mode 100644 xml/src/main/resources/xml/attribute_expected.xml create mode 100644 xml/src/test/java/com/baeldung/xml/attribute/Dom4jProcessorUnitTest.java create mode 100644 xml/src/test/java/com/baeldung/xml/attribute/JaxpProcessorUnitTest.java create mode 100644 xml/src/test/java/com/baeldung/xml/attribute/JooxProcessorUnitTest.java create mode 100644 xml/src/test/resources/xml/attribute.xml create mode 100644 xml/src/test/resources/xml/attribute_expected.xml diff --git a/xml/pom.xml b/xml/pom.xml index 123875b1d9..540b1fc03b 100644 --- a/xml/pom.xml +++ b/xml/pom.xml @@ -1,4 +1,5 @@ - 4.0.0 xml @@ -14,7 +15,7 @@ - dom4j + org.dom4j dom4j ${dom4j.version} @@ -23,18 +24,31 @@ jaxen ${jaxen.version} - + + org.jooq + joox-java-6 + ${joox.version} + org.jdom jdom2 ${jdom2.version} - - javax.xml + javax.xml.bind jaxb-api ${jaxb-api.version} + + com.sun.xml.bind + jaxb-impl + ${jaxb-impl.version} + + + com.sun.xml.bind + jaxb-core + ${jaxb-core.version} + javax.xml jaxp-api @@ -45,7 +59,17 @@ stax-api ${stax-api.version} - + + + org.openjdk.jmh + jmh-core + ${jmh.version} + + + org.openjdk.jmh + jmh-generator-annprocess + ${jmh.version} + commons-io @@ -76,6 +100,31 @@ commons-lang ${commons-lang.version} + + + org.junit.jupiter + junit-jupiter + ${junit-jupiter.version} + test + + + org.junit.vintage + junit-vintage-engine + ${junit-jupiter.version} + test + + + org.assertj + assertj-core + ${assertj-core.version} + test + + + org.xmlunit + xmlunit-assertj + ${xmlunit-assertj.version} + test + @@ -86,6 +135,16 @@ true + + + maven-compiler-plugin + ${maven-compiler-plugin.version} + + + maven-surefire-plugin + ${maven-surefire-plugin.version} + + @@ -213,7 +272,8 @@ - + maven-assembly-plugin ${project.basedir} @@ -232,8 +292,10 @@ - make-assembly - package + make-assembly + package attached @@ -246,17 +308,31 @@ - 1.6.1 - 1.1.6 + 2.1.1 + 1.2.0 2.0.6 + 1.6.2 + 2.5 4.1 1.2.4.5 - 2.1 + 2.3.1 1.4.2 + 2.3.0.1 + 2.3.2 1.0-2 + 3.12.2 + 2.6.3 + 5.5.0 + 1.21 + + 3.5 + 2.4 + 1.8 1.3.1 + 3.8.0 + 2.22.2 diff --git a/xml/src/main/java/com/baeldung/xml/attribute/Dom4jTransformer.java b/xml/src/main/java/com/baeldung/xml/attribute/Dom4jTransformer.java new file mode 100644 index 0000000000..a1922ad224 --- /dev/null +++ b/xml/src/main/java/com/baeldung/xml/attribute/Dom4jTransformer.java @@ -0,0 +1,45 @@ +package com.baeldung.xml.attribute; + +import org.dom4j.*; +import org.dom4j.io.DocumentSource; +import org.dom4j.io.SAXReader; + +import javax.xml.XMLConstants; +import javax.xml.transform.OutputKeys; +import javax.xml.transform.Transformer; +import javax.xml.transform.TransformerException; +import javax.xml.transform.TransformerFactory; +import javax.xml.transform.stream.StreamResult; +import java.io.StringWriter; +import java.io.Writer; +import java.util.List; + +public class Dom4jTransformer { + private final Document input; + + public Dom4jTransformer(String resourcePath) throws DocumentException { + // 1- Build the doc from the XML file + SAXReader xmlReader = new SAXReader(); + this.input = xmlReader.read(resourcePath); + } + + public String modifyAttribute(String attribute, String oldValue, String newValue) throws TransformerException { + // 2- Locate the node(s) with xpath, we can use index and iterator too. + String expr = String.format("//*[contains(@%s, '%s')]", attribute, oldValue); + XPath xpath = DocumentHelper.createXPath(expr); + List nodes = xpath.selectNodes(input); + // 3- Make the change on the selected nodes + for (int i = 0; i < nodes.size(); i++) { + Element element = (Element) nodes.get(i); + element.addAttribute(attribute, newValue); + } + // 4- Save the result to a new XML doc + TransformerFactory factory = TransformerFactory.newInstance(); + factory.setFeature(XMLConstants.FEATURE_SECURE_PROCESSING, true); + Transformer xformer = factory.newTransformer(); + xformer.setOutputProperty(OutputKeys.INDENT, "yes"); + Writer output = new StringWriter(); + xformer.transform(new DocumentSource(input), new StreamResult(output)); + return output.toString(); + } +} diff --git a/xml/src/main/java/com/baeldung/xml/attribute/JaxpTransformer.java b/xml/src/main/java/com/baeldung/xml/attribute/JaxpTransformer.java new file mode 100644 index 0000000000..a2266a2b44 --- /dev/null +++ b/xml/src/main/java/com/baeldung/xml/attribute/JaxpTransformer.java @@ -0,0 +1,63 @@ +package com.baeldung.xml.attribute; + +import java.io.IOException; +import java.io.StringWriter; +import java.io.Writer; + +import javax.xml.XMLConstants; +import javax.xml.parsers.DocumentBuilderFactory; +import javax.xml.parsers.ParserConfigurationException; +import javax.xml.transform.OutputKeys; +import javax.xml.transform.Transformer; +import javax.xml.transform.TransformerException; +import javax.xml.transform.TransformerFactory; +import javax.xml.transform.TransformerFactoryConfigurationError; +import javax.xml.transform.dom.DOMSource; +import javax.xml.transform.stream.StreamResult; +import javax.xml.xpath.XPath; +import javax.xml.xpath.XPathConstants; +import javax.xml.xpath.XPathExpressionException; +import javax.xml.xpath.XPathFactory; + +import org.w3c.dom.Document; +import org.w3c.dom.Element; +import org.w3c.dom.NodeList; +import org.xml.sax.SAXException; + +public class JaxpTransformer { + + private Document input; + + public JaxpTransformer(String resourcePath) throws SAXException, IOException, ParserConfigurationException { + // 1- Build the doc from the XML file + DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); + factory.setFeature(XMLConstants.FEATURE_SECURE_PROCESSING, true); + input = factory.newDocumentBuilder() + .parse(resourcePath); + } + + public String modifyAttribute(String attribute, String oldValue, String newValue) throws XPathExpressionException, TransformerFactoryConfigurationError, TransformerException { + // 2- Locate the node(s) with xpath + XPath xpath = XPathFactory.newInstance() + .newXPath(); + NodeList nodes = (NodeList) xpath.evaluate(String.format("//*[contains(@%s, '%s')]", attribute, oldValue), input, XPathConstants.NODESET); + // 3- Make the change on the selected nodes + for (int i = 0; i < nodes.getLength(); i++) { + Element value = (Element) nodes.item(i); + value.setAttribute(attribute, newValue); + } + //Stream api syntax + // IntStream + // .range(0, nodes.getLength()) + // .mapToObj(i -> (Element) nodes.item(i)) + // .forEach(value -> value.setAttribute(attribute, newValue)); + // 4- Save the result to a new XML doc + TransformerFactory factory = TransformerFactory.newInstance(); + factory.setFeature(XMLConstants.FEATURE_SECURE_PROCESSING, true); + Transformer xformer = factory.newTransformer(); + xformer.setOutputProperty(OutputKeys.INDENT, "yes"); + Writer output = new StringWriter(); + xformer.transform(new DOMSource(input), new StreamResult(output)); + return output.toString(); + } +} diff --git a/xml/src/main/java/com/baeldung/xml/attribute/JooxTransformer.java b/xml/src/main/java/com/baeldung/xml/attribute/JooxTransformer.java new file mode 100644 index 0000000000..d36d60ec59 --- /dev/null +++ b/xml/src/main/java/com/baeldung/xml/attribute/JooxTransformer.java @@ -0,0 +1,38 @@ +package com.baeldung.xml.attribute; + +import org.joox.JOOX; +import org.joox.Match; +import org.w3c.dom.Document; +import org.xml.sax.SAXException; + +import javax.xml.parsers.DocumentBuilder; +import javax.xml.transform.TransformerFactoryConfigurationError; +import java.io.IOException; + +import static org.joox.JOOX.$; + +public class JooxTransformer { + + private final Document input; + + public JooxTransformer(String resourcePath) throws SAXException, IOException { + // 1- Build the doc from the XML file + DocumentBuilder builder = JOOX.builder(); + input = builder.parse(resourcePath); + } + + public String modifyAttribute(String attribute, String oldValue, String newValue) throws TransformerFactoryConfigurationError { + // 2- Select the document + Match $ = $(input); + // 3 - Find node to modify + String expr = String.format("//*[contains(@%s, '%s')]", attribute, oldValue); + $ + // .find("to") or with xpath + .xpath(expr) + .get() + .stream() + .forEach(e -> e.setAttribute(attribute, newValue)); + // 4- Return result as String + return $.toString(); + } +} diff --git a/xml/src/main/java/com/baeldung/xml/attribute/jmh/AttributeBenchMark.java b/xml/src/main/java/com/baeldung/xml/attribute/jmh/AttributeBenchMark.java new file mode 100644 index 0000000000..064e181713 --- /dev/null +++ b/xml/src/main/java/com/baeldung/xml/attribute/jmh/AttributeBenchMark.java @@ -0,0 +1,72 @@ +package com.baeldung.xml.attribute.jmh; + +import org.dom4j.DocumentException; +import org.openjdk.jmh.annotations.*; +import org.openjdk.jmh.runner.Runner; +import org.openjdk.jmh.runner.RunnerException; +import org.openjdk.jmh.runner.options.Options; +import org.openjdk.jmh.runner.options.OptionsBuilder; +import org.xml.sax.SAXException; + +import com.baeldung.xml.attribute.Dom4jTransformer; +import com.baeldung.xml.attribute.JaxpTransformer; +import com.baeldung.xml.attribute.JooxTransformer; + +import javax.xml.parsers.ParserConfigurationException; +import javax.xml.transform.TransformerException; +import javax.xml.xpath.XPathExpressionException; +import java.io.IOException; +import java.util.concurrent.TimeUnit; + +@BenchmarkMode(Mode.AverageTime) +@OutputTimeUnit(TimeUnit.MILLISECONDS) +@State(Scope.Benchmark) +public class AttributeBenchMark { + + public static void main(String[] args) throws RunnerException { + Options opt = new OptionsBuilder() + .include(AttributeBenchMark.class.getSimpleName()) + .forks(1) + .build(); + new Runner(opt).run(); + } + + @Benchmark + public String dom4jBenchmark() throws DocumentException, TransformerException { + String path = getClass() + .getResource("/xml/attribute.xml") + .toString(); + Dom4jTransformer transformer = new Dom4jTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + + return transformer.modifyAttribute(attribute, oldValue, newValue); + } + + @Benchmark + public String jooxBenchmark() throws IOException, SAXException { + String path = getClass() + .getResource("/xml/attribute.xml") + .toString(); + JooxTransformer transformer = new JooxTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + + return transformer.modifyAttribute(attribute, oldValue, newValue); + } + + @Benchmark + public String jaxpBenchmark() throws TransformerException, ParserConfigurationException, SAXException, IOException, XPathExpressionException { + String path = getClass() + .getResource("/xml/attribute.xml") + .toString(); + JaxpTransformer transformer = new JaxpTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + + return transformer.modifyAttribute(attribute, oldValue, newValue); + } +} diff --git a/xml/src/main/resources/xml/attribute.xml b/xml/src/main/resources/xml/attribute.xml new file mode 100644 index 0000000000..c8fa3f1071 --- /dev/null +++ b/xml/src/main/resources/xml/attribute.xml @@ -0,0 +1,5 @@ + + + john@email.com + mary@email.com + \ No newline at end of file diff --git a/xml/src/main/resources/xml/attribute_expected.xml b/xml/src/main/resources/xml/attribute_expected.xml new file mode 100644 index 0000000000..1d5d7b0cea --- /dev/null +++ b/xml/src/main/resources/xml/attribute_expected.xml @@ -0,0 +1,5 @@ + + + john@email.com + mary@email.com + \ No newline at end of file diff --git a/xml/src/test/java/com/baeldung/xml/attribute/Dom4jProcessorUnitTest.java b/xml/src/test/java/com/baeldung/xml/attribute/Dom4jProcessorUnitTest.java new file mode 100644 index 0000000000..485744f9a5 --- /dev/null +++ b/xml/src/test/java/com/baeldung/xml/attribute/Dom4jProcessorUnitTest.java @@ -0,0 +1,55 @@ +package com.baeldung.xml.attribute; + +import org.dom4j.DocumentException; +import org.junit.jupiter.api.Test; + +import javax.xml.transform.TransformerException; +import javax.xml.transform.TransformerFactoryConfigurationError; +import java.io.IOException; +import java.net.URISyntaxException; +import java.nio.file.Files; +import java.nio.file.Paths; + +import static org.xmlunit.assertj.XmlAssert.assertThat; + +/** + * Unit test for {@link Dom4jTransformer}. + */ +public class Dom4jProcessorUnitTest { + + @Test + public void givenXmlWithAttributes_whenModifyAttribute_thenGetXmlUpdated() throws TransformerFactoryConfigurationError, TransformerException, DocumentException { + String path = getClass() + .getResource("/xml/attribute.xml") + .toString(); + Dom4jTransformer transformer = new Dom4jTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + + String result = transformer.modifyAttribute(attribute, oldValue, newValue); + + assertThat(result).hasXPath("//*[contains(@customer, 'false')]"); + } + + @Test + public void givenTwoXml_whenModifyAttribute_thenGetSimilarXml() throws IOException, TransformerFactoryConfigurationError, TransformerException, URISyntaxException, DocumentException { + String path = getClass() + .getResource("/xml/attribute.xml") + .toString(); + Dom4jTransformer transformer = new Dom4jTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + String expectedXml = new String(Files.readAllBytes((Paths.get(getClass() + .getResource("/xml/attribute_expected.xml") + .toURI())))); + + String result = transformer.modifyAttribute(attribute, oldValue, newValue); + + assertThat(result) + .and(expectedXml) + .areSimilar(); + } + +} diff --git a/xml/src/test/java/com/baeldung/xml/attribute/JaxpProcessorUnitTest.java b/xml/src/test/java/com/baeldung/xml/attribute/JaxpProcessorUnitTest.java new file mode 100644 index 0000000000..8394016dbd --- /dev/null +++ b/xml/src/test/java/com/baeldung/xml/attribute/JaxpProcessorUnitTest.java @@ -0,0 +1,34 @@ +package com.baeldung.xml.attribute; + +import static org.xmlunit.assertj.XmlAssert.assertThat; + +import java.io.IOException; + +import javax.xml.parsers.ParserConfigurationException; +import javax.xml.transform.TransformerException; +import javax.xml.transform.TransformerFactoryConfigurationError; +import javax.xml.xpath.XPathExpressionException; + +import org.junit.jupiter.api.Test; +import org.xml.sax.SAXException; + +/** + * Unit test for {@link JaxpTransformer}. + */ +public class JaxpProcessorUnitTest { + + @Test + public void givenXmlWithAttributes_whenModifyAttribute_thenGetXmlUpdated() throws IOException, SAXException, ParserConfigurationException, XPathExpressionException, TransformerFactoryConfigurationError, TransformerException { + String path = getClass().getResource("/xml/attribute.xml") + .toString(); + JaxpTransformer transformer = new JaxpTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + + String result = transformer.modifyAttribute(attribute, oldValue, newValue); + + assertThat(result).hasXPath("//*[contains(@customer, 'false')]"); + } + +} diff --git a/xml/src/test/java/com/baeldung/xml/attribute/JooxProcessorUnitTest.java b/xml/src/test/java/com/baeldung/xml/attribute/JooxProcessorUnitTest.java new file mode 100644 index 0000000000..38c7c59789 --- /dev/null +++ b/xml/src/test/java/com/baeldung/xml/attribute/JooxProcessorUnitTest.java @@ -0,0 +1,54 @@ +package com.baeldung.xml.attribute; + +import org.junit.jupiter.api.Test; +import org.xml.sax.SAXException; + +import javax.xml.transform.TransformerFactoryConfigurationError; +import java.io.IOException; +import java.net.URISyntaxException; +import java.nio.file.Files; +import java.nio.file.Paths; + +import static org.xmlunit.assertj.XmlAssert.assertThat; + +/** + * Unit test for {@link JooxTransformer}. + */ +public class JooxProcessorUnitTest { + + @Test + public void givenXmlWithAttributes_whenModifyAttribute_thenGetXmlUpdated() throws IOException, SAXException, TransformerFactoryConfigurationError { + String path = getClass() + .getResource("/xml/attribute.xml") + .toString(); + JooxTransformer transformer = new JooxTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + + String result = transformer.modifyAttribute(attribute, oldValue, newValue); + + assertThat(result).hasXPath("//*[contains(@customer, 'false')]"); + } + + @Test + public void givenTwoXml_whenModifyAttribute_thenGetSimilarXml() throws IOException, TransformerFactoryConfigurationError, URISyntaxException, SAXException { + String path = getClass() + .getResource("/xml/attribute.xml") + .toString(); + JooxTransformer transformer = new JooxTransformer(path); + String attribute = "customer"; + String oldValue = "true"; + String newValue = "false"; + String expectedXml = new String(Files.readAllBytes((Paths.get(getClass() + .getResource("/xml/attribute_expected.xml") + .toURI())))); + + String result = transformer.modifyAttribute(attribute, oldValue, newValue); + + assertThat(result) + .and(expectedXml) + .areSimilar(); + } + +} diff --git a/xml/src/test/resources/xml/attribute.xml b/xml/src/test/resources/xml/attribute.xml new file mode 100644 index 0000000000..c8fa3f1071 --- /dev/null +++ b/xml/src/test/resources/xml/attribute.xml @@ -0,0 +1,5 @@ + + + john@email.com + mary@email.com + \ No newline at end of file diff --git a/xml/src/test/resources/xml/attribute_expected.xml b/xml/src/test/resources/xml/attribute_expected.xml new file mode 100644 index 0000000000..1d5d7b0cea --- /dev/null +++ b/xml/src/test/resources/xml/attribute_expected.xml @@ -0,0 +1,5 @@ + + + john@email.com + mary@email.com + \ No newline at end of file From dd0003a478ab37c80e1e5ea7f706fe9a92e5338f Mon Sep 17 00:00:00 2001 From: cdjole Date: Tue, 23 Jul 2019 07:36:04 +0200 Subject: [PATCH 052/107] Shell sort (#7391) * Shell sort * Add new line at the end --- .../algorithms/shellsort/ShellSort.java | 20 +++++++++++++++++++ .../shellsort/ShellSortUnitTest.java | 17 ++++++++++++++++ 2 files changed, 37 insertions(+) create mode 100644 algorithms-sorting/src/main/java/com/baeldung/algorithms/shellsort/ShellSort.java create mode 100644 algorithms-sorting/src/test/java/com/baeldung/algorithms/shellsort/ShellSortUnitTest.java diff --git a/algorithms-sorting/src/main/java/com/baeldung/algorithms/shellsort/ShellSort.java b/algorithms-sorting/src/main/java/com/baeldung/algorithms/shellsort/ShellSort.java new file mode 100644 index 0000000000..c130e2d866 --- /dev/null +++ b/algorithms-sorting/src/main/java/com/baeldung/algorithms/shellsort/ShellSort.java @@ -0,0 +1,20 @@ +package com.baeldung.algorithms.shellsort; + +public class ShellSort { + + public static void sort(int arrayToSort[]) { + int n = arrayToSort.length; + + for (int gap = n / 2; gap > 0; gap /= 2) { + for (int i = gap; i < n; i++) { + int key = arrayToSort[i]; + int j = i; + while (j >= gap && arrayToSort[j - gap] > key) { + arrayToSort[j] = arrayToSort[j - gap]; + j -= gap; + } + arrayToSort[j] = key; + } + } + } +} diff --git a/algorithms-sorting/src/test/java/com/baeldung/algorithms/shellsort/ShellSortUnitTest.java b/algorithms-sorting/src/test/java/com/baeldung/algorithms/shellsort/ShellSortUnitTest.java new file mode 100644 index 0000000000..91a27c41d0 --- /dev/null +++ b/algorithms-sorting/src/test/java/com/baeldung/algorithms/shellsort/ShellSortUnitTest.java @@ -0,0 +1,17 @@ +package com.baeldung.algorithms.shellsort; + +import static org.junit.Assert.*; +import static org.junit.Assert.assertArrayEquals; + +import org.junit.Test; + +public class ShellSortUnitTest { + + @Test + public void givenUnsortedArray_whenShellSort_thenSortedAsc() { + int[] input = {41, 15, 82, 5, 65, 19, 32, 43, 8}; + ShellSort.sort(input); + int[] expected = {5, 8, 15, 19, 32, 41, 43, 65, 82}; + assertArrayEquals("the two arrays are not equal", expected, input); + } +} From b6de1db857aec5368fe74cae9396fa0cb452bb77 Mon Sep 17 00:00:00 2001 From: eelhazati Date: Tue, 23 Jul 2019 09:09:56 +0100 Subject: [PATCH 053/107] add refresh token feature. --- .../server/api/TokenEndpoint.java | 4 +- .../handler/AbstractGrantTypeHandler.java | 87 +++++++++++++++++++ .../AuthorizationCodeGrantTypeHandler.java | 53 +---------- .../handler/RefreshTokenGrantTypeHandler.java | 64 ++++++++++++++ .../oauth2/client/AbstractServlet.java | 23 +++++ .../oauth2/client/CallbackServlet.java | 3 + .../oauth2/client/RefreshTokenServlet.java | 52 +++++++++++ .../oauth2-client/src/main/webapp/index.jsp | 16 +++- 8 files changed, 250 insertions(+), 52 deletions(-) create mode 100644 oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AbstractGrantTypeHandler.java create mode 100644 oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java create mode 100644 oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/AbstractServlet.java create mode 100644 oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java index f39bb2ea2d..df4011ddc1 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java @@ -15,15 +15,15 @@ import javax.ws.rs.core.HttpHeaders; import javax.ws.rs.core.MediaType; import javax.ws.rs.core.MultivaluedMap; import javax.ws.rs.core.Response; +import java.util.Arrays; import java.util.Base64; -import java.util.Collections; import java.util.List; import java.util.Objects; @Path("token") public class TokenEndpoint { - List supportedGrantTypes = Collections.singletonList("authorization_code"); + List supportedGrantTypes = Arrays.asList("authorization_code", "refresh_token"); @Inject private AppDataRepository appDataRepository; diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AbstractGrantTypeHandler.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AbstractGrantTypeHandler.java new file mode 100644 index 0000000000..324bacb33f --- /dev/null +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AbstractGrantTypeHandler.java @@ -0,0 +1,87 @@ +package com.baeldung.oauth2.authorization.server.handler; + +import com.baeldung.oauth2.authorization.server.PEMKeyUtils; +import com.nimbusds.jose.*; +import com.nimbusds.jose.crypto.RSASSASigner; +import com.nimbusds.jose.crypto.RSASSAVerifier; +import com.nimbusds.jose.jwk.JWK; +import com.nimbusds.jose.jwk.RSAKey; +import com.nimbusds.jwt.JWTClaimsSet; +import com.nimbusds.jwt.SignedJWT; +import org.eclipse.microprofile.config.Config; + +import javax.inject.Inject; +import java.time.Instant; +import java.time.temporal.ChronoUnit; +import java.util.Arrays; +import java.util.Date; +import java.util.UUID; + +public abstract class AbstractGrantTypeHandler implements AuthorizationGrantTypeHandler { + + //Always RSA 256, but could be parametrized + protected JWSHeader jwsHeader = new JWSHeader.Builder(JWSAlgorithm.RS256).type(JOSEObjectType.JWT).build(); + + @Inject + protected Config config; + + //30 min + protected Long expiresInMin = 30L; + + protected JWSVerifier getJWSVerifier() throws Exception { + String verificationkey = config.getValue("verificationkey", String.class); + String pemEncodedRSAPublicKey = PEMKeyUtils.readKeyAsString(verificationkey); + RSAKey rsaPublicKey = (RSAKey) JWK.parseFromPEMEncodedObjects(pemEncodedRSAPublicKey); + return new RSASSAVerifier(rsaPublicKey); + } + + protected JWSSigner getJwsSigner() throws Exception { + String signingkey = config.getValue("signingkey", String.class); + String pemEncodedRSAPrivateKey = PEMKeyUtils.readKeyAsString(signingkey); + RSAKey rsaKey = (RSAKey) JWK.parseFromPEMEncodedObjects(pemEncodedRSAPrivateKey); + return new RSASSASigner(rsaKey.toRSAPrivateKey()); + } + + protected String getAccessToken(String clientId, String subject, String approvedScope) throws Exception { + //4. Signing + JWSSigner jwsSigner = getJwsSigner(); + + Instant now = Instant.now(); + //Long expiresInMin = 30L; + Date expirationTime = Date.from(now.plus(expiresInMin, ChronoUnit.MINUTES)); + + //3. JWT Payload or claims + JWTClaimsSet jwtClaims = new JWTClaimsSet.Builder() + .issuer("http://localhost:9080") + .subject(subject) + .claim("upn", subject) + .claim("client_id", clientId) + .audience("http://localhost:9280") + .claim("scope", approvedScope) + .claim("groups", Arrays.asList(approvedScope.split(" "))) + .expirationTime(expirationTime) // expires in 30 minutes + .notBeforeTime(Date.from(now)) + .issueTime(Date.from(now)) + .jwtID(UUID.randomUUID().toString()) + .build(); + SignedJWT signedJWT = new SignedJWT(jwsHeader, jwtClaims); + signedJWT.sign(jwsSigner); + return signedJWT.serialize(); + } + + protected String getRefreshToken(String clientId, String subject, String approvedScope) throws Exception { + JWSSigner jwsSigner = getJwsSigner(); + Instant now = Instant.now(); + //6.Build refresh token + JWTClaimsSet refreshTokenClaims = new JWTClaimsSet.Builder() + .subject(subject) + .claim("client_id", clientId) + .claim("scope", approvedScope) + //refresh token for 1 day. + .expirationTime(Date.from(now.plus(1, ChronoUnit.DAYS))) + .build(); + SignedJWT signedRefreshToken = new SignedJWT(jwsHeader, refreshTokenClaims); + signedRefreshToken.sign(jwsSigner); + return signedRefreshToken.serialize(); + } +} diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AuthorizationCodeGrantTypeHandler.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AuthorizationCodeGrantTypeHandler.java index 889c7fcea2..78128aead6 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AuthorizationCodeGrantTypeHandler.java +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/AuthorizationCodeGrantTypeHandler.java @@ -1,18 +1,7 @@ package com.baeldung.oauth2.authorization.server.handler; -import com.baeldung.oauth2.authorization.server.PEMKeyUtils; import com.baeldung.oauth2.authorization.server.model.AuthorizationCode; -import com.nimbusds.jose.JOSEObjectType; -import com.nimbusds.jose.JWSAlgorithm; -import com.nimbusds.jose.JWSHeader; -import com.nimbusds.jose.crypto.RSASSASigner; -import com.nimbusds.jose.jwk.JWK; -import com.nimbusds.jose.jwk.RSAKey; -import com.nimbusds.jwt.JWTClaimsSet; -import com.nimbusds.jwt.SignedJWT; -import org.eclipse.microprofile.config.Config; -import javax.inject.Inject; import javax.inject.Named; import javax.json.Json; import javax.json.JsonObject; @@ -20,22 +9,14 @@ import javax.persistence.EntityManager; import javax.persistence.PersistenceContext; import javax.ws.rs.WebApplicationException; import javax.ws.rs.core.MultivaluedMap; -import java.time.Instant; import java.time.LocalDateTime; -import java.time.temporal.ChronoUnit; -import java.util.Arrays; -import java.util.Date; -import java.util.UUID; @Named("authorization_code") -public class AuthorizationCodeGrantTypeHandler implements AuthorizationGrantTypeHandler { +public class AuthorizationCodeGrantTypeHandler extends AbstractGrantTypeHandler { @PersistenceContext private EntityManager entityManager; - @Inject - private Config config; - @Override public JsonObject createAccessToken(String clientId, MultivaluedMap params) throws Exception { //1. code is required @@ -58,42 +39,16 @@ public class AuthorizationCodeGrantTypeHandler implements AuthorizationGrantType throw new WebApplicationException("invalid_grant"); } - //JWT Header - JWSHeader jwsHeader = new JWSHeader.Builder(JWSAlgorithm.RS256).type(JOSEObjectType.JWT).build(); - - Instant now = Instant.now(); - Long expiresInMin = 30L; - Date expiresIn = Date.from(now.plus(expiresInMin, ChronoUnit.MINUTES)); - //3. JWT Payload or claims - JWTClaimsSet jwtClaims = new JWTClaimsSet.Builder() - .issuer("http://localhost:9080") - .subject(authorizationCode.getUserId()) - .claim("upn", authorizationCode.getUserId()) - .audience("http://localhost:9280") - .claim("scope", authorizationCode.getApprovedScopes()) - .claim("groups", Arrays.asList(authorizationCode.getApprovedScopes().split(" "))) - .expirationTime(expiresIn) // expires in 30 minutes - .notBeforeTime(Date.from(now)) - .issueTime(Date.from(now)) - .jwtID(UUID.randomUUID().toString()) - .build(); - SignedJWT signedJWT = new SignedJWT(jwsHeader, jwtClaims); - - //4. Signing - String signingkey = config.getValue("signingkey", String.class); - String pemEncodedRSAPrivateKey = PEMKeyUtils.readKeyAsString(signingkey); - RSAKey rsaKey = (RSAKey) JWK.parseFromPEMEncodedObjects(pemEncodedRSAPrivateKey); - signedJWT.sign(new RSASSASigner(rsaKey.toRSAPrivateKey())); - - //5. Finally the JWT access token - String accessToken = signedJWT.serialize(); + String accessToken = getAccessToken(clientId, authorizationCode.getUserId(), authorizationCode.getApprovedScopes()); + String refreshToken = getRefreshToken(clientId, authorizationCode.getUserId(), authorizationCode.getApprovedScopes()); return Json.createObjectBuilder() .add("token_type", "Bearer") .add("access_token", accessToken) .add("expires_in", expiresInMin * 60) .add("scope", authorizationCode.getApprovedScopes()) + .add("refresh_token", refreshToken) .build(); } } diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java new file mode 100644 index 0000000000..27c0ed4427 --- /dev/null +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java @@ -0,0 +1,64 @@ +package com.baeldung.oauth2.authorization.server.handler; + +import com.nimbusds.jose.JWSVerifier; +import com.nimbusds.jwt.SignedJWT; + +import javax.inject.Named; +import javax.json.Json; +import javax.json.JsonObject; +import javax.ws.rs.WebApplicationException; +import javax.ws.rs.core.MultivaluedMap; +import java.util.*; + +@Named("refresh_token") +public class RefreshTokenGrantTypeHandler extends AbstractGrantTypeHandler { + + @Override + public JsonObject createAccessToken(String clientId, MultivaluedMap params) throws Exception { + String refreshToken = params.getFirst("refresh_token"); + if (refreshToken == null || "".equals(refreshToken)) { + throw new WebApplicationException("invalid_grant"); + } + + //Decode refresh token + SignedJWT signedRefreshToken = SignedJWT.parse(refreshToken); + JWSVerifier verifier = getJWSVerifier(); + + if (!signedRefreshToken.verify(verifier)) { + throw new WebApplicationException("Invalid refresh token."); + } + if (!(new Date().before(signedRefreshToken.getJWTClaimsSet().getExpirationTime()))) { + throw new WebApplicationException("Refresh token expired."); + } + String refreshTokenClientId = signedRefreshToken.getJWTClaimsSet().getStringClaim("client_id"); + if (!clientId.equals(refreshTokenClientId)) { + throw new WebApplicationException("Invalid client_id."); + } + + //At this point, the refresh token is valid and not yet expired + //So create a new access token from it. + String subject = signedRefreshToken.getJWTClaimsSet().getSubject(); + String approvedScopes = signedRefreshToken.getJWTClaimsSet().getStringClaim("scope"); + + String finalScope = approvedScopes; + String requestedScopes = params.getFirst("scope"); + if (requestedScopes != null && !requestedScopes.isEmpty()) { + Set allowedScopes = new LinkedHashSet<>(); + Set rScopes = new HashSet(Arrays.asList(requestedScopes.split(" "))); + Set aScopes = new HashSet(Arrays.asList(approvedScopes.split(" "))); + for (String scope : rScopes) { + if (aScopes.contains(scope)) allowedScopes.add(scope); + } + finalScope = String.join(" ", allowedScopes); + } + + String accessToken = getAccessToken(clientId, subject, finalScope); + return Json.createObjectBuilder() + .add("token_type", "Bearer") + .add("access_token", accessToken) + .add("expires_in", expiresInMin * 60) + .add("scope", finalScope) + .add("refresh_token", refreshToken) + .build(); + } +} diff --git a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/AbstractServlet.java b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/AbstractServlet.java new file mode 100644 index 0000000000..7059c4f7e1 --- /dev/null +++ b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/AbstractServlet.java @@ -0,0 +1,23 @@ +package com.baeldung.oauth2.client; + +import javax.servlet.RequestDispatcher; +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import java.io.IOException; +import java.util.Base64; + +public abstract class AbstractServlet extends HttpServlet { + + protected void dispatch(String location, HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { + RequestDispatcher requestDispatcher = request.getRequestDispatcher(location); + requestDispatcher.forward(request, response); + } + + protected String getAuthorizationHeaderValue(String clientId, String clientSecret) { + String token = clientId + ":" + clientSecret; + String encodedString = Base64.getEncoder().encodeToString(token.getBytes()); + return "Basic " + encodedString; + } +} diff --git a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java index 87aa8bc668..a172d20235 100644 --- a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java +++ b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java @@ -29,6 +29,9 @@ public class CallbackServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { + String clientId = config.getValue("client.clientId", String.class); + String clientSecret = config.getValue("client.clientSecret", String.class); + //Error: String error = request.getParameter("error"); if (error != null) { diff --git a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java new file mode 100644 index 0000000000..2cfadc700f --- /dev/null +++ b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java @@ -0,0 +1,52 @@ +package com.baeldung.oauth2.client; + +import org.eclipse.microprofile.config.Config; + +import javax.inject.Inject; +import javax.json.JsonObject; +import javax.servlet.ServletException; +import javax.servlet.annotation.WebServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import javax.ws.rs.client.Client; +import javax.ws.rs.client.ClientBuilder; +import javax.ws.rs.client.Entity; +import javax.ws.rs.client.WebTarget; +import javax.ws.rs.core.Form; +import javax.ws.rs.core.HttpHeaders; +import javax.ws.rs.core.MediaType; +import java.io.IOException; + +@WebServlet(urlPatterns = "/refreshtoken") +public class RefreshTokenServlet extends AbstractServlet { + + @Inject + private Config config; + + @Override + protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { + + String clientId = config.getValue("client.clientId", String.class); + String clientSecret = config.getValue("client.clientSecret", String.class); + + JsonObject actualTokenResponse = (JsonObject) request.getSession().getAttribute("tokenResponse"); + Client client = ClientBuilder.newClient(); + WebTarget target = client.target(config.getValue("provider.tokenUri", String.class)); + + Form form = new Form(); + form.param("grant_type", "refresh_token"); + form.param("refresh_token", actualTokenResponse.getString("refresh_token")); + + String scope = request.getParameter("scope"); + if (scope != null && !scope.isEmpty()) { + form.param("scope", scope); + } + + JsonObject tokenResponse = target.request(MediaType.APPLICATION_JSON_TYPE) + .header(HttpHeaders.AUTHORIZATION, getAuthorizationHeaderValue(clientId, clientSecret)) + .post(Entity.entity(form, MediaType.APPLICATION_FORM_URLENCODED_TYPE), JsonObject.class); + + request.getSession().setAttribute("tokenResponse", tokenResponse); + dispatch("/", request, response); + } +} diff --git a/oauth2-framework-impl/oauth2-client/src/main/webapp/index.jsp b/oauth2-framework-impl/oauth2-client/src/main/webapp/index.jsp index 23fec70f33..ccb74df228 100644 --- a/oauth2-framework-impl/oauth2-client/src/main/webapp/index.jsp +++ b/oauth2-framework-impl/oauth2-client/src/main/webapp/index.jsp @@ -10,6 +10,7 @@ body { margin: 0px; } + input[type=text], input[type=password] { width: 75%; padding: 4px 0px; @@ -17,6 +18,7 @@ border: 1px solid #502bcc; box-sizing: border-box; } + .container-error { padding: 16px; border: 1px solid #cc102a; @@ -25,6 +27,7 @@ margin-left: 25px; margin-bottom: 25px; } + .container { padding: 16px; border: 1px solid #130ecc; @@ -81,8 +84,20 @@
  • access_token: ${tokenResponse.getString("access_token")}
  • scope: ${tokenResponse.getString("scope")}
  • Expires in (s): ${tokenResponse.getInt("expires_in")}
  • +
  • refresh_token: ${tokenResponse.getString("refresh_token")}
  • + + +

    OAuth2 Resource Server Call


    @@ -90,7 +105,6 @@
  • Read Protected Resource
  • Write Protected Resource
  • -
    From 7486f1a305855f3c27c3dacae97365a9dc3efc8b Mon Sep 17 00:00:00 2001 From: eelhazati Date: Tue, 23 Jul 2019 09:24:25 +0100 Subject: [PATCH 054/107] scope in refresh token request should be a subset of those authorized by the resource owner. --- .../handler/RefreshTokenGrantTypeHandler.java | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java index 27c0ed4427..513bcc2cf0 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java @@ -8,7 +8,10 @@ import javax.json.Json; import javax.json.JsonObject; import javax.ws.rs.WebApplicationException; import javax.ws.rs.core.MultivaluedMap; -import java.util.*; +import java.util.Arrays; +import java.util.Date; +import java.util.HashSet; +import java.util.Set; @Named("refresh_token") public class RefreshTokenGrantTypeHandler extends AbstractGrantTypeHandler { @@ -40,24 +43,23 @@ public class RefreshTokenGrantTypeHandler extends AbstractGrantTypeHandler { String subject = signedRefreshToken.getJWTClaimsSet().getSubject(); String approvedScopes = signedRefreshToken.getJWTClaimsSet().getStringClaim("scope"); - String finalScope = approvedScopes; String requestedScopes = params.getFirst("scope"); if (requestedScopes != null && !requestedScopes.isEmpty()) { - Set allowedScopes = new LinkedHashSet<>(); Set rScopes = new HashSet(Arrays.asList(requestedScopes.split(" "))); Set aScopes = new HashSet(Arrays.asList(approvedScopes.split(" "))); - for (String scope : rScopes) { - if (aScopes.contains(scope)) allowedScopes.add(scope); + if (!aScopes.containsAll(rScopes)) { + throw new WebApplicationException("Requested scopes should be a subset of those authorized by the resource owner."); } - finalScope = String.join(" ", allowedScopes); + } else { + requestedScopes = approvedScopes; } - String accessToken = getAccessToken(clientId, subject, finalScope); + String accessToken = getAccessToken(clientId, subject, requestedScopes); return Json.createObjectBuilder() .add("token_type", "Bearer") .add("access_token", accessToken) .add("expires_in", expiresInMin * 60) - .add("scope", finalScope) + .add("scope", requestedScopes) .add("refresh_token", refreshToken) .build(); } From e314cddbe66eb1c063369f1b460792b19682547d Mon Sep 17 00:00:00 2001 From: eelhazati Date: Tue, 23 Jul 2019 10:03:17 +0100 Subject: [PATCH 055/107] scope in refresh token request should be a subset of those authorized by the resource owner. --- .../oauth2/client/CallbackServlet.java | 32 ++++++------------- .../oauth2/client/RefreshTokenServlet.java | 7 +++- 2 files changed, 16 insertions(+), 23 deletions(-) diff --git a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java index a172d20235..e72877076c 100644 --- a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java +++ b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/CallbackServlet.java @@ -4,10 +4,8 @@ import org.eclipse.microprofile.config.Config; import javax.inject.Inject; import javax.json.JsonObject; -import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.annotation.WebServlet; -import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.ws.rs.client.Client; @@ -18,10 +16,9 @@ import javax.ws.rs.core.Form; import javax.ws.rs.core.HttpHeaders; import javax.ws.rs.core.MediaType; import java.io.IOException; -import java.util.Base64; @WebServlet(urlPatterns = "/callback") -public class CallbackServlet extends HttpServlet { +public class CallbackServlet extends AbstractServlet { @Inject private Config config; @@ -56,24 +53,15 @@ public class CallbackServlet extends HttpServlet { form.param("code", code); form.param("redirect_uri", config.getValue("client.redirectUri", String.class)); - JsonObject tokenResponse = target.request(MediaType.APPLICATION_JSON_TYPE) - .header(HttpHeaders.AUTHORIZATION, getAuthorizationHeaderValue()) - .post(Entity.entity(form, MediaType.APPLICATION_FORM_URLENCODED_TYPE), JsonObject.class); - - request.getSession().setAttribute("tokenResponse", tokenResponse); + try { + JsonObject tokenResponse = target.request(MediaType.APPLICATION_JSON_TYPE) + .header(HttpHeaders.AUTHORIZATION, getAuthorizationHeaderValue(clientId, clientSecret)) + .post(Entity.entity(form, MediaType.APPLICATION_FORM_URLENCODED_TYPE), JsonObject.class); + request.getSession().setAttribute("tokenResponse", tokenResponse); + } catch (Exception ex) { + System.out.println(ex.getMessage()); + request.setAttribute("error", ex.getMessage()); + } dispatch("/", request, response); } - - private void dispatch(String location, HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { - RequestDispatcher requestDispatcher = request.getRequestDispatcher(location); - requestDispatcher.forward(request, response); - } - - private String getAuthorizationHeaderValue() { - String clientId = config.getValue("client.clientId", String.class); - String clientSecret = config.getValue("client.clientSecret", String.class); - String token = clientId + ":" + clientSecret; - String encodedString = Base64.getEncoder().encodeToString(token.getBytes()); - return "Basic " + encodedString; - } } diff --git a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java index 2cfadc700f..b9fd7a4a21 100644 --- a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java +++ b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java @@ -46,7 +46,12 @@ public class RefreshTokenServlet extends AbstractServlet { .header(HttpHeaders.AUTHORIZATION, getAuthorizationHeaderValue(clientId, clientSecret)) .post(Entity.entity(form, MediaType.APPLICATION_FORM_URLENCODED_TYPE), JsonObject.class); - request.getSession().setAttribute("tokenResponse", tokenResponse); + String error = tokenResponse.getString("error"); + if (error != null) { + request.setAttribute("error", error); + } else { + request.getSession().setAttribute("tokenResponse", tokenResponse); + } dispatch("/", request, response); } } From 5903f4b60f3b7d0b1a2f46774051c6d0377bfaaf Mon Sep 17 00:00:00 2001 From: Carlos Cano Date: Tue, 23 Jul 2019 13:48:24 +0200 Subject: [PATCH 056/107] [BAEL-3041] Spring boot mysql timezone (#7154) * testing with user CRUD * update project * rename location * delete maven files --- .../spring-boot-mysql/.gitignore | 5 ++ persistence-modules/spring-boot-mysql/pom.xml | 59 +++++++++++++++++++ .../java/com/baeldung/boot/Application.java | 20 +++++++ .../java/com/baeldung/boot/Controller.java | 27 +++++++++ .../src/main/java/com/baeldung/boot/User.java | 40 +++++++++++++ .../com/baeldung/boot/UserRepository.java | 10 ++++ .../src/main/resources/application.yml | 14 +++++ 7 files changed, 175 insertions(+) create mode 100644 persistence-modules/spring-boot-mysql/.gitignore create mode 100644 persistence-modules/spring-boot-mysql/pom.xml create mode 100644 persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Application.java create mode 100644 persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Controller.java create mode 100644 persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/User.java create mode 100644 persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/UserRepository.java create mode 100644 persistence-modules/spring-boot-mysql/src/main/resources/application.yml diff --git a/persistence-modules/spring-boot-mysql/.gitignore b/persistence-modules/spring-boot-mysql/.gitignore new file mode 100644 index 0000000000..96136ab255 --- /dev/null +++ b/persistence-modules/spring-boot-mysql/.gitignore @@ -0,0 +1,5 @@ +/target/ +.settings/ +.classpath +.project +.mvn/ \ No newline at end of file diff --git a/persistence-modules/spring-boot-mysql/pom.xml b/persistence-modules/spring-boot-mysql/pom.xml new file mode 100644 index 0000000000..6be58332aa --- /dev/null +++ b/persistence-modules/spring-boot-mysql/pom.xml @@ -0,0 +1,59 @@ + + + 4.0.0 + spring-boot-mysql + 0.1.0 + spring-boot-mysql + + + parent-boot-2 + com.baeldung + 0.0.1-SNAPSHOT + ../../parent-boot-2 + + + + + org.springframework.boot + spring-boot-starter-web + 2.1.5.RELEASE + + + org.springframework.boot + spring-boot-starter-data-jpa + + + org.springframework.boot + spring-boot-starter-test + + + org.springframework.boot + spring-boot-devtools + true + + + mysql + mysql-connector-java + + + + + spring-boot-mysql-timezone + + + src/main/resources + true + + + + + + + + + UTF-8 + 8.0.12 + + + diff --git a/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Application.java b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Application.java new file mode 100644 index 0000000000..d69f66fc7a --- /dev/null +++ b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Application.java @@ -0,0 +1,20 @@ +package com.baeldung.boot; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +import javax.annotation.PostConstruct; +import java.util.TimeZone; + +@SpringBootApplication +public class Application { + + @PostConstruct + void started() { + TimeZone.setDefault(TimeZone.getTimeZone("UTC")); + } + + public static void main(String[] args) { + SpringApplication.run(Application.class, args); + } +} diff --git a/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Controller.java b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Controller.java new file mode 100644 index 0000000000..48864269fe --- /dev/null +++ b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/Controller.java @@ -0,0 +1,27 @@ +package com.baeldung.boot; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RestController; + +import java.util.List; + +@RestController +public class Controller { + + @Autowired + UserRepository userRepository; + + @GetMapping + public User get() { + User user = new User(); + userRepository.save(user); + return user; + } + + @GetMapping("/find") + public List find() { + List users = userRepository.findAll(); + return users; + } +} diff --git a/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/User.java b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/User.java new file mode 100644 index 0000000000..55cb97dec2 --- /dev/null +++ b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/User.java @@ -0,0 +1,40 @@ +package com.baeldung.boot; + + +import org.springframework.data.annotation.CreatedDate; + +import javax.persistence.*; +import java.util.Date; + +@Entity +public class User { + @Id + @GeneratedValue(strategy = GenerationType.AUTO) + private Integer id; + + @Column + private String name; + + @CreatedDate + private Date createdDate = new Date(); + + public Date getCreatedDate() { + return createdDate; + } + + public Integer getId() { + return id; + } + + public void setId(Integer id) { + this.id = id; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } +} diff --git a/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/UserRepository.java b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/UserRepository.java new file mode 100644 index 0000000000..3c50c30cce --- /dev/null +++ b/persistence-modules/spring-boot-mysql/src/main/java/com/baeldung/boot/UserRepository.java @@ -0,0 +1,10 @@ +package com.baeldung.boot; + +import org.springframework.data.jpa.repository.JpaRepository; +import org.springframework.stereotype.Repository; + +import java.io.Serializable; + +@Repository +public interface UserRepository extends JpaRepository { +} diff --git a/persistence-modules/spring-boot-mysql/src/main/resources/application.yml b/persistence-modules/spring-boot-mysql/src/main/resources/application.yml new file mode 100644 index 0000000000..5404555d49 --- /dev/null +++ b/persistence-modules/spring-boot-mysql/src/main/resources/application.yml @@ -0,0 +1,14 @@ +spring: + datasource: + url: jdbc:mysql://localhost:3306/test?useLegacyDatetimeCode=false + username: root + password: + + jpa: + hibernate: + ddl-auto: update + properties: + hibernate: + dialect: org.hibernate.dialect.MySQL5Dialect + jdbc: + time_zone: UTC \ No newline at end of file From b6b90f556af9099e0e0db47a151fa5f0ca4dcb4c Mon Sep 17 00:00:00 2001 From: "EZZEDDINE.ELHAZATI" Date: Tue, 23 Jul 2019 13:26:23 +0100 Subject: [PATCH 057/107] refactoring. --- .../server/api/TokenEndpoint.java | 42 +++++++++++-------- 1 file changed, 24 insertions(+), 18 deletions(-) diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java index df4011ddc1..4716c1bb26 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java @@ -18,7 +18,6 @@ import javax.ws.rs.core.Response; import java.util.Arrays; import java.util.Base64; import java.util.List; -import java.util.Objects; @Path("token") public class TokenEndpoint { @@ -39,28 +38,26 @@ public class TokenEndpoint { //Check grant_type params String grantType = params.getFirst("grant_type"); - Objects.requireNonNull(grantType, "grant_type params is required"); - if (!supportedGrantTypes.contains(grantType)) { - JsonObject error = Json.createObjectBuilder() - .add("error", "unsupported_grant_type") - .add("error_description", "grant type should be one of :" + supportedGrantTypes) - .build(); - return Response.status(Response.Status.BAD_REQUEST) - .entity(error).build(); + if (grantType == null || grantType.isEmpty()) + return responseError("Invalid_request", "grant_type is required", Response.Status.BAD_REQUEST); + if (!supportedGrantTypes.contains(grantType)) { + return responseError("unsupported_grant_type", "grant_type should be one of :" + supportedGrantTypes, Response.Status.BAD_REQUEST); } //Client Authentication String[] clientCredentials = extract(authHeader); + if (clientCredentials.length != 2) { + return responseError("Invalid_request", "Bad Credentials client_id/client_secret", Response.Status.BAD_REQUEST); + } String clientId = clientCredentials[0]; - String clientSecret = clientCredentials[1]; Client client = appDataRepository.getClient(clientId); - if (client == null || clientSecret == null || !clientSecret.equals(client.getClientSecret())) { - JsonObject error = Json.createObjectBuilder() - .add("error", "invalid_client") - .build(); - return Response.status(Response.Status.UNAUTHORIZED) - .entity(error).build(); + if (client == null) { + return responseError("Invalid_request", "Invalid client_id", Response.Status.BAD_REQUEST); + } + String clientSecret = clientCredentials[1]; + if (!clientSecret.equals(client.getClientSecret())) { + return responseError("Invalid_request", "Invalid client_secret", Response.Status.UNAUTHORIZED); } AuthorizationGrantTypeHandler authorizationGrantTypeHandler = authorizationGrantTypeHandlers.select(NamedLiteral.of(grantType)).get(); @@ -68,7 +65,7 @@ public class TokenEndpoint { try { tokenResponse = authorizationGrantTypeHandler.createAccessToken(clientId, params); } catch (Exception e) { - e.printStackTrace(); + return responseError("Invalid_request", "Can't get token", Response.Status.INTERNAL_SERVER_ERROR); } return Response.ok(tokenResponse) @@ -81,6 +78,15 @@ public class TokenEndpoint { if (authHeader != null && authHeader.startsWith("Basic ")) { return new String(Base64.getDecoder().decode(authHeader.substring(6))).split(":"); } - return null; + return new String[]{}; + } + + private Response responseError(String error, String errorDescription, Response.Status status) { + JsonObject errorResponse = Json.createObjectBuilder() + .add("error", error) + .add("error_description", errorDescription) + .build(); + return Response.status(status) + .entity(errorResponse).build(); } } From 4c6182d45f4edabf0b54e7c88e108db6b634ba28 Mon Sep 17 00:00:00 2001 From: "EZZEDDINE.ELHAZATI" Date: Tue, 23 Jul 2019 16:04:35 +0100 Subject: [PATCH 058/107] refactoring. --- .../authorization/server/api/TokenEndpoint.java | 2 ++ .../handler/RefreshTokenGrantTypeHandler.java | 8 +++++++- .../oauth2/client/RefreshTokenServlet.java | 14 ++++++-------- 3 files changed, 15 insertions(+), 9 deletions(-) diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java index 4716c1bb26..0ea12da16e 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/api/TokenEndpoint.java @@ -64,6 +64,8 @@ public class TokenEndpoint { JsonObject tokenResponse = null; try { tokenResponse = authorizationGrantTypeHandler.createAccessToken(clientId, params); + } catch (WebApplicationException e) { + return e.getResponse(); } catch (Exception e) { return responseError("Invalid_request", "Can't get token", Response.Status.INTERNAL_SERVER_ERROR); } diff --git a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java index 513bcc2cf0..63e3552353 100644 --- a/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java +++ b/oauth2-framework-impl/oauth2-authorization-server/src/main/java/com/baeldung/oauth2/authorization/server/handler/RefreshTokenGrantTypeHandler.java @@ -8,6 +8,7 @@ import javax.json.Json; import javax.json.JsonObject; import javax.ws.rs.WebApplicationException; import javax.ws.rs.core.MultivaluedMap; +import javax.ws.rs.core.Response; import java.util.Arrays; import java.util.Date; import java.util.HashSet; @@ -48,7 +49,12 @@ public class RefreshTokenGrantTypeHandler extends AbstractGrantTypeHandler { Set rScopes = new HashSet(Arrays.asList(requestedScopes.split(" "))); Set aScopes = new HashSet(Arrays.asList(approvedScopes.split(" "))); if (!aScopes.containsAll(rScopes)) { - throw new WebApplicationException("Requested scopes should be a subset of those authorized by the resource owner."); + JsonObject error = Json.createObjectBuilder() + .add("error", "Invalid_request") + .add("error_description", "Requested scopes should be a subset of the original scopes.") + .build(); + Response response = Response.status(Response.Status.BAD_REQUEST).entity(error).build(); + throw new WebApplicationException(response); } } else { requestedScopes = approvedScopes; diff --git a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java index b9fd7a4a21..766a4e3f1f 100644 --- a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java +++ b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java @@ -15,6 +15,7 @@ import javax.ws.rs.client.WebTarget; import javax.ws.rs.core.Form; import javax.ws.rs.core.HttpHeaders; import javax.ws.rs.core.MediaType; +import javax.ws.rs.core.Response; import java.io.IOException; @WebServlet(urlPatterns = "/refreshtoken") @@ -42,16 +43,13 @@ public class RefreshTokenServlet extends AbstractServlet { form.param("scope", scope); } - JsonObject tokenResponse = target.request(MediaType.APPLICATION_JSON_TYPE) + Response jaxrsResponse = target.request(MediaType.APPLICATION_JSON_TYPE) .header(HttpHeaders.AUTHORIZATION, getAuthorizationHeaderValue(clientId, clientSecret)) - .post(Entity.entity(form, MediaType.APPLICATION_FORM_URLENCODED_TYPE), JsonObject.class); + .post(Entity.entity(form, MediaType.APPLICATION_FORM_URLENCODED_TYPE), Response.class); + JsonObject tokenResponse = jaxrsResponse.readEntity(JsonObject.class); + System.out.println(tokenResponse); - String error = tokenResponse.getString("error"); - if (error != null) { - request.setAttribute("error", error); - } else { - request.getSession().setAttribute("tokenResponse", tokenResponse); - } + request.getSession().setAttribute("tokenResponse", tokenResponse); dispatch("/", request, response); } } From 4998ed9be4dcaaa58ee729f3b1f79b73fd8fda89 Mon Sep 17 00:00:00 2001 From: Justin Albano Date: Tue, 23 Jul 2019 10:59:02 -0400 Subject: [PATCH 059/107] BAEL-3153: Added test cases for String toLowerCase and toUpperCase The toLowerCase and toUpperCase methods are simple enough that no new classes are needed under the main/ directory. The included tests exercise the changing of case for an English string using the default locale, a foreign string using the default locale, and a foreign string using a provided locale. --- java-strings-2/README.MD | 14 ++++----- .../changecase/ToLowerCaseUnitTest.java | 29 +++++++++++++++++++ .../changecase/ToUpperCaseUnitTest.java | 29 +++++++++++++++++++ 3 files changed, 65 insertions(+), 7 deletions(-) create mode 100644 java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java create mode 100644 java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java diff --git a/java-strings-2/README.MD b/java-strings-2/README.MD index c6d4f0222a..4db93f64e0 100644 --- a/java-strings-2/README.MD +++ b/java-strings-2/README.MD @@ -1,7 +1,7 @@ -## Relevant Articles - -- [Java Localization – Formatting Messages](https://www.baeldung.com/java-localization-messages-formatting) -- [Check If a String Contains a Substring](https://www.baeldung.com/java-string-contains-substring) -- [Removing Stopwords from a String in Java](https://www.baeldung.com/java-string-remove-stopwords) -- [Blank and Empty Strings in Java](https://www.baeldung.com/java-blank-empty-strings) -- [String Initialization in Java](https://www.baeldung.com/java-string-initialization) +## Relevant Articles + +- [Java Localization – Formatting Messages](https://www.baeldung.com/java-localization-messages-formatting) +- [Check If a String Contains a Substring](https://www.baeldung.com/java-string-contains-substring) +- [Removing Stopwords from a String in Java](https://www.baeldung.com/java-string-remove-stopwords) +- [Blank and Empty Strings in Java](https://www.baeldung.com/java-blank-empty-strings) +- [String Initialization in Java](https://www.baeldung.com/java-string-initialization) diff --git a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java new file mode 100644 index 0000000000..14102be993 --- /dev/null +++ b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java @@ -0,0 +1,29 @@ +package com.baeldung.string.changecase; + +import static org.junit.Assert.assertEquals; + +import java.util.Locale; + +import org.junit.Test; + +public class ToLowerCaseUnitTest { + + private static final Locale TURKISH = new Locale("tr"); + private String name = "John Doe"; + private String foreignUppercase = "\u0049"; + + @Test + public void givenMixedCaseString_WhenToLowerCase_ThenResultIsLowerCase() { + assertEquals("john doe", name.toLowerCase()); + } + + @Test + public void givenForeignString_WhenToLowerCaseWithoutLocale_ThenResultIsLowerCase() { + assertEquals("\u0069", foreignUppercase.toLowerCase()); + } + + @Test + public void givenForeignString_WhenToLowerCaseWithLocale_ThenResultIsLowerCase() { + assertEquals("\u0131", foreignUppercase.toLowerCase(TURKISH)); + } +} diff --git a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java new file mode 100644 index 0000000000..90b80714a7 --- /dev/null +++ b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java @@ -0,0 +1,29 @@ +package com.baeldung.string.changecase; + +import static org.junit.Assert.assertEquals; + +import java.util.Locale; + +import org.junit.Test; + +public class ToUpperCaseUnitTest { + + private static final Locale TURKISH = new Locale("tr"); + private String name = "John Doe"; + private String foreignUppercase = "\u0069"; + + @Test + public void givenMixedCaseString_WhenToUpperCase_ThenResultIsUpperCase() { + assertEquals("JOHN DOE", name.toUpperCase()); + } + + @Test + public void givenForeignString_WhenToUpperCaseWithoutLocale_ThenResultIsUpperCase() { + assertEquals("\u0049", foreignUppercase.toUpperCase()); + } + + @Test + public void givenForeignString_WhenToUpperCaseWithLocale_ThenResultIsUpperCase() { + assertEquals("\u0130", foreignUppercase.toUpperCase(TURKISH)); + } +} From ce9e9561993eaf36255cb516aea372cf363fac6b Mon Sep 17 00:00:00 2001 From: "EZZEDDINE.ELHAZATI" Date: Tue, 23 Jul 2019 16:13:48 +0100 Subject: [PATCH 060/107] refactoring. --- .../com/baeldung/oauth2/client/RefreshTokenServlet.java | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java index 766a4e3f1f..a519a53070 100644 --- a/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java +++ b/oauth2-framework-impl/oauth2-client/src/main/java/com/baeldung/oauth2/client/RefreshTokenServlet.java @@ -47,9 +47,11 @@ public class RefreshTokenServlet extends AbstractServlet { .header(HttpHeaders.AUTHORIZATION, getAuthorizationHeaderValue(clientId, clientSecret)) .post(Entity.entity(form, MediaType.APPLICATION_FORM_URLENCODED_TYPE), Response.class); JsonObject tokenResponse = jaxrsResponse.readEntity(JsonObject.class); - System.out.println(tokenResponse); - - request.getSession().setAttribute("tokenResponse", tokenResponse); + if (jaxrsResponse.getStatus() == 200) { + request.getSession().setAttribute("tokenResponse", tokenResponse); + } else { + request.setAttribute("error", tokenResponse.getString("error_description", "error!")); + } dispatch("/", request, response); } } From 7000dfe094d88cff47166f12584995de2c915eba Mon Sep 17 00:00:00 2001 From: rahul Date: Tue, 23 Jul 2019 21:49:03 +0530 Subject: [PATCH 061/107] Checking if a URL Exists in Java --- .../core-java-networking-2/.gitignore | 25 ++++++++++++ .../core-java-networking-2/README.md | 7 ++++ .../core-java-networking-2/pom.xml | 22 +++++++++++ .../java/com/baeldung/url/UrlChecker.java | 25 ++++++++++++ .../com/baeldung/url/UrlCheckerUnitTest.java | 39 +++++++++++++++++++ 5 files changed, 118 insertions(+) create mode 100644 core-java-modules/core-java-networking-2/.gitignore create mode 100644 core-java-modules/core-java-networking-2/README.md create mode 100644 core-java-modules/core-java-networking-2/pom.xml create mode 100644 core-java-modules/core-java-networking-2/src/main/java/com/baeldung/url/UrlChecker.java create mode 100644 core-java-modules/core-java-networking-2/src/test/java/com/baeldung/url/UrlCheckerUnitTest.java diff --git a/core-java-modules/core-java-networking-2/.gitignore b/core-java-modules/core-java-networking-2/.gitignore new file mode 100644 index 0000000000..374c8bf907 --- /dev/null +++ b/core-java-modules/core-java-networking-2/.gitignore @@ -0,0 +1,25 @@ +*.class + +0.* + +#folders# +/target +/neoDb* +/data +/src/main/webapp/WEB-INF/classes +*/META-INF/* +.resourceCache + +# Packaged files # +*.jar +*.war +*.ear + +# Files generated by integration tests +backup-pom.xml +/bin/ +/temp + +#IntelliJ specific +.idea/ +*.iml \ No newline at end of file diff --git a/core-java-modules/core-java-networking-2/README.md b/core-java-modules/core-java-networking-2/README.md new file mode 100644 index 0000000000..15cccf4a60 --- /dev/null +++ b/core-java-modules/core-java-networking-2/README.md @@ -0,0 +1,7 @@ +========= + +## Core Java Networking - 2 + +### Relevant Articles + +- [Checking if a URL Exists in Java](https://www.baeldung.com/checking-if-a-url-exists-with-java) diff --git a/core-java-modules/core-java-networking-2/pom.xml b/core-java-modules/core-java-networking-2/pom.xml new file mode 100644 index 0000000000..88e038d4c9 --- /dev/null +++ b/core-java-modules/core-java-networking-2/pom.xml @@ -0,0 +1,22 @@ + + 4.0.0 + core-java-networking-2 + 0.1.0-SNAPSHOT + core-java-networking-2 + jar + + + com.baeldung + parent-java + 0.0.1-SNAPSHOT + ../../parent-java + + + + + + + core-java-networking-2 + + diff --git a/core-java-modules/core-java-networking-2/src/main/java/com/baeldung/url/UrlChecker.java b/core-java-modules/core-java-networking-2/src/main/java/com/baeldung/url/UrlChecker.java new file mode 100644 index 0000000000..b99e74f8bf --- /dev/null +++ b/core-java-modules/core-java-networking-2/src/main/java/com/baeldung/url/UrlChecker.java @@ -0,0 +1,25 @@ +package com.baeldung.url; + +import java.io.IOException; +import java.net.HttpURLConnection; +import java.net.URL; + +public class UrlChecker { + + public int getResponseCodeForURL(String address) throws IOException { + return getResponseCodeForURLUsing(address, "GET"); + } + + public int getResponseCodeForURLUsingHead(String address) throws IOException { + return getResponseCodeForURLUsing(address, "HEAD"); + } + + private int getResponseCodeForURLUsing(String address, String method) throws IOException { + HttpURLConnection.setFollowRedirects(false); // Set follow redirects to false + final URL url = new URL(address); + HttpURLConnection huc = (HttpURLConnection) url.openConnection(); + huc.setRequestMethod(method); + return huc.getResponseCode(); + } + +} diff --git a/core-java-modules/core-java-networking-2/src/test/java/com/baeldung/url/UrlCheckerUnitTest.java b/core-java-modules/core-java-networking-2/src/test/java/com/baeldung/url/UrlCheckerUnitTest.java new file mode 100644 index 0000000000..5e295e65a0 --- /dev/null +++ b/core-java-modules/core-java-networking-2/src/test/java/com/baeldung/url/UrlCheckerUnitTest.java @@ -0,0 +1,39 @@ +package com.baeldung.url; + +import static org.junit.jupiter.api.Assertions.assertEquals; + +import java.io.IOException; + +import org.junit.Test; + +public class UrlCheckerUnitTest { + + @Test + public void givenValidUrl_WhenUsingHEAD_ThenReturn200() throws IOException { + UrlChecker tester = new UrlChecker(); + int responseCode = tester.getResponseCodeForURLUsingHead("http://www.example.com"); + assertEquals(200, responseCode); + } + + @Test + public void givenInvalidIUrl_WhenUsingHEAD_ThenReturn404() throws IOException { + UrlChecker tester = new UrlChecker(); + int responseCode = tester.getResponseCodeForURLUsingHead("http://www.example.com/unkownurl"); + assertEquals(404, responseCode); + } + + @Test + public void givenValidUrl_WhenUsingGET_ThenReturn200() throws IOException { + UrlChecker tester = new UrlChecker(); + int responseCode = tester.getResponseCodeForURL("http://www.example.com"); + assertEquals(200, responseCode); + } + + @Test + public void givenInvalidIUrl_WhenUsingGET_ThenReturn404() throws IOException { + UrlChecker tester = new UrlChecker(); + int responseCode = tester.getResponseCodeForURL("http://www.example.com/unkownurl"); + assertEquals(404, responseCode); + } + +} From 22d6a3efb2b95944c0b12e3382f4dc8692013447 Mon Sep 17 00:00:00 2001 From: Loredana Date: Tue, 23 Jul 2019 22:18:39 +0300 Subject: [PATCH 062/107] exclude modules with failing tests --- pom.xml | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/pom.xml b/pom.xml index 21a42f89d6..aa4e497844 100644 --- a/pom.xml +++ b/pom.xml @@ -663,22 +663,23 @@ spring-boot-vue spring-boot-libraries - spring-cloud - spring-cloud-bus + + + - spring-cloud-data-flow + spring-core spring-core-2 spring-cucumber spring-data-rest - spring-data-rest-querydsl + spring-dispatcher-servlet spring-drools spring-ehcache - spring-ejb + spring-exceptions spring-freemarker @@ -752,7 +753,7 @@ spring-security-stormpath spring-security-thymeleaf spring-security-x509 - spring-session + spring-sleuth spring-soap spring-social-login @@ -763,10 +764,10 @@ spring-thymeleaf - spring-vault + spring-vertx - spring-webflux-amqp + spring-zuul From b355af4d01472a32d823685a3ff35f1d3736cc9a Mon Sep 17 00:00:00 2001 From: Gerardo Roza Date: Tue, 23 Jul 2019 16:22:20 -0300 Subject: [PATCH 063/107] fixed migration to spring boot 2, plus now added properties in articles --- spring-security-mvc-session/pom.xml | 87 +++++-------------- .../baeldung/SpringSessionApplication.java | 2 +- .../monitoring/MetricRegistrySingleton.java | 2 +- ...SimpleUrlAuthenticationSuccessHandler.java | 2 +- .../baeldung/security/SessionFilter.java | 2 +- .../java/com/baeldung/spring/MvcConfig.java | 33 +++++++ .../baeldung/spring/SecSecurityConfig.java | 11 ++- .../web/SessionListenerWithMetrics.java | 5 +- .../java/org/baeldung/spring/MvcConfig.java | 44 ---------- .../src/main/resources/application.properties | 8 ++ .../SpringContextIntegrationTest.java | 15 ++++ .../SpringContextIntegrationTest.java | 19 ---- .../java/org/baeldung/SpringContextTest.java | 19 ---- 13 files changed, 90 insertions(+), 159 deletions(-) rename spring-security-mvc-session/src/main/java/{org => com}/baeldung/SpringSessionApplication.java (93%) rename spring-security-mvc-session/src/main/java/{org => com}/baeldung/monitoring/MetricRegistrySingleton.java (95%) rename spring-security-mvc-session/src/main/java/{org => com}/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java (99%) rename spring-security-mvc-session/src/main/java/{org => com}/baeldung/security/SessionFilter.java (97%) create mode 100644 spring-security-mvc-session/src/main/java/com/baeldung/spring/MvcConfig.java rename spring-security-mvc-session/src/main/java/{org => com}/baeldung/spring/SecSecurityConfig.java (91%) rename spring-security-mvc-session/src/main/java/{org => com}/baeldung/web/SessionListenerWithMetrics.java (92%) delete mode 100644 spring-security-mvc-session/src/main/java/org/baeldung/spring/MvcConfig.java create mode 100644 spring-security-mvc-session/src/main/resources/application.properties create mode 100644 spring-security-mvc-session/src/test/java/com/baeldung/SpringContextIntegrationTest.java delete mode 100644 spring-security-mvc-session/src/test/java/org/baeldung/SpringContextIntegrationTest.java delete mode 100644 spring-security-mvc-session/src/test/java/org/baeldung/SpringContextTest.java diff --git a/spring-security-mvc-session/pom.xml b/spring-security-mvc-session/pom.xml index b55ce70517..5ed7fbecd3 100644 --- a/spring-security-mvc-session/pom.xml +++ b/spring-security-mvc-session/pom.xml @@ -1,18 +1,19 @@ - + 4.0.0 com.baeldung spring-security-mvc-session 0.1-SNAPSHOT spring-security-mvc-session - war + jar - parent-boot-2 com.baeldung + parent-boot-2 0.0.1-SNAPSHOT ../parent-boot-2 - + @@ -35,20 +36,13 @@ org.apache.tomcat.embed tomcat-embed-jasper + provided org.springframework.boot spring-boot-starter-tomcat - - - - javax.servlet - javax.servlet-api - provided - - javax.servlet jstl @@ -56,70 +50,35 @@ - - com.codahale.metrics + io.dropwizard.metrics metrics-core - ${codahale.metrics.version} - + - org.springframework.boot - spring-boot-starter-test - test - - + org.springframework.boot + spring-boot-starter-test + test + + + org.springframework.security + spring-security-test + test + - spring-security-mvc-session - - - src/main/resources - true - - - - - org.apache.maven.plugins - maven-war-plugin - ${maven-war-plugin.version} - - - - org.codehaus.cargo - cargo-maven2-plugin - ${cargo-maven2-plugin.version} + org.springframework.boot + spring-boot-maven-plugin - true - - jetty8x - embedded - - - - - - - 8082 - - + com.baeldung.SpringSessionApplication + JAR - - - - - 3.0.2 - - - 1.6.1 - - - \ No newline at end of file + diff --git a/spring-security-mvc-session/src/main/java/org/baeldung/SpringSessionApplication.java b/spring-security-mvc-session/src/main/java/com/baeldung/SpringSessionApplication.java similarity index 93% rename from spring-security-mvc-session/src/main/java/org/baeldung/SpringSessionApplication.java rename to spring-security-mvc-session/src/main/java/com/baeldung/SpringSessionApplication.java index 9e52f0430a..c2a4b35df0 100644 --- a/spring-security-mvc-session/src/main/java/org/baeldung/SpringSessionApplication.java +++ b/spring-security-mvc-session/src/main/java/com/baeldung/SpringSessionApplication.java @@ -1,4 +1,4 @@ -package org.baeldung; +package com.baeldung; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; diff --git a/spring-security-mvc-session/src/main/java/org/baeldung/monitoring/MetricRegistrySingleton.java b/spring-security-mvc-session/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java similarity index 95% rename from spring-security-mvc-session/src/main/java/org/baeldung/monitoring/MetricRegistrySingleton.java rename to spring-security-mvc-session/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java index ed253305ed..e2224996c2 100644 --- a/spring-security-mvc-session/src/main/java/org/baeldung/monitoring/MetricRegistrySingleton.java +++ b/spring-security-mvc-session/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java @@ -1,4 +1,4 @@ -package org.baeldung.monitoring; +package com.baeldung.monitoring; import java.util.concurrent.TimeUnit; diff --git a/spring-security-mvc-session/src/main/java/org/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java b/spring-security-mvc-session/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java similarity index 99% rename from spring-security-mvc-session/src/main/java/org/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java rename to spring-security-mvc-session/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java index 19f49ea59d..9d4fc19098 100644 --- a/spring-security-mvc-session/src/main/java/org/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java +++ b/spring-security-mvc-session/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java @@ -1,4 +1,4 @@ -package org.baeldung.security; +package com.baeldung.security; import java.io.IOException; import java.util.Collection; diff --git a/spring-security-mvc-session/src/main/java/org/baeldung/security/SessionFilter.java b/spring-security-mvc-session/src/main/java/com/baeldung/security/SessionFilter.java similarity index 97% rename from spring-security-mvc-session/src/main/java/org/baeldung/security/SessionFilter.java rename to spring-security-mvc-session/src/main/java/com/baeldung/security/SessionFilter.java index d37d46e478..f4f876af9c 100644 --- a/spring-security-mvc-session/src/main/java/org/baeldung/security/SessionFilter.java +++ b/spring-security-mvc-session/src/main/java/com/baeldung/security/SessionFilter.java @@ -1,4 +1,4 @@ -package org.baeldung.security; +package com.baeldung.security; import java.io.IOException; import java.util.Arrays; diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/spring/MvcConfig.java b/spring-security-mvc-session/src/main/java/com/baeldung/spring/MvcConfig.java new file mode 100644 index 0000000000..38a4f3f81b --- /dev/null +++ b/spring-security-mvc-session/src/main/java/com/baeldung/spring/MvcConfig.java @@ -0,0 +1,33 @@ +package com.baeldung.spring; + +import org.springframework.context.annotation.Configuration; +import org.springframework.web.servlet.config.annotation.ViewControllerRegistry; +import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; + +@Configuration +public class MvcConfig implements WebMvcConfigurer { + + @Override + public void addViewControllers(final ViewControllerRegistry registry) { + registry.addViewController("/anonymous.html"); + + registry.addViewController("/login.html"); + registry.addViewController("/homepage.html"); + registry.addViewController("/sessionExpired.html"); + registry.addViewController("/invalidSession.html"); + registry.addViewController("/console.html"); + } + + + /* + * Spring Boot supports configuring a ViewResolver with properties + */ +// @Bean +// public ViewResolver viewResolver() { +// final InternalResourceViewResolver bean = new InternalResourceViewResolver(); +// +// bean.setViewClass(JstlView.class); +// bean.setPrefix("/WEB-INF/view/"); +// bean.setSuffix(".jsp"); +// } +} diff --git a/spring-security-mvc-session/src/main/java/org/baeldung/spring/SecSecurityConfig.java b/spring-security-mvc-session/src/main/java/com/baeldung/spring/SecSecurityConfig.java similarity index 91% rename from spring-security-mvc-session/src/main/java/org/baeldung/spring/SecSecurityConfig.java rename to spring-security-mvc-session/src/main/java/com/baeldung/spring/SecSecurityConfig.java index b7996ebf18..a922ba6f7f 100644 --- a/spring-security-mvc-session/src/main/java/org/baeldung/spring/SecSecurityConfig.java +++ b/spring-security-mvc-session/src/main/java/com/baeldung/spring/SecSecurityConfig.java @@ -1,11 +1,9 @@ -package org.baeldung.spring; +package com.baeldung.spring; -import org.baeldung.security.MySimpleUrlAuthenticationSuccessHandler; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; import org.springframework.security.config.annotation.web.builders.HttpSecurity; -import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter; import org.springframework.security.config.http.SessionCreationPolicy; import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; @@ -13,9 +11,10 @@ import org.springframework.security.crypto.password.PasswordEncoder; import org.springframework.security.web.authentication.AuthenticationSuccessHandler; import org.springframework.security.web.session.HttpSessionEventPublisher; +import com.baeldung.security.MySimpleUrlAuthenticationSuccessHandler; + @Configuration // @ImportResource({ "classpath:webSecurityConfig.xml" }) -@EnableWebSecurity public class SecSecurityConfig extends WebSecurityConfigurerAdapter { public SecSecurityConfig() { @@ -39,7 +38,7 @@ public class SecSecurityConfig extends WebSecurityConfigurerAdapter { .csrf().disable() .authorizeRequests() .antMatchers("/anonymous*").anonymous() - .antMatchers("/login*").permitAll() + .antMatchers("/login*","/invalidSession*", "/sessionExpired*").permitAll() .anyRequest().authenticated() .and() .formLogin() @@ -70,7 +69,7 @@ public class SecSecurityConfig extends WebSecurityConfigurerAdapter { public HttpSessionEventPublisher httpSessionEventPublisher() { return new HttpSessionEventPublisher(); } - + @Bean public PasswordEncoder passwordEncoder() { return new BCryptPasswordEncoder(); diff --git a/spring-security-mvc-session/src/main/java/org/baeldung/web/SessionListenerWithMetrics.java b/spring-security-mvc-session/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java similarity index 92% rename from spring-security-mvc-session/src/main/java/org/baeldung/web/SessionListenerWithMetrics.java rename to spring-security-mvc-session/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java index 46bf2708f7..fb1a81744e 100644 --- a/spring-security-mvc-session/src/main/java/org/baeldung/web/SessionListenerWithMetrics.java +++ b/spring-security-mvc-session/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java @@ -1,12 +1,11 @@ -package org.baeldung.web; +package com.baeldung.web; import java.util.concurrent.atomic.AtomicInteger; import javax.servlet.http.HttpSessionEvent; import javax.servlet.http.HttpSessionListener; -import org.baeldung.monitoring.MetricRegistrySingleton; - +import com.baeldung.monitoring.MetricRegistrySingleton; import com.codahale.metrics.Counter; public class SessionListenerWithMetrics implements HttpSessionListener { diff --git a/spring-security-mvc-session/src/main/java/org/baeldung/spring/MvcConfig.java b/spring-security-mvc-session/src/main/java/org/baeldung/spring/MvcConfig.java deleted file mode 100644 index b9f50ded73..0000000000 --- a/spring-security-mvc-session/src/main/java/org/baeldung/spring/MvcConfig.java +++ /dev/null @@ -1,44 +0,0 @@ -package org.baeldung.spring; - -import org.springframework.context.annotation.Bean; -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.ViewControllerRegistry; -import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; -import org.springframework.web.servlet.view.InternalResourceViewResolver; -import org.springframework.web.servlet.view.JstlView; - -@EnableWebMvc -@Configuration -public class MvcConfig implements WebMvcConfigurer { - - public MvcConfig() { - super(); - } - - // API - - @Override - public void addViewControllers(final ViewControllerRegistry registry) { - - registry.addViewController("/anonymous.html"); - - registry.addViewController("/login.html"); - registry.addViewController("/homepage.html"); - registry.addViewController("/sessionExpired.html"); - registry.addViewController("/invalidExpired.html"); - registry.addViewController("/console.html"); - } - - @Bean - public ViewResolver viewResolver() { - final InternalResourceViewResolver bean = new InternalResourceViewResolver(); - - bean.setViewClass(JstlView.class); - bean.setPrefix("/WEB-INF/view/"); - bean.setSuffix(".jsp"); - - return bean; - } -} \ No newline at end of file diff --git a/spring-security-mvc-session/src/main/resources/application.properties b/spring-security-mvc-session/src/main/resources/application.properties new file mode 100644 index 0000000000..39ec0a0b27 --- /dev/null +++ b/spring-security-mvc-session/src/main/resources/application.properties @@ -0,0 +1,8 @@ +server.servlet.session.timeout=60s + +spring.mvc.view.prefix=/WEB-INF/view/ +spring.mvc.view.suffix=.jsp + +## Secure Session Cookie configurations +#server.servlet.session.cookie.http-only=true +#server.servlet.session.cookie.secure=true \ No newline at end of file diff --git a/spring-security-mvc-session/src/test/java/com/baeldung/SpringContextIntegrationTest.java b/spring-security-mvc-session/src/test/java/com/baeldung/SpringContextIntegrationTest.java new file mode 100644 index 0000000000..8e53a6371a --- /dev/null +++ b/spring-security-mvc-session/src/test/java/com/baeldung/SpringContextIntegrationTest.java @@ -0,0 +1,15 @@ +package com.baeldung; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.test.context.junit4.SpringRunner; + +@RunWith(SpringRunner.class) +@SpringBootTest +public class SpringContextIntegrationTest { + + @Test + public void whenSpringContextIsBootstrapped_thenNoExceptions() { + } +} diff --git a/spring-security-mvc-session/src/test/java/org/baeldung/SpringContextIntegrationTest.java b/spring-security-mvc-session/src/test/java/org/baeldung/SpringContextIntegrationTest.java deleted file mode 100644 index 9e74e83a53..0000000000 --- a/spring-security-mvc-session/src/test/java/org/baeldung/SpringContextIntegrationTest.java +++ /dev/null @@ -1,19 +0,0 @@ -package org.baeldung; - -import org.baeldung.spring.MvcConfig; -import org.baeldung.spring.SecSecurityConfig; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.springframework.test.context.ContextConfiguration; -import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; -import org.springframework.test.context.web.WebAppConfiguration; - -@RunWith(SpringJUnit4ClassRunner.class) -@ContextConfiguration(classes = { MvcConfig.class, SecSecurityConfig.class }) -@WebAppConfiguration -public class SpringContextIntegrationTest { - - @Test - public void whenSpringContextIsBootstrapped_thenNoExceptions() { - } -} diff --git a/spring-security-mvc-session/src/test/java/org/baeldung/SpringContextTest.java b/spring-security-mvc-session/src/test/java/org/baeldung/SpringContextTest.java deleted file mode 100644 index 5ee80d856a..0000000000 --- a/spring-security-mvc-session/src/test/java/org/baeldung/SpringContextTest.java +++ /dev/null @@ -1,19 +0,0 @@ -package org.baeldung; - -import org.baeldung.spring.MvcConfig; -import org.baeldung.spring.SecSecurityConfig; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.springframework.test.context.ContextConfiguration; -import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; -import org.springframework.test.context.web.WebAppConfiguration; - -@RunWith(SpringJUnit4ClassRunner.class) -@ContextConfiguration(classes = { MvcConfig.class, SecSecurityConfig.class }) -@WebAppConfiguration -public class SpringContextTest { - - @Test - public void whenSpringContextIsBootstrapped_thenNoExceptions() { - } -} From d3ed9d75fd959cbba33c09d6d4f4d391fb8693cb Mon Sep 17 00:00:00 2001 From: Alessio Stalla Date: Wed, 24 Jul 2019 23:32:58 +0200 Subject: [PATCH 064/107] Tests for BAEL-2991 --- persistence-modules/java-sql2o/README.md | 3 + persistence-modules/java-sql2o/pom.xml | 55 +++ .../jdbi/Sql2oIntegrationTest.java | 343 ++++++++++++++++++ persistence-modules/pom.xml | 1 + 4 files changed, 402 insertions(+) create mode 100644 persistence-modules/java-sql2o/README.md create mode 100644 persistence-modules/java-sql2o/pom.xml create mode 100644 persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/jdbi/Sql2oIntegrationTest.java diff --git a/persistence-modules/java-sql2o/README.md b/persistence-modules/java-sql2o/README.md new file mode 100644 index 0000000000..4c1ff931ce --- /dev/null +++ b/persistence-modules/java-sql2o/README.md @@ -0,0 +1,3 @@ +### Relevant Articles: + +- [A Guide to Jdbi](http://www.baeldung.com/jdbi) diff --git a/persistence-modules/java-sql2o/pom.xml b/persistence-modules/java-sql2o/pom.xml new file mode 100644 index 0000000000..54838c32cb --- /dev/null +++ b/persistence-modules/java-sql2o/pom.xml @@ -0,0 +1,55 @@ + + + 4.0.0 + com.baeldung + java-sql2o + 1.0-SNAPSHOT + + + + org.apache.maven.plugins + maven-compiler-plugin + + 8 + 8 + + + + + java-sql2o + + + + + + org.sql2o + sql2o + ${sql2o.version} + + + org.hsqldb + hsqldb + ${hsqldb.version} + test + + + junit + junit + ${junit.version} + test + + + + + 2.4.0 + 4.12 + 1.6.0 + + + diff --git a/persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/jdbi/Sql2oIntegrationTest.java b/persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/jdbi/Sql2oIntegrationTest.java new file mode 100644 index 0000000000..56f2e3a62e --- /dev/null +++ b/persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/jdbi/Sql2oIntegrationTest.java @@ -0,0 +1,343 @@ +package com.baeldung.persistence.jdbi; + +import org.junit.Test; +import org.sql2o.Connection; +import org.sql2o.Query; +import org.sql2o.ResultSetIterable; +import org.sql2o.Sql2o; +import org.sql2o.data.Row; +import org.sql2o.data.Table; + +import java.sql.PreparedStatement; +import java.sql.SQLException; +import java.text.SimpleDateFormat; +import java.util.*; +import java.util.function.Supplier; +import java.util.stream.Stream; + +import static org.junit.Assert.*; + +public class Sql2oIntegrationTest { + + @Test + public void whenSql2oCreated_thenSuccess() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + java.sql.Connection jdbcConnection = connection.getJdbcConnection(); + assertFalse(jdbcConnection.isClosed()); + } catch (SQLException e) { + fail(e.getMessage()); + } + } + + @Test + public void whenTableCreated_thenInsertIsPossible() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_1 (id integer identity, name varchar(50), url varchar(100))").executeUpdate(); + assertEquals(0, connection.getResult()); + connection.createQuery("INSERT INTO PROJECT_1 VALUES (1, 'tutorials', 'github.com/eugenp/tutorials')").executeUpdate(); + assertEquals(1, connection.getResult()); + connection.createQuery("drop table PROJECT_1").executeUpdate(); + } + } + + @Test + public void whenIdentityColumn_thenInsertReturnsNewId() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_2 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + Query query = connection.createQuery( + "INSERT INTO PROJECT_2 (NAME, URL) VALUES ('tutorials', 'github.com/eugenp/tutorials')", + true); + assertEquals(0, query.executeUpdate().getKey()); + query = connection.createQuery("INSERT INTO PROJECT_2 (NAME, URL) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring')", + true); + assertEquals(1, query.executeUpdate().getKeys()[0]); + connection.createQuery("drop table PROJECT_2").executeUpdate(); + } + } + + @Test + public void whenSelect_thenResultsAreObjects() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_3 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_3 (NAME, URL) VALUES ('tutorials', 'github.com/eugenp/tutorials')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_3 (NAME, URL) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring')").executeUpdate(); + Query query = connection.createQuery("select * from PROJECT_3 order by id"); + List list = query.executeAndFetch(Project.class); + + assertEquals("tutorials", list.get(0).getName()); + assertEquals("REST with Spring", list.get(1).getName()); + + connection.createQuery("drop table PROJECT_3").executeUpdate(); + } + } + + @Test + public void whenSelectAlias_thenResultsAreObjects() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_4 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100), creation_date date)").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_4 (NAME, URL, creation_date) VALUES ('tutorials', 'github.com/eugenp/tutorials', '2019-01-01')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_4 (NAME, URL, creation_date) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring', '2019-02-01')").executeUpdate(); + Query query = connection.createQuery("select NAME, URL, creation_date as creationDate from PROJECT_4 order by id"); + List list = query.executeAndFetch(Project.class); + SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); + assertEquals("2019-01-01", sdf.format(list.get(0).getCreationDate())); + assertEquals("2019-02-01", sdf.format(list.get(1).getCreationDate())); + + connection.createQuery("drop table PROJECT_4").executeUpdate(); + } + } + + @Test + public void whenSelectMapping_thenResultsAreObjects() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_5 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100), creation_date date)").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_5 (NAME, URL, creation_date) VALUES ('tutorials', 'github.com/eugenp/tutorials', '2019-01-01')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_5 (NAME, URL, creation_date) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring', '2019-02-01')").executeUpdate(); + Query query = connection.createQuery("select * from PROJECT_5 order by id") + .addColumnMapping("CrEaTiOn_date", "creationDate"); + List list = query.executeAndFetch(Project.class); + SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); + assertEquals("2019-01-01", sdf.format(list.get(0).getCreationDate())); + assertEquals("2019-02-01", sdf.format(list.get(1).getCreationDate())); + + connection.createQuery("drop table PROJECT_5").executeUpdate(); + } + } + + @Test + public void whenSelectCount_thenResultIsScalar() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_6 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100), creation_date date)").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_6 (NAME, URL, creation_date) VALUES ('tutorials', 'github.com/eugenp/tutorials', '2019-01-01')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_6 (NAME, URL, creation_date) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring', '2019-02-01')").executeUpdate(); + Query query = connection.createQuery("select count(*) from PROJECT_6"); + assertEquals(2.0, query.executeScalar(Double.TYPE), 0.001); + connection.createQuery("drop table PROJECT_6").executeUpdate(); + } + } + + @Test + public void whenFetchTable_thenResultsAreMaps() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_5 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100), creation_date date)").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_5 (NAME, URL, creation_date) VALUES ('tutorials', 'github.com/eugenp/tutorials', '2019-01-01')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_5 (NAME, URL, creation_date) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring', '2019-02-01')").executeUpdate(); + Query query = connection.createQuery("select * from PROJECT_5 order by id"); + Table table = query.executeAndFetchTable(); + List> list = table.asList(); + + assertEquals("tutorials", list.get(0).get("name")); + assertEquals("REST with Spring", list.get(1).get("name")); + + connection.createQuery("drop table PROJECT_5").executeUpdate(); + } + } + + @Test + public void whenFetchTable_thenResultsAreRows() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_5 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100), creation_date date)").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_5 (NAME, URL, creation_date) VALUES ('tutorials', 'github.com/eugenp/tutorials', '2019-01-01')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_5 (NAME, URL, creation_date) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring', '2019-02-01')").executeUpdate(); + Query query = connection.createQuery("select * from PROJECT_5 order by id"); + Table table = query.executeAndFetchTable(); + List rows = table.rows(); + + assertEquals("tutorials", rows.get(0).getString("name")); + assertEquals("REST with Spring", rows.get(1).getString("name")); + + connection.createQuery("drop table PROJECT_5").executeUpdate(); + } + } + + @Test + public void whenParameters_thenReplacement() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_10 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + Query query = connection.createQuery("INSERT INTO PROJECT_10 (NAME, URL) VALUES (:name, :url)") + .addParameter("name", "REST with Spring") + .addParameter("url", "github.com/eugenp/REST-With-Spring"); + assertEquals(1, query.executeUpdate().getResult()); + + List list = connection.createQuery("SELECT * FROM PROJECT_10 WHERE NAME = 'REST with Spring'").executeAndFetch(Project.class); + assertEquals(1, list.size()); + + connection.createQuery("drop table PROJECT_10").executeUpdate(); + } + } + + @Test + public void whenPOJOParameters_thenReplacement() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_11 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + + Project project = new Project(); + project.setName("REST with Spring"); + project.setUrl("github.com/eugenp/REST-With-Spring"); + connection.createQuery("INSERT INTO PROJECT_11 (NAME, URL) VALUES (:name, :url)") + .bind(project).executeUpdate(); + assertEquals(1, connection.getResult()); + + List list = connection.createQuery("SELECT * FROM PROJECT_11 WHERE NAME = 'REST with Spring'").executeAndFetch(Project.class); + assertEquals(1, list.size()); + + connection.createQuery("drop table PROJECT_11").executeUpdate(); + } + } + + @Test + public void whenTransactionRollback_thenNoDataInserted() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.beginTransaction()) { + connection.createQuery("create table PROJECT_12 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_12 (NAME, URL) VALUES ('tutorials', 'https://github.com/eugenp/tutorials')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_12 (NAME, URL) VALUES ('REST with Spring', 'https://github.com/eugenp/REST-With-Spring')").executeUpdate(); + connection.rollback(); + List> list = connection.createQuery("SELECT * FROM PROJECT_12").executeAndFetchTable().asList(); + assertEquals(0, list.size()); + } + } + + @Test + public void whenTransactionEnds_thenSubsequentStatementsNotRolledBack() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.beginTransaction()) { + connection.createQuery("create table PROJECT_13 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_13 (NAME, URL) VALUES ('tutorials', 'https://github.com/eugenp/tutorials')").executeUpdate(); + List> list = connection.createQuery("SELECT * FROM PROJECT_13").executeAndFetchTable().asList(); + assertEquals(1, list.size()); + connection.rollback(); + list = connection.createQuery("SELECT * FROM PROJECT_13").executeAndFetchTable().asList(); + assertEquals(0, list.size()); + connection.createQuery("INSERT INTO PROJECT_13 (NAME, URL) VALUES ('REST with Spring', 'https://github.com/eugenp/REST-With-Spring')").executeUpdate(); + list = connection.createQuery("SELECT * FROM PROJECT_13").executeAndFetchTable().asList(); + assertEquals(1, list.size()); + //No implicit rollback + } + try(Connection connection = sql2o.beginTransaction()) { + List> list = connection.createQuery("SELECT * FROM PROJECT_13").executeAndFetchTable().asList(); + assertEquals(1, list.size()); + } + } + + @Test + public void whenTransactionRollbackThenCommit_thenOnlyLastInserted() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.beginTransaction()) { + connection.createQuery("create table PROJECT_14 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_14 (NAME, URL) VALUES ('tutorials', 'https://github.com/eugenp/tutorials')").executeUpdate(); + List> list = connection.createQuery("SELECT * FROM PROJECT_14").executeAndFetchTable().asList(); + assertEquals(1, list.size()); + connection.rollback(false); + list = connection.createQuery("SELECT * FROM PROJECT_14").executeAndFetchTable().asList(); + assertEquals(0, list.size()); + connection.createQuery("INSERT INTO PROJECT_14 (NAME, URL) VALUES ('REST with Spring', 'https://github.com/eugenp/REST-With-Spring')").executeUpdate(); + list = connection.createQuery("SELECT * FROM PROJECT_14").executeAndFetchTable().asList(); + assertEquals(1, list.size()); + //Implicit rollback + } + try(Connection connection = sql2o.beginTransaction()) { + List> list = connection.createQuery("SELECT * FROM PROJECT_14").executeAndFetchTable().asList(); + assertEquals(0, list.size()); + connection.createQuery("INSERT INTO PROJECT_14 (NAME, URL) VALUES ('tutorials', 'https://github.com/eugenp/tutorials')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_14 (NAME, URL) VALUES ('REST with Spring', 'https://github.com/eugenp/REST-With-Spring')").executeUpdate(); + connection.commit(); + list = connection.createQuery("SELECT * FROM PROJECT_14").executeAndFetchTable().asList(); + assertEquals(2, list.size()); + } + try(Connection connection = sql2o.beginTransaction()) { + List> list = connection.createQuery("SELECT * FROM PROJECT_14").executeAndFetchTable().asList(); + assertEquals(2, list.size()); + } + } + + @Test + public void whenBatch_thenMultipleInserts() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.beginTransaction()) { + connection.createQuery("create table PROJECT_15 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + Query query = connection.createQuery("INSERT INTO PROJECT_15 (NAME, URL) VALUES (:name, :url)"); + for(int i = 0; i < 1000; i++) { + query.addParameter("name", "tutorials" + i); + query.addParameter("url", "https://github.com/eugenp/tutorials" + i); + query.addToBatch(); + } + query.executeBatch(); + connection.commit(); + } + try(Connection connection = sql2o.beginTransaction()) { + assertEquals(1000L, connection.createQuery("SELECT count(*) FROM PROJECT_15").executeScalar()); + } + } + + @Test + public void whenLazyFetch_thenResultsAreObjects() { + Sql2o sql2o = new Sql2o("jdbc:hsqldb:mem:testDB", "sa", ""); + try(Connection connection = sql2o.open()) { + connection.createQuery("create table PROJECT_16 (ID IDENTITY, NAME VARCHAR (50), URL VARCHAR (100))").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_16 (NAME, URL) VALUES ('tutorials', 'github.com/eugenp/tutorials')").executeUpdate(); + connection.createQuery("INSERT INTO PROJECT_16 (NAME, URL) VALUES ('REST with Spring', 'github.com/eugenp/REST-With-Spring')").executeUpdate(); + Query query = connection.createQuery("select * from PROJECT_16 order by id"); + try(ResultSetIterable projects = query.executeAndFetchLazy(Project.class)) { + for(Project p : projects) { + assertNotNull(p.getName()); + assertNotNull(p.getUrl()); + assertNull(p.getCreationDate()); + } + } + connection.createQuery("drop table PROJECT_16").executeUpdate(); + } + } + + static class Project { + private long id; + private String name; + private String url; + private Date creationDate; + + public long getId() { + return id; + } + + public void setId(long id) { + this.id = id; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + this.url = url; + } + + public Date getCreationDate() { + return creationDate; + } + + public void setCreationDate(Date creationDate) { + this.creationDate = creationDate; + } + } + + +} diff --git a/persistence-modules/pom.xml b/persistence-modules/pom.xml index 390bcc9d51..5df91b5a8d 100644 --- a/persistence-modules/pom.xml +++ b/persistence-modules/pom.xml @@ -30,6 +30,7 @@ java-jdbi java-jpa java-mongodb + java-sql2o jnosql liquibase orientdb From 155d3ea52f328f3bb6cfaa98d18fc4671e5a63e2 Mon Sep 17 00:00:00 2001 From: Alessio Stalla Date: Wed, 24 Jul 2019 23:35:22 +0200 Subject: [PATCH 065/107] Fix readme --- persistence-modules/java-sql2o/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/persistence-modules/java-sql2o/README.md b/persistence-modules/java-sql2o/README.md index 4c1ff931ce..a86e45f1c8 100644 --- a/persistence-modules/java-sql2o/README.md +++ b/persistence-modules/java-sql2o/README.md @@ -1,3 +1,3 @@ ### Relevant Articles: -- [A Guide to Jdbi](http://www.baeldung.com/jdbi) +- [A Guide to Sql2o](http://www.baeldung.com/sql2o) From 2b5e275716fb5d032c65dba07a4ef846b76cb20c Mon Sep 17 00:00:00 2001 From: Alessio Stalla Date: Wed, 24 Jul 2019 23:35:54 +0200 Subject: [PATCH 066/107] Fix package name --- .../persistence/{jdbi => sql2o}/Sql2oIntegrationTest.java | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) rename persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/{jdbi => sql2o}/Sql2oIntegrationTest.java (99%) diff --git a/persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/jdbi/Sql2oIntegrationTest.java b/persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/sql2o/Sql2oIntegrationTest.java similarity index 99% rename from persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/jdbi/Sql2oIntegrationTest.java rename to persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/sql2o/Sql2oIntegrationTest.java index 56f2e3a62e..4429b1578c 100644 --- a/persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/jdbi/Sql2oIntegrationTest.java +++ b/persistence-modules/java-sql2o/src/test/java/com/baeldung/persistence/sql2o/Sql2oIntegrationTest.java @@ -1,4 +1,4 @@ -package com.baeldung.persistence.jdbi; +package com.baeldung.persistence.sql2o; import org.junit.Test; import org.sql2o.Connection; @@ -8,12 +8,9 @@ import org.sql2o.Sql2o; import org.sql2o.data.Row; import org.sql2o.data.Table; -import java.sql.PreparedStatement; import java.sql.SQLException; import java.text.SimpleDateFormat; import java.util.*; -import java.util.function.Supplier; -import java.util.stream.Stream; import static org.junit.Assert.*; From 45f85e2c7d010d8cedeece71e270a7f81b8428d5 Mon Sep 17 00:00:00 2001 From: rahul Date: Thu, 25 Jul 2019 07:49:53 +0530 Subject: [PATCH 067/107] Changing the parent pom for core-java-networking-2 --- core-java-modules/core-java-networking-2/README.md | 7 ------- core-java-modules/core-java-networking-2/pom.xml | 8 +++----- core-java-modules/pom.xml | 1 + 3 files changed, 4 insertions(+), 12 deletions(-) delete mode 100644 core-java-modules/core-java-networking-2/README.md diff --git a/core-java-modules/core-java-networking-2/README.md b/core-java-modules/core-java-networking-2/README.md deleted file mode 100644 index 15cccf4a60..0000000000 --- a/core-java-modules/core-java-networking-2/README.md +++ /dev/null @@ -1,7 +0,0 @@ -========= - -## Core Java Networking - 2 - -### Relevant Articles - -- [Checking if a URL Exists in Java](https://www.baeldung.com/checking-if-a-url-exists-with-java) diff --git a/core-java-modules/core-java-networking-2/pom.xml b/core-java-modules/core-java-networking-2/pom.xml index 88e038d4c9..8a26f6ab9f 100644 --- a/core-java-modules/core-java-networking-2/pom.xml +++ b/core-java-modules/core-java-networking-2/pom.xml @@ -2,15 +2,13 @@ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0 core-java-networking-2 - 0.1.0-SNAPSHOT core-java-networking-2 jar - com.baeldung - parent-java - 0.0.1-SNAPSHOT - ../../parent-java + com.baeldung.core-java-modules + core-java-modules + 1.0.0-SNAPSHOT diff --git a/core-java-modules/pom.xml b/core-java-modules/pom.xml index 11a1003460..2dca62005d 100644 --- a/core-java-modules/pom.xml +++ b/core-java-modules/pom.xml @@ -17,6 +17,7 @@ pre-jpms core-java-exceptions core-java-optional + core-java-networking-2 From 2c53cdd44e9fdc4d8ef1386e99dd370990fb13da Mon Sep 17 00:00:00 2001 From: Amy DeGregorio Date: Thu, 25 Jul 2019 01:22:28 -0400 Subject: [PATCH 068/107] BAEL-3010 (#7408) * BAEL-3010 changing template dir * BAEL-3010 Add ThymeleafConfig --- .../baeldung/thymeleaf/ThymeleafConfig.java | 23 +++++++++++++++++++ .../templatedir/HelloController.java | 13 +++++++++++ .../src/main/resources/application.properties | 1 + .../src/main/resources/templates-2/hello.html | 10 ++++++++ 4 files changed, 47 insertions(+) create mode 100644 spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/ThymeleafConfig.java create mode 100644 spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/templatedir/HelloController.java create mode 100644 spring-thymeleaf-2/src/main/resources/application.properties create mode 100644 spring-thymeleaf-2/src/main/resources/templates-2/hello.html diff --git a/spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/ThymeleafConfig.java b/spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/ThymeleafConfig.java new file mode 100644 index 0000000000..2fd11628ad --- /dev/null +++ b/spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/ThymeleafConfig.java @@ -0,0 +1,23 @@ +package com.baeldung.thymeleaf; + +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.thymeleaf.templatemode.TemplateMode; +import org.thymeleaf.templateresolver.ClassLoaderTemplateResolver; + +@Configuration +public class ThymeleafConfig { + + @Bean + public ClassLoaderTemplateResolver secondaryTemplateResolver() { + ClassLoaderTemplateResolver secondaryTemplateResolver = new ClassLoaderTemplateResolver(); + secondaryTemplateResolver.setPrefix("templates-2/"); + secondaryTemplateResolver.setSuffix(".html"); + secondaryTemplateResolver.setTemplateMode(TemplateMode.HTML); + secondaryTemplateResolver.setCharacterEncoding("UTF-8"); + secondaryTemplateResolver.setOrder(1); + secondaryTemplateResolver.setCheckExistence(true); + + return secondaryTemplateResolver; + } +} diff --git a/spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/templatedir/HelloController.java b/spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/templatedir/HelloController.java new file mode 100644 index 0000000000..b404418106 --- /dev/null +++ b/spring-thymeleaf-2/src/main/java/com/baeldung/thymeleaf/templatedir/HelloController.java @@ -0,0 +1,13 @@ +package com.baeldung.thymeleaf.templatedir; + +import org.springframework.stereotype.Controller; +import org.springframework.web.bind.annotation.GetMapping; + +@Controller +public class HelloController { + + @GetMapping("/hello") + public String sayHello() { + return "hello"; + } +} diff --git a/spring-thymeleaf-2/src/main/resources/application.properties b/spring-thymeleaf-2/src/main/resources/application.properties new file mode 100644 index 0000000000..b09232bb1b --- /dev/null +++ b/spring-thymeleaf-2/src/main/resources/application.properties @@ -0,0 +1 @@ +#spring.thymeleaf.prefix=classpath:/templates-2/ \ No newline at end of file diff --git a/spring-thymeleaf-2/src/main/resources/templates-2/hello.html b/spring-thymeleaf-2/src/main/resources/templates-2/hello.html new file mode 100644 index 0000000000..035904c8ba --- /dev/null +++ b/spring-thymeleaf-2/src/main/resources/templates-2/hello.html @@ -0,0 +1,10 @@ + + + + +Enums in Thymeleaf + + +

    Hello from 'templates/templates-2'

    + + \ No newline at end of file From ffada1e2a749cf5903d28921e4697760f2b9569f Mon Sep 17 00:00:00 2001 From: Justin Albano Date: Thu, 25 Jul 2019 07:52:18 -0400 Subject: [PATCH 069/107] BAEL-3153: Updated code format to match standard Baeldung format Converted tabs into spaces --- .../changecase/ToLowerCaseUnitTest.java | 36 +++++++++---------- .../changecase/ToUpperCaseUnitTest.java | 34 +++++++++--------- 2 files changed, 35 insertions(+), 35 deletions(-) diff --git a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java index 14102be993..c395b61068 100644 --- a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java +++ b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToLowerCaseUnitTest.java @@ -7,23 +7,23 @@ import java.util.Locale; import org.junit.Test; public class ToLowerCaseUnitTest { - - private static final Locale TURKISH = new Locale("tr"); - private String name = "John Doe"; - private String foreignUppercase = "\u0049"; - @Test - public void givenMixedCaseString_WhenToLowerCase_ThenResultIsLowerCase() { - assertEquals("john doe", name.toLowerCase()); - } - - @Test - public void givenForeignString_WhenToLowerCaseWithoutLocale_ThenResultIsLowerCase() { - assertEquals("\u0069", foreignUppercase.toLowerCase()); - } - - @Test - public void givenForeignString_WhenToLowerCaseWithLocale_ThenResultIsLowerCase() { - assertEquals("\u0131", foreignUppercase.toLowerCase(TURKISH)); - } + private static final Locale TURKISH = new Locale("tr"); + private String name = "John Doe"; + private String foreignUppercase = "\u0049"; + + @Test + public void givenMixedCaseString_WhenToLowerCase_ThenResultIsLowerCase() { + assertEquals("john doe", name.toLowerCase()); + } + + @Test + public void givenForeignString_WhenToLowerCaseWithoutLocale_ThenResultIsLowerCase() { + assertEquals("\u0069", foreignUppercase.toLowerCase()); + } + + @Test + public void givenForeignString_WhenToLowerCaseWithLocale_ThenResultIsLowerCase() { + assertEquals("\u0131", foreignUppercase.toLowerCase(TURKISH)); + } } diff --git a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java index 90b80714a7..365b5ae52f 100644 --- a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java +++ b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java @@ -8,22 +8,22 @@ import org.junit.Test; public class ToUpperCaseUnitTest { - private static final Locale TURKISH = new Locale("tr"); - private String name = "John Doe"; - private String foreignUppercase = "\u0069"; + private static final Locale TURKISH = new Locale("tr"); + private String name = "John Doe"; + private String foreignUppercase = "\u0069"; - @Test - public void givenMixedCaseString_WhenToUpperCase_ThenResultIsUpperCase() { - assertEquals("JOHN DOE", name.toUpperCase()); - } - - @Test - public void givenForeignString_WhenToUpperCaseWithoutLocale_ThenResultIsUpperCase() { - assertEquals("\u0049", foreignUppercase.toUpperCase()); - } - - @Test - public void givenForeignString_WhenToUpperCaseWithLocale_ThenResultIsUpperCase() { - assertEquals("\u0130", foreignUppercase.toUpperCase(TURKISH)); - } + @Test + public void givenMixedCaseString_WhenToUpperCase_ThenResultIsUpperCase() { + assertEquals("JOHN DOE", name.toUpperCase()); + } + + @Test + public void givenForeignString_WhenToUpperCaseWithoutLocale_ThenResultIsUpperCase() { + assertEquals("\u0049", foreignUppercase.toUpperCase()); + } + + @Test + public void givenForeignString_WhenToUpperCaseWithLocale_ThenResultIsUpperCase() { + assertEquals("\u0130", foreignUppercase.toUpperCase(TURKISH)); + } } From b981da41c825aeb1bb821c4268cc78b0f8ec9d47 Mon Sep 17 00:00:00 2001 From: Gerardo Roza Date: Thu, 25 Jul 2019 11:40:21 -0300 Subject: [PATCH 070/107] added live tests for session timeout properties --- .../baeldung/web/SessionRestController.java | 17 ++++ .../src/main/resources/application.properties | 2 +- .../SessionConfigurationIntegrationTest.java | 92 +++++++++++++++++++ 3 files changed, 110 insertions(+), 1 deletion(-) create mode 100644 spring-security-mvc-session/src/main/java/com/baeldung/web/SessionRestController.java create mode 100644 spring-security-mvc-session/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/web/SessionRestController.java b/spring-security-mvc-session/src/main/java/com/baeldung/web/SessionRestController.java new file mode 100644 index 0000000000..1353ee25d0 --- /dev/null +++ b/spring-security-mvc-session/src/main/java/com/baeldung/web/SessionRestController.java @@ -0,0 +1,17 @@ +package com.baeldung.web; + +import javax.servlet.http.HttpSession; + +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.ResponseBody; +import org.springframework.web.bind.annotation.RestController; + +@RestController +public class SessionRestController { + + @GetMapping("/session-max-interval") + @ResponseBody + public String retrieveMaxSessionIncativeInterval(HttpSession session) { + return "Max Inactive Interval before Session expires: " + session.getMaxInactiveInterval(); + } +} diff --git a/spring-security-mvc-session/src/main/resources/application.properties b/spring-security-mvc-session/src/main/resources/application.properties index 39ec0a0b27..56b2b7b123 100644 --- a/spring-security-mvc-session/src/main/resources/application.properties +++ b/spring-security-mvc-session/src/main/resources/application.properties @@ -1,4 +1,4 @@ -server.servlet.session.timeout=60s +server.servlet.session.timeout=65s spring.mvc.view.prefix=/WEB-INF/view/ spring.mvc.view.suffix=.jsp diff --git a/spring-security-mvc-session/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java b/spring-security-mvc-session/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java new file mode 100644 index 0000000000..5a9bf72077 --- /dev/null +++ b/spring-security-mvc-session/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java @@ -0,0 +1,92 @@ +package com.baeldung.session; + +import static io.restassured.RestAssured.given; +import static org.assertj.core.api.Assertions.assertThat; + +import java.util.Optional; + +import org.junit.Test; +import org.springframework.http.HttpStatus; + +import io.restassured.filter.session.SessionFilter; +import io.restassured.response.Response; +import io.restassured.specification.RequestSpecification; + +/** + * This Live Test requires the service to be up and running. + */ +public class SessionConfigurationIntegrationTest { + + private static final String USER = "user1"; + private static final String PASSWORD = "user1Pass"; + private static final String SESSION_SVC_URL = "http://localhost:8080/session-max-interval"; + + @Test + public void givenValidUser_whenRequestResourceAfterSessionExpiration_thenRedirectedToInvalidSessionUri() throws Exception { + SessionFilter sessionFilter = new SessionFilter(); + simpleSvcRequestLoggingIn(sessionFilter); + Response resp2 = simpleResponseRequestUsingSessionNotFollowingRedirects(sessionFilter); + assertThat(resp2.getStatusCode()).isEqualTo(HttpStatus.OK.value()); + assertThat(resp2.getBody() + .asString()).isEqualTo("Max Inactive Interval before Session expires: 60"); + + // session will be expired in 60 seconds... + Thread.sleep(62000); + Response resp3 = simpleResponseRequestUsingSessionNotFollowingRedirects(sessionFilter); + + assertThat(resp3.getStatusCode()).isEqualTo(HttpStatus.FOUND.value()); + assertThat(resp3.getHeader("Location")).isEqualTo("http://localhost:8080/invalidSession.html"); + } + + @Test + public void givenValidUser_whenLoginMoreThanMaxValidSession_thenRedirectedToExpiredSessionUri() throws Exception { + SessionFilter sessionFilter = new SessionFilter(); + simpleSvcRequestLoggingIn(sessionFilter); + simpleSvcRequestLoggingIn(); + + // this login will expire the first session + simpleSvcRequestLoggingIn(); + + // now try to access a resource using expired session + Response resp4 = given().filter(sessionFilter) + .and() + .redirects() + .follow(false) + .when() + .get(SESSION_SVC_URL); + + assertThat(resp4.getStatusCode()).isEqualTo(HttpStatus.FOUND.value()); + assertThat(resp4.getHeader("Location")).isEqualTo("http://localhost:8080/sessionExpired.html"); + } + + private static void simpleSvcRequestLoggingIn() { + simpleSvcRequestLoggingIn(null); + } + + private static void simpleSvcRequestLoggingIn(SessionFilter sessionFilter) { + Response response = simpleResponseSvcRequestLoggingIn(Optional.ofNullable(sessionFilter)); + + assertThat(response.getStatusCode()).isEqualTo(HttpStatus.OK.value()); + assertThat(response.getBody() + .asString()).isEqualTo("Max Inactive Interval before Session expires: 60"); + } + + private static Response simpleResponseSvcRequestLoggingIn(Optional sessionFilter) { + RequestSpecification spec = given().auth() + .form(USER, PASSWORD); + sessionFilter.ifPresent(filter -> spec.and() + .filter(filter)); + return spec.when() + .get(SESSION_SVC_URL); + } + + private static Response simpleResponseRequestUsingSessionNotFollowingRedirects(SessionFilter sessionFilter) { + return given().filter(sessionFilter) + .and() + .redirects() + .follow(false) + .when() + .get(SESSION_SVC_URL); + } + +} From 30f4da3dd5b6d29dd64778fa68ab4e51167025c3 Mon Sep 17 00:00:00 2001 From: Gerardo Roza Date: Thu, 25 Jul 2019 12:08:47 -0300 Subject: [PATCH 071/107] renamed spring-security-mvc-session to simply spring-security-mvc --- pom.xml | 6 +++--- .../.gitignore | 0 .../README.md | 0 .../pom.xml | 4 ++-- .../main/java/com/baeldung/SpringSessionApplication.java | 0 .../com/baeldung/monitoring/MetricRegistrySingleton.java | 0 .../security/MySimpleUrlAuthenticationSuccessHandler.java | 0 .../src/main/java/com/baeldung/security/SessionFilter.java | 0 .../src/main/java/com/baeldung/spring/MvcConfig.java | 0 .../main/java/com/baeldung/spring/SecSecurityConfig.java | 0 .../java/com/baeldung/web/SessionListenerWithMetrics.java | 0 .../main/java/com/baeldung/web/SessionRestController.java | 0 .../src/main/resources/application.properties | 0 .../src/main/resources/logback.xml | 0 .../src/main/resources/webSecurityConfig.xml | 0 .../src/main/webapp/WEB-INF/mvc-servlet.xml | 0 .../src/main/webapp/WEB-INF/view/anonymous.jsp | 0 .../src/main/webapp/WEB-INF/view/console.jsp | 0 .../src/main/webapp/WEB-INF/view/homepage.jsp | 0 .../src/main/webapp/WEB-INF/view/invalidSession.jsp | 0 .../src/main/webapp/WEB-INF/view/login.jsp | 0 .../src/main/webapp/WEB-INF/view/sessionExpired.jsp | 0 .../src/main/webapp/WEB-INF/web.xml | 0 .../java/com/baeldung/SpringContextIntegrationTest.java | 0 .../session/SessionConfigurationIntegrationTest.java | 0 .../src/test/resources/.gitignore | 0 26 files changed, 5 insertions(+), 5 deletions(-) rename {spring-security-mvc-session => spring-security-mvc}/.gitignore (100%) rename {spring-security-mvc-session => spring-security-mvc}/README.md (100%) rename {spring-security-mvc-session => spring-security-mvc}/pom.xml (96%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/SpringSessionApplication.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/security/SessionFilter.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/spring/MvcConfig.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/spring/SecSecurityConfig.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/java/com/baeldung/web/SessionRestController.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/resources/application.properties (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/resources/logback.xml (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/resources/webSecurityConfig.xml (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/mvc-servlet.xml (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/view/anonymous.jsp (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/view/console.jsp (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/view/homepage.jsp (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/view/invalidSession.jsp (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/view/login.jsp (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/view/sessionExpired.jsp (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/main/webapp/WEB-INF/web.xml (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/test/java/com/baeldung/SpringContextIntegrationTest.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java (100%) rename {spring-security-mvc-session => spring-security-mvc}/src/test/resources/.gitignore (100%) diff --git a/pom.xml b/pom.xml index 21a42f89d6..81baa611d8 100644 --- a/pom.xml +++ b/pom.xml @@ -741,7 +741,7 @@ spring-security-mvc-ldap spring-security-mvc-login spring-security-mvc-persisted-remember-me - spring-security-mvc-session + spring-security-mvc spring-security-mvc-socket spring-security-openid @@ -916,7 +916,7 @@ spring-security-mvc-digest-auth spring-security-mvc-ldap spring-security-mvc-persisted-remember-me - spring-security-mvc-session + spring-security-mvc spring-security-mvc-socket spring-security-rest spring-security-sso @@ -1407,7 +1407,7 @@ spring-security-mvc-ldap spring-security-mvc-login spring-security-mvc-persisted-remember-me - spring-security-mvc-session + spring-security-mvc spring-security-mvc-socket spring-security-openid diff --git a/spring-security-mvc-session/.gitignore b/spring-security-mvc/.gitignore similarity index 100% rename from spring-security-mvc-session/.gitignore rename to spring-security-mvc/.gitignore diff --git a/spring-security-mvc-session/README.md b/spring-security-mvc/README.md similarity index 100% rename from spring-security-mvc-session/README.md rename to spring-security-mvc/README.md diff --git a/spring-security-mvc-session/pom.xml b/spring-security-mvc/pom.xml similarity index 96% rename from spring-security-mvc-session/pom.xml rename to spring-security-mvc/pom.xml index 5ed7fbecd3..98ad3daa46 100644 --- a/spring-security-mvc-session/pom.xml +++ b/spring-security-mvc/pom.xml @@ -3,9 +3,9 @@ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0 com.baeldung - spring-security-mvc-session + spring-security-mvc 0.1-SNAPSHOT - spring-security-mvc-session + spring-security-mvc jar diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/SpringSessionApplication.java b/spring-security-mvc/src/main/java/com/baeldung/SpringSessionApplication.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/SpringSessionApplication.java rename to spring-security-mvc/src/main/java/com/baeldung/SpringSessionApplication.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java b/spring-security-mvc/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java rename to spring-security-mvc/src/main/java/com/baeldung/monitoring/MetricRegistrySingleton.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java b/spring-security-mvc/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java rename to spring-security-mvc/src/main/java/com/baeldung/security/MySimpleUrlAuthenticationSuccessHandler.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/security/SessionFilter.java b/spring-security-mvc/src/main/java/com/baeldung/security/SessionFilter.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/security/SessionFilter.java rename to spring-security-mvc/src/main/java/com/baeldung/security/SessionFilter.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/spring/MvcConfig.java b/spring-security-mvc/src/main/java/com/baeldung/spring/MvcConfig.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/spring/MvcConfig.java rename to spring-security-mvc/src/main/java/com/baeldung/spring/MvcConfig.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/spring/SecSecurityConfig.java b/spring-security-mvc/src/main/java/com/baeldung/spring/SecSecurityConfig.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/spring/SecSecurityConfig.java rename to spring-security-mvc/src/main/java/com/baeldung/spring/SecSecurityConfig.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java b/spring-security-mvc/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java rename to spring-security-mvc/src/main/java/com/baeldung/web/SessionListenerWithMetrics.java diff --git a/spring-security-mvc-session/src/main/java/com/baeldung/web/SessionRestController.java b/spring-security-mvc/src/main/java/com/baeldung/web/SessionRestController.java similarity index 100% rename from spring-security-mvc-session/src/main/java/com/baeldung/web/SessionRestController.java rename to spring-security-mvc/src/main/java/com/baeldung/web/SessionRestController.java diff --git a/spring-security-mvc-session/src/main/resources/application.properties b/spring-security-mvc/src/main/resources/application.properties similarity index 100% rename from spring-security-mvc-session/src/main/resources/application.properties rename to spring-security-mvc/src/main/resources/application.properties diff --git a/spring-security-mvc-session/src/main/resources/logback.xml b/spring-security-mvc/src/main/resources/logback.xml similarity index 100% rename from spring-security-mvc-session/src/main/resources/logback.xml rename to spring-security-mvc/src/main/resources/logback.xml diff --git a/spring-security-mvc-session/src/main/resources/webSecurityConfig.xml b/spring-security-mvc/src/main/resources/webSecurityConfig.xml similarity index 100% rename from spring-security-mvc-session/src/main/resources/webSecurityConfig.xml rename to spring-security-mvc/src/main/resources/webSecurityConfig.xml diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/mvc-servlet.xml b/spring-security-mvc/src/main/webapp/WEB-INF/mvc-servlet.xml similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/mvc-servlet.xml rename to spring-security-mvc/src/main/webapp/WEB-INF/mvc-servlet.xml diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/view/anonymous.jsp b/spring-security-mvc/src/main/webapp/WEB-INF/view/anonymous.jsp similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/view/anonymous.jsp rename to spring-security-mvc/src/main/webapp/WEB-INF/view/anonymous.jsp diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/view/console.jsp b/spring-security-mvc/src/main/webapp/WEB-INF/view/console.jsp similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/view/console.jsp rename to spring-security-mvc/src/main/webapp/WEB-INF/view/console.jsp diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/view/homepage.jsp b/spring-security-mvc/src/main/webapp/WEB-INF/view/homepage.jsp similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/view/homepage.jsp rename to spring-security-mvc/src/main/webapp/WEB-INF/view/homepage.jsp diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/view/invalidSession.jsp b/spring-security-mvc/src/main/webapp/WEB-INF/view/invalidSession.jsp similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/view/invalidSession.jsp rename to spring-security-mvc/src/main/webapp/WEB-INF/view/invalidSession.jsp diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/view/login.jsp b/spring-security-mvc/src/main/webapp/WEB-INF/view/login.jsp similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/view/login.jsp rename to spring-security-mvc/src/main/webapp/WEB-INF/view/login.jsp diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/view/sessionExpired.jsp b/spring-security-mvc/src/main/webapp/WEB-INF/view/sessionExpired.jsp similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/view/sessionExpired.jsp rename to spring-security-mvc/src/main/webapp/WEB-INF/view/sessionExpired.jsp diff --git a/spring-security-mvc-session/src/main/webapp/WEB-INF/web.xml b/spring-security-mvc/src/main/webapp/WEB-INF/web.xml similarity index 100% rename from spring-security-mvc-session/src/main/webapp/WEB-INF/web.xml rename to spring-security-mvc/src/main/webapp/WEB-INF/web.xml diff --git a/spring-security-mvc-session/src/test/java/com/baeldung/SpringContextIntegrationTest.java b/spring-security-mvc/src/test/java/com/baeldung/SpringContextIntegrationTest.java similarity index 100% rename from spring-security-mvc-session/src/test/java/com/baeldung/SpringContextIntegrationTest.java rename to spring-security-mvc/src/test/java/com/baeldung/SpringContextIntegrationTest.java diff --git a/spring-security-mvc-session/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java b/spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java similarity index 100% rename from spring-security-mvc-session/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java rename to spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java diff --git a/spring-security-mvc-session/src/test/resources/.gitignore b/spring-security-mvc/src/test/resources/.gitignore similarity index 100% rename from spring-security-mvc-session/src/test/resources/.gitignore rename to spring-security-mvc/src/test/resources/.gitignore From 29e2806ade867f6189db6ba76aa1dbac73bdcf52 Mon Sep 17 00:00:00 2001 From: amit2103 Date: Fri, 26 Jul 2019 00:26:13 +0530 Subject: [PATCH 072/107] [BAEL-10984-1] - Added new URL for MyUIServlet and updated Grid creation logic --- .../java/com/baeldung/introduction/Row.java | 45 +++++++++++++++++++ .../com/baeldung/introduction/VaadinUI.java | 14 +++--- 2 files changed, 54 insertions(+), 5 deletions(-) create mode 100644 vaadin/src/main/java/com/baeldung/introduction/Row.java diff --git a/vaadin/src/main/java/com/baeldung/introduction/Row.java b/vaadin/src/main/java/com/baeldung/introduction/Row.java new file mode 100644 index 0000000000..412a286376 --- /dev/null +++ b/vaadin/src/main/java/com/baeldung/introduction/Row.java @@ -0,0 +1,45 @@ +package com.baeldung.introduction; + +public class Row { + + private String column1; + + private String column2; + + private String column3; + + public Row() { + + } + + public Row(String column1, String column2, String column3) { + super(); + this.column1 = column1; + this.column2 = column2; + this.column3 = column3; + } + + public String getColumn1() { + return column1; + } + + public void setColumn1(String column1) { + this.column1 = column1; + } + + public String getColumn2() { + return column2; + } + + public void setColumn2(String column2) { + this.column2 = column2; + } + + public String getColumn3() { + return column3; + } + + public void setColumn3(String column3) { + this.column3 = column3; + } +} \ No newline at end of file diff --git a/vaadin/src/main/java/com/baeldung/introduction/VaadinUI.java b/vaadin/src/main/java/com/baeldung/introduction/VaadinUI.java index 68be53b1b3..22ce19f5e0 100644 --- a/vaadin/src/main/java/com/baeldung/introduction/VaadinUI.java +++ b/vaadin/src/main/java/com/baeldung/introduction/VaadinUI.java @@ -201,10 +201,14 @@ public class VaadinUI extends UI { TwinColSelect twinColSelect = new TwinColSelect("TwinColSelect"); twinColSelect.setItems(numbers); - Grid grid = new Grid("Grid"); - grid.setColumns("Column1", "Column2", "Column3"); - grid.setItems("Item1", "Item2", "Item3"); - grid.setItems("Item4", "Item5", "Item6"); + Grid grid = new Grid(Row.class); + grid.setColumns("column1", "column2", "column3"); + Row row1 = new Row("Item1", "Item2", "Item3"); + Row row2 = new Row("Item4", "Item5", "Item6"); + List rows = new ArrayList(); + rows.add(row1); + rows.add(row2); + grid.setItems(rows); Panel panel = new Panel("Panel"); panel.setContent(grid); @@ -271,7 +275,7 @@ public class VaadinUI extends UI { setContent(verticalLayout); } - @WebServlet(urlPatterns = "/*", name = "MyUIServlet", asyncSupported = true) + @WebServlet(urlPatterns = "/VAADIN/*", name = "MyUIServlet", asyncSupported = true) @VaadinServletConfiguration(ui = VaadinUI.class, productionMode = false) public static class MyUIServlet extends VaadinServlet { } From 0d7a1747cc3c421174b42016cda053141350a686 Mon Sep 17 00:00:00 2001 From: Carlos Cano Date: Thu, 25 Jul 2019 21:09:02 +0200 Subject: [PATCH 073/107] Checking if an array is sorted in java (#7385) * SortedArrayChecker * add recursivity method with custom object * change test names * add new case with comparator * update methods with comparable param * format * fix test * change sign by comparable * change employee by object. Rename method --- .../baeldung/array/SortedArrayChecker.java | 38 ++++++++----------- .../array/SortedArrayCheckerUnitTest.java | 30 +++++++++------ 2 files changed, 34 insertions(+), 34 deletions(-) diff --git a/core-java-modules/core-java-arrays/src/main/java/com/baeldung/array/SortedArrayChecker.java b/core-java-modules/core-java-arrays/src/main/java/com/baeldung/array/SortedArrayChecker.java index ec612fd53b..78a9a8f4d1 100644 --- a/core-java-modules/core-java-arrays/src/main/java/com/baeldung/array/SortedArrayChecker.java +++ b/core-java-modules/core-java-arrays/src/main/java/com/baeldung/array/SortedArrayChecker.java @@ -2,7 +2,10 @@ package com.baeldung.array; import com.baeldung.arraycopy.model.Employee; +import java.util.Comparator; + public class SortedArrayChecker { + boolean isSorted(int[] array, int length) { if (array == null || length < 2) return true; @@ -22,7 +25,7 @@ public class SortedArrayChecker { return true; } - boolean isSorted(String[] array, int length) { + boolean isSorted(Comparable[] array, int length) { if (array == null || length < 2) return true; @@ -32,40 +35,31 @@ public class SortedArrayChecker { return isSorted(array, length - 1); } -boolean isSorted(String[] array) { - for (int i = 0; i < array.length - 1; ++i) { - if (array[i].compareTo(array[i + 1]) > 0) - return false; - } - - return true; -} - - boolean isSortedByName(Employee[] array) { + boolean isSorted(Comparable[] array) { for (int i = 0; i < array.length - 1; ++i) { - if (array[i].getName().compareTo(array[i + 1].getName()) > 0) + if (array[i].compareTo(array[i + 1]) > 0) return false; } return true; } -boolean isSortedByAge(Employee[] array) { - for (int i = 0; i < array.length - 1; ++i) { - if (array[i].getAge() > (array[i + 1].getAge())) - return false; + boolean isSorted(Object[] array, Comparator comparator) { + for (int i = 0; i < array.length - 1; ++i) { + if (comparator.compare(array[i], (array[i + 1])) > 0) + return false; + } + + return true; } - return true; -} - - boolean isSortedByAge(Employee[] array, int length) { + boolean isSorted(Object[] array, Comparator comparator, int length) { if (array == null || length < 2) return true; - if (array[length - 2].getAge() > array[length - 1].getAge()) + if (comparator.compare(array[length - 2], array[length - 1]) > 0) return false; - return isSortedByAge(array, length - 1); + return isSorted(array, comparator, length - 1); } } diff --git a/core-java-modules/core-java-arrays/src/test/java/com/baeldung/array/SortedArrayCheckerUnitTest.java b/core-java-modules/core-java-arrays/src/test/java/com/baeldung/array/SortedArrayCheckerUnitTest.java index 29866a3c22..7971e0eab7 100644 --- a/core-java-modules/core-java-arrays/src/test/java/com/baeldung/array/SortedArrayCheckerUnitTest.java +++ b/core-java-modules/core-java-arrays/src/test/java/com/baeldung/array/SortedArrayCheckerUnitTest.java @@ -4,32 +4,33 @@ import com.baeldung.arraycopy.model.Employee; import org.junit.Before; import org.junit.Test; +import java.util.Comparator; + import static org.assertj.core.api.Assertions.assertThat; -class SortedArrayCheckerUnitTest { - +public class SortedArrayCheckerUnitTest { private static final int[] INTEGER_SORTED = {1, 3, 5, 7, 9}; private static final int[] INTEGER_NOT_SORTED = {1, 3, 11, 7}; private static final String[] STRING_SORTED = {"abc", "cde", "fgh"}; private static final String[] STRING_NOT_SORTED = {"abc", "fgh", "cde", "ijk"}; - private final Employee[] EMPLOYEES_SORTED_BY_NAME = { + private static final Employee[] EMPLOYEES_SORTED_BY_NAME = { new Employee(1, "Carlos", 26), new Employee(2, "Daniel", 31), new Employee(3, "Marta", 27)}; - private final Employee[] EMPLOYEES_NOT_SORTED_BY_NAME = { + private static final Employee[] EMPLOYEES_NOT_SORTED_BY_NAME = { new Employee(1, "Daniel", 31), new Employee(2, "Carlos", 26), new Employee(3, "Marta", 27)}; - private final Employee[] EMPLOYEES_SORTED_BY_AGE = { + private static final Employee[] EMPLOYEES_SORTED_BY_AGE = { new Employee(1, "Carlos", 26), new Employee(2, "Marta", 27), new Employee(3, "Daniel", 31)}; - private final Employee[] EMPLOYEES_NOT_SORTED_BY_AGE = { + private static final Employee[] EMPLOYEES_NOT_SORTED_BY_AGE = { new Employee(1, "Marta", 27), new Employee(2, "Carlos", 26), new Employee(3, "Daniel", 31)}; @@ -61,13 +62,18 @@ class SortedArrayCheckerUnitTest { @Test public void givenEmployeeArray_thenReturnIfItIsSortedOrNot() { - assertThat(sortedArrayChecker.isSortedByName(EMPLOYEES_SORTED_BY_NAME)).isEqualTo(true); - assertThat(sortedArrayChecker.isSortedByName(EMPLOYEES_NOT_SORTED_BY_NAME)).isEqualTo(false); + assertThat(sortedArrayChecker.isSorted(EMPLOYEES_SORTED_BY_NAME, Comparator.comparing(Employee::getName))).isEqualTo(true); + assertThat(sortedArrayChecker.isSorted(EMPLOYEES_NOT_SORTED_BY_NAME, Comparator.comparing(Employee::getName))).isEqualTo(false); - assertThat(sortedArrayChecker.isSortedByAge(EMPLOYEES_SORTED_BY_AGE)).isEqualTo(true); - assertThat(sortedArrayChecker.isSortedByAge(EMPLOYEES_NOT_SORTED_BY_AGE)).isEqualTo(false); + assertThat(sortedArrayChecker.isSorted(EMPLOYEES_SORTED_BY_AGE, Comparator.comparingInt(Employee::getAge))).isEqualTo(true); + assertThat(sortedArrayChecker.isSorted(EMPLOYEES_NOT_SORTED_BY_AGE, Comparator.comparingInt(Employee::getAge))).isEqualTo(false); - assertThat(sortedArrayChecker.isSortedByAge(EMPLOYEES_SORTED_BY_AGE, EMPLOYEES_SORTED_BY_AGE.length)).isEqualTo(true); - assertThat(sortedArrayChecker.isSortedByAge(EMPLOYEES_NOT_SORTED_BY_AGE, EMPLOYEES_NOT_SORTED_BY_AGE.length)).isEqualTo(false); + assertThat(sortedArrayChecker + .isSorted(EMPLOYEES_SORTED_BY_AGE, Comparator.comparingInt(Employee::getAge), EMPLOYEES_SORTED_BY_AGE.length)) + .isEqualTo(true); + assertThat(sortedArrayChecker + .isSorted(EMPLOYEES_NOT_SORTED_BY_AGE, Comparator.comparingInt(Employee::getAge), EMPLOYEES_NOT_SORTED_BY_AGE.length)) + .isEqualTo(false); } + } \ No newline at end of file From 8358d5b2ecc5e9fe6889bfc593f31c8387d0028d Mon Sep 17 00:00:00 2001 From: Rodrigo Graciano Date: Thu, 25 Jul 2019 22:14:58 -0400 Subject: [PATCH 074/107] Rename unit test to follow naming standards --- .../{HelloResourceTest.java => HelloResourceUnitTest.java} | 2 +- .../test/java/com/baeldung/quarkus/NativeHelloResourceIT.java | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) rename quarkus/src/test/java/com/baeldung/quarkus/{HelloResourceTest.java => HelloResourceUnitTest.java} (91%) diff --git a/quarkus/src/test/java/com/baeldung/quarkus/HelloResourceTest.java b/quarkus/src/test/java/com/baeldung/quarkus/HelloResourceUnitTest.java similarity index 91% rename from quarkus/src/test/java/com/baeldung/quarkus/HelloResourceTest.java rename to quarkus/src/test/java/com/baeldung/quarkus/HelloResourceUnitTest.java index 3d0fff7562..a5ed99f585 100644 --- a/quarkus/src/test/java/com/baeldung/quarkus/HelloResourceTest.java +++ b/quarkus/src/test/java/com/baeldung/quarkus/HelloResourceUnitTest.java @@ -7,7 +7,7 @@ import static io.restassured.RestAssured.given; import static org.hamcrest.CoreMatchers.is; @QuarkusTest -public class HelloResourceTest { +public class HelloResourceUnitTest { @Test public void testHelloEndpoint() { diff --git a/quarkus/src/test/java/com/baeldung/quarkus/NativeHelloResourceIT.java b/quarkus/src/test/java/com/baeldung/quarkus/NativeHelloResourceIT.java index 4b0606f588..9ada64b6a5 100644 --- a/quarkus/src/test/java/com/baeldung/quarkus/NativeHelloResourceIT.java +++ b/quarkus/src/test/java/com/baeldung/quarkus/NativeHelloResourceIT.java @@ -3,7 +3,7 @@ package com.baeldung.quarkus; import io.quarkus.test.junit.SubstrateTest; @SubstrateTest -public class NativeHelloResourceIT extends HelloResourceTest { +public class NativeHelloResourceIT extends HelloResourceUnitTest { // Execute the same tests but in native mode. } \ No newline at end of file From c7433926c5122f639a90fa646b661531640ac064 Mon Sep 17 00:00:00 2001 From: Sam Millington Date: Fri, 26 Jul 2019 05:18:20 +0100 Subject: [PATCH 075/107] [BAEL-2951] - Sorting a string that may contain a number code (#7388) --- .../NaturalOrderComparators.java | 30 +++++++ .../NaturalOrderComparatorsUnitTest.java | 79 +++++++++++++++++++ 2 files changed, 109 insertions(+) create mode 100644 algorithms-miscellaneous-3/src/main/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparators.java create mode 100644 algorithms-miscellaneous-3/src/test/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparatorsUnitTest.java diff --git a/algorithms-miscellaneous-3/src/main/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparators.java b/algorithms-miscellaneous-3/src/main/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparators.java new file mode 100644 index 0000000000..376b196aa1 --- /dev/null +++ b/algorithms-miscellaneous-3/src/main/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparators.java @@ -0,0 +1,30 @@ +package com.baeldung.algorithms.stringsortingbynumber; + +import java.util.Comparator; + +public final class NaturalOrderComparators { + + private static final String DIGIT_AND_DECIMAL_REGEX = "[^\\d.]"; + + private NaturalOrderComparators() { + throw new AssertionError("Let's keep this static"); + } + + public static Comparator createNaturalOrderRegexComparator() { + return Comparator.comparingDouble(NaturalOrderComparators::parseStringToNumber); + } + + private static double parseStringToNumber(String input){ + + final String digitsOnly = input.replaceAll(DIGIT_AND_DECIMAL_REGEX, ""); + + if("".equals(digitsOnly)) return 0; + + try{ + return Double.parseDouble(digitsOnly); + }catch (NumberFormatException nfe){ + return 0; + } + } + +} diff --git a/algorithms-miscellaneous-3/src/test/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparatorsUnitTest.java b/algorithms-miscellaneous-3/src/test/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparatorsUnitTest.java new file mode 100644 index 0000000000..549151bc93 --- /dev/null +++ b/algorithms-miscellaneous-3/src/test/java/com/baeldung/algorithms/stringsortingbynumber/NaturalOrderComparatorsUnitTest.java @@ -0,0 +1,79 @@ +package com.baeldung.algorithms.stringsortingbynumber; + +import com.baeldung.algorithms.stringsortingbynumber.NaturalOrderComparators; +import org.junit.Test; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +import static org.junit.Assert.*; + +public class NaturalOrderComparatorsUnitTest { + + @Test + public void givenSimpleStringsContainingIntsAndDoubles_whenSortedByRegex_checkSortingCorrect() { + + List testStrings = Arrays.asList("a1", "b3", "c4", "d2.2", "d2.4", "d2.3d"); + + testStrings.sort(NaturalOrderComparators.createNaturalOrderRegexComparator()); + + List expected = Arrays.asList("a1", "d2.2", "d2.3d", "d2.4", "b3", "c4"); + + assertEquals(expected, testStrings); + + + } + + @Test + public void givenSimpleStringsContainingIntsAndDoublesWithAnInvalidNumber_whenSortedByRegex_checkSortingCorrect() { + + List testStrings = Arrays.asList("a1", "b3", "c4", "d2.2", "d2.4", "d2.3.3d"); + + testStrings.sort(NaturalOrderComparators.createNaturalOrderRegexComparator()); + + List expected = Arrays.asList("d2.3.3d", "a1", "d2.2", "d2.4", "b3", "c4"); + + assertEquals(expected, testStrings); + + + } + + @Test + public void givenAllForseenProblems_whenSortedByRegex_checkSortingCorrect() { + + List testStrings = Arrays.asList("a1", "b3", "c4", "d2.2", "d2.f4", "d2.3.3d"); + + testStrings.sort(NaturalOrderComparators.createNaturalOrderRegexComparator()); + + List expected = Arrays.asList("d2.3.3d", "a1", "d2.2", "d2.f4", "b3", "c4"); + + assertEquals(expected, testStrings); + + + } + + @Test + public void givenComplexStringsContainingSeparatedNumbers_whenSortedByRegex_checkNumbersCondensedAndSorted() { + + List testStrings = Arrays.asList("a1b2c5", "b3ght3.2", "something65.thensomething5"); //125, 33.2, 65.5 + + List expected = Arrays.asList("b3ght3.2", "something65.thensomething5", "a1b2c5" ); + + testStrings.sort(NaturalOrderComparators.createNaturalOrderRegexComparator()); + + assertEquals(expected, testStrings); + + } + + @Test + public void givenStringsNotContainingNumbers_whenSortedByRegex_checkOrderNotChanged() { + + List testStrings = Arrays.asList("a", "c", "d", "e"); + List expected = new ArrayList<>(testStrings); + + testStrings.sort(NaturalOrderComparators.createNaturalOrderRegexComparator()); + + assertEquals(expected, testStrings); + } +} \ No newline at end of file From 76bb391379d56032ce55b4559c5fc0e67638e279 Mon Sep 17 00:00:00 2001 From: psevestre Date: Fri, 26 Jul 2019 01:32:23 -0300 Subject: [PATCH 076/107] [BAEL-2284] R2DBC Sample Project (#7314) * [BAEL-2284] Sample project * [BAEL-2284] Sample project * [BAEL-2284] Sample code adjustments * [BAEL-2284] Sample code adjustments * [BAEL-2284] Sample code adjustments * [BAEL-2284] Add README --- persistence-modules/pom.xml | 1 + persistence-modules/r2dbc/.gitignore | 31 ++ .../.mvn/wrapper/MavenWrapperDownloader.java | 114 +++++++ .../r2dbc/.mvn/wrapper/maven-wrapper.jar | Bin 0 -> 48337 bytes .../.mvn/wrapper/maven-wrapper.properties | 1 + persistence-modules/r2dbc/README.md | 3 + persistence-modules/r2dbc/mvnw | 286 ++++++++++++++++++ persistence-modules/r2dbc/mvnw.cmd | 161 ++++++++++ persistence-modules/r2dbc/pom.xml | 90 ++++++ .../org/baeldung/examples/r2dbc/Account.java | 68 +++++ .../examples/r2dbc/AccountResource.java | 56 ++++ .../examples/r2dbc/DatasourceConfig.java | 65 ++++ .../r2dbc/R2DBCConfigurationProperties.java | 58 ++++ .../r2dbc/R2dbcExampleApplication.java | 17 ++ .../examples/r2dbc/ReactiveAccountDao.java | 76 +++++ ...itional-spring-configuration-metadata.json | 5 + .../r2dbc/src/main/resources/application.yml | 13 + .../r2dbc/R2dbcExampleApplicationTests.java | 102 +++++++ .../r2dbc/src/test/resources/application.yml | 6 + spring-cloud/spring-cloud-vault/pom.xml | 12 + .../spring/cloud/vaultsample/AccountRepo.java | 10 + .../cloud/vaultsample/AccountResource.java | 27 ++ .../cloud/vaultsample/SecretResource.java | 37 +++ .../cloud/vaultsample/domain/Account.java | 133 ++++++++ .../src/main/resources/application.yml | 17 +- .../src/main/resources/bootstrap.yml | 20 +- .../src/test/vault-config/vault-test.hcl | 3 + .../spring-cloud-vault/vault-cheatsheet.txt | 19 +- .../spring-cloud-vault/vault-unseal.bat | 8 +- 29 files changed, 1408 insertions(+), 31 deletions(-) create mode 100644 persistence-modules/r2dbc/.gitignore create mode 100644 persistence-modules/r2dbc/.mvn/wrapper/MavenWrapperDownloader.java create mode 100644 persistence-modules/r2dbc/.mvn/wrapper/maven-wrapper.jar create mode 100644 persistence-modules/r2dbc/.mvn/wrapper/maven-wrapper.properties create mode 100644 persistence-modules/r2dbc/README.md create mode 100644 persistence-modules/r2dbc/mvnw create mode 100644 persistence-modules/r2dbc/mvnw.cmd create mode 100644 persistence-modules/r2dbc/pom.xml create mode 100644 persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/Account.java create mode 100644 persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/AccountResource.java create mode 100644 persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/DatasourceConfig.java create mode 100644 persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2DBCConfigurationProperties.java create mode 100644 persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2dbcExampleApplication.java create mode 100644 persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/ReactiveAccountDao.java create mode 100644 persistence-modules/r2dbc/src/main/resources/META-INF/additional-spring-configuration-metadata.json create mode 100644 persistence-modules/r2dbc/src/main/resources/application.yml create mode 100644 persistence-modules/r2dbc/src/test/java/org/baeldung/examples/r2dbc/R2dbcExampleApplicationTests.java create mode 100644 persistence-modules/r2dbc/src/test/resources/application.yml create mode 100644 spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountRepo.java create mode 100644 spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountResource.java create mode 100644 spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/SecretResource.java create mode 100644 spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/domain/Account.java diff --git a/persistence-modules/pom.xml b/persistence-modules/pom.xml index 390bcc9d51..849c904604 100644 --- a/persistence-modules/pom.xml +++ b/persistence-modules/pom.xml @@ -58,5 +58,6 @@ spring-jpa spring-persistence-simple jpa-hibernate-cascade-type + r2dbc
    diff --git a/persistence-modules/r2dbc/.gitignore b/persistence-modules/r2dbc/.gitignore new file mode 100644 index 0000000000..a2a3040aa8 --- /dev/null +++ b/persistence-modules/r2dbc/.gitignore @@ -0,0 +1,31 @@ +HELP.md +target/ +!.mvn/wrapper/maven-wrapper.jar +!**/src/main/** +!**/src/test/** + +### STS ### +.apt_generated +.classpath +.factorypath +.project +.settings +.springBeans +.sts4-cache + +### IntelliJ IDEA ### +.idea +*.iws +*.iml +*.ipr + +### NetBeans ### +/nbproject/private/ +/nbbuild/ +/dist/ +/nbdist/ +/.nb-gradle/ +build/ + +### VS Code ### +.vscode/ diff --git a/persistence-modules/r2dbc/.mvn/wrapper/MavenWrapperDownloader.java b/persistence-modules/r2dbc/.mvn/wrapper/MavenWrapperDownloader.java new file mode 100644 index 0000000000..72308aa479 --- /dev/null +++ b/persistence-modules/r2dbc/.mvn/wrapper/MavenWrapperDownloader.java @@ -0,0 +1,114 @@ +/* +Licensed to the Apache Software Foundation (ASF) under one +or more contributor license agreements. See the NOTICE file +distributed with this work for additional information +regarding copyright ownership. The ASF licenses this file +to you 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 + + https://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. +*/ + +import java.io.File; +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.io.IOException; +import java.net.URL; +import java.nio.channels.Channels; +import java.nio.channels.ReadableByteChannel; +import java.util.Properties; + +public class MavenWrapperDownloader { + + /** + * Default URL to download the maven-wrapper.jar from, if no 'downloadUrl' is provided. + */ + private static final String DEFAULT_DOWNLOAD_URL = + "https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/0.4.2/maven-wrapper-0.4.2.jar"; + + /** + * Path to the maven-wrapper.properties file, which might contain a downloadUrl property to + * use instead of the default one. + */ + private static final String MAVEN_WRAPPER_PROPERTIES_PATH = + ".mvn/wrapper/maven-wrapper.properties"; + + /** + * Path where the maven-wrapper.jar will be saved to. + */ + private static final String MAVEN_WRAPPER_JAR_PATH = + ".mvn/wrapper/maven-wrapper.jar"; + + /** + * Name of the property which should be used to override the default download url for the wrapper. + */ + private static final String PROPERTY_NAME_WRAPPER_URL = "wrapperUrl"; + + public static void main(String args[]) { + System.out.println("- Downloader started"); + File baseDirectory = new File(args[0]); + System.out.println("- Using base directory: " + baseDirectory.getAbsolutePath()); + + // If the maven-wrapper.properties exists, read it and check if it contains a custom + // wrapperUrl parameter. + File mavenWrapperPropertyFile = new File(baseDirectory, MAVEN_WRAPPER_PROPERTIES_PATH); + String url = DEFAULT_DOWNLOAD_URL; + if(mavenWrapperPropertyFile.exists()) { + FileInputStream mavenWrapperPropertyFileInputStream = null; + try { + mavenWrapperPropertyFileInputStream = new FileInputStream(mavenWrapperPropertyFile); + Properties mavenWrapperProperties = new Properties(); + mavenWrapperProperties.load(mavenWrapperPropertyFileInputStream); + url = mavenWrapperProperties.getProperty(PROPERTY_NAME_WRAPPER_URL, url); + } catch (IOException e) { + System.out.println("- ERROR loading '" + MAVEN_WRAPPER_PROPERTIES_PATH + "'"); + } finally { + try { + if(mavenWrapperPropertyFileInputStream != null) { + mavenWrapperPropertyFileInputStream.close(); + } + } catch (IOException e) { + // Ignore ... + } + } + } + System.out.println("- Downloading from: : " + url); + + File outputFile = new File(baseDirectory.getAbsolutePath(), MAVEN_WRAPPER_JAR_PATH); + if(!outputFile.getParentFile().exists()) { + if(!outputFile.getParentFile().mkdirs()) { + System.out.println( + "- ERROR creating output direcrory '" + outputFile.getParentFile().getAbsolutePath() + "'"); + } + } + System.out.println("- Downloading to: " + outputFile.getAbsolutePath()); + try { + downloadFileFromURL(url, outputFile); + System.out.println("Done"); + System.exit(0); + } catch (Throwable e) { + System.out.println("- Error downloading"); + e.printStackTrace(); + System.exit(1); + } + } + + private static void downloadFileFromURL(String urlString, File destination) throws Exception { + URL website = new URL(urlString); + ReadableByteChannel rbc; + rbc = Channels.newChannel(website.openStream()); + FileOutputStream fos = new FileOutputStream(destination); + fos.getChannel().transferFrom(rbc, 0, Long.MAX_VALUE); + fos.close(); + rbc.close(); + } + +} diff --git a/persistence-modules/r2dbc/.mvn/wrapper/maven-wrapper.jar b/persistence-modules/r2dbc/.mvn/wrapper/maven-wrapper.jar new file mode 100644 index 0000000000000000000000000000000000000000..01e67997377a393fd672c7dcde9dccbedf0cb1e9 GIT binary patch literal 48337 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 \(.*\)$'` + if expr "$link" : '/.*' > /dev/null; then + PRG="$link" + else + PRG="`dirname "$PRG"`/$link" + fi + done + + saveddir=`pwd` + + M2_HOME=`dirname "$PRG"`/.. + + # make it fully qualified + M2_HOME=`cd "$M2_HOME" && pwd` + + cd "$saveddir" + # echo Using m2 at $M2_HOME +fi + +# For Cygwin, ensure paths are in UNIX format before anything is touched +if $cygwin ; then + [ -n "$M2_HOME" ] && + M2_HOME=`cygpath --unix "$M2_HOME"` + [ -n "$JAVA_HOME" ] && + JAVA_HOME=`cygpath --unix "$JAVA_HOME"` + [ -n "$CLASSPATH" ] && + CLASSPATH=`cygpath --path --unix "$CLASSPATH"` +fi + +# For Mingw, ensure paths are in UNIX format before anything is touched +if $mingw ; then + [ -n "$M2_HOME" ] && + M2_HOME="`(cd "$M2_HOME"; pwd)`" + [ -n "$JAVA_HOME" ] && + JAVA_HOME="`(cd "$JAVA_HOME"; pwd)`" + # TODO classpath? +fi + +if [ -z "$JAVA_HOME" ]; then + javaExecutable="`which javac`" + if [ -n "$javaExecutable" ] && ! [ "`expr \"$javaExecutable\" : '\([^ ]*\)'`" = "no" ]; then + # readlink(1) is not available as standard on Solaris 10. + readLink=`which readlink` + if [ ! `expr "$readLink" : '\([^ ]*\)'` = "no" ]; then + if $darwin ; then + javaHome="`dirname \"$javaExecutable\"`" + javaExecutable="`cd \"$javaHome\" && pwd -P`/javac" + else + javaExecutable="`readlink -f \"$javaExecutable\"`" + fi + javaHome="`dirname \"$javaExecutable\"`" + javaHome=`expr "$javaHome" : '\(.*\)/bin'` + JAVA_HOME="$javaHome" + export JAVA_HOME + fi + fi +fi + +if [ -z "$JAVACMD" ] ; then + if [ -n "$JAVA_HOME" ] ; then + if [ -x "$JAVA_HOME/jre/sh/java" ] ; then + # IBM's JDK on AIX uses strange locations for the executables + JAVACMD="$JAVA_HOME/jre/sh/java" + else + JAVACMD="$JAVA_HOME/bin/java" + fi + else + JAVACMD="`which java`" + fi +fi + +if [ ! -x "$JAVACMD" ] ; then + echo "Error: JAVA_HOME is not defined correctly." >&2 + echo " We cannot execute $JAVACMD" >&2 + exit 1 +fi + +if [ -z "$JAVA_HOME" ] ; then + echo "Warning: JAVA_HOME environment variable is not set." +fi + +CLASSWORLDS_LAUNCHER=org.codehaus.plexus.classworlds.launcher.Launcher + +# traverses directory structure from process work directory to filesystem root +# first directory with .mvn subdirectory is considered project base directory +find_maven_basedir() { + + if [ -z "$1" ] + then + echo "Path not specified to find_maven_basedir" + return 1 + fi + + basedir="$1" + wdir="$1" + while [ "$wdir" != '/' ] ; do + if [ -d "$wdir"/.mvn ] ; then + basedir=$wdir + break + fi + # workaround for JBEAP-8937 (on Solaris 10/Sparc) + if [ -d "${wdir}" ]; then + wdir=`cd "$wdir/.."; pwd` + fi + # end of workaround + done + echo "${basedir}" +} + +# concatenates all lines of a file +concat_lines() { + if [ -f "$1" ]; then + echo "$(tr -s '\n' ' ' < "$1")" + fi +} + +BASE_DIR=`find_maven_basedir "$(pwd)"` +if [ -z "$BASE_DIR" ]; then + exit 1; +fi + +########################################################################################## +# Extension to allow automatically downloading the maven-wrapper.jar from Maven-central +# This allows using the maven wrapper in projects that prohibit checking in binary data. +########################################################################################## +if [ -r "$BASE_DIR/.mvn/wrapper/maven-wrapper.jar" ]; then + if [ "$MVNW_VERBOSE" = true ]; then + echo "Found .mvn/wrapper/maven-wrapper.jar" + fi +else + if [ "$MVNW_VERBOSE" = true ]; then + echo "Couldn't find .mvn/wrapper/maven-wrapper.jar, downloading it ..." + fi + jarUrl="https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/0.4.2/maven-wrapper-0.4.2.jar" + while IFS="=" read key value; do + case "$key" in (wrapperUrl) jarUrl="$value"; break ;; + esac + done < "$BASE_DIR/.mvn/wrapper/maven-wrapper.properties" + if [ "$MVNW_VERBOSE" = true ]; then + echo "Downloading from: $jarUrl" + fi + wrapperJarPath="$BASE_DIR/.mvn/wrapper/maven-wrapper.jar" + + if command -v wget > /dev/null; then + if [ "$MVNW_VERBOSE" = true ]; then + echo "Found wget ... using wget" + fi + wget "$jarUrl" -O "$wrapperJarPath" + elif command -v curl > /dev/null; then + if [ "$MVNW_VERBOSE" = true ]; then + echo "Found curl ... using curl" + fi + curl -o "$wrapperJarPath" "$jarUrl" + else + if [ "$MVNW_VERBOSE" = true ]; then + echo "Falling back to using Java to download" + fi + javaClass="$BASE_DIR/.mvn/wrapper/MavenWrapperDownloader.java" + if [ -e "$javaClass" ]; then + if [ ! -e "$BASE_DIR/.mvn/wrapper/MavenWrapperDownloader.class" ]; then + if [ "$MVNW_VERBOSE" = true ]; then + echo " - Compiling MavenWrapperDownloader.java ..." + fi + # Compiling the Java class + ("$JAVA_HOME/bin/javac" "$javaClass") + fi + if [ -e "$BASE_DIR/.mvn/wrapper/MavenWrapperDownloader.class" ]; then + # Running the downloader + if [ "$MVNW_VERBOSE" = true ]; then + echo " - Running MavenWrapperDownloader.java ..." + fi + ("$JAVA_HOME/bin/java" -cp .mvn/wrapper MavenWrapperDownloader "$MAVEN_PROJECTBASEDIR") + fi + fi + fi +fi +########################################################################################## +# End of extension +########################################################################################## + +export MAVEN_PROJECTBASEDIR=${MAVEN_BASEDIR:-"$BASE_DIR"} +if [ "$MVNW_VERBOSE" = true ]; then + echo $MAVEN_PROJECTBASEDIR +fi +MAVEN_OPTS="$(concat_lines "$MAVEN_PROJECTBASEDIR/.mvn/jvm.config") $MAVEN_OPTS" + +# For Cygwin, switch paths to Windows format before running java +if $cygwin; then + [ -n "$M2_HOME" ] && + M2_HOME=`cygpath --path --windows "$M2_HOME"` + [ -n "$JAVA_HOME" ] && + JAVA_HOME=`cygpath --path --windows "$JAVA_HOME"` + [ -n "$CLASSPATH" ] && + CLASSPATH=`cygpath --path --windows "$CLASSPATH"` + [ -n "$MAVEN_PROJECTBASEDIR" ] && + MAVEN_PROJECTBASEDIR=`cygpath --path --windows "$MAVEN_PROJECTBASEDIR"` +fi + +WRAPPER_LAUNCHER=org.apache.maven.wrapper.MavenWrapperMain + +exec "$JAVACMD" \ + $MAVEN_OPTS \ + -classpath "$MAVEN_PROJECTBASEDIR/.mvn/wrapper/maven-wrapper.jar" \ + "-Dmaven.home=${M2_HOME}" "-Dmaven.multiModuleProjectDirectory=${MAVEN_PROJECTBASEDIR}" \ + ${WRAPPER_LAUNCHER} $MAVEN_CONFIG "$@" diff --git a/persistence-modules/r2dbc/mvnw.cmd b/persistence-modules/r2dbc/mvnw.cmd new file mode 100644 index 0000000000..fef5a8f7f9 --- /dev/null +++ b/persistence-modules/r2dbc/mvnw.cmd @@ -0,0 +1,161 @@ +@REM ---------------------------------------------------------------------------- +@REM Licensed to the Apache Software Foundation (ASF) under one +@REM or more contributor license agreements. See the NOTICE file +@REM distributed with this work for additional information +@REM regarding copyright ownership. The ASF licenses this file +@REM to you under the Apache License, Version 2.0 (the +@REM "License"); you may not use this file except in compliance +@REM with the License. You may obtain a copy of the License at +@REM +@REM https://www.apache.org/licenses/LICENSE-2.0 +@REM +@REM Unless required by applicable law or agreed to in writing, +@REM software distributed under the License is distributed on an +@REM "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +@REM KIND, either express or implied. See the License for the +@REM specific language governing permissions and limitations +@REM under the License. +@REM ---------------------------------------------------------------------------- + +@REM ---------------------------------------------------------------------------- +@REM Maven2 Start Up Batch script +@REM +@REM Required ENV vars: +@REM JAVA_HOME - location of a JDK home dir +@REM +@REM Optional ENV vars +@REM M2_HOME - location of maven2's installed home dir +@REM MAVEN_BATCH_ECHO - set to 'on' to enable the echoing of the batch commands +@REM MAVEN_BATCH_PAUSE - set to 'on' to wait for a key stroke before ending +@REM MAVEN_OPTS - parameters passed to the Java VM when running Maven +@REM e.g. to debug Maven itself, use +@REM set MAVEN_OPTS=-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000 +@REM MAVEN_SKIP_RC - flag to disable loading of mavenrc files +@REM ---------------------------------------------------------------------------- + +@REM Begin all REM lines with '@' in case MAVEN_BATCH_ECHO is 'on' +@echo off +@REM set title of command window +title %0 +@REM enable echoing my setting MAVEN_BATCH_ECHO to 'on' +@if "%MAVEN_BATCH_ECHO%" == "on" echo %MAVEN_BATCH_ECHO% + +@REM set %HOME% to equivalent of $HOME +if "%HOME%" == "" (set "HOME=%HOMEDRIVE%%HOMEPATH%") + +@REM Execute a user defined script before this one +if not "%MAVEN_SKIP_RC%" == "" goto skipRcPre +@REM check for pre script, once with legacy .bat ending and once with .cmd ending +if exist "%HOME%\mavenrc_pre.bat" call "%HOME%\mavenrc_pre.bat" +if exist "%HOME%\mavenrc_pre.cmd" call "%HOME%\mavenrc_pre.cmd" +:skipRcPre + +@setlocal + +set ERROR_CODE=0 + +@REM To isolate internal variables from possible post scripts, we use another setlocal +@setlocal + +@REM ==== START VALIDATION ==== +if not "%JAVA_HOME%" == "" goto OkJHome + +echo. +echo Error: JAVA_HOME not found in your environment. >&2 +echo Please set the JAVA_HOME variable in your environment to match the >&2 +echo location of your Java installation. >&2 +echo. +goto error + +:OkJHome +if exist "%JAVA_HOME%\bin\java.exe" goto init + +echo. +echo Error: JAVA_HOME is set to an invalid directory. >&2 +echo JAVA_HOME = "%JAVA_HOME%" >&2 +echo Please set the JAVA_HOME variable in your environment to match the >&2 +echo location of your Java installation. >&2 +echo. +goto error + +@REM ==== END VALIDATION ==== + +:init + +@REM Find the project base dir, i.e. the directory that contains the folder ".mvn". +@REM Fallback to current working directory if not found. + +set MAVEN_PROJECTBASEDIR=%MAVEN_BASEDIR% +IF NOT "%MAVEN_PROJECTBASEDIR%"=="" goto endDetectBaseDir + +set EXEC_DIR=%CD% +set WDIR=%EXEC_DIR% +:findBaseDir +IF EXIST "%WDIR%"\.mvn goto baseDirFound +cd .. +IF "%WDIR%"=="%CD%" goto baseDirNotFound +set WDIR=%CD% +goto findBaseDir + +:baseDirFound +set MAVEN_PROJECTBASEDIR=%WDIR% +cd "%EXEC_DIR%" +goto endDetectBaseDir + +:baseDirNotFound +set MAVEN_PROJECTBASEDIR=%EXEC_DIR% +cd "%EXEC_DIR%" + +:endDetectBaseDir + +IF NOT EXIST "%MAVEN_PROJECTBASEDIR%\.mvn\jvm.config" goto endReadAdditionalConfig + +@setlocal EnableExtensions EnableDelayedExpansion +for /F "usebackq delims=" %%a in ("%MAVEN_PROJECTBASEDIR%\.mvn\jvm.config") do set JVM_CONFIG_MAVEN_PROPS=!JVM_CONFIG_MAVEN_PROPS! %%a +@endlocal & set JVM_CONFIG_MAVEN_PROPS=%JVM_CONFIG_MAVEN_PROPS% + +:endReadAdditionalConfig + +SET MAVEN_JAVA_EXE="%JAVA_HOME%\bin\java.exe" +set WRAPPER_JAR="%MAVEN_PROJECTBASEDIR%\.mvn\wrapper\maven-wrapper.jar" +set WRAPPER_LAUNCHER=org.apache.maven.wrapper.MavenWrapperMain + +set DOWNLOAD_URL="https://repo.maven.apache.org/maven2/io/takari/maven-wrapper/0.4.2/maven-wrapper-0.4.2.jar" +FOR /F "tokens=1,2 delims==" %%A IN (%MAVEN_PROJECTBASEDIR%\.mvn\wrapper\maven-wrapper.properties) DO ( + IF "%%A"=="wrapperUrl" SET DOWNLOAD_URL=%%B +) + +@REM Extension to allow automatically downloading the maven-wrapper.jar from Maven-central +@REM This allows using the maven wrapper in projects that prohibit checking in binary data. +if exist %WRAPPER_JAR% ( + echo Found %WRAPPER_JAR% +) else ( + echo Couldn't find %WRAPPER_JAR%, downloading it ... + echo Downloading from: %DOWNLOAD_URL% + powershell -Command "(New-Object Net.WebClient).DownloadFile('%DOWNLOAD_URL%', '%WRAPPER_JAR%')" + echo Finished downloading %WRAPPER_JAR% +) +@REM End of extension + +%MAVEN_JAVA_EXE% %JVM_CONFIG_MAVEN_PROPS% %MAVEN_OPTS% %MAVEN_DEBUG_OPTS% -classpath %WRAPPER_JAR% "-Dmaven.multiModuleProjectDirectory=%MAVEN_PROJECTBASEDIR%" %WRAPPER_LAUNCHER% %MAVEN_CONFIG% %* +if ERRORLEVEL 1 goto error +goto end + +:error +set ERROR_CODE=1 + +:end +@endlocal & set ERROR_CODE=%ERROR_CODE% + +if not "%MAVEN_SKIP_RC%" == "" goto skipRcPost +@REM check for post script, once with legacy .bat ending and once with .cmd ending +if exist "%HOME%\mavenrc_post.bat" call "%HOME%\mavenrc_post.bat" +if exist "%HOME%\mavenrc_post.cmd" call "%HOME%\mavenrc_post.cmd" +:skipRcPost + +@REM pause the script if MAVEN_BATCH_PAUSE is set to 'on' +if "%MAVEN_BATCH_PAUSE%" == "on" pause + +if "%MAVEN_TERMINATE_CMD%" == "on" exit %ERROR_CODE% + +exit /B %ERROR_CODE% diff --git a/persistence-modules/r2dbc/pom.xml b/persistence-modules/r2dbc/pom.xml new file mode 100644 index 0000000000..388abafdaf --- /dev/null +++ b/persistence-modules/r2dbc/pom.xml @@ -0,0 +1,90 @@ + + + 4.0.0 + + org.springframework.boot + spring-boot-starter-parent + 2.1.6.RELEASE + + + org.baeldung.examples.r2dbc + r2dbc-example + 0.0.1-SNAPSHOT + r2dbc-example + Sample R2DBC Project + + + 1.8 + + + + + org.springframework.boot + spring-boot-starter-webflux + + + + org.springframework.boot + spring-boot-starter-test + test + + + io.projectreactor + reactor-test + test + + + + + + io.r2dbc + r2dbc-h2 + 0.8.0.M8 + + + + org.springframework.boot + spring-boot-configuration-processor + true + + + org.springframework.boot + spring-boot-devtools + + + + + + + org.springframework.boot + spring-boot-maven-plugin + + + + + + + + + spring-snapshots + Spring Snapshots + https://repo.spring.io/snapshot + + true + + + + + spring-milestones + Spring Milestones + https://repo.spring.io/milestone + + false + + + + + + diff --git a/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/Account.java b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/Account.java new file mode 100644 index 0000000000..65bf33168e --- /dev/null +++ b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/Account.java @@ -0,0 +1,68 @@ +package org.baeldung.examples.r2dbc; + +import java.math.BigDecimal; + +public class Account { + + private Long id; + private String iban; + private BigDecimal balance; + + + public Account() {} + + public Account(Long id, String iban, BigDecimal balance) { + this.id = id; + this.iban = iban; + this.balance = balance; + } + + public Account(Long id, String iban, Double balance) { + this.id = id; + this.iban = iban; + this.balance = new BigDecimal(balance); + } + + /** + * @return the id + */ + public Long getId() { + return id; + } + + /** + * @param id the id to set + */ + public void setId(Long id) { + this.id = id; + } + + /** + * @return the iban + */ + public String getIban() { + return iban; + } + + /** + * @param iban the iban to set + */ + public void setIban(String iban) { + this.iban = iban; + } + + /** + * @return the balance + */ + public BigDecimal getBalance() { + return balance; + } + + /** + * @param balance the balance to set + */ + public void setBalance(BigDecimal balance) { + this.balance = balance; + } + +} diff --git a/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/AccountResource.java b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/AccountResource.java new file mode 100644 index 0000000000..90816a7522 --- /dev/null +++ b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/AccountResource.java @@ -0,0 +1,56 @@ +/** + * + */ +package org.baeldung.examples.r2dbc; + +import java.math.BigDecimal; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.PostMapping; +import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.RestController; + +import io.r2dbc.spi.Connection; +import io.r2dbc.spi.ConnectionFactory; +import reactor.core.publisher.Flux; +import reactor.core.publisher.Mono; + +/** + * @author Philippe + * + */ +@RestController +public class AccountResource { + + private final ReactiveAccountDao accountDao; + + public AccountResource(ReactiveAccountDao accountDao) { + this.accountDao = accountDao; + } + + @GetMapping("/accounts/{id}") + public Mono> getAccount(@PathVariable("id") Long id) { + + return accountDao.findById(id) + .map(acc -> new ResponseEntity<>(acc, HttpStatus.OK)) + .switchIfEmpty(Mono.just(new ResponseEntity<>(null, HttpStatus.NOT_FOUND))); + } + + @GetMapping("/accounts") + public Flux getAllAccounts() { + return accountDao.findAll(); + } + + @PostMapping("/accounts") + public Mono> postAccount(@RequestBody Account account) { + return accountDao.createAccount(account) + .map(acc -> new ResponseEntity<>(acc, HttpStatus.CREATED)) + .log(); + } + +} diff --git a/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/DatasourceConfig.java b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/DatasourceConfig.java new file mode 100644 index 0000000000..5b695f39f5 --- /dev/null +++ b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/DatasourceConfig.java @@ -0,0 +1,65 @@ +package org.baeldung.examples.r2dbc; + +import org.springframework.boot.CommandLineRunner; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.util.StringUtils; + +import io.netty.util.internal.StringUtil; +import io.r2dbc.spi.ConnectionFactories; +import io.r2dbc.spi.ConnectionFactory; +import io.r2dbc.spi.ConnectionFactoryOptions; +import io.r2dbc.spi.ConnectionFactoryOptions.Builder; +import io.r2dbc.spi.Option; +import reactor.core.publisher.Flux; + +import static io.r2dbc.spi.ConnectionFactoryOptions.*; + + +@Configuration +public class DatasourceConfig { + + @Bean + public ConnectionFactory connectionFactory(R2DBCConfigurationProperties properties) { + + ConnectionFactoryOptions baseOptions = ConnectionFactoryOptions.parse(properties.getUrl()); + Builder ob = ConnectionFactoryOptions.builder().from(baseOptions); + if ( !StringUtil.isNullOrEmpty(properties.getUser())) { + ob = ob.option(USER, properties.getUser()); + } + + if ( !StringUtil.isNullOrEmpty(properties.getPassword())) { + ob = ob.option(PASSWORD, properties.getPassword()); + } + + ConnectionFactory cf = ConnectionFactories.get(ob.build()); + return cf; + } + + + @Bean + public CommandLineRunner initDatabase(ConnectionFactory cf) { + + return (args) -> + Flux.from(cf.create()) + .flatMap(c -> + Flux.from(c.createBatch() + .add("drop table if exists Account") + .add("create table Account(" + + "id IDENTITY(1,1)," + + "iban varchar(80) not null," + + "balance DECIMAL(18,2) not null)") + .add("insert into Account(iban,balance)" + + "values('BR430120980198201982',100.00)") + .add("insert into Account(iban,balance)" + + "values('BR430120998729871000',250.00)") + .execute()) + .doFinally((st) -> c.close()) + ) + .log() + .blockLast(); + } + + +} + diff --git a/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2DBCConfigurationProperties.java b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2DBCConfigurationProperties.java new file mode 100644 index 0000000000..02733ebed9 --- /dev/null +++ b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2DBCConfigurationProperties.java @@ -0,0 +1,58 @@ +package org.baeldung.examples.r2dbc; + +import javax.validation.constraints.NotEmpty; + +import org.springframework.boot.context.properties.ConfigurationProperties; + +@ConfigurationProperties(prefix = "r2dbc") +public class R2DBCConfigurationProperties { + + @NotEmpty + private String url; + + private String user; + private String password; + + /** + * @return the url + */ + public String getUrl() { + return url; + } + + /** + * @param url the url to set + */ + public void setUrl(String url) { + this.url = url; + } + + /** + * @return the user + */ + public String getUser() { + return user; + } + + /** + * @param user the user to set + */ + public void setUser(String user) { + this.user = user; + } + + /** + * @return the password + */ + public String getPassword() { + return password; + } + + /** + * @param password the password to set + */ + public void setPassword(String password) { + this.password = password; + } + +} diff --git a/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2dbcExampleApplication.java b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2dbcExampleApplication.java new file mode 100644 index 0000000000..1147936e2d --- /dev/null +++ b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/R2dbcExampleApplication.java @@ -0,0 +1,17 @@ +package org.baeldung.examples.r2dbc; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.boot.context.properties.EnableConfigurationProperties; + +@SpringBootApplication +@EnableConfigurationProperties(R2DBCConfigurationProperties.class) +public class R2dbcExampleApplication { + + public static void main(String[] args) { + SpringApplication.run(R2dbcExampleApplication.class, args); + } + + + +} diff --git a/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/ReactiveAccountDao.java b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/ReactiveAccountDao.java new file mode 100644 index 0000000000..f9717d4b9b --- /dev/null +++ b/persistence-modules/r2dbc/src/main/java/org/baeldung/examples/r2dbc/ReactiveAccountDao.java @@ -0,0 +1,76 @@ +package org.baeldung.examples.r2dbc; + +import java.math.BigDecimal; + +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; +import org.springframework.stereotype.Component; + +import io.r2dbc.spi.Connection; +import io.r2dbc.spi.ConnectionFactory; +import reactor.core.publisher.Flux; +import reactor.core.publisher.Mono; + +@Component +public class ReactiveAccountDao { + + private ConnectionFactory connectionFactory; + + public ReactiveAccountDao(ConnectionFactory connectionFactory) { + this.connectionFactory = connectionFactory; + } + + public Mono findById(long id) { + + return Mono.from(connectionFactory.create()) + .flatMap(c -> Mono.from(c.createStatement("select id,iban,balance from Account where id = $1") + .bind("$1", id) + .execute()) + .doFinally((st) -> close(c))) + .map(result -> result.map((row, meta) -> + new Account(row.get("id", Long.class), + row.get("iban", String.class), + row.get("balance", BigDecimal.class)))) + .flatMap( p -> Mono.from(p)); + } + + public Flux findAll() { + + return Mono.from(connectionFactory.create()) + .flatMap((c) -> Mono.from(c.createStatement("select id,iban,balance from Account") + .execute()) + .doFinally((st) -> close(c))) + .flatMapMany(result -> Flux.from(result.map((row, meta) -> { + Account acc = new Account(); + acc.setId(row.get("id", Long.class)); + acc.setIban(row.get("iban", String.class)); + acc.setBalance(row.get("balance", BigDecimal.class)); + return acc; + }))); + } + + public Mono createAccount(Account account) { + + return Mono.from(connectionFactory.create()) + .flatMap(c -> Mono.from(c.beginTransaction()) + .then(Mono.from(c.createStatement("insert into Account(iban,balance) values($1,$2)") + .bind("$1", account.getIban()) + .bind("$2", account.getBalance()) + .returnGeneratedValues("id") + .execute())) + .map(result -> result.map((row, meta) -> + new Account(row.get("id", Long.class), + account.getIban(), + account.getBalance()))) + .flatMap(pub -> Mono.from(pub)) + .delayUntil(r -> c.commitTransaction()) + .doFinally((st) -> c.close())); + + } + + private Mono close(Connection connection) { + return Mono.from(connection.close()) + .then(Mono.empty()); + } + +} diff --git a/persistence-modules/r2dbc/src/main/resources/META-INF/additional-spring-configuration-metadata.json b/persistence-modules/r2dbc/src/main/resources/META-INF/additional-spring-configuration-metadata.json new file mode 100644 index 0000000000..55eb5659a7 --- /dev/null +++ b/persistence-modules/r2dbc/src/main/resources/META-INF/additional-spring-configuration-metadata.json @@ -0,0 +1,5 @@ +{"properties": [{ + "name": "r2dbc", + "type": "org.baeldung.examples.r2dbc.R2DBCConfigurationProperties", + "description": "R2DBC Connection properties" +}]} \ No newline at end of file diff --git a/persistence-modules/r2dbc/src/main/resources/application.yml b/persistence-modules/r2dbc/src/main/resources/application.yml new file mode 100644 index 0000000000..bb47c7261c --- /dev/null +++ b/persistence-modules/r2dbc/src/main/resources/application.yml @@ -0,0 +1,13 @@ +spring: + application: + name: r2dbc-test + +# R2DBC URL +r2dbc: + url: r2dbc:h2:mem://./testdb + + + + + + diff --git a/persistence-modules/r2dbc/src/test/java/org/baeldung/examples/r2dbc/R2dbcExampleApplicationTests.java b/persistence-modules/r2dbc/src/test/java/org/baeldung/examples/r2dbc/R2dbcExampleApplicationTests.java new file mode 100644 index 0000000000..a1d433847b --- /dev/null +++ b/persistence-modules/r2dbc/src/test/java/org/baeldung/examples/r2dbc/R2dbcExampleApplicationTests.java @@ -0,0 +1,102 @@ +package org.baeldung.examples.r2dbc; + +import static org.hamcrest.CoreMatchers.*; +import static org.junit.Assert.*; + +import java.util.List; + +import org.hamcrest.core.IsNull; +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.CommandLineRunner; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.http.MediaType; +import org.springframework.test.context.junit4.SpringRunner; +import org.springframework.test.web.reactive.server.WebTestClient; + +import io.r2dbc.spi.ConnectionFactory; +import reactor.core.publisher.Flux; + +@RunWith(SpringRunner.class) +@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) +public class R2dbcExampleApplicationTests { + + + @Autowired + private WebTestClient webTestClient; + + @Autowired + ConnectionFactory cf; + + @Before + public void initDatabase() { + + Flux.from(cf.create()) + .flatMap(c -> + c.createBatch() + .add("drop table if exists Account") + .add("create table Account(id IDENTITY(1,1), iban varchar(80) not null, balance DECIMAL(18,2) not null)") + .add("insert into Account(iban,balance) values ( 'BR430120980198201982', 100.00 ) ") + .add("insert into Account(iban,balance) values ( 'BR430120998729871000', 250.00 ) ") + .execute() + ) + .log() + .blockLast(); + } + + @Test + public void givenExistingAccountId_whenGetAccount_thenReturnExistingAccountInfo() { + + webTestClient + .get() + .uri("/accounts/1") + .accept(MediaType.APPLICATION_JSON) + .exchange() + .expectStatus() + .isOk() + .expectBody(Account.class) + .value((acc) -> { + assertThat(acc.getId(),is(1l)); + }); + } + + @Test + public void givenDatabaseHasSomeAccounts_whenGetAccount_thenReturnExistingAccounts() { + + webTestClient + .get() + .uri("/accounts") + .accept(MediaType.APPLICATION_JSON) + .exchange() + .expectStatus() + .isOk() + .expectBody(List.class) + .value((accounts) -> { + assertThat(accounts.size(),not(is(0))); + }); + } + + + @Test + public void givenNewAccountData_whenPostAccount_thenReturnNewAccountInfo() { + + webTestClient + .post() + .uri("/accounts") + .syncBody(new Account(null,"BR4303010298012098", 151.00 )) + .accept(MediaType.APPLICATION_JSON) + .exchange() + .expectStatus() + .is2xxSuccessful() + .expectBody(Account.class) + .value((acc) -> { + assertThat(acc.getId(),is(notNullValue())); + }); + + } + +} diff --git a/persistence-modules/r2dbc/src/test/resources/application.yml b/persistence-modules/r2dbc/src/test/resources/application.yml new file mode 100644 index 0000000000..8925116e4a --- /dev/null +++ b/persistence-modules/r2dbc/src/test/resources/application.yml @@ -0,0 +1,6 @@ +# R2DBC Test configuration +r2dbc: + url: r2dbc:h2:mem://./testdb + + + diff --git a/spring-cloud/spring-cloud-vault/pom.xml b/spring-cloud/spring-cloud-vault/pom.xml index 9a1be3f5c0..faf27b6ac8 100644 --- a/spring-cloud/spring-cloud-vault/pom.xml +++ b/spring-cloud/spring-cloud-vault/pom.xml @@ -42,6 +42,18 @@ org.springframework.boot spring-boot-starter-jdbc + + org.springframework.boot + spring-boot-devtools + + + org.springframework.boot + spring-boot-starter-web + + + org.springframework.boot + spring-boot-starter-data-jpa + diff --git a/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountRepo.java b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountRepo.java new file mode 100644 index 0000000000..318cc84957 --- /dev/null +++ b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountRepo.java @@ -0,0 +1,10 @@ +package org.baeldung.spring.cloud.vaultsample; + +import org.baeldung.spring.cloud.vaultsample.domain.Account; +import org.springframework.data.jpa.repository.JpaRepository; +import org.springframework.stereotype.Repository; + +@Repository +public interface AccountRepo extends JpaRepository{ + +} diff --git a/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountResource.java b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountResource.java new file mode 100644 index 0000000000..8fcaa9e2aa --- /dev/null +++ b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/AccountResource.java @@ -0,0 +1,27 @@ +package org.baeldung.spring.cloud.vaultsample; + +import org.baeldung.spring.cloud.vaultsample.domain.Account; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RestController; + +@RestController +public class AccountResource { + @Autowired + private AccountRepo repo; + + @GetMapping("/account/{id}") + public ResponseEntity getAccount(@PathVariable("id") Long id) { + + Account acc = repo.findById(id).orElse(null); + if ( acc != null ) { + return new ResponseEntity(acc, HttpStatus.OK); + } + else { + return new ResponseEntity<>(HttpStatus.NOT_FOUND); + } + } +} diff --git a/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/SecretResource.java b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/SecretResource.java new file mode 100644 index 0000000000..c4579da045 --- /dev/null +++ b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/SecretResource.java @@ -0,0 +1,37 @@ +/** + * + */ +package org.baeldung.spring.cloud.vaultsample; + + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.core.env.Environment; +import org.springframework.http.HttpStatus; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.PathVariable; +import org.springframework.web.bind.annotation.RestController; + +/** + * @author Philippe + * + */ +@RestController +public class SecretResource { + + @Autowired + Environment env; + + @GetMapping("/secret/{key}") + public ResponseEntity readSecret(@PathVariable("key") String key) { + + String value = env.getProperty(key); + + if ( value != null ) { + return new ResponseEntity(value, HttpStatus.OK); + } + else { + return new ResponseEntity("not found", HttpStatus.NOT_FOUND); + } + } +} diff --git a/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/domain/Account.java b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/domain/Account.java new file mode 100644 index 0000000000..df4778831b --- /dev/null +++ b/spring-cloud/spring-cloud-vault/src/main/java/org/baeldung/spring/cloud/vaultsample/domain/Account.java @@ -0,0 +1,133 @@ +/** + * + */ +package org.baeldung.spring.cloud.vaultsample.domain; + +import javax.persistence.Entity; +import javax.persistence.Id; +import javax.persistence.Table; +import javax.validation.constraints.NotNull; + +/** + * @author Philippe + * + */ +@Entity +@Table(name = "account") +public class Account { + + @Id + private Long id; + + @NotNull + private String name; + + private Long branchId; + private Long customerId; + + /** + * @return the id + */ + public Long getId() { + return id; + } + + /** + * @param id the id to set + */ + public void setId(Long id) { + this.id = id; + } + + /** + * @return the name + */ + public String getName() { + return name; + } + + /** + * @param name the name to set + */ + public void setName(String name) { + this.name = name; + } + + /** + * @return the branchId + */ + public Long getBranchId() { + return branchId; + } + + /** + * @param branchId the branchId to set + */ + public void setBranchId(Long branchId) { + this.branchId = branchId; + } + + /** + * @return the customerId + */ + public Long getCustomerId() { + return customerId; + } + + /** + * @param customerId the customerId to set + */ + public void setCustomerId(Long customerId) { + this.customerId = customerId; + } + + /* (non-Javadoc) + * @see java.lang.Object#hashCode() + */ + @Override + public int hashCode() { + final int prime = 31; + int result = 1; + result = prime * result + ((branchId == null) ? 0 : branchId.hashCode()); + result = prime * result + ((customerId == null) ? 0 : customerId.hashCode()); + result = prime * result + ((id == null) ? 0 : id.hashCode()); + result = prime * result + ((name == null) ? 0 : name.hashCode()); + return result; + } + + /* (non-Javadoc) + * @see java.lang.Object#equals(java.lang.Object) + */ + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null) + return false; + if (getClass() != obj.getClass()) + return false; + Account other = (Account) obj; + if (branchId == null) { + if (other.branchId != null) + return false; + } else if (!branchId.equals(other.branchId)) + return false; + if (customerId == null) { + if (other.customerId != null) + return false; + } else if (!customerId.equals(other.customerId)) + return false; + if (id == null) { + if (other.id != null) + return false; + } else if (!id.equals(other.id)) + return false; + if (name == null) { + if (other.name != null) + return false; + } else if (!name.equals(other.name)) + return false; + return true; + } + +} diff --git a/spring-cloud/spring-cloud-vault/src/main/resources/application.yml b/spring-cloud/spring-cloud-vault/src/main/resources/application.yml index 3d347ec855..1c75ac21e6 100644 --- a/spring-cloud/spring-cloud-vault/src/main/resources/application.yml +++ b/spring-cloud/spring-cloud-vault/src/main/resources/application.yml @@ -1,6 +1,11 @@ -spring: - application: - name: fakebank - - datasource: - url: jdbc:mysql://localhost:3306/fakebank +spring: + application: + name: fakebank + + datasource: + url: jdbc:mysql://localhost:3306/fakebank?serverTimezone=GMT-3 + hikari: connection-test-query: select 1 + idle-timeout: 5000 + max-lifetime: 120000 + maximum-pool-size: 5 + minimum-idle: 5 diff --git a/spring-cloud/spring-cloud-vault/src/main/resources/bootstrap.yml b/spring-cloud/spring-cloud-vault/src/main/resources/bootstrap.yml index 1e837c4920..7d38b06c0f 100644 --- a/spring-cloud/spring-cloud-vault/src/main/resources/bootstrap.yml +++ b/spring-cloud/spring-cloud-vault/src/main/resources/bootstrap.yml @@ -4,8 +4,6 @@ spring: uri: https://localhost:8200 connection-timeout: 5000 read-timeout: 15000 - config: - order: -10 ssl: trust-store: classpath:/vault.jks @@ -15,17 +13,19 @@ spring: enabled: true application-name: fakebank - kv: - enabled: false - backend: kv - application-name: fakebank - +# kv: +# enabled: false +# backend: kv +# application-name: fakebank +# database: enabled: true role: fakebank-accounts-rw -# backend: database -# username-property: spring.datasource.username -# password-property: spring.datasource.password + backend: database + username-property: spring.datasource.username + password-property: spring.datasource.password +# +# diff --git a/spring-cloud/spring-cloud-vault/src/test/vault-config/vault-test.hcl b/spring-cloud/spring-cloud-vault/src/test/vault-config/vault-test.hcl index c880f2d744..d16665a744 100644 --- a/spring-cloud/spring-cloud-vault/src/test/vault-config/vault-test.hcl +++ b/spring-cloud/spring-cloud-vault/src/test/vault-config/vault-test.hcl @@ -17,4 +17,7 @@ listener "tcp" { tls_key_file = "./src/test/vault-config/localhost.key" } +// Audit to stdout + + diff --git a/spring-cloud/spring-cloud-vault/vault-cheatsheet.txt b/spring-cloud/spring-cloud-vault/vault-cheatsheet.txt index b965a95321..2d5f2363ac 100644 --- a/spring-cloud/spring-cloud-vault/vault-cheatsheet.txt +++ b/spring-cloud/spring-cloud-vault/vault-cheatsheet.txt @@ -5,16 +5,13 @@ 2. Open another shell and execute the command below: > vault operator init -Vault will output the unseal keys and root token: STORE THEM SAFELY !!! +Unseal Key 1: Iwvpd4IVofhcmQ2HEIPs5HMUbz4tz6JhqmLZ6+1MhAPx +Unseal Key 2: ANQDXUFGGtLtt6grX25YsdmeKELhM/ioKWzwFukJIe2f +Unseal Key 3: 8MHyzFnOvlwVQzdWYJ3BIN4xPDOn8a4VemZ/Qe5HgurU +Unseal Key 4: ywT9YR9OfxIpA4l1RniNNCvSZWAuNZsAEFRyD7aqFOrp +Unseal Key 5: q1c7M+lnlT72jGLoCH+jjri6KGSBhc5lCzlT0I1R9URU -Example output: -Unseal Key 1: OfCseaSZzjTZmrxhfx+5clKobwLGCNiJdAlfixSG9E3o -Unseal Key 2: iplVLPTHW0n0WL5XuI6QWwyNtWbKTek1SoKcG0gR7vdT -Unseal Key 3: K0TleK3OYUvWFF+uIDsQuf5a+/gkv1PtZ3O47ornzRoF -Unseal Key 4: +5zhysLAO4hIdZs0kiZpkrRovw11uQacfloiBwnZBJA/ -Unseal Key 5: GDwSq18lXV3Cw4MoHsKIH137kuI0mdl36UiD9WxOdulc - -Initial Root Token: d341fdaf-1cf9-936a-3c38-cf5eec94b5c0 +Initial Root Token: dee7107a-8819-0719-62a3-cea3ea854589 ... @@ -73,8 +70,8 @@ flush privileges; > vault write database/roles/fakebank-accounts-rw ^ db_name=mysql-fakebank ^ creation_statements="CREATE USER '{{name}}'@'%' IDENTIFIED BY '{{password}}';GRANT SELECT,INSERT,UPDATE ON fakebank.* TO '{{name}}'@'%';" ^ - default_ttl="1m" ^ - max_ttl="2m" + default_ttl="5m" ^ + max_ttl="30m" === Get credentials > vault read database/creds/fakebank-accounts-rw diff --git a/spring-cloud/spring-cloud-vault/vault-unseal.bat b/spring-cloud/spring-cloud-vault/vault-unseal.bat index 8133f90892..1e3f229fcf 100644 --- a/spring-cloud/spring-cloud-vault/vault-unseal.bat +++ b/spring-cloud/spring-cloud-vault/vault-unseal.bat @@ -1,7 +1,7 @@ call %~dp0%/vault-env.bat -vault operator unseal OfCseaSZzjTZmrxhfx+5clKobwLGCNiJdAlfixSG9E3o -vault operator unseal iplVLPTHW0n0WL5XuI6QWwyNtWbKTek1SoKcG0gR7vdT -vault operator unseal iplVLPTHW0n0WL5XuI6QWwyNtWbKTek1SoKcG0gR7vdT -vault operator unseal K0TleK3OYUvWFF+uIDsQuf5a+/gkv1PtZ3O47ornzRoF +vault operator unseal Iwvpd4IVofhcmQ2HEIPs5HMUbz4tz6JhqmLZ6+1MhAPx +vault operator unseal ANQDXUFGGtLtt6grX25YsdmeKELhM/ioKWzwFukJIe2f +vault operator unseal 8MHyzFnOvlwVQzdWYJ3BIN4xPDOn8a4VemZ/Qe5HgurU + From dee7128b928056d4fadf6e840035f47a0d1c6986 Mon Sep 17 00:00:00 2001 From: Maiklins Date: Fri, 26 Jul 2019 07:01:03 +0200 Subject: [PATCH 077/107] BAEL-3012 Spring Request Parameters with Thymeleaf (#7412) --- .../controller/ParticipantController.java | 28 ++++++++++++++++ .../resources/templates/participants.html | 32 +++++++++++++++++++ 2 files changed, 60 insertions(+) create mode 100644 spring-thymeleaf/src/main/java/com/baeldung/thymeleaf/controller/ParticipantController.java create mode 100644 spring-thymeleaf/src/main/resources/templates/participants.html diff --git a/spring-thymeleaf/src/main/java/com/baeldung/thymeleaf/controller/ParticipantController.java b/spring-thymeleaf/src/main/java/com/baeldung/thymeleaf/controller/ParticipantController.java new file mode 100644 index 0000000000..eebe37e000 --- /dev/null +++ b/spring-thymeleaf/src/main/java/com/baeldung/thymeleaf/controller/ParticipantController.java @@ -0,0 +1,28 @@ +package com.example.demo; + +import org.springframework.stereotype.Controller; +import org.springframework.ui.Model; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RequestParam; + +import java.util.List; + +import static java.util.Arrays.asList; + +@Controller +public class ParticipantController { + + @RequestMapping("/") + public String index( + @RequestParam(value = "participant", required = false) String participant, + @RequestParam(value = "country", required = false) String country, + @RequestParam(value = "action", required = false) String action, + @RequestParam(value = "id", required = false) Integer id, + Model model + ) { + model.addAttribute("id", id); + List userIds = asList(1,2,3,4); + model.addAttribute("userIds", userIds); + return "participants"; + } +} diff --git a/spring-thymeleaf/src/main/resources/templates/participants.html b/spring-thymeleaf/src/main/resources/templates/participants.html new file mode 100644 index 0000000000..8d4e552093 --- /dev/null +++ b/spring-thymeleaf/src/main/resources/templates/participants.html @@ -0,0 +1,32 @@ + + + + + +

    Enter participant

    +
    + + + + + +
    + + +

    User Details

    +

    Details for user [[${id}]] ...

    +
    + +

    Users

    + +

    + User [[${userId}]] +

    +
    + + From f1d68f74f6298025354adb494feae9f7df5e5d65 Mon Sep 17 00:00:00 2001 From: Krzysztof Majewski Date: Fri, 26 Jul 2019 12:33:04 +0200 Subject: [PATCH 078/107] add new module --- persistence-modules/java-jpa-2/README.md | 1 + persistence-modules/java-jpa-2/pom.xml | 115 ++++++++++++++++++ .../java/com/baeldung/jpa/entity/Article.java | 0 .../java-jpa-2/src/main/resources/logback.xml | 13 ++ persistence-modules/pom.xml | 1 + pom.xml | 2 + 6 files changed, 132 insertions(+) create mode 100644 persistence-modules/java-jpa-2/README.md create mode 100644 persistence-modules/java-jpa-2/pom.xml rename persistence-modules/{java-jpa => java-jpa-2}/src/main/java/com/baeldung/jpa/entity/Article.java (100%) create mode 100644 persistence-modules/java-jpa-2/src/main/resources/logback.xml diff --git a/persistence-modules/java-jpa-2/README.md b/persistence-modules/java-jpa-2/README.md new file mode 100644 index 0000000000..e65ce65a95 --- /dev/null +++ b/persistence-modules/java-jpa-2/README.md @@ -0,0 +1 @@ +# Relevant Articles diff --git a/persistence-modules/java-jpa-2/pom.xml b/persistence-modules/java-jpa-2/pom.xml new file mode 100644 index 0000000000..c8c9a24599 --- /dev/null +++ b/persistence-modules/java-jpa-2/pom.xml @@ -0,0 +1,115 @@ + + + 4.0.0 + java-jpa-2 + java-jpa-2 + + + parent-modules + com.baeldung + 1.0.0-SNAPSHOT + ../../pom.xml + + + + + org.hibernate + hibernate-core + ${hibernate.version} + + + org.hibernate + hibernate-jpamodelgen + ${hibernate.version} + + + com.h2database + h2 + ${h2.version} + + + + + javax.persistence + javax.persistence-api + ${javax.persistence-api.version} + + + + + org.eclipse.persistence + eclipselink + ${eclipselink.version} + runtime + + + org.postgresql + postgresql + ${postgres.version} + runtime + + + + + + + org.apache.maven.plugins + maven-compiler-plugin + 3.5.1 + + -proc:none + + + + org.bsc.maven + maven-processor-plugin + 3.3.3 + + + process + + process + + generate-sources + + target/metamodel + + org.hibernate.jpamodelgen.JPAMetaModelEntityProcessor + + + + + + + + org.codehaus.mojo + build-helper-maven-plugin + 3.0.0 + + + add-source + generate-sources + + add-source + + + + target/metamodel + + + + + + + + + + 5.4.0.Final + 2.7.4-RC1 + 42.2.5 + 2.2 + + + diff --git a/persistence-modules/java-jpa/src/main/java/com/baeldung/jpa/entity/Article.java b/persistence-modules/java-jpa-2/src/main/java/com/baeldung/jpa/entity/Article.java similarity index 100% rename from persistence-modules/java-jpa/src/main/java/com/baeldung/jpa/entity/Article.java rename to persistence-modules/java-jpa-2/src/main/java/com/baeldung/jpa/entity/Article.java diff --git a/persistence-modules/java-jpa-2/src/main/resources/logback.xml b/persistence-modules/java-jpa-2/src/main/resources/logback.xml new file mode 100644 index 0000000000..7d900d8ea8 --- /dev/null +++ b/persistence-modules/java-jpa-2/src/main/resources/logback.xml @@ -0,0 +1,13 @@ + + + + + %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n + + + + + + + + \ No newline at end of file diff --git a/persistence-modules/pom.xml b/persistence-modules/pom.xml index 390bcc9d51..79879fc2ff 100644 --- a/persistence-modules/pom.xml +++ b/persistence-modules/pom.xml @@ -29,6 +29,7 @@ java-cockroachdb java-jdbi java-jpa + java-jpa-2 java-mongodb jnosql liquibase diff --git a/pom.xml b/pom.xml index 2e34254bf5..a4e74f8423 100644 --- a/pom.xml +++ b/pom.xml @@ -988,6 +988,7 @@ persistence-modules/hibernate5 persistence-modules/hibernate-mapping persistence-modules/java-jpa + persistence-modules/java-jpa-2 persistence-modules/java-mongodb persistence-modules/jnosql @@ -1500,6 +1501,7 @@ persistence-modules/hibernate5 persistence-modules/java-jpa + persistence-modules/java-jpa-2 persistence-modules/java-mongodb persistence-modules/jnosql From 7486e228856e486261a2459276c9969c39c176e3 Mon Sep 17 00:00:00 2001 From: Justin Albano Date: Fri, 26 Jul 2019 11:42:52 -0400 Subject: [PATCH 079/107] =?UTF-8?q?=C2=96BAEL-3153:=20Reverted=20READ=20fi?= =?UTF-8?q?le=20to=20original=20contents.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- java-strings-2/README.MD | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/java-strings-2/README.MD b/java-strings-2/README.MD index 4db93f64e0..c6d4f0222a 100644 --- a/java-strings-2/README.MD +++ b/java-strings-2/README.MD @@ -1,7 +1,7 @@ -## Relevant Articles - -- [Java Localization – Formatting Messages](https://www.baeldung.com/java-localization-messages-formatting) -- [Check If a String Contains a Substring](https://www.baeldung.com/java-string-contains-substring) -- [Removing Stopwords from a String in Java](https://www.baeldung.com/java-string-remove-stopwords) -- [Blank and Empty Strings in Java](https://www.baeldung.com/java-blank-empty-strings) -- [String Initialization in Java](https://www.baeldung.com/java-string-initialization) +## Relevant Articles + +- [Java Localization – Formatting Messages](https://www.baeldung.com/java-localization-messages-formatting) +- [Check If a String Contains a Substring](https://www.baeldung.com/java-string-contains-substring) +- [Removing Stopwords from a String in Java](https://www.baeldung.com/java-string-remove-stopwords) +- [Blank and Empty Strings in Java](https://www.baeldung.com/java-blank-empty-strings) +- [String Initialization in Java](https://www.baeldung.com/java-string-initialization) From e67462412e8deb5b0a23ed162ce82c5b8ecaf097 Mon Sep 17 00:00:00 2001 From: Justin Albano Date: Fri, 26 Jul 2019 23:33:34 -0400 Subject: [PATCH 080/107] BAEL-3153: Corrected name of foreign lower case variable in tests --- .../com/baeldung/string/changecase/ToUpperCaseUnitTest.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java index 365b5ae52f..1807f854b2 100644 --- a/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java +++ b/java-strings-2/src/test/java/com/baeldung/string/changecase/ToUpperCaseUnitTest.java @@ -10,7 +10,7 @@ public class ToUpperCaseUnitTest { private static final Locale TURKISH = new Locale("tr"); private String name = "John Doe"; - private String foreignUppercase = "\u0069"; + private String foreignLowercase = "\u0069"; @Test public void givenMixedCaseString_WhenToUpperCase_ThenResultIsUpperCase() { @@ -19,11 +19,11 @@ public class ToUpperCaseUnitTest { @Test public void givenForeignString_WhenToUpperCaseWithoutLocale_ThenResultIsUpperCase() { - assertEquals("\u0049", foreignUppercase.toUpperCase()); + assertEquals("\u0049", foreignLowercase.toUpperCase()); } @Test public void givenForeignString_WhenToUpperCaseWithLocale_ThenResultIsUpperCase() { - assertEquals("\u0130", foreignUppercase.toUpperCase(TURKISH)); + assertEquals("\u0130", foreignLowercase.toUpperCase(TURKISH)); } } From f1232810e2f3b569a72ce145d2e4d08ba072e0ea Mon Sep 17 00:00:00 2001 From: rpvilao Date: Sat, 27 Jul 2019 09:40:59 +0200 Subject: [PATCH 081/107] Fixes the parent boot (#7409) --- parent-boot-performance/README.md | 1 - parent-boot-performance/pom.xml | 92 ------------------------------- spring-boot-performance/pom.xml | 6 +- 3 files changed, 3 insertions(+), 96 deletions(-) delete mode 100644 parent-boot-performance/README.md delete mode 100644 parent-boot-performance/pom.xml diff --git a/parent-boot-performance/README.md b/parent-boot-performance/README.md deleted file mode 100644 index fce9e101da..0000000000 --- a/parent-boot-performance/README.md +++ /dev/null @@ -1 +0,0 @@ -This is a parent module for projects that want to take advantage of the latest Spring Boot improvements/features. \ No newline at end of file diff --git a/parent-boot-performance/pom.xml b/parent-boot-performance/pom.xml deleted file mode 100644 index b7d12e2ba4..0000000000 --- a/parent-boot-performance/pom.xml +++ /dev/null @@ -1,92 +0,0 @@ - - 4.0.0 - parent-boot-performance - 0.0.1-SNAPSHOT - parent-boot-performance - pom - Parent for all modules that want to take advantage of the latest Spring Boot improvements/features. Current version: 2.2 - - - com.baeldung - parent-modules - 1.0.0-SNAPSHOT - - - - - - org.springframework.boot - spring-boot-dependencies - ${spring-boot.version} - pom - import - - - - - - - io.rest-assured - rest-assured - - - org.springframework.boot - spring-boot-starter-test - test - - - - - - - - org.springframework.boot - spring-boot-maven-plugin - ${spring-boot.version} - - ${start-class} - - - - - - - - - - spring-milestones - Spring Milestones - https://repo.spring.io/milestone - - - - - - thin-jar - - - - org.springframework.boot - spring-boot-maven-plugin - - - - org.springframework.boot.experimental - spring-boot-thin-layout - ${thin.version} - - - - - - - - - - 3.1.0 - - 1.0.21.RELEASE - 2.2.0.M3 - - diff --git a/spring-boot-performance/pom.xml b/spring-boot-performance/pom.xml index f51df8bc0c..a4efa4a8d7 100644 --- a/spring-boot-performance/pom.xml +++ b/spring-boot-performance/pom.xml @@ -8,10 +8,10 @@ This is a simple Spring Boot application taking advantage of the latest Spring Boot improvements/features. Current version: 2.2 - parent-boot-performance + parent-boot-2 com.baeldung 0.0.1-SNAPSHOT - ../parent-boot-performance + ../parent-boot-2 @@ -42,4 +42,4 @@ com.baeldung.lazyinitialization.Application -
    \ No newline at end of file +
    From 8d62e17b8e05f07f14b9fdf3f9c0c86063d13046 Mon Sep 17 00:00:00 2001 From: maryarm <45322329+maryarm@users.noreply.github.com> Date: Sat, 27 Jul 2019 16:50:52 +0430 Subject: [PATCH 082/107] #BAEL-2888- Reloading Properties Files in Spring (#7392) Code samples for BAEL-2888 --- spring-boot-properties/.gitignore | 17 ++ spring-boot-properties/README.md | 2 + spring-boot-properties/extra.properties | 1 + spring-boot-properties/extra2.properties | 1 + spring-boot-properties/pom.xml | 104 +++++++++++ .../SpringBootPropertiesApplication.java | 44 +++++ .../configs/PropertiesException.java | 10 ++ .../configs/ReloadableProperties.java | 49 ++++++ .../configs/ReloadablePropertySource.java | 33 ++++ .../ReloadablePropertySourceConfig.java | 29 ++++ .../ReloadablePropertySourceFactory.java | 25 +++ .../src/main/resources/application.properties | 3 + .../PropertiesReloadIntegrationTest.java | 161 ++++++++++++++++++ .../SpringBootPropertiesTestApplication.java | 28 +++ ...figurationPropertiesRefreshConfigBean.java | 20 +++ .../beans/EnvironmentConfigBean.java | 26 +++ .../beans/PropertiesConfigBean.java | 19 +++ .../beans/ValueRefreshConfigBean.java | 13 ++ .../src/test/resources/application.properties | 3 + 19 files changed, 588 insertions(+) create mode 100644 spring-boot-properties/.gitignore create mode 100644 spring-boot-properties/README.md create mode 100644 spring-boot-properties/extra.properties create mode 100644 spring-boot-properties/extra2.properties create mode 100644 spring-boot-properties/pom.xml create mode 100644 spring-boot-properties/src/main/java/com/baeldung/properties/SpringBootPropertiesApplication.java create mode 100644 spring-boot-properties/src/main/java/com/baeldung/properties/configs/PropertiesException.java create mode 100644 spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadableProperties.java create mode 100644 spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySource.java create mode 100644 spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceConfig.java create mode 100644 spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceFactory.java create mode 100644 spring-boot-properties/src/main/resources/application.properties create mode 100644 spring-boot-properties/src/test/java/com/baeldung/properties/PropertiesReloadIntegrationTest.java create mode 100644 spring-boot-properties/src/test/java/com/baeldung/properties/SpringBootPropertiesTestApplication.java create mode 100644 spring-boot-properties/src/test/java/com/baeldung/properties/beans/ConfigurationPropertiesRefreshConfigBean.java create mode 100644 spring-boot-properties/src/test/java/com/baeldung/properties/beans/EnvironmentConfigBean.java create mode 100644 spring-boot-properties/src/test/java/com/baeldung/properties/beans/PropertiesConfigBean.java create mode 100644 spring-boot-properties/src/test/java/com/baeldung/properties/beans/ValueRefreshConfigBean.java create mode 100644 spring-boot-properties/src/test/resources/application.properties diff --git a/spring-boot-properties/.gitignore b/spring-boot-properties/.gitignore new file mode 100644 index 0000000000..0532ef1888 --- /dev/null +++ b/spring-boot-properties/.gitignore @@ -0,0 +1,17 @@ +*.class + +#folders# +/target +/neoDb* +/data +/src/main/webapp/WEB-INF/classes +*/META-INF/* + +# Packaged files # +*.jar +*.war +*.ear + +*.ipr +*.iml +*.iws diff --git a/spring-boot-properties/README.md b/spring-boot-properties/README.md new file mode 100644 index 0000000000..c43cf4865c --- /dev/null +++ b/spring-boot-properties/README.md @@ -0,0 +1,2 @@ +### Relevant Articles: +- [Reloading Properties in Spring](https://www.baeldung.com/reloading-properties-files-in-spring/) \ No newline at end of file diff --git a/spring-boot-properties/extra.properties b/spring-boot-properties/extra.properties new file mode 100644 index 0000000000..8e28a6f889 --- /dev/null +++ b/spring-boot-properties/extra.properties @@ -0,0 +1 @@ +application.theme.color=blue \ No newline at end of file diff --git a/spring-boot-properties/extra2.properties b/spring-boot-properties/extra2.properties new file mode 100644 index 0000000000..2c46edc584 --- /dev/null +++ b/spring-boot-properties/extra2.properties @@ -0,0 +1 @@ +application.theme.background=red \ No newline at end of file diff --git a/spring-boot-properties/pom.xml b/spring-boot-properties/pom.xml new file mode 100644 index 0000000000..27ac48252b --- /dev/null +++ b/spring-boot-properties/pom.xml @@ -0,0 +1,104 @@ + + + 4.0.0 + spring-boot-properties + jar + spring-boot-properties + Spring Boot Properties Module + + + parent-boot-2 + com.baeldung + 0.0.1-SNAPSHOT + ../parent-boot-2 + + + + + commons-configuration + commons-configuration + ${commons-configuration.version} + + + org.springframework.boot + spring-boot-starter-web + + + org.springframework.boot + spring-boot-starter-actuator + + + org.springframework.cloud + spring-cloud-starter + + + org.springframework.boot + spring-boot-starter-test + test + + + + + + + org.springframework.cloud + spring-cloud-dependencies + ${spring-cloud.version} + pom + import + + + + + + spring-boot-properties + + + src/main/resources + true + + + + + + + integration + + + + org.apache.maven.plugins + maven-surefire-plugin + + + integration-test + + test + + + + **/*LiveTest.java + **/*IntegrationTest.java + **/*IntTest.java + + + + + + + json + + + + + + + + + + 1.8 + Greenwich.SR1 + 1.10 + + + diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/SpringBootPropertiesApplication.java b/spring-boot-properties/src/main/java/com/baeldung/properties/SpringBootPropertiesApplication.java new file mode 100644 index 0000000000..67bbddf9f1 --- /dev/null +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/SpringBootPropertiesApplication.java @@ -0,0 +1,44 @@ +package com.baeldung.properties; + +import com.baeldung.properties.configs.ReloadableProperties; +import java.io.File; +import java.util.Properties; +import org.apache.commons.configuration.PropertiesConfiguration; +import org.apache.commons.configuration.reloading.FileChangedReloadingStrategy; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.boot.autoconfigure.condition.ConditionalOnBean; +import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Primary; + +@SpringBootApplication +public class SpringBootPropertiesApplication { + + @Bean + @ConditionalOnProperty(name = "spring.config.location", matchIfMissing = false) + public PropertiesConfiguration propertiesConfiguration( + @Value("${spring.config.location}") String path, + @Value("${spring.properties.refreshDelay}") long refreshDelay) throws Exception { + String filePath = path.substring("file:".length()); + PropertiesConfiguration configuration = new PropertiesConfiguration(new File(filePath).getCanonicalPath()); + FileChangedReloadingStrategy fileChangedReloadingStrategy = new FileChangedReloadingStrategy(); + fileChangedReloadingStrategy.setRefreshDelay(refreshDelay); + configuration.setReloadingStrategy(fileChangedReloadingStrategy); + return configuration; + } + + @Bean + @ConditionalOnBean(PropertiesConfiguration.class) + @Primary + public Properties properties(PropertiesConfiguration propertiesConfiguration) throws Exception { + ReloadableProperties properties = new ReloadableProperties(propertiesConfiguration); + return properties; + } + + public static void main(String[] args) { + SpringApplication.run(SpringBootPropertiesApplication.class, args); + } + +} diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/PropertiesException.java b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/PropertiesException.java new file mode 100644 index 0000000000..5ec3a042f7 --- /dev/null +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/PropertiesException.java @@ -0,0 +1,10 @@ +package com.baeldung.properties.configs; + +public class PropertiesException extends RuntimeException { + public PropertiesException() { + } + + public PropertiesException(Throwable cause) { + super(cause); + } +} diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadableProperties.java b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadableProperties.java new file mode 100644 index 0000000000..33d503b9bd --- /dev/null +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadableProperties.java @@ -0,0 +1,49 @@ +package com.baeldung.properties.configs; + +import java.io.FileReader; +import java.io.IOException; +import java.io.InputStream; +import java.io.Reader; +import java.util.Properties; +import javax.naming.OperationNotSupportedException; +import org.apache.commons.configuration.PropertiesConfiguration; + +public class ReloadableProperties extends Properties { + private PropertiesConfiguration propertiesConfiguration; + + public ReloadableProperties(PropertiesConfiguration propertiesConfiguration) throws IOException { + super.load(new FileReader(propertiesConfiguration.getFile())); + this.propertiesConfiguration = propertiesConfiguration; + } + + @Override + public synchronized Object setProperty(String key, String value) { + propertiesConfiguration.setProperty(key, value); + return super.setProperty(key, value); + } + + @Override + public String getProperty(String key) { + String val = propertiesConfiguration.getString(key); + super.setProperty(key, val); + return val; + } + + @Override + public String getProperty(String key, String defaultValue) { + String val = propertiesConfiguration.getString(key, defaultValue); + super.setProperty(key, val); + return val; + } + + @Override + public synchronized void load(Reader reader) throws IOException { + throw new PropertiesException(new OperationNotSupportedException()); + } + + @Override + public synchronized void load(InputStream inStream) throws IOException { + throw new PropertiesException(new OperationNotSupportedException()); + } + +} diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySource.java b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySource.java new file mode 100644 index 0000000000..8a0cef955f --- /dev/null +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySource.java @@ -0,0 +1,33 @@ +package com.baeldung.properties.configs; + +import org.apache.commons.configuration.PropertiesConfiguration; +import org.apache.commons.configuration.reloading.FileChangedReloadingStrategy; +import org.springframework.core.env.PropertySource; +import org.springframework.util.StringUtils; + +public class ReloadablePropertySource extends PropertySource { + + PropertiesConfiguration propertiesConfiguration; + + public ReloadablePropertySource(String name, PropertiesConfiguration propertiesConfiguration) { + super(name); + this.propertiesConfiguration = propertiesConfiguration; + } + + public ReloadablePropertySource(String name, String path) { + super(StringUtils.isEmpty(name) ? path : name); + try { + this.propertiesConfiguration = new PropertiesConfiguration(path); + FileChangedReloadingStrategy strategy = new FileChangedReloadingStrategy(); + strategy.setRefreshDelay(1000); + this.propertiesConfiguration.setReloadingStrategy(strategy); + } catch (Exception e) { + throw new PropertiesException(e); + } + } + + @Override + public Object getProperty(String s) { + return propertiesConfiguration.getProperty(s); + } +} diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceConfig.java b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceConfig.java new file mode 100644 index 0000000000..37e1a04839 --- /dev/null +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceConfig.java @@ -0,0 +1,29 @@ +package com.baeldung.properties.configs; + +import org.apache.commons.configuration.PropertiesConfiguration; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.core.env.ConfigurableEnvironment; +import org.springframework.core.env.MutablePropertySources; + +@Configuration +public class ReloadablePropertySourceConfig { + + private ConfigurableEnvironment env; + + public ReloadablePropertySourceConfig(@Autowired ConfigurableEnvironment env) { + this.env = env; + } + + @Bean + @ConditionalOnProperty(name = "spring.config.location", matchIfMissing = false) + public ReloadablePropertySource reloadablePropertySource(PropertiesConfiguration properties) { + ReloadablePropertySource ret = new ReloadablePropertySource("dynamic", properties); + MutablePropertySources sources = env.getPropertySources(); + sources.addFirst(ret); + return ret; + } + +} diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceFactory.java b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceFactory.java new file mode 100644 index 0000000000..574362b3bf --- /dev/null +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceFactory.java @@ -0,0 +1,25 @@ +package com.baeldung.properties.configs; + +import java.io.IOException; +import org.springframework.core.env.PropertySource; +import org.springframework.core.io.FileSystemResource; +import org.springframework.core.io.FileUrlResource; +import org.springframework.core.io.Resource; +import org.springframework.core.io.support.DefaultPropertySourceFactory; +import org.springframework.core.io.support.EncodedResource; + +public class ReloadablePropertySourceFactory extends DefaultPropertySourceFactory { + @Override + public PropertySource createPropertySource(String s, EncodedResource encodedResource) throws IOException { + Resource internal = encodedResource.getResource(); + if (internal instanceof FileSystemResource) { + return new ReloadablePropertySource(s, ((FileSystemResource) internal).getPath()); + } + if (internal instanceof FileUrlResource) { + return new ReloadablePropertySource(s, ((FileUrlResource) internal) + .getURL() + .getPath()); + } + return super.createPropertySource(s, encodedResource); + } +} diff --git a/spring-boot-properties/src/main/resources/application.properties b/spring-boot-properties/src/main/resources/application.properties new file mode 100644 index 0000000000..f976004a04 --- /dev/null +++ b/spring-boot-properties/src/main/resources/application.properties @@ -0,0 +1,3 @@ +management.endpoints.web.exposure.include=refresh +spring.properties.refreshDelay=1000 +spring.config.location=file:extra.properties diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/PropertiesReloadIntegrationTest.java b/spring-boot-properties/src/test/java/com/baeldung/properties/PropertiesReloadIntegrationTest.java new file mode 100644 index 0000000000..a73311ded8 --- /dev/null +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/PropertiesReloadIntegrationTest.java @@ -0,0 +1,161 @@ +package com.baeldung.properties; + +import com.baeldung.properties.beans.ConfigurationPropertiesRefreshConfigBean; +import com.baeldung.properties.beans.EnvironmentConfigBean; +import com.baeldung.properties.beans.PropertiesConfigBean; +import com.baeldung.properties.beans.ValueRefreshConfigBean; +import java.io.FileOutputStream; +import org.junit.After; +import org.junit.Assert; +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Qualifier; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.http.MediaType; +import org.springframework.mock.web.MockHttpServletResponse; +import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; +import org.springframework.test.web.servlet.MockMvc; +import org.springframework.test.web.servlet.MvcResult; +import org.springframework.test.web.servlet.request.MockMvcRequestBuilders; +import org.springframework.test.web.servlet.setup.MockMvcBuilders; +import org.springframework.web.context.WebApplicationContext; + +@RunWith(SpringJUnit4ClassRunner.class) +@SpringBootTest(classes = SpringBootPropertiesTestApplication.class) +public class PropertiesReloadIntegrationTest { + + protected MockMvc mvc; + + protected long refreshDelay = 3000; + + @Autowired + WebApplicationContext webApplicationContext; + + @Autowired + ValueRefreshConfigBean valueRefreshConfigBean; + + @Autowired + ConfigurationPropertiesRefreshConfigBean configurationPropertiesRefreshConfigBean; + + @Autowired + EnvironmentConfigBean environmentConfigBean; + + @Autowired + PropertiesConfigBean propertiesConfigBean; + + @Autowired + @Qualifier("singletonValueRefreshConfigBean") + ValueRefreshConfigBean singletonValueRefreshConfigBean; + + + @Before + public void setUp() throws Exception { + mvc = MockMvcBuilders + .webAppContextSetup(webApplicationContext) + .build(); + createConfig("extra.properties", "application.theme.color", "blue"); + createConfig("extra2.properties", "application.theme.background", "red"); + Thread.sleep(refreshDelay); + callRefresh(); + } + + @After + public void tearDown() throws Exception { + createConfig("extra.properties", "application.theme.color", "blue"); + createConfig("extra2.properties", "application.theme.background", "red"); + } + + @Test + public void givenEnvironmentReader_whenColorChanged_thenExpectChangeValue() throws Exception { + Assert.assertEquals("blue", environmentConfigBean.getColor()); + + createConfig("extra.properties", "application.theme.color", "red"); + Thread.sleep(refreshDelay); + + Assert.assertEquals("red", environmentConfigBean.getColor()); + } + + @Test + public void givenEnvironmentReader_whenBackgroundChanged_thenExpectChangeValue() throws Exception { + Assert.assertEquals("red", environmentConfigBean.getBackgroundColor()); + + createConfig("extra2.properties", "application.theme.background", "blue"); + Thread.sleep(refreshDelay); + + Assert.assertEquals("blue", environmentConfigBean.getBackgroundColor()); + } + + @Test + public void givenPropertiesReader_whenColorChanged_thenExpectChangeValue() throws Exception { + Assert.assertEquals("blue", propertiesConfigBean.getColor()); + + createConfig("extra.properties", "application.theme.color", "red"); + Thread.sleep(refreshDelay); + + Assert.assertEquals("red", propertiesConfigBean.getColor()); + } + + @Test + public void givenRefreshScopedValueReader_whenColorChangedAndRefreshCalled_thenExpectChangeValue() throws Exception { + Assert.assertEquals("blue", valueRefreshConfigBean.getColor()); + + createConfig("extra.properties", "application.theme.color", "red"); + Thread.sleep(refreshDelay); + + Assert.assertEquals("blue", valueRefreshConfigBean.getColor()); + + callRefresh(); + + Assert.assertEquals("red", valueRefreshConfigBean.getColor()); + } + + @Test + public void givenSingletonRefreshScopedValueReader_whenColorChangedAndRefreshCalled_thenExpectOldValue() throws Exception { + + Assert.assertEquals("blue", singletonValueRefreshConfigBean.getColor()); + + createConfig("extra.properties", "application.theme.color", "red"); + Thread.sleep(refreshDelay); + + Assert.assertEquals("blue", singletonValueRefreshConfigBean.getColor()); + + callRefresh(); + + Assert.assertEquals("blue", singletonValueRefreshConfigBean.getColor()); + } + + @Test + public void givenRefreshScopedConfigurationPropertiesReader_whenColorChangedAndRefreshCalled_thenExpectChangeValue() throws Exception { + + Assert.assertEquals("blue", configurationPropertiesRefreshConfigBean.getColor()); + + createConfig("extra.properties", "application.theme.color", "red"); + Thread.sleep(refreshDelay); + + Assert.assertEquals("blue", configurationPropertiesRefreshConfigBean.getColor()); + + callRefresh(); + + Assert.assertEquals("red", configurationPropertiesRefreshConfigBean.getColor()); + } + + public void callRefresh() throws Exception { + MvcResult mvcResult = mvc + .perform(MockMvcRequestBuilders + .post("/actuator/refresh") + .accept(MediaType.APPLICATION_JSON_VALUE)) + .andReturn(); + MockHttpServletResponse response = mvcResult.getResponse(); + Assert.assertEquals(response.getStatus(), 200); + } + + public void createConfig(String file, String key, String value) throws Exception { + FileOutputStream fo = new FileOutputStream(file); + fo.write(String + .format("%s=%s", key, value) + .getBytes()); + fo.close(); + } +} diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/SpringBootPropertiesTestApplication.java b/spring-boot-properties/src/test/java/com/baeldung/properties/SpringBootPropertiesTestApplication.java new file mode 100644 index 0000000000..c572a6c053 --- /dev/null +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/SpringBootPropertiesTestApplication.java @@ -0,0 +1,28 @@ +package com.baeldung.properties; + +import com.baeldung.properties.beans.ValueRefreshConfigBean; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.cloud.context.config.annotation.RefreshScope; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Scope; +import org.springframework.test.context.web.WebAppConfiguration; + +@SpringBootApplication +@WebAppConfiguration +public class SpringBootPropertiesTestApplication { + + @Bean("singletonValueRefreshConfigBean") + @RefreshScope + @Scope("singleton") + public ValueRefreshConfigBean singletonValueRefreshConfigBean(@Value("${application.theme.color:null}") String val) { + return new ValueRefreshConfigBean(val); + } + + @Bean + @RefreshScope + public ValueRefreshConfigBean valueRefreshConfigBean(@Value("${application.theme.color:null}") String val) { + return new ValueRefreshConfigBean(val); + } + +} diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ConfigurationPropertiesRefreshConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ConfigurationPropertiesRefreshConfigBean.java new file mode 100644 index 0000000000..31f168fdcc --- /dev/null +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ConfigurationPropertiesRefreshConfigBean.java @@ -0,0 +1,20 @@ +package com.baeldung.properties.beans; + +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.cloud.context.config.annotation.RefreshScope; +import org.springframework.stereotype.Component; + +@Component +@ConfigurationProperties(prefix = "application.theme") +@RefreshScope +public class ConfigurationPropertiesRefreshConfigBean { + private String color; + + public String getColor() { + return color; + } + + public void setColor(String color) { + this.color = color; + } +} diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/EnvironmentConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/EnvironmentConfigBean.java new file mode 100644 index 0000000000..fef12f8656 --- /dev/null +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/EnvironmentConfigBean.java @@ -0,0 +1,26 @@ +package com.baeldung.properties.beans; + +import com.baeldung.properties.configs.ReloadablePropertySourceFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.PropertySource; +import org.springframework.core.env.Environment; +import org.springframework.stereotype.Component; + +@Component +@PropertySource(value = "file:extra2.properties", factory = ReloadablePropertySourceFactory.class) +public class EnvironmentConfigBean { + + private Environment environment; + + public EnvironmentConfigBean(@Autowired Environment environment) { + this.environment = environment; + } + + public String getColor() { + return environment.getProperty("application.theme.color"); + } + + public String getBackgroundColor() { + return environment.getProperty("application.theme.background"); + } +} diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/PropertiesConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/PropertiesConfigBean.java new file mode 100644 index 0000000000..da773b283a --- /dev/null +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/PropertiesConfigBean.java @@ -0,0 +1,19 @@ +package com.baeldung.properties.beans; + +import java.util.Properties; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Component; + +@Component +public class PropertiesConfigBean { + + private Properties properties; + + public PropertiesConfigBean(@Autowired Properties properties) { + this.properties = properties; + } + + public String getColor() { + return properties.getProperty("application.theme.color"); + } +} diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ValueRefreshConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ValueRefreshConfigBean.java new file mode 100644 index 0000000000..d806938092 --- /dev/null +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ValueRefreshConfigBean.java @@ -0,0 +1,13 @@ +package com.baeldung.properties.beans; + +public class ValueRefreshConfigBean { + private String color; + + public ValueRefreshConfigBean(String color) { + this.color = color; + } + + public String getColor() { + return color; + } +} diff --git a/spring-boot-properties/src/test/resources/application.properties b/spring-boot-properties/src/test/resources/application.properties new file mode 100644 index 0000000000..6fc241a106 --- /dev/null +++ b/spring-boot-properties/src/test/resources/application.properties @@ -0,0 +1,3 @@ +management.endpoints.web.exposure.include=refresh +spring.properties.refreshDelay=1000 +spring.config.location=file:extra.properties \ No newline at end of file From 1be61beeb38de84a792550fbd4af889f38eeb086 Mon Sep 17 00:00:00 2001 From: amit2103 Date: Sat, 27 Jul 2019 17:58:14 +0530 Subject: [PATCH 083/107] [BAEL-16086] - Moved core-java-arrays module, added missing pom.xml, fixed pmd errors --- .../core-java-arrays-2/.gitignore | 25 ++++++++++ .../core-java-arrays-2}/README.MD | 0 core-java-modules/core-java-arrays-2/pom.xml | 50 +++++++++++++++++++ .../conversions/StreamArrayConversion.java | 0 .../array/looping/LoopDiagonally.java | 0 .../StreamArrayConversionUnitTest.java | 0 .../array/looping/LoopDiagonallyUnitTest.java | 2 +- pom.xml | 2 + 8 files changed, 78 insertions(+), 1 deletion(-) create mode 100644 core-java-modules/core-java-arrays-2/.gitignore rename {core-java-arrays => core-java-modules/core-java-arrays-2}/README.MD (100%) create mode 100644 core-java-modules/core-java-arrays-2/pom.xml rename {core-java-arrays => core-java-modules/core-java-arrays-2}/src/main/java/com/baeldung/array/conversions/StreamArrayConversion.java (100%) rename {core-java-arrays => core-java-modules/core-java-arrays-2}/src/main/java/com/baeldung/array/looping/LoopDiagonally.java (100%) rename {core-java-arrays => core-java-modules/core-java-arrays-2}/src/test/java/com/baeldung/array/conversions/StreamArrayConversionUnitTest.java (100%) rename core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java => core-java-modules/core-java-arrays-2/src/test/java/com/baeldung/array/looping/LoopDiagonallyUnitTest.java (93%) diff --git a/core-java-modules/core-java-arrays-2/.gitignore b/core-java-modules/core-java-arrays-2/.gitignore new file mode 100644 index 0000000000..374c8bf907 --- /dev/null +++ b/core-java-modules/core-java-arrays-2/.gitignore @@ -0,0 +1,25 @@ +*.class + +0.* + +#folders# +/target +/neoDb* +/data +/src/main/webapp/WEB-INF/classes +*/META-INF/* +.resourceCache + +# Packaged files # +*.jar +*.war +*.ear + +# Files generated by integration tests +backup-pom.xml +/bin/ +/temp + +#IntelliJ specific +.idea/ +*.iml \ No newline at end of file diff --git a/core-java-arrays/README.MD b/core-java-modules/core-java-arrays-2/README.MD similarity index 100% rename from core-java-arrays/README.MD rename to core-java-modules/core-java-arrays-2/README.MD diff --git a/core-java-modules/core-java-arrays-2/pom.xml b/core-java-modules/core-java-arrays-2/pom.xml new file mode 100644 index 0000000000..bfe8a349e1 --- /dev/null +++ b/core-java-modules/core-java-arrays-2/pom.xml @@ -0,0 +1,50 @@ + + 4.0.0 + com.baeldung + core-java-arrays-2 + 0.1.0-SNAPSHOT + core-java-arrays-2 + jar + + + com.baeldung + parent-java + 0.0.1-SNAPSHOT + ../../parent-java + + + + + org.apache.commons + commons-lang3 + ${commons-lang3.version} + + + + org.assertj + assertj-core + ${assertj-core.version} + test + + + + + core-java-arrays-2 + + + src/main/resources + true + + + + + + + + 3.9 + + 3.10.0 + + + diff --git a/core-java-arrays/src/main/java/com/baeldung/array/conversions/StreamArrayConversion.java b/core-java-modules/core-java-arrays-2/src/main/java/com/baeldung/array/conversions/StreamArrayConversion.java similarity index 100% rename from core-java-arrays/src/main/java/com/baeldung/array/conversions/StreamArrayConversion.java rename to core-java-modules/core-java-arrays-2/src/main/java/com/baeldung/array/conversions/StreamArrayConversion.java diff --git a/core-java-arrays/src/main/java/com/baeldung/array/looping/LoopDiagonally.java b/core-java-modules/core-java-arrays-2/src/main/java/com/baeldung/array/looping/LoopDiagonally.java similarity index 100% rename from core-java-arrays/src/main/java/com/baeldung/array/looping/LoopDiagonally.java rename to core-java-modules/core-java-arrays-2/src/main/java/com/baeldung/array/looping/LoopDiagonally.java diff --git a/core-java-arrays/src/test/java/com/baeldung/array/conversions/StreamArrayConversionUnitTest.java b/core-java-modules/core-java-arrays-2/src/test/java/com/baeldung/array/conversions/StreamArrayConversionUnitTest.java similarity index 100% rename from core-java-arrays/src/test/java/com/baeldung/array/conversions/StreamArrayConversionUnitTest.java rename to core-java-modules/core-java-arrays-2/src/test/java/com/baeldung/array/conversions/StreamArrayConversionUnitTest.java diff --git a/core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java b/core-java-modules/core-java-arrays-2/src/test/java/com/baeldung/array/looping/LoopDiagonallyUnitTest.java similarity index 93% rename from core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java rename to core-java-modules/core-java-arrays-2/src/test/java/com/baeldung/array/looping/LoopDiagonallyUnitTest.java index df6079270b..5f670f4a59 100644 --- a/core-java-arrays/src/test/java/com/baeldung/array/looping/LoopDiagonallyTest.java +++ b/core-java-modules/core-java-arrays-2/src/test/java/com/baeldung/array/looping/LoopDiagonallyUnitTest.java @@ -4,7 +4,7 @@ import org.junit.Test; import static org.junit.Assert.assertEquals; -public class LoopDiagonallyTest { +public class LoopDiagonallyUnitTest { @Test public void twoArrayIsLoopedDiagonallyAsExpected() { diff --git a/pom.xml b/pom.xml index c46a9a5d5a..6cdb35063e 100644 --- a/pom.xml +++ b/pom.xml @@ -392,6 +392,7 @@ core-java-modules/core-java-arrays + core-java-modules/core-java-arrays-2 core-java-modules/core-java-collections core-java-modules/core-java-collections-list core-java-modules/core-java-collections-list-2 @@ -1088,6 +1089,7 @@ core-java-modules/core-java-arrays + core-java-modules/core-java-arrays-2 core-java-modules/core-java-collections core-java-modules/core-java-collections-list core-java-modules/core-java-collections-list-2 From 49cfd94439b2283051ab2587043544e97b0a740e Mon Sep 17 00:00:00 2001 From: amit2103 Date: Sat, 27 Jul 2019 18:06:02 +0530 Subject: [PATCH 084/107] [BAEL-15959] - Removed spring-security dependency --- spring-5-mvc/pom.xml | 4 ---- 1 file changed, 4 deletions(-) diff --git a/spring-5-mvc/pom.xml b/spring-5-mvc/pom.xml index 302080a8b4..1d96df3d03 100644 --- a/spring-5-mvc/pom.xml +++ b/spring-5-mvc/pom.xml @@ -23,10 +23,6 @@ org.springframework.boot spring-boot-starter-data-jpa - - org.springframework.boot - spring-boot-starter-security - org.springframework.boot spring-boot-starter-validation From c4110e5fe8a297c9688f6530de973b443382808f Mon Sep 17 00:00:00 2001 From: Devender Kumar <47500074+kumar-devender@users.noreply.github.com> Date: Sun, 28 Jul 2019 06:19:16 +0200 Subject: [PATCH 085/107] Added big decimal validation (#7379) * Added cascading type mudule * fix compile error * updated dependency version in pom * Added BigDecimal validation classes * Updated test cases * Remove syso from test cases * Updated test cases --- .../bigdecimal/Invoice.java | 19 ++++++ .../bigdecimal/InvoiceUnitTest.java | 62 +++++++++++++++++++ .../jpa-hibernate-cascade-type/pom.xml | 8 +-- 3 files changed, 85 insertions(+), 4 deletions(-) create mode 100644 javaxval/src/main/java/org/baeldung/javabeanconstraints/bigdecimal/Invoice.java create mode 100644 javaxval/src/test/java/org/baeldung/javabeanconstraints/bigdecimal/InvoiceUnitTest.java diff --git a/javaxval/src/main/java/org/baeldung/javabeanconstraints/bigdecimal/Invoice.java b/javaxval/src/main/java/org/baeldung/javabeanconstraints/bigdecimal/Invoice.java new file mode 100644 index 0000000000..6df1b79a60 --- /dev/null +++ b/javaxval/src/main/java/org/baeldung/javabeanconstraints/bigdecimal/Invoice.java @@ -0,0 +1,19 @@ +package org.baeldung.javabeanconstraints.bigdecimal; + +import java.math.BigDecimal; + +import javax.validation.constraints.DecimalMin; +import javax.validation.constraints.Digits; + +public class Invoice { + + @DecimalMin(value = "0.0", inclusive = false) + @Digits(integer=3, fraction=2) + private BigDecimal price; + private String description; + + public Invoice(BigDecimal price, String description) { + this.price = price; + this.description = description; + } +} diff --git a/javaxval/src/test/java/org/baeldung/javabeanconstraints/bigdecimal/InvoiceUnitTest.java b/javaxval/src/test/java/org/baeldung/javabeanconstraints/bigdecimal/InvoiceUnitTest.java new file mode 100644 index 0000000000..525dd7d1ad --- /dev/null +++ b/javaxval/src/test/java/org/baeldung/javabeanconstraints/bigdecimal/InvoiceUnitTest.java @@ -0,0 +1,62 @@ +package org.baeldung.javabeanconstraints.bigdecimal; + +import static org.assertj.core.api.Assertions.assertThat; + +import java.math.BigDecimal; +import java.util.Set; + +import javax.validation.ConstraintViolation; +import javax.validation.Validation; +import javax.validation.Validator; + +import org.junit.BeforeClass; +import org.junit.Test; + +public class InvoiceUnitTest { + + private static Validator validator; + + @BeforeClass + public static void setupValidatorInstance() { + validator = Validation.buildDefaultValidatorFactory().getValidator(); + } + + @Test + public void whenPriceIntegerDigitLessThanThreeWithDecimalValue_thenShouldGiveConstraintViolations() { + Invoice invoice = new Invoice(new BigDecimal(10.21), "Book purchased"); + Set> violations = validator.validate(invoice); + assertThat(violations.size()).isEqualTo(1); + violations.forEach(action-> assertThat(action.getMessage()).isEqualTo("numeric value out of bounds (<3 digits>.<2 digits> expected)")); + } + + @Test + public void whenPriceIntegerDigitLessThanThreeWithIntegerValue_thenShouldNotGiveConstraintViolations() { + Invoice invoice = new Invoice(new BigDecimal(10), "Book purchased"); + Set> violations = validator.validate(invoice); + assertThat(violations.size()).isEqualTo(0); + } + + @Test + public void whenPriceIntegerDigitGreaterThanThree_thenShouldGiveConstraintViolations() { + Invoice invoice = new Invoice(new BigDecimal(1021.21), "Book purchased"); + Set> violations = validator.validate(invoice); + assertThat(violations.size()).isEqualTo(1); + violations.forEach(action-> assertThat(action.getMessage()).isEqualTo("numeric value out of bounds (<3 digits>.<2 digits> expected)")); + } + + @Test + public void whenPriceIsZero_thenShouldGiveConstraintViolations() { + Invoice invoice = new Invoice(new BigDecimal(000.00), "Book purchased"); + Set> violations = validator.validate(invoice); + assertThat(violations.size()).isEqualTo(1); + violations.forEach(action-> assertThat(action.getMessage()).isEqualTo("must be greater than 0.0")); + } + + @Test + public void whenPriceIsGreaterThanZero_thenShouldNotGiveConstraintViolations() { + Invoice invoice = new Invoice(new BigDecimal(100.50), "Book purchased"); + Set> violations = validator.validate(invoice); + assertThat(violations.size()).isEqualTo(0); + } + +} diff --git a/persistence-modules/jpa-hibernate-cascade-type/pom.xml b/persistence-modules/jpa-hibernate-cascade-type/pom.xml index a45f297a6b..8cfc2a5fa2 100644 --- a/persistence-modules/jpa-hibernate-cascade-type/pom.xml +++ b/persistence-modules/jpa-hibernate-cascade-type/pom.xml @@ -2,10 +2,6 @@ - jpa-hibernate-cascade-type - 4.0.0 - 1.0.0-SNAPSHOT - com.baeldung parent-modules @@ -13,6 +9,10 @@ ../../ + jpa-hibernate-cascade-type + 4.0.0 + 1.0.0-SNAPSHOT + org.hibernate From 76aa185add844f125c481171236e17a5fcbca07f Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:32:42 +0300 Subject: [PATCH 086/107] changing case --- {Twitter4J => twitter4J-temp}/README.md | 0 {Twitter4J => twitter4J-temp}/pom.xml | 0 .../src/main/java/com/baeldung/Application.java | 0 {Twitter4J => twitter4J-temp}/src/main/resources/logback.xml | 0 .../src/main/resources/twitter4j.properties | 0 .../src/test/java/com/baeldung/ApplicationIntegrationTest.java | 0 6 files changed, 0 insertions(+), 0 deletions(-) rename {Twitter4J => twitter4J-temp}/README.md (100%) rename {Twitter4J => twitter4J-temp}/pom.xml (100%) rename {Twitter4J => twitter4J-temp}/src/main/java/com/baeldung/Application.java (100%) rename {Twitter4J => twitter4J-temp}/src/main/resources/logback.xml (100%) rename {Twitter4J => twitter4J-temp}/src/main/resources/twitter4j.properties (100%) rename {Twitter4J => twitter4J-temp}/src/test/java/com/baeldung/ApplicationIntegrationTest.java (100%) diff --git a/Twitter4J/README.md b/twitter4J-temp/README.md similarity index 100% rename from Twitter4J/README.md rename to twitter4J-temp/README.md diff --git a/Twitter4J/pom.xml b/twitter4J-temp/pom.xml similarity index 100% rename from Twitter4J/pom.xml rename to twitter4J-temp/pom.xml diff --git a/Twitter4J/src/main/java/com/baeldung/Application.java b/twitter4J-temp/src/main/java/com/baeldung/Application.java similarity index 100% rename from Twitter4J/src/main/java/com/baeldung/Application.java rename to twitter4J-temp/src/main/java/com/baeldung/Application.java diff --git a/Twitter4J/src/main/resources/logback.xml b/twitter4J-temp/src/main/resources/logback.xml similarity index 100% rename from Twitter4J/src/main/resources/logback.xml rename to twitter4J-temp/src/main/resources/logback.xml diff --git a/Twitter4J/src/main/resources/twitter4j.properties b/twitter4J-temp/src/main/resources/twitter4j.properties similarity index 100% rename from Twitter4J/src/main/resources/twitter4j.properties rename to twitter4J-temp/src/main/resources/twitter4j.properties diff --git a/Twitter4J/src/test/java/com/baeldung/ApplicationIntegrationTest.java b/twitter4J-temp/src/test/java/com/baeldung/ApplicationIntegrationTest.java similarity index 100% rename from Twitter4J/src/test/java/com/baeldung/ApplicationIntegrationTest.java rename to twitter4J-temp/src/test/java/com/baeldung/ApplicationIntegrationTest.java From 7502f58b990b8f761d001035e60e8b7751593015 Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:33:07 +0300 Subject: [PATCH 087/107] changing case --- {twitter4J-temp => twitter4j}/README.md | 0 {twitter4J-temp => twitter4j}/pom.xml | 0 .../src/main/java/com/baeldung/Application.java | 0 {twitter4J-temp => twitter4j}/src/main/resources/logback.xml | 0 .../src/main/resources/twitter4j.properties | 0 .../src/test/java/com/baeldung/ApplicationIntegrationTest.java | 0 6 files changed, 0 insertions(+), 0 deletions(-) rename {twitter4J-temp => twitter4j}/README.md (100%) rename {twitter4J-temp => twitter4j}/pom.xml (100%) rename {twitter4J-temp => twitter4j}/src/main/java/com/baeldung/Application.java (100%) rename {twitter4J-temp => twitter4j}/src/main/resources/logback.xml (100%) rename {twitter4J-temp => twitter4j}/src/main/resources/twitter4j.properties (100%) rename {twitter4J-temp => twitter4j}/src/test/java/com/baeldung/ApplicationIntegrationTest.java (100%) diff --git a/twitter4J-temp/README.md b/twitter4j/README.md similarity index 100% rename from twitter4J-temp/README.md rename to twitter4j/README.md diff --git a/twitter4J-temp/pom.xml b/twitter4j/pom.xml similarity index 100% rename from twitter4J-temp/pom.xml rename to twitter4j/pom.xml diff --git a/twitter4J-temp/src/main/java/com/baeldung/Application.java b/twitter4j/src/main/java/com/baeldung/Application.java similarity index 100% rename from twitter4J-temp/src/main/java/com/baeldung/Application.java rename to twitter4j/src/main/java/com/baeldung/Application.java diff --git a/twitter4J-temp/src/main/resources/logback.xml b/twitter4j/src/main/resources/logback.xml similarity index 100% rename from twitter4J-temp/src/main/resources/logback.xml rename to twitter4j/src/main/resources/logback.xml diff --git a/twitter4J-temp/src/main/resources/twitter4j.properties b/twitter4j/src/main/resources/twitter4j.properties similarity index 100% rename from twitter4J-temp/src/main/resources/twitter4j.properties rename to twitter4j/src/main/resources/twitter4j.properties diff --git a/twitter4J-temp/src/test/java/com/baeldung/ApplicationIntegrationTest.java b/twitter4j/src/test/java/com/baeldung/ApplicationIntegrationTest.java similarity index 100% rename from twitter4J-temp/src/test/java/com/baeldung/ApplicationIntegrationTest.java rename to twitter4j/src/test/java/com/baeldung/ApplicationIntegrationTest.java From b8d65f954b72cb10f2c1ec808195e687c777f086 Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:34:07 +0300 Subject: [PATCH 088/107] changing case --- {JGit => jgit-temp}/README.md | 0 {JGit => jgit-temp}/pom.xml | 0 .../src/main/java/com/baeldung/jgit/CreateNewRepository.java | 0 .../src/main/java/com/baeldung/jgit/OpenRepository.java | 0 .../src/main/java/com/baeldung/jgit/helper/Helper.java | 0 .../src/main/java/com/baeldung/jgit/porcelain/AddFile.java | 0 .../src/main/java/com/baeldung/jgit/porcelain/CommitAll.java | 0 .../main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java | 0 .../src/main/java/com/baeldung/jgit/porcelain/Log.java | 0 {JGit => jgit-temp}/src/main/resources/logback.xml | 0 .../src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java | 0 .../test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java | 0 12 files changed, 0 insertions(+), 0 deletions(-) rename {JGit => jgit-temp}/README.md (100%) rename {JGit => jgit-temp}/pom.xml (100%) rename {JGit => jgit-temp}/src/main/java/com/baeldung/jgit/CreateNewRepository.java (100%) rename {JGit => jgit-temp}/src/main/java/com/baeldung/jgit/OpenRepository.java (100%) rename {JGit => jgit-temp}/src/main/java/com/baeldung/jgit/helper/Helper.java (100%) rename {JGit => jgit-temp}/src/main/java/com/baeldung/jgit/porcelain/AddFile.java (100%) rename {JGit => jgit-temp}/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java (100%) rename {JGit => jgit-temp}/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java (100%) rename {JGit => jgit-temp}/src/main/java/com/baeldung/jgit/porcelain/Log.java (100%) rename {JGit => jgit-temp}/src/main/resources/logback.xml (100%) rename {JGit => jgit-temp}/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java (100%) rename {JGit => jgit-temp}/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java (100%) diff --git a/JGit/README.md b/jgit-temp/README.md similarity index 100% rename from JGit/README.md rename to jgit-temp/README.md diff --git a/JGit/pom.xml b/jgit-temp/pom.xml similarity index 100% rename from JGit/pom.xml rename to jgit-temp/pom.xml diff --git a/JGit/src/main/java/com/baeldung/jgit/CreateNewRepository.java b/jgit-temp/src/main/java/com/baeldung/jgit/CreateNewRepository.java similarity index 100% rename from JGit/src/main/java/com/baeldung/jgit/CreateNewRepository.java rename to jgit-temp/src/main/java/com/baeldung/jgit/CreateNewRepository.java diff --git a/JGit/src/main/java/com/baeldung/jgit/OpenRepository.java b/jgit-temp/src/main/java/com/baeldung/jgit/OpenRepository.java similarity index 100% rename from JGit/src/main/java/com/baeldung/jgit/OpenRepository.java rename to jgit-temp/src/main/java/com/baeldung/jgit/OpenRepository.java diff --git a/JGit/src/main/java/com/baeldung/jgit/helper/Helper.java b/jgit-temp/src/main/java/com/baeldung/jgit/helper/Helper.java similarity index 100% rename from JGit/src/main/java/com/baeldung/jgit/helper/Helper.java rename to jgit-temp/src/main/java/com/baeldung/jgit/helper/Helper.java diff --git a/JGit/src/main/java/com/baeldung/jgit/porcelain/AddFile.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/AddFile.java similarity index 100% rename from JGit/src/main/java/com/baeldung/jgit/porcelain/AddFile.java rename to jgit-temp/src/main/java/com/baeldung/jgit/porcelain/AddFile.java diff --git a/JGit/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java similarity index 100% rename from JGit/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java rename to jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java diff --git a/JGit/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java similarity index 100% rename from JGit/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java rename to jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java diff --git a/JGit/src/main/java/com/baeldung/jgit/porcelain/Log.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/Log.java similarity index 100% rename from JGit/src/main/java/com/baeldung/jgit/porcelain/Log.java rename to jgit-temp/src/main/java/com/baeldung/jgit/porcelain/Log.java diff --git a/JGit/src/main/resources/logback.xml b/jgit-temp/src/main/resources/logback.xml similarity index 100% rename from JGit/src/main/resources/logback.xml rename to jgit-temp/src/main/resources/logback.xml diff --git a/JGit/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java b/jgit-temp/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java similarity index 100% rename from JGit/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java rename to jgit-temp/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java diff --git a/JGit/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java b/jgit-temp/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java similarity index 100% rename from JGit/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java rename to jgit-temp/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java From 38b37df87367bbeff2746b634dcaea7576632add Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:35:40 +0300 Subject: [PATCH 089/107] changing case --- jgit-temp/README.md | 3 - jgit-temp/pom.xml | 53 ------------- .../baeldung/jgit/CreateNewRepository.java | 30 -------- .../com/baeldung/jgit/OpenRepository.java | 65 ---------------- .../java/com/baeldung/jgit/helper/Helper.java | 33 --------- .../com/baeldung/jgit/porcelain/AddFile.java | 36 --------- .../baeldung/jgit/porcelain/CommitAll.java | 51 ------------- .../jgit/porcelain/CreateAndDeleteTag.java | 56 -------------- .../java/com/baeldung/jgit/porcelain/Log.java | 74 ------------------- jgit-temp/src/main/resources/logback.xml | 13 ---- .../baeldung/jgit/JGitBugIntegrationTest.java | 33 --------- .../jgit/porcelain/PorcelainUnitTest.java | 17 ----- 12 files changed, 464 deletions(-) delete mode 100644 jgit-temp/README.md delete mode 100644 jgit-temp/pom.xml delete mode 100644 jgit-temp/src/main/java/com/baeldung/jgit/CreateNewRepository.java delete mode 100644 jgit-temp/src/main/java/com/baeldung/jgit/OpenRepository.java delete mode 100644 jgit-temp/src/main/java/com/baeldung/jgit/helper/Helper.java delete mode 100644 jgit-temp/src/main/java/com/baeldung/jgit/porcelain/AddFile.java delete mode 100644 jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java delete mode 100644 jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java delete mode 100644 jgit-temp/src/main/java/com/baeldung/jgit/porcelain/Log.java delete mode 100644 jgit-temp/src/main/resources/logback.xml delete mode 100644 jgit-temp/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java delete mode 100644 jgit-temp/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java diff --git a/jgit-temp/README.md b/jgit-temp/README.md deleted file mode 100644 index 5c65f1101b..0000000000 --- a/jgit-temp/README.md +++ /dev/null @@ -1,3 +0,0 @@ -## Relevant articles: - -- [A Guide to JGit](http://www.baeldung.com/jgit) diff --git a/jgit-temp/pom.xml b/jgit-temp/pom.xml deleted file mode 100644 index deae1e45e3..0000000000 --- a/jgit-temp/pom.xml +++ /dev/null @@ -1,53 +0,0 @@ - - - 4.0.0 - com.baeldung - JGit - 1.0-SNAPSHOT - JGit - jar - http://maven.apache.org - - - com.baeldung - parent-modules - 1.0.0-SNAPSHOT - - - - - jgit-repository - https://repo.eclipse.org/content/groups/releases/ - - - - - - - org.eclipse.jgit - org.eclipse.jgit - ${org.eclipse.jgit.version} - - - org.eclipse.jgit - org.eclipse.jgit.archive - ${org.eclipse.jgit.version} - - - commons-io - commons-io - ${commons-io.version} - - - org.slf4j - slf4j-simple - ${org.slf4j.version} - - - - - 4.5.0.201609210915-r - - - \ No newline at end of file diff --git a/jgit-temp/src/main/java/com/baeldung/jgit/CreateNewRepository.java b/jgit-temp/src/main/java/com/baeldung/jgit/CreateNewRepository.java deleted file mode 100644 index 1702efc315..0000000000 --- a/jgit-temp/src/main/java/com/baeldung/jgit/CreateNewRepository.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.baeldung.jgit; - -import java.io.File; -import java.io.IOException; -import org.apache.commons.io.FileUtils; -import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.errors.GitAPIException; - -/** - * Simple snippet which shows how to create a new repository - * - * - */ -public class CreateNewRepository { - - public static void main(String[] args) throws IOException, IllegalStateException, GitAPIException { - // prepare a new folder - File localPath = File.createTempFile("TestGitRepository", ""); - if(!localPath.delete()) { - throw new IOException("Could not delete temporary file " + localPath); - } - - // create the directory - try (Git git = Git.init().setDirectory(localPath).call()) { - System.out.println("Having repository: " + git.getRepository().getDirectory()); - } - - FileUtils.deleteDirectory(localPath); - } -} diff --git a/jgit-temp/src/main/java/com/baeldung/jgit/OpenRepository.java b/jgit-temp/src/main/java/com/baeldung/jgit/OpenRepository.java deleted file mode 100644 index 671df2a844..0000000000 --- a/jgit-temp/src/main/java/com/baeldung/jgit/OpenRepository.java +++ /dev/null @@ -1,65 +0,0 @@ -package com.baeldung.jgit; - -import com.baeldung.jgit.helper.Helper; -import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.errors.GitAPIException; -import org.eclipse.jgit.lib.Ref; -import org.eclipse.jgit.lib.Repository; -import org.eclipse.jgit.storage.file.FileRepositoryBuilder; -import java.io.File; -import java.io.IOException; - -/** - * Simple snippet which shows how to open an existing repository - * - * - */ -public class OpenRepository { - - public static void main(String[] args) throws IOException, GitAPIException { - // first create a test-repository, the return is including the .get directory here! - File repoDir = createSampleGitRepo(); - - // now open the resulting repository with a FileRepositoryBuilder - FileRepositoryBuilder builder = new FileRepositoryBuilder(); - try (Repository repository = builder.setGitDir(repoDir) - .readEnvironment() // scan environment GIT_* variables - .findGitDir() // scan up the file system tree - .build()) { - System.out.println("Having repository: " + repository.getDirectory()); - - // the Ref holds an ObjectId for any type of object (tree, commit, blob, tree) - Ref head = repository.exactRef("refs/heads/master"); - System.out.println("Ref of refs/heads/master: " + head); - } - } - - private static File createSampleGitRepo() throws IOException, GitAPIException { - try (Repository repository = Helper.createNewRepository()) { - System.out.println("Temporary repository at " + repository.getDirectory()); - - // create the file - File myfile = new File(repository.getDirectory().getParent(), "testfile"); - if(!myfile.createNewFile()) { - throw new IOException("Could not create file " + myfile); - } - - // run the add-call - try (Git git = new Git(repository)) { - git.add() - .addFilepattern("testfile") - .call(); - - - // and then commit the changes - git.commit() - .setMessage("Added testfile") - .call(); - } - - System.out.println("Added file " + myfile + " to repository at " + repository.getDirectory()); - - return repository.getDirectory(); - } - } -} diff --git a/jgit-temp/src/main/java/com/baeldung/jgit/helper/Helper.java b/jgit-temp/src/main/java/com/baeldung/jgit/helper/Helper.java deleted file mode 100644 index 39d7b767d2..0000000000 --- a/jgit-temp/src/main/java/com/baeldung/jgit/helper/Helper.java +++ /dev/null @@ -1,33 +0,0 @@ - -package com.baeldung.jgit.helper; - -import java.io.File; -import java.io.IOException; -import org.eclipse.jgit.lib.Repository; -import org.eclipse.jgit.storage.file.FileRepositoryBuilder; - -public class Helper { - - public static Repository openJGitRepository() throws IOException { - FileRepositoryBuilder builder = new FileRepositoryBuilder(); - return builder - .readEnvironment() // scan environment GIT_* variables - .findGitDir() // scan up the file system tree - .build(); - } - - public static Repository createNewRepository() throws IOException { - // prepare a new folder - File localPath = File.createTempFile("TestGitRepository", ""); - if(!localPath.delete()) { - throw new IOException("Could not delete temporary file " + localPath); - } - - // create the directory - Repository repository = FileRepositoryBuilder.create(new File(localPath, ".git")); - repository.create(); - - return repository; - } - -} diff --git a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/AddFile.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/AddFile.java deleted file mode 100644 index 314366f08c..0000000000 --- a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/AddFile.java +++ /dev/null @@ -1,36 +0,0 @@ -package com.baeldung.jgit.porcelain; - -import java.io.File; -import java.io.IOException; -import com.baeldung.jgit.helper.Helper; -import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.errors.GitAPIException; -import org.eclipse.jgit.lib.Repository; - -/** - * Simple snippet which shows how to add a file to the index - * - * - */ -public class AddFile { - - public static void main(String[] args) throws IOException, GitAPIException { - // prepare a new test-repository - try (Repository repository = Helper.createNewRepository()) { - try (Git git = new Git(repository)) { - // create the file - File myfile = new File(repository.getDirectory().getParent(), "testfile"); - if(!myfile.createNewFile()) { - throw new IOException("Could not create file " + myfile); - } - - // run the add-call - git.add() - .addFilepattern("testfile") - .call(); - - System.out.println("Added file " + myfile + " to repository at " + repository.getDirectory()); - } - } - } -} diff --git a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java deleted file mode 100644 index 4c0956ebf8..0000000000 --- a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java +++ /dev/null @@ -1,51 +0,0 @@ -package com.baeldung.jgit.porcelain; - -import java.io.File; -import java.io.IOException; -import java.io.PrintWriter; -import com.baeldung.jgit.helper.Helper; -import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.errors.GitAPIException; -import org.eclipse.jgit.lib.Repository; - -/** - * Simple snippet which shows how to commit all files - * - * - */ -public class CommitAll { - - public static void main(String[] args) throws IOException, GitAPIException { - // prepare a new test-repository - try (Repository repository = Helper.createNewRepository()) { - try (Git git = new Git(repository)) { - // create the file - File myfile = new File(repository.getDirectory().getParent(), "testfile"); - if(!myfile.createNewFile()) { - throw new IOException("Could not create file " + myfile); - } - - // Stage all files in the repo including new files - git.add().addFilepattern(".").call(); - - // and then commit the changes. - git.commit() - .setMessage("Commit all changes including additions") - .call(); - - try(PrintWriter writer = new PrintWriter(myfile)) { - writer.append("Hello, world!"); - } - - // Stage all changed files, omitting new files, and commit with one command - git.commit() - .setAll(true) - .setMessage("Commit changes to all files") - .call(); - - - System.out.println("Committed all changes to repository at " + repository.getDirectory()); - } - } - } -} diff --git a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java deleted file mode 100644 index 0f735daf8c..0000000000 --- a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java +++ /dev/null @@ -1,56 +0,0 @@ -package com.baeldung.jgit.porcelain; - -import java.io.IOException; -import com.baeldung.jgit.helper.Helper; -import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.errors.GitAPIException; -import org.eclipse.jgit.lib.ObjectId; -import org.eclipse.jgit.lib.Ref; -import org.eclipse.jgit.lib.Repository; -import org.eclipse.jgit.revwalk.RevCommit; -import org.eclipse.jgit.revwalk.RevWalk; - -/** - * Simple snippet which shows how to create a tag - * - * - */ -public class CreateAndDeleteTag { - - public static void main(String[] args) throws IOException, GitAPIException { - // prepare test-repository - try (Repository repository = Helper.openJGitRepository()) { - try (Git git = new Git(repository)) { - // remove the tag before creating it - git.tagDelete().setTags("tag_for_testing").call(); - - // set it on the current HEAD - Ref tag = git.tag().setName("tag_for_testing").call(); - System.out.println("Created/moved tag " + tag + " to repository at " + repository.getDirectory()); - - // remove the tag again - git.tagDelete().setTags("tag_for_testing").call(); - - // read some other commit and set the tag on it - ObjectId id = repository.resolve("HEAD^"); - try (RevWalk walk = new RevWalk(repository)) { - RevCommit commit = walk.parseCommit(id); - tag = git.tag().setObjectId(commit).setName("tag_for_testing").call(); - System.out.println("Created/moved tag " + tag + " to repository at " + repository.getDirectory()); - - // remove the tag again - git.tagDelete().setTags("tag_for_testing").call(); - - // create an annotated tag - tag = git.tag().setName("tag_for_testing").setAnnotated(true).call(); - System.out.println("Created/moved tag " + tag + " to repository at " + repository.getDirectory()); - - // remove the tag again - git.tagDelete().setTags("tag_for_testing").call(); - - walk.dispose(); - } - } - } - } -} diff --git a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/Log.java b/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/Log.java deleted file mode 100644 index a50028a9ae..0000000000 --- a/jgit-temp/src/main/java/com/baeldung/jgit/porcelain/Log.java +++ /dev/null @@ -1,74 +0,0 @@ -package com.baeldung.jgit.porcelain; - -import java.io.IOException; -import com.baeldung.jgit.helper.Helper; -import org.eclipse.jgit.api.Git; -import org.eclipse.jgit.api.errors.GitAPIException; -import org.eclipse.jgit.lib.Repository; -import org.eclipse.jgit.revwalk.RevCommit; - -/** - * Simple snippet which shows how to get the commit-ids for a file to provide log information. - * - * - */ -public class Log { - - @SuppressWarnings("unused") - public static void main(String[] args) throws IOException, GitAPIException { - try (Repository repository = Helper.openJGitRepository()) { - try (Git git = new Git(repository)) { - Iterable logs = git.log() - .call(); - int count = 0; - for (RevCommit rev : logs) { - //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); - count++; - } - System.out.println("Had " + count + " commits overall on current branch"); - - logs = git.log() - .add(repository.resolve(git.getRepository().getFullBranch())) - .call(); - count = 0; - for (RevCommit rev : logs) { - System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); - count++; - } - System.out.println("Had " + count + " commits overall on "+git.getRepository().getFullBranch()); - - logs = git.log() - .all() - .call(); - count = 0; - for (RevCommit rev : logs) { - //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); - count++; - } - System.out.println("Had " + count + " commits overall in repository"); - - logs = git.log() - // for all log.all() - .addPath("README.md") - .call(); - count = 0; - for (RevCommit rev : logs) { - //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); - count++; - } - System.out.println("Had " + count + " commits on README.md"); - - logs = git.log() - // for all log.all() - .addPath("pom.xml") - .call(); - count = 0; - for (RevCommit rev : logs) { - //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); - count++; - } - System.out.println("Had " + count + " commits on pom.xml"); - } - } - } -} diff --git a/jgit-temp/src/main/resources/logback.xml b/jgit-temp/src/main/resources/logback.xml deleted file mode 100644 index 7d900d8ea8..0000000000 --- a/jgit-temp/src/main/resources/logback.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n - - - - - - - - \ No newline at end of file diff --git a/jgit-temp/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java b/jgit-temp/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java deleted file mode 100644 index ad34890996..0000000000 --- a/jgit-temp/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java +++ /dev/null @@ -1,33 +0,0 @@ -package com.baeldung.jgit; - -import com.baeldung.jgit.helper.Helper; -import org.eclipse.jgit.lib.ObjectLoader; -import org.eclipse.jgit.lib.ObjectReader; -import org.eclipse.jgit.lib.Ref; -import org.eclipse.jgit.lib.Repository; -import org.eclipse.jgit.revwalk.RevWalk; -import org.junit.Test; -import java.io.IOException; -import static org.junit.Assert.assertNotNull; - -/** - * Tests which show issues with JGit that we reported upstream. - */ -public class JGitBugIntegrationTest { - @Test - public void testRevWalkDisposeClosesReader() throws IOException { - try (Repository repo = Helper.openJGitRepository()) { - try (ObjectReader reader = repo.newObjectReader()) { - try (RevWalk walk = new RevWalk(reader)) { - walk.dispose(); - - Ref head = repo.exactRef("refs/heads/master"); - System.out.println("Found head: " + head); - - ObjectLoader loader = reader.open(head.getObjectId()); - assertNotNull(loader); - } - } - } - } -} diff --git a/jgit-temp/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java b/jgit-temp/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java deleted file mode 100644 index d3b3358664..0000000000 --- a/jgit-temp/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java +++ /dev/null @@ -1,17 +0,0 @@ -package com.baeldung.jgit.porcelain; - -import org.junit.Test; - -public class PorcelainUnitTest { - @Test - public void runSamples() throws Exception { - // simply call all the samples to see any severe problems with the samples - AddFile.main(null); - - CommitAll.main(null); - - CreateAndDeleteTag.main(null); - - Log.main(null); - } -} From 1db074d22d61b5ebca3ba3d6116ae03cabc48bf1 Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:35:46 +0300 Subject: [PATCH 090/107] changing case --- jgit/README.md | 3 + jgit/pom.xml | 53 +++++++++++++ .../baeldung/jgit/CreateNewRepository.java | 30 ++++++++ .../com/baeldung/jgit/OpenRepository.java | 65 ++++++++++++++++ .../java/com/baeldung/jgit/helper/Helper.java | 33 +++++++++ .../com/baeldung/jgit/porcelain/AddFile.java | 36 +++++++++ .../baeldung/jgit/porcelain/CommitAll.java | 51 +++++++++++++ .../jgit/porcelain/CreateAndDeleteTag.java | 56 ++++++++++++++ .../java/com/baeldung/jgit/porcelain/Log.java | 74 +++++++++++++++++++ jgit/src/main/resources/logback.xml | 13 ++++ .../baeldung/jgit/JGitBugIntegrationTest.java | 33 +++++++++ .../jgit/porcelain/PorcelainUnitTest.java | 17 +++++ 12 files changed, 464 insertions(+) create mode 100644 jgit/README.md create mode 100644 jgit/pom.xml create mode 100644 jgit/src/main/java/com/baeldung/jgit/CreateNewRepository.java create mode 100644 jgit/src/main/java/com/baeldung/jgit/OpenRepository.java create mode 100644 jgit/src/main/java/com/baeldung/jgit/helper/Helper.java create mode 100644 jgit/src/main/java/com/baeldung/jgit/porcelain/AddFile.java create mode 100644 jgit/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java create mode 100644 jgit/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java create mode 100644 jgit/src/main/java/com/baeldung/jgit/porcelain/Log.java create mode 100644 jgit/src/main/resources/logback.xml create mode 100644 jgit/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java create mode 100644 jgit/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java diff --git a/jgit/README.md b/jgit/README.md new file mode 100644 index 0000000000..5c65f1101b --- /dev/null +++ b/jgit/README.md @@ -0,0 +1,3 @@ +## Relevant articles: + +- [A Guide to JGit](http://www.baeldung.com/jgit) diff --git a/jgit/pom.xml b/jgit/pom.xml new file mode 100644 index 0000000000..deae1e45e3 --- /dev/null +++ b/jgit/pom.xml @@ -0,0 +1,53 @@ + + + 4.0.0 + com.baeldung + JGit + 1.0-SNAPSHOT + JGit + jar + http://maven.apache.org + + + com.baeldung + parent-modules + 1.0.0-SNAPSHOT + + + + + jgit-repository + https://repo.eclipse.org/content/groups/releases/ + + + + + + + org.eclipse.jgit + org.eclipse.jgit + ${org.eclipse.jgit.version} + + + org.eclipse.jgit + org.eclipse.jgit.archive + ${org.eclipse.jgit.version} + + + commons-io + commons-io + ${commons-io.version} + + + org.slf4j + slf4j-simple + ${org.slf4j.version} + + + + + 4.5.0.201609210915-r + + + \ No newline at end of file diff --git a/jgit/src/main/java/com/baeldung/jgit/CreateNewRepository.java b/jgit/src/main/java/com/baeldung/jgit/CreateNewRepository.java new file mode 100644 index 0000000000..1702efc315 --- /dev/null +++ b/jgit/src/main/java/com/baeldung/jgit/CreateNewRepository.java @@ -0,0 +1,30 @@ +package com.baeldung.jgit; + +import java.io.File; +import java.io.IOException; +import org.apache.commons.io.FileUtils; +import org.eclipse.jgit.api.Git; +import org.eclipse.jgit.api.errors.GitAPIException; + +/** + * Simple snippet which shows how to create a new repository + * + * + */ +public class CreateNewRepository { + + public static void main(String[] args) throws IOException, IllegalStateException, GitAPIException { + // prepare a new folder + File localPath = File.createTempFile("TestGitRepository", ""); + if(!localPath.delete()) { + throw new IOException("Could not delete temporary file " + localPath); + } + + // create the directory + try (Git git = Git.init().setDirectory(localPath).call()) { + System.out.println("Having repository: " + git.getRepository().getDirectory()); + } + + FileUtils.deleteDirectory(localPath); + } +} diff --git a/jgit/src/main/java/com/baeldung/jgit/OpenRepository.java b/jgit/src/main/java/com/baeldung/jgit/OpenRepository.java new file mode 100644 index 0000000000..671df2a844 --- /dev/null +++ b/jgit/src/main/java/com/baeldung/jgit/OpenRepository.java @@ -0,0 +1,65 @@ +package com.baeldung.jgit; + +import com.baeldung.jgit.helper.Helper; +import org.eclipse.jgit.api.Git; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.lib.Ref; +import org.eclipse.jgit.lib.Repository; +import org.eclipse.jgit.storage.file.FileRepositoryBuilder; +import java.io.File; +import java.io.IOException; + +/** + * Simple snippet which shows how to open an existing repository + * + * + */ +public class OpenRepository { + + public static void main(String[] args) throws IOException, GitAPIException { + // first create a test-repository, the return is including the .get directory here! + File repoDir = createSampleGitRepo(); + + // now open the resulting repository with a FileRepositoryBuilder + FileRepositoryBuilder builder = new FileRepositoryBuilder(); + try (Repository repository = builder.setGitDir(repoDir) + .readEnvironment() // scan environment GIT_* variables + .findGitDir() // scan up the file system tree + .build()) { + System.out.println("Having repository: " + repository.getDirectory()); + + // the Ref holds an ObjectId for any type of object (tree, commit, blob, tree) + Ref head = repository.exactRef("refs/heads/master"); + System.out.println("Ref of refs/heads/master: " + head); + } + } + + private static File createSampleGitRepo() throws IOException, GitAPIException { + try (Repository repository = Helper.createNewRepository()) { + System.out.println("Temporary repository at " + repository.getDirectory()); + + // create the file + File myfile = new File(repository.getDirectory().getParent(), "testfile"); + if(!myfile.createNewFile()) { + throw new IOException("Could not create file " + myfile); + } + + // run the add-call + try (Git git = new Git(repository)) { + git.add() + .addFilepattern("testfile") + .call(); + + + // and then commit the changes + git.commit() + .setMessage("Added testfile") + .call(); + } + + System.out.println("Added file " + myfile + " to repository at " + repository.getDirectory()); + + return repository.getDirectory(); + } + } +} diff --git a/jgit/src/main/java/com/baeldung/jgit/helper/Helper.java b/jgit/src/main/java/com/baeldung/jgit/helper/Helper.java new file mode 100644 index 0000000000..39d7b767d2 --- /dev/null +++ b/jgit/src/main/java/com/baeldung/jgit/helper/Helper.java @@ -0,0 +1,33 @@ + +package com.baeldung.jgit.helper; + +import java.io.File; +import java.io.IOException; +import org.eclipse.jgit.lib.Repository; +import org.eclipse.jgit.storage.file.FileRepositoryBuilder; + +public class Helper { + + public static Repository openJGitRepository() throws IOException { + FileRepositoryBuilder builder = new FileRepositoryBuilder(); + return builder + .readEnvironment() // scan environment GIT_* variables + .findGitDir() // scan up the file system tree + .build(); + } + + public static Repository createNewRepository() throws IOException { + // prepare a new folder + File localPath = File.createTempFile("TestGitRepository", ""); + if(!localPath.delete()) { + throw new IOException("Could not delete temporary file " + localPath); + } + + // create the directory + Repository repository = FileRepositoryBuilder.create(new File(localPath, ".git")); + repository.create(); + + return repository; + } + +} diff --git a/jgit/src/main/java/com/baeldung/jgit/porcelain/AddFile.java b/jgit/src/main/java/com/baeldung/jgit/porcelain/AddFile.java new file mode 100644 index 0000000000..314366f08c --- /dev/null +++ b/jgit/src/main/java/com/baeldung/jgit/porcelain/AddFile.java @@ -0,0 +1,36 @@ +package com.baeldung.jgit.porcelain; + +import java.io.File; +import java.io.IOException; +import com.baeldung.jgit.helper.Helper; +import org.eclipse.jgit.api.Git; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.lib.Repository; + +/** + * Simple snippet which shows how to add a file to the index + * + * + */ +public class AddFile { + + public static void main(String[] args) throws IOException, GitAPIException { + // prepare a new test-repository + try (Repository repository = Helper.createNewRepository()) { + try (Git git = new Git(repository)) { + // create the file + File myfile = new File(repository.getDirectory().getParent(), "testfile"); + if(!myfile.createNewFile()) { + throw new IOException("Could not create file " + myfile); + } + + // run the add-call + git.add() + .addFilepattern("testfile") + .call(); + + System.out.println("Added file " + myfile + " to repository at " + repository.getDirectory()); + } + } + } +} diff --git a/jgit/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java b/jgit/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java new file mode 100644 index 0000000000..4c0956ebf8 --- /dev/null +++ b/jgit/src/main/java/com/baeldung/jgit/porcelain/CommitAll.java @@ -0,0 +1,51 @@ +package com.baeldung.jgit.porcelain; + +import java.io.File; +import java.io.IOException; +import java.io.PrintWriter; +import com.baeldung.jgit.helper.Helper; +import org.eclipse.jgit.api.Git; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.lib.Repository; + +/** + * Simple snippet which shows how to commit all files + * + * + */ +public class CommitAll { + + public static void main(String[] args) throws IOException, GitAPIException { + // prepare a new test-repository + try (Repository repository = Helper.createNewRepository()) { + try (Git git = new Git(repository)) { + // create the file + File myfile = new File(repository.getDirectory().getParent(), "testfile"); + if(!myfile.createNewFile()) { + throw new IOException("Could not create file " + myfile); + } + + // Stage all files in the repo including new files + git.add().addFilepattern(".").call(); + + // and then commit the changes. + git.commit() + .setMessage("Commit all changes including additions") + .call(); + + try(PrintWriter writer = new PrintWriter(myfile)) { + writer.append("Hello, world!"); + } + + // Stage all changed files, omitting new files, and commit with one command + git.commit() + .setAll(true) + .setMessage("Commit changes to all files") + .call(); + + + System.out.println("Committed all changes to repository at " + repository.getDirectory()); + } + } + } +} diff --git a/jgit/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java b/jgit/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java new file mode 100644 index 0000000000..0f735daf8c --- /dev/null +++ b/jgit/src/main/java/com/baeldung/jgit/porcelain/CreateAndDeleteTag.java @@ -0,0 +1,56 @@ +package com.baeldung.jgit.porcelain; + +import java.io.IOException; +import com.baeldung.jgit.helper.Helper; +import org.eclipse.jgit.api.Git; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.lib.ObjectId; +import org.eclipse.jgit.lib.Ref; +import org.eclipse.jgit.lib.Repository; +import org.eclipse.jgit.revwalk.RevCommit; +import org.eclipse.jgit.revwalk.RevWalk; + +/** + * Simple snippet which shows how to create a tag + * + * + */ +public class CreateAndDeleteTag { + + public static void main(String[] args) throws IOException, GitAPIException { + // prepare test-repository + try (Repository repository = Helper.openJGitRepository()) { + try (Git git = new Git(repository)) { + // remove the tag before creating it + git.tagDelete().setTags("tag_for_testing").call(); + + // set it on the current HEAD + Ref tag = git.tag().setName("tag_for_testing").call(); + System.out.println("Created/moved tag " + tag + " to repository at " + repository.getDirectory()); + + // remove the tag again + git.tagDelete().setTags("tag_for_testing").call(); + + // read some other commit and set the tag on it + ObjectId id = repository.resolve("HEAD^"); + try (RevWalk walk = new RevWalk(repository)) { + RevCommit commit = walk.parseCommit(id); + tag = git.tag().setObjectId(commit).setName("tag_for_testing").call(); + System.out.println("Created/moved tag " + tag + " to repository at " + repository.getDirectory()); + + // remove the tag again + git.tagDelete().setTags("tag_for_testing").call(); + + // create an annotated tag + tag = git.tag().setName("tag_for_testing").setAnnotated(true).call(); + System.out.println("Created/moved tag " + tag + " to repository at " + repository.getDirectory()); + + // remove the tag again + git.tagDelete().setTags("tag_for_testing").call(); + + walk.dispose(); + } + } + } + } +} diff --git a/jgit/src/main/java/com/baeldung/jgit/porcelain/Log.java b/jgit/src/main/java/com/baeldung/jgit/porcelain/Log.java new file mode 100644 index 0000000000..a50028a9ae --- /dev/null +++ b/jgit/src/main/java/com/baeldung/jgit/porcelain/Log.java @@ -0,0 +1,74 @@ +package com.baeldung.jgit.porcelain; + +import java.io.IOException; +import com.baeldung.jgit.helper.Helper; +import org.eclipse.jgit.api.Git; +import org.eclipse.jgit.api.errors.GitAPIException; +import org.eclipse.jgit.lib.Repository; +import org.eclipse.jgit.revwalk.RevCommit; + +/** + * Simple snippet which shows how to get the commit-ids for a file to provide log information. + * + * + */ +public class Log { + + @SuppressWarnings("unused") + public static void main(String[] args) throws IOException, GitAPIException { + try (Repository repository = Helper.openJGitRepository()) { + try (Git git = new Git(repository)) { + Iterable logs = git.log() + .call(); + int count = 0; + for (RevCommit rev : logs) { + //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); + count++; + } + System.out.println("Had " + count + " commits overall on current branch"); + + logs = git.log() + .add(repository.resolve(git.getRepository().getFullBranch())) + .call(); + count = 0; + for (RevCommit rev : logs) { + System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); + count++; + } + System.out.println("Had " + count + " commits overall on "+git.getRepository().getFullBranch()); + + logs = git.log() + .all() + .call(); + count = 0; + for (RevCommit rev : logs) { + //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); + count++; + } + System.out.println("Had " + count + " commits overall in repository"); + + logs = git.log() + // for all log.all() + .addPath("README.md") + .call(); + count = 0; + for (RevCommit rev : logs) { + //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); + count++; + } + System.out.println("Had " + count + " commits on README.md"); + + logs = git.log() + // for all log.all() + .addPath("pom.xml") + .call(); + count = 0; + for (RevCommit rev : logs) { + //System.out.println("Commit: " + rev /* + ", name: " + rev.getName() + ", id: " + rev.getId().getName() */); + count++; + } + System.out.println("Had " + count + " commits on pom.xml"); + } + } + } +} diff --git a/jgit/src/main/resources/logback.xml b/jgit/src/main/resources/logback.xml new file mode 100644 index 0000000000..7d900d8ea8 --- /dev/null +++ b/jgit/src/main/resources/logback.xml @@ -0,0 +1,13 @@ + + + + + %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n + + + + + + + + \ No newline at end of file diff --git a/jgit/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java b/jgit/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java new file mode 100644 index 0000000000..ad34890996 --- /dev/null +++ b/jgit/src/test/java/com/baeldung/jgit/JGitBugIntegrationTest.java @@ -0,0 +1,33 @@ +package com.baeldung.jgit; + +import com.baeldung.jgit.helper.Helper; +import org.eclipse.jgit.lib.ObjectLoader; +import org.eclipse.jgit.lib.ObjectReader; +import org.eclipse.jgit.lib.Ref; +import org.eclipse.jgit.lib.Repository; +import org.eclipse.jgit.revwalk.RevWalk; +import org.junit.Test; +import java.io.IOException; +import static org.junit.Assert.assertNotNull; + +/** + * Tests which show issues with JGit that we reported upstream. + */ +public class JGitBugIntegrationTest { + @Test + public void testRevWalkDisposeClosesReader() throws IOException { + try (Repository repo = Helper.openJGitRepository()) { + try (ObjectReader reader = repo.newObjectReader()) { + try (RevWalk walk = new RevWalk(reader)) { + walk.dispose(); + + Ref head = repo.exactRef("refs/heads/master"); + System.out.println("Found head: " + head); + + ObjectLoader loader = reader.open(head.getObjectId()); + assertNotNull(loader); + } + } + } + } +} diff --git a/jgit/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java b/jgit/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java new file mode 100644 index 0000000000..d3b3358664 --- /dev/null +++ b/jgit/src/test/java/com/baeldung/jgit/porcelain/PorcelainUnitTest.java @@ -0,0 +1,17 @@ +package com.baeldung.jgit.porcelain; + +import org.junit.Test; + +public class PorcelainUnitTest { + @Test + public void runSamples() throws Exception { + // simply call all the samples to see any severe problems with the samples + AddFile.main(null); + + CommitAll.main(null); + + CreateAndDeleteTag.main(null); + + Log.main(null); + } +} From 0094c08a3d86338a402e6401cc04a8d7a349a7dc Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:39:48 +0300 Subject: [PATCH 091/107] changing case in the pom --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 6cdb35063e..0754b186cf 100644 --- a/pom.xml +++ b/pom.xml @@ -483,7 +483,7 @@ jee-7 --> jee-7-security jersey - JGit + jgit jgroups jhipster-5 jib @@ -781,7 +781,7 @@ testing-modules twilio - Twitter4J + twitter4j undertow From 0a5d51461ce8e581ff1bc98972e99584bfc3b85e Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:40:25 +0300 Subject: [PATCH 092/107] changing case in the pom --- pom.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pom.xml b/pom.xml index 0754b186cf..5b5058763d 100644 --- a/pom.xml +++ b/pom.xml @@ -1176,7 +1176,7 @@ jee-7 --> jee-7-security jersey - JGit + jgit jgroups jhipster-5 jib @@ -1451,7 +1451,7 @@ testing-modules twilio - Twitter4J + twitter4j undertow From c0308756da53ba3486bec13915de4d27fbca76e6 Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:45:13 +0300 Subject: [PATCH 093/107] Update README.md --- README.md | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index 7f78cf1515..cc3f48d8ed 100644 --- a/README.md +++ b/README.md @@ -1,12 +1,16 @@ -The "REST with Spring" Classes +The Courses ============================== -Here's the Master Class of REST With Spring (along with the newly announced Boot 2 material):
    -**[>> THE REST WITH SPRING - MASTER CLASS](http://www.baeldung.com/rest-with-spring-course?utm_source=github&utm_medium=social&utm_content=tutorials&utm_campaign=rws#master-class)** -And here's the Master Class of Learn Spring Security:
    -**[>> LEARN SPRING SECURITY - MASTER CLASS](http://www.baeldung.com/learn-spring-security-course?utm_source=github&utm_medium=social&utm_content=tutorials&utm_campaign=lss#master-class)** +Here's the new "Learn Spring" course:
    +**[>> LEARN SPRING - THE MASTER CLASS](https://www.baeldung.com/learn-spring-course?utm_source=github&utm_medium=social&utm_content=tutorials&utm_campaign=ls#master-class)** + +Here's the Master Class of "REST With Spring" (along with the new announced Boot 2 material):
    +**[>> THE REST WITH SPRING - MASTER CLASS](https://www.baeldung.com/rest-with-spring-course?utm_source=github&utm_medium=social&utm_content=tutorials&utm_campaign=rws#master-class)** + +And here's the Master Class of "Learn Spring Security":
    +**[>> LEARN SPRING SECURITY - MASTER CLASS](https://www.baeldung.com/learn-spring-security-course?utm_source=github&utm_medium=social&utm_content=tutorials&utm_campaign=lss#master-class)** @@ -15,7 +19,7 @@ Java and Spring Tutorials This project is **a collection of small and focused tutorials** - each covering a single and well defined area of development in the Java ecosystem. A strong focus of these is, of course, the Spring Framework - Spring, Spring Boot and Spring Security. -In additional to Spring, the following technologies are in focus: `core Java`, `Jackson`, `HttpClient`, `Guava`. +In additional to Spring, the modules here are covering a number of aspects in Java. Building the project @@ -32,6 +36,7 @@ Running a Spring Boot module ==================== To run a Spring Boot module run the command: `mvn spring-boot:run` in the module directory + ###Running Tests The command `mvn clean install` will run the unit tests in a module. From 8ae248ce42bde06937b5477f8b114bb0ad061408 Mon Sep 17 00:00:00 2001 From: Eugen Date: Sun, 28 Jul 2019 09:47:03 +0300 Subject: [PATCH 094/107] Update README.md --- README.md | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index cc3f48d8ed..4cad075cc3 100644 --- a/README.md +++ b/README.md @@ -37,8 +37,14 @@ Running a Spring Boot module To run a Spring Boot module run the command: `mvn spring-boot:run` in the module directory -###Running Tests +Working with the IDE +==================== +This repo contains a large number of modules. +When you're working with an individual module, there's no need to import all of them (or build all of them) - you can simply import that particular module in either Eclipse or IntelliJ. + +Running Tests +============= The command `mvn clean install` will run the unit tests in a module. To run the integration tests, use the command `mvn clean install -Pintegration-lite-first` From 9b97533de725e7050db6da71774b8866822ad023 Mon Sep 17 00:00:00 2001 From: fanatixan Date: Mon, 29 Jul 2019 07:46:22 +0200 Subject: [PATCH 095/107] bael-3119 (#7436) --- .../relationships/aggregation/Car.java | 9 ++++++ .../aggregation/CarWithStaticInnerWheel.java | 13 +++++++++ .../relationships/aggregation/Wheel.java | 7 +++++ .../relationships/association/Child.java | 7 +++++ .../relationships/association/Mother.java | 9 ++++++ .../relationships/composition/Building.java | 18 ++++++++++++ .../BuildingWithDefinitionRoomInMethod.java | 28 +++++++++++++++++++ .../relationships/university/Department.java | 9 ++++++ .../relationships/university/Professor.java | 10 +++++++ .../relationships/university/University.java | 9 ++++++ 10 files changed, 119 insertions(+) create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Car.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/CarWithStaticInnerWheel.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Wheel.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Child.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Mother.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/Building.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/BuildingWithDefinitionRoomInMethod.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Department.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Professor.java create mode 100644 core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/University.java diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Car.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Car.java new file mode 100644 index 0000000000..6be9a18781 --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Car.java @@ -0,0 +1,9 @@ +package com.baeldung.relationships.aggregation; + +import java.util.List; + +public class Car { + + private List wheels; + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/CarWithStaticInnerWheel.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/CarWithStaticInnerWheel.java new file mode 100644 index 0000000000..96c07f13a4 --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/CarWithStaticInnerWheel.java @@ -0,0 +1,13 @@ +package com.baeldung.relationships.aggregation; + +import java.util.List; + +public class CarWithStaticInnerWheel { + + private List wheels; + + public static class Wheel { + + } + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Wheel.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Wheel.java new file mode 100644 index 0000000000..1f38ea85ad --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/aggregation/Wheel.java @@ -0,0 +1,7 @@ +package com.baeldung.relationships.aggregation; + +public class Wheel { + + private Car car; + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Child.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Child.java new file mode 100644 index 0000000000..4c748e8084 --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Child.java @@ -0,0 +1,7 @@ +package com.baeldung.relationships.association; + +public class Child { + + private Mother mother; + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Mother.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Mother.java new file mode 100644 index 0000000000..0e8edef125 --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/association/Mother.java @@ -0,0 +1,9 @@ +package com.baeldung.relationships.association; + +import java.util.List; + +public class Mother { + + private List children; + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/Building.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/Building.java new file mode 100644 index 0000000000..1ab44f73fa --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/Building.java @@ -0,0 +1,18 @@ +package com.baeldung.relationships.composition; + +import java.util.List; + +public class Building { + + private String address; + private List rooms; + + public class Room { + + public String getBuildingAddress() { + return Building.this.address; + } + + } + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/BuildingWithDefinitionRoomInMethod.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/BuildingWithDefinitionRoomInMethod.java new file mode 100644 index 0000000000..4e3411cf30 --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/composition/BuildingWithDefinitionRoomInMethod.java @@ -0,0 +1,28 @@ +package com.baeldung.relationships.composition; + +public class BuildingWithDefinitionRoomInMethod { + + public Room createAnonymousRoom() { + return new Room() { + @Override + public void doInRoom() {} + }; + } + + public Room createInlineRoom() { + class InlineRoom implements Room { + @Override + public void doInRoom() {} + } + return new InlineRoom(); + } + + public Room createLambdaRoom() { + return () -> {}; + } + + public interface Room { + void doInRoom(); + } + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Department.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Department.java new file mode 100644 index 0000000000..63cfd1b89e --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Department.java @@ -0,0 +1,9 @@ +package com.baeldung.relationships.university; + +import java.util.List; + +public class Department { + + private List professors; + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Professor.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Professor.java new file mode 100644 index 0000000000..8e1258c3e6 --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/Professor.java @@ -0,0 +1,10 @@ +package com.baeldung.relationships.university; + +import java.util.List; + +public class Professor { + + private List department; + private List friends; + +} diff --git a/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/University.java b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/University.java new file mode 100644 index 0000000000..e5e518e0f1 --- /dev/null +++ b/core-java-modules/core-java-lang-oop-2/src/main/java/com/baeldung/relationships/university/University.java @@ -0,0 +1,9 @@ +package com.baeldung.relationships.university; + +import java.util.List; + +public class University { + + private List department; + +} From 5aecdeb0211c9dc44e3e5138d4a30bf837d19204 Mon Sep 17 00:00:00 2001 From: Ger Roza Date: Mon, 29 Jul 2019 02:56:21 -0300 Subject: [PATCH 096/107] [BAEL-3066] Spring Security: Exploring JDBC Authentication (#7441) * created multi-module project from spring-security-mvc-boot * Added JDBC Authentication application to spring-security-mvc-boot-default * Added JDBC Authentication application to spring-security-mvc-boot-mysql * Added JDBC Authentication application to spring-security-mvc-boot-postgre * adding new modules to parent spring-security-mvc-boot module, reformatting sql scripts, and added form fields to H2 LiveTest --- spring-security-mvc-boot/pom.xml | 32 ++++------- .../spring-security-mvc-boot-default/pom.xml | 42 +++++++++++++++ .../src/main/java/com/baeldung/AppConfig.java | 0 .../com/baeldung/SpringSecurityConfig.java | 0 .../data/repositories/TweetRepository.java | 0 .../data/repositories/UserRepository.java | 0 .../java/com/baeldung/models/AppUser.java | 0 .../main/java/com/baeldung/models/Tweet.java | 0 .../baeldung/security/AppUserPrincipal.java | 0 .../AuthenticationSuccessHandlerImpl.java | 0 .../security/CustomUserDetailsService.java | 0 .../com/baeldung/util/DummyContentUtil.java | 0 .../java/org/baeldung/custom/Application.java | 4 -- .../custom/config/MethodSecurityConfig.java | 0 .../org/baeldung/custom/config/MvcConfig.java | 0 .../custom/config/SecurityConfig.java | 0 .../custom/persistence/SetupData.java | 0 .../dao/OrganizationRepository.java | 0 .../persistence/dao/PrivilegeRepository.java | 0 .../persistence/dao/UserRepository.java | 0 .../custom/persistence/model/Foo.java | 0 .../persistence/model/Organization.java | 0 .../custom/persistence/model/Privilege.java | 0 .../custom/persistence/model/User.java | 0 ...CustomMethodSecurityExpressionHandler.java | 0 .../CustomMethodSecurityExpressionRoot.java | 0 .../security/CustomPermissionEvaluator.java | 0 .../security/MySecurityExpressionRoot.java | 0 .../custom/security/MyUserDetailsService.java | 0 .../custom/security/MyUserPrincipal.java | 0 .../baeldung/custom/web/MainController.java | 0 .../java/org/baeldung/ip/IpApplication.java | 0 .../CustomIpAuthenticationProvider.java | 0 .../baeldung/ip/config/SecurityConfig.java | 0 .../baeldung/ip/config/SecurityXmlConfig.java | 0 .../org/baeldung/ip/web/MainController.java | 0 .../h2/H2JdbcAuthenticationApplication.java | 15 ++++++ .../h2/config/SecurityConfiguration.java | 51 ++++++++++++++++++ .../h2/web/UserController.java | 17 ++++++ .../CustomAuthenticationProvider.java | 0 .../MultipleAuthController.java | 0 .../MultipleAuthProvidersApplication.java | 0 .../MultipleAuthProvidersSecurityConfig.java | 0 .../MultipleEntryPointsApplication.java | 0 .../MultipleEntryPointsSecurityConfig.java | 0 .../multipleentrypoints/PagesController.java | 0 .../MultipleLoginApplication.java | 5 +- .../multiplelogin/MultipleLoginMvcConfig.java | 0 .../MultipleLoginSecurityConfig.java | 0 .../multiplelogin/UsersController.java | 0 .../CustomAuthenticationProvider.java | 0 .../MyLogoutSuccessHandler.java | 0 .../MyUserDetailsService.java | 0 .../RolesAuthoritiesApplication.java | 0 .../rolesauthorities/config/MvcConfig.java | 0 .../config/SecurityConfig.java | 0 .../rolesauthorities/model/Privilege.java | 0 .../baeldung/rolesauthorities/model/Role.java | 0 .../baeldung/rolesauthorities/model/User.java | 0 .../persistence/IUserService.java | 0 .../persistence/PrivilegeRepository.java | 0 .../persistence/RoleRepository.java | 0 .../persistence/SetupDataLoader.java | 0 .../persistence/UserRepository.java | 0 .../persistence/UserService.java | 0 .../baeldung/ssl/HttpsEnabledApplication.java | 0 .../java/org/baeldung/ssl/SecurityConfig.java | 0 .../org/baeldung/ssl/WelcomeController.java | 0 .../org/baeldung/voter/MinuteBasedVoter.java | 0 .../org/baeldung/voter/VoterApplication.java | 0 .../org/baeldung/voter/VoterMvcConfig.java | 0 .../org/baeldung/voter/WebSecurityConfig.java | 0 .../org/baeldung/voter/XmlSecurityConfig.java | 0 .../main/resources/application-ssl.properties | 0 .../src/main/resources/application.properties | 4 +- .../src/main/resources/keystore/baeldung.p12 | Bin .../src/main/resources/logback.xml | 0 .../main/resources/persistence-h2.properties | 0 .../spring-security-custom-voter.xml | 0 .../src/main/resources/spring-security-ip.xml | 0 ...pring-security-multiple-auth-providers.xml | 0 .../spring-security-multiple-entry.xml | 0 .../src/main/resources/templates/403.html | 0 .../main/resources/templates/adminPage.html | 0 .../src/main/resources/templates/index.html | 0 .../src/main/resources/templates/login.html | 0 .../main/resources/templates/loginAdmin.html | 0 .../main/resources/templates/loginUser.html | 0 .../templates/multipleHttpElems/login.html | 0 .../multipleHttpElems/loginWithWarning.html | 0 .../multipleHttpElems/multipleHttpLinks.html | 0 .../multipleHttpElems/myAdminPage.html | 0 .../multipleHttpElems/myGuestPage.html | 0 .../multipleHttpElems/myPrivateUserPage.html | 0 .../multipleHttpElems/myUserPage.html | 0 .../src/main/resources/templates/private.html | 0 .../resources/templates/protectedLinks.html | 0 .../templates/rolesauthorities/home.html | 0 .../templates/rolesauthorities/login.html | 0 .../protectedbyauthority.html | 0 .../rolesauthorities/protectedbynothing.html | 0 .../rolesauthorities/protectedbyrole.html | 0 .../main/resources/templates/ssl/welcome.html | 0 .../main/resources/templates/userPage.html | 0 ...SpringDataWithSecurityIntegrationTest.java | 0 .../SpringContextIntegrationTest.java | 0 .../h2/web/UserControllerLiveTest.java | 35 ++++++++++++ .../org/baeldung/web/ApplicationLiveTest.java | 0 ...stomUserDetailsServiceIntegrationTest.java | 0 .../web/HttpsApplicationIntegrationTest.java | 0 .../java/org/baeldung/web/IpLiveTest.java | 0 ...thProvidersApplicationIntegrationTest.java | 0 .../MultipleEntryPointsIntegrationTest.java | 0 .../spring-security-mvc-boot-mysql/pom.xml | 28 ++++++++++ .../MySqlJdbcAuthenticationApplication.java | 13 +++++ .../mysql/config/SecurityConfiguration.java | 35 ++++++++++++ .../mysql/web/UserController.java | 17 ++++++ .../src/main/resources/application.properties | 8 +++ .../src/main/resources/data.sql | 4 ++ .../src/main/resources/schema.sql | 18 +++++++ .../mysql/SpringContextIntegrationTest.java | 15 ++++++ .../mysql/web/UserControllerLiveTest.java | 35 ++++++++++++ .../spring-security-mvc-boot-postgre/pom.xml | 28 ++++++++++ .../PostgreJdbcAuthenticationApplication.java | 13 +++++ .../postgre/config/SecurityConfiguration.java | 29 ++++++++++ .../postgre/web/UserController.java | 17 ++++++ .../src/main/resources/application.properties | 8 +++ .../src/main/resources/data.sql | 4 ++ .../src/main/resources/schema.sql | 16 ++++++ .../postgre/SpringContextIntegrationTest.java | 17 ++++++ .../postgre/web/UserControllerLiveTest.java | 35 ++++++++++++ 131 files changed, 514 insertions(+), 31 deletions(-) create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-default/pom.xml rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/AppConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/SpringSecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/data/repositories/TweetRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/data/repositories/UserRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/models/AppUser.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/models/Tweet.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/security/AppUserPrincipal.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/security/AuthenticationSuccessHandlerImpl.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/security/CustomUserDetailsService.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/com/baeldung/util/DummyContentUtil.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/Application.java (61%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/config/MethodSecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/config/MvcConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/config/SecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/SetupData.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/dao/OrganizationRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/dao/PrivilegeRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/dao/UserRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/model/Foo.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/model/Organization.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/model/Privilege.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/persistence/model/User.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionHandler.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionRoot.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/security/CustomPermissionEvaluator.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/security/MySecurityExpressionRoot.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/security/MyUserDetailsService.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/security/MyUserPrincipal.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/custom/web/MainController.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ip/IpApplication.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ip/config/CustomIpAuthenticationProvider.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ip/config/SecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ip/config/SecurityXmlConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ip/web/MainController.java (100%) create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/H2JdbcAuthenticationApplication.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/config/SecurityConfiguration.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/web/UserController.java rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multipleauthproviders/CustomAuthenticationProvider.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthController.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersApplication.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersSecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsApplication.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsSecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multipleentrypoints/PagesController.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multiplelogin/MultipleLoginApplication.java (69%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multiplelogin/MultipleLoginMvcConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multiplelogin/MultipleLoginSecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/multiplelogin/UsersController.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/CustomAuthenticationProvider.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/MyLogoutSuccessHandler.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/MyUserDetailsService.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/RolesAuthoritiesApplication.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/config/MvcConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/config/SecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/model/Privilege.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/model/Role.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/model/User.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/persistence/IUserService.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/persistence/PrivilegeRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/persistence/RoleRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/persistence/SetupDataLoader.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/persistence/UserRepository.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/rolesauthorities/persistence/UserService.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ssl/HttpsEnabledApplication.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ssl/SecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/ssl/WelcomeController.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/voter/MinuteBasedVoter.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/voter/VoterApplication.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/voter/VoterMvcConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/voter/WebSecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/java/org/baeldung/voter/XmlSecurityConfig.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/application-ssl.properties (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/application.properties (74%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/keystore/baeldung.p12 (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/logback.xml (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/persistence-h2.properties (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/spring-security-custom-voter.xml (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/spring-security-ip.xml (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/spring-security-multiple-auth-providers.xml (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/spring-security-multiple-entry.xml (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/403.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/adminPage.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/index.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/login.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/loginAdmin.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/loginUser.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/multipleHttpElems/login.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/multipleHttpElems/loginWithWarning.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/multipleHttpElems/multipleHttpLinks.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/multipleHttpElems/myAdminPage.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/multipleHttpElems/myGuestPage.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/multipleHttpElems/myPrivateUserPage.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/multipleHttpElems/myUserPage.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/private.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/protectedLinks.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/rolesauthorities/home.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/rolesauthorities/login.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/rolesauthorities/protectedbyauthority.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/rolesauthorities/protectedbynothing.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/rolesauthorities/protectedbyrole.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/ssl/welcome.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/main/resources/templates/userPage.html (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/com/baeldung/relationships/SpringDataWithSecurityIntegrationTest.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/org/baeldung/SpringContextIntegrationTest.java (100%) create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/jdbcauthentication/h2/web/UserControllerLiveTest.java rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/org/baeldung/web/ApplicationLiveTest.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/org/baeldung/web/CustomUserDetailsServiceIntegrationTest.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/org/baeldung/web/HttpsApplicationIntegrationTest.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/org/baeldung/web/IpLiveTest.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/org/baeldung/web/MultipleAuthProvidersApplicationIntegrationTest.java (100%) rename spring-security-mvc-boot/{ => spring-security-mvc-boot-default}/src/test/java/org/baeldung/web/MultipleEntryPointsIntegrationTest.java (100%) create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/pom.xml create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/MySqlJdbcAuthenticationApplication.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/config/SecurityConfiguration.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/web/UserController.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/application.properties create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/data.sql create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/schema.sql create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/SpringContextIntegrationTest.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/web/UserControllerLiveTest.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/pom.xml create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/PostgreJdbcAuthenticationApplication.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/config/SecurityConfiguration.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/web/UserController.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/application.properties create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/data.sql create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/schema.sql create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/SpringContextIntegrationTest.java create mode 100644 spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/web/UserControllerLiveTest.java diff --git a/spring-security-mvc-boot/pom.xml b/spring-security-mvc-boot/pom.xml index 4c25dc01e8..906bebf442 100644 --- a/spring-security-mvc-boot/pom.xml +++ b/spring-security-mvc-boot/pom.xml @@ -1,12 +1,13 @@ - + 4.0.0 com.baeldung spring-security-mvc-boot 0.0.1-SNAPSHOT spring-security-mvc-boot - war + pom Spring Security MVC Boot @@ -45,10 +46,6 @@ org.springframework.security spring-security-data
    - - com.h2database - h2 - org.hamcrest hamcrest-core @@ -198,7 +195,7 @@ **/*LiveTest.java **/*IntegrationTest.java - **/*IntTest.java + **/*IntTest.java **/*EntryPointsTest.java @@ -217,22 +214,13 @@ + + spring-security-mvc-boot-default + spring-security-mvc-boot-mysql + spring-security-mvc-boot-postgre + - org.baeldung.custom.Application - - - - - - - - - 1.1.2 1.6.1 2.6.11 diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-default/pom.xml b/spring-security-mvc-boot/spring-security-mvc-boot-default/pom.xml new file mode 100644 index 0000000000..8f7f18f093 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/pom.xml @@ -0,0 +1,42 @@ + + + 4.0.0 + com.baeldung + spring-security-mvc-boot-default + 0.0.1-SNAPSHOT + spring-security-mvc-boot-default + jar + Spring Security MVC Boot + + + spring-security-mvc-boot + com.baeldung + 0.0.1-SNAPSHOT + ../ + + + + + com.h2database + h2 + + + + + org.baeldung.custom.Application + + + + + + + + + + + diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/AppConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/AppConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/AppConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/AppConfig.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/SpringSecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/SpringSecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/SpringSecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/SpringSecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/data/repositories/TweetRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/data/repositories/TweetRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/data/repositories/TweetRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/data/repositories/TweetRepository.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/data/repositories/UserRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/data/repositories/UserRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/data/repositories/UserRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/data/repositories/UserRepository.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/models/AppUser.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/models/AppUser.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/models/AppUser.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/models/AppUser.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/models/Tweet.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/models/Tweet.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/models/Tweet.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/models/Tweet.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/security/AppUserPrincipal.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/security/AppUserPrincipal.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/security/AppUserPrincipal.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/security/AppUserPrincipal.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/security/AuthenticationSuccessHandlerImpl.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/security/AuthenticationSuccessHandlerImpl.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/security/AuthenticationSuccessHandlerImpl.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/security/AuthenticationSuccessHandlerImpl.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/security/CustomUserDetailsService.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/security/CustomUserDetailsService.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/security/CustomUserDetailsService.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/security/CustomUserDetailsService.java diff --git a/spring-security-mvc-boot/src/main/java/com/baeldung/util/DummyContentUtil.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/util/DummyContentUtil.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/com/baeldung/util/DummyContentUtil.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/com/baeldung/util/DummyContentUtil.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/Application.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/Application.java similarity index 61% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/Application.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/Application.java index f932ac3066..682d429963 100644 --- a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/Application.java +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/Application.java @@ -1,12 +1,8 @@ package org.baeldung.custom; import org.springframework.boot.SpringApplication; -import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.web.servlet.support.SpringBootServletInitializer; -import org.springframework.context.annotation.ComponentScan; -import org.springframework.context.annotation.Configuration; -import org.springframework.data.jpa.repository.config.EnableJpaRepositories; @SpringBootApplication public class Application extends SpringBootServletInitializer { diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/config/MethodSecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/config/MethodSecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/config/MethodSecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/config/MethodSecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/config/MvcConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/config/MvcConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/config/MvcConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/config/MvcConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/config/SecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/config/SecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/config/SecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/config/SecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/SetupData.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/SetupData.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/SetupData.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/SetupData.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/dao/OrganizationRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/dao/OrganizationRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/dao/OrganizationRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/dao/OrganizationRepository.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/dao/PrivilegeRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/dao/PrivilegeRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/dao/PrivilegeRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/dao/PrivilegeRepository.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/dao/UserRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/dao/UserRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/dao/UserRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/dao/UserRepository.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/Foo.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/Foo.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/Foo.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/Foo.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/Organization.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/Organization.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/Organization.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/Organization.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/Privilege.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/Privilege.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/Privilege.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/Privilege.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/User.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/User.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/persistence/model/User.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/persistence/model/User.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionHandler.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionHandler.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionHandler.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionHandler.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionRoot.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionRoot.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionRoot.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/CustomMethodSecurityExpressionRoot.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/CustomPermissionEvaluator.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/CustomPermissionEvaluator.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/CustomPermissionEvaluator.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/CustomPermissionEvaluator.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/MySecurityExpressionRoot.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/MySecurityExpressionRoot.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/MySecurityExpressionRoot.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/MySecurityExpressionRoot.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/MyUserDetailsService.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/MyUserDetailsService.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/MyUserDetailsService.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/MyUserDetailsService.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/MyUserPrincipal.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/MyUserPrincipal.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/security/MyUserPrincipal.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/security/MyUserPrincipal.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/custom/web/MainController.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/web/MainController.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/custom/web/MainController.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/custom/web/MainController.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ip/IpApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/IpApplication.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ip/IpApplication.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/IpApplication.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ip/config/CustomIpAuthenticationProvider.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/config/CustomIpAuthenticationProvider.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ip/config/CustomIpAuthenticationProvider.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/config/CustomIpAuthenticationProvider.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ip/config/SecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/config/SecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ip/config/SecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/config/SecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ip/config/SecurityXmlConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/config/SecurityXmlConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ip/config/SecurityXmlConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/config/SecurityXmlConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ip/web/MainController.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/web/MainController.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ip/web/MainController.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ip/web/MainController.java diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/H2JdbcAuthenticationApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/H2JdbcAuthenticationApplication.java new file mode 100644 index 0000000000..6bd30414ef --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/H2JdbcAuthenticationApplication.java @@ -0,0 +1,15 @@ +package org.baeldung.jdbcauthentication.h2; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; + +@SpringBootApplication +@EnableWebSecurity +public class H2JdbcAuthenticationApplication { + + public static void main(String[] args) { + SpringApplication.run(H2JdbcAuthenticationApplication.class, args); + } + +} diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/config/SecurityConfiguration.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/config/SecurityConfiguration.java new file mode 100644 index 0000000000..8b8696f0b2 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/config/SecurityConfiguration.java @@ -0,0 +1,51 @@ +package org.baeldung.jdbcauthentication.h2.config; + +import javax.sql.DataSource; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; +import org.springframework.security.config.annotation.web.builders.HttpSecurity; +import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter; +import org.springframework.security.core.userdetails.User; +import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; +import org.springframework.security.crypto.password.PasswordEncoder; + +@Configuration +public class SecurityConfiguration extends WebSecurityConfigurerAdapter { + @Override + protected void configure(HttpSecurity httpSecurity) throws Exception { + httpSecurity.authorizeRequests() + .antMatchers("/h2-console/**") + .permitAll() + .anyRequest() + .authenticated() + .and() + .formLogin() + .permitAll(); + httpSecurity.csrf() + .ignoringAntMatchers("/h2-console/**"); + httpSecurity.headers() + .frameOptions() + .sameOrigin(); + } + + @Autowired + private DataSource dataSource; + + @Autowired + public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception { + auth.jdbcAuthentication() + .dataSource(dataSource) + .withDefaultSchema() + .withUser(User.withUsername("user") + .password(passwordEncoder().encode("pass")) + .roles("USER")); + } + + @Bean + public PasswordEncoder passwordEncoder() { + return new BCryptPasswordEncoder(); + } +} \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/web/UserController.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/web/UserController.java new file mode 100644 index 0000000000..0955061614 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/jdbcauthentication/h2/web/UserController.java @@ -0,0 +1,17 @@ +package org.baeldung.jdbcauthentication.h2.web; + +import java.security.Principal; + +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +@RestController +@RequestMapping("/principal") +public class UserController { + + @GetMapping + public Principal retrievePrincipal(Principal principal) { + return principal; + } +} diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/CustomAuthenticationProvider.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/CustomAuthenticationProvider.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/CustomAuthenticationProvider.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/CustomAuthenticationProvider.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthController.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthController.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthController.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthController.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersApplication.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersApplication.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersApplication.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersSecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersSecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersSecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleauthproviders/MultipleAuthProvidersSecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsApplication.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsApplication.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsApplication.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsSecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsSecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsSecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleentrypoints/MultipleEntryPointsSecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multipleentrypoints/PagesController.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleentrypoints/PagesController.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multipleentrypoints/PagesController.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multipleentrypoints/PagesController.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/MultipleLoginApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/MultipleLoginApplication.java similarity index 69% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/MultipleLoginApplication.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/MultipleLoginApplication.java index e9dc541ad3..d25324eb54 100644 --- a/spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/MultipleLoginApplication.java +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/MultipleLoginApplication.java @@ -1,11 +1,8 @@ package org.baeldung.multiplelogin; import org.springframework.boot.SpringApplication; -import org.springframework.boot.autoconfigure.EnableAutoConfiguration; -import org.springframework.context.annotation.ComponentScan; -import org.springframework.context.annotation.Configuration; import org.springframework.boot.autoconfigure.SpringBootApplication; -import org.springframework.boot.builder.SpringApplicationBuilder; +import org.springframework.context.annotation.ComponentScan; @SpringBootApplication @ComponentScan("org.baeldung.multiplelogin") diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/MultipleLoginMvcConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/MultipleLoginMvcConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/MultipleLoginMvcConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/MultipleLoginMvcConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/MultipleLoginSecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/MultipleLoginSecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/MultipleLoginSecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/MultipleLoginSecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/UsersController.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/UsersController.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/multiplelogin/UsersController.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/multiplelogin/UsersController.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/CustomAuthenticationProvider.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/CustomAuthenticationProvider.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/CustomAuthenticationProvider.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/CustomAuthenticationProvider.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/MyLogoutSuccessHandler.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/MyLogoutSuccessHandler.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/MyLogoutSuccessHandler.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/MyLogoutSuccessHandler.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/MyUserDetailsService.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/MyUserDetailsService.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/MyUserDetailsService.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/MyUserDetailsService.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/RolesAuthoritiesApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/RolesAuthoritiesApplication.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/RolesAuthoritiesApplication.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/RolesAuthoritiesApplication.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/config/MvcConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/config/MvcConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/config/MvcConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/config/MvcConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/config/SecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/config/SecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/config/SecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/config/SecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/model/Privilege.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/model/Privilege.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/model/Privilege.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/model/Privilege.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/model/Role.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/model/Role.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/model/Role.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/model/Role.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/model/User.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/model/User.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/model/User.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/model/User.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/IUserService.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/IUserService.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/IUserService.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/IUserService.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/PrivilegeRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/PrivilegeRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/PrivilegeRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/PrivilegeRepository.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/RoleRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/RoleRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/RoleRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/RoleRepository.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/SetupDataLoader.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/SetupDataLoader.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/SetupDataLoader.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/SetupDataLoader.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/UserRepository.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/UserRepository.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/UserRepository.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/UserRepository.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/UserService.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/UserService.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/rolesauthorities/persistence/UserService.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/rolesauthorities/persistence/UserService.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ssl/HttpsEnabledApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ssl/HttpsEnabledApplication.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ssl/HttpsEnabledApplication.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ssl/HttpsEnabledApplication.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ssl/SecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ssl/SecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ssl/SecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ssl/SecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/ssl/WelcomeController.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ssl/WelcomeController.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/ssl/WelcomeController.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/ssl/WelcomeController.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/voter/MinuteBasedVoter.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/MinuteBasedVoter.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/voter/MinuteBasedVoter.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/MinuteBasedVoter.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/voter/VoterApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/VoterApplication.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/voter/VoterApplication.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/VoterApplication.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/voter/VoterMvcConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/VoterMvcConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/voter/VoterMvcConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/VoterMvcConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/voter/WebSecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/WebSecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/voter/WebSecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/WebSecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/java/org/baeldung/voter/XmlSecurityConfig.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/XmlSecurityConfig.java similarity index 100% rename from spring-security-mvc-boot/src/main/java/org/baeldung/voter/XmlSecurityConfig.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/java/org/baeldung/voter/XmlSecurityConfig.java diff --git a/spring-security-mvc-boot/src/main/resources/application-ssl.properties b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/application-ssl.properties similarity index 100% rename from spring-security-mvc-boot/src/main/resources/application-ssl.properties rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/application-ssl.properties diff --git a/spring-security-mvc-boot/src/main/resources/application.properties b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/application.properties similarity index 74% rename from spring-security-mvc-boot/src/main/resources/application.properties rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/application.properties index 25eac743d1..365dedab9e 100644 --- a/spring-security-mvc-boot/src/main/resources/application.properties +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/application.properties @@ -8,5 +8,7 @@ spring.jpa.database=H2 spring.jpa.show-sql=false spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.H2Dialect +logging.level.org.springframework.security.web.FilterChainProxy=DEBUG -#logging.level.org.springframework.security.web.FilterChainProxy=DEBUG \ No newline at end of file +spring.h2.console.enabled=true +spring.h2.console.path=/h2-console \ No newline at end of file diff --git a/spring-security-mvc-boot/src/main/resources/keystore/baeldung.p12 b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/keystore/baeldung.p12 similarity index 100% rename from spring-security-mvc-boot/src/main/resources/keystore/baeldung.p12 rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/keystore/baeldung.p12 diff --git a/spring-security-mvc-boot/src/main/resources/logback.xml b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/logback.xml similarity index 100% rename from spring-security-mvc-boot/src/main/resources/logback.xml rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/logback.xml diff --git a/spring-security-mvc-boot/src/main/resources/persistence-h2.properties b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/persistence-h2.properties similarity index 100% rename from spring-security-mvc-boot/src/main/resources/persistence-h2.properties rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/persistence-h2.properties diff --git a/spring-security-mvc-boot/src/main/resources/spring-security-custom-voter.xml b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-custom-voter.xml similarity index 100% rename from spring-security-mvc-boot/src/main/resources/spring-security-custom-voter.xml rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-custom-voter.xml diff --git a/spring-security-mvc-boot/src/main/resources/spring-security-ip.xml b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-ip.xml similarity index 100% rename from spring-security-mvc-boot/src/main/resources/spring-security-ip.xml rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-ip.xml diff --git a/spring-security-mvc-boot/src/main/resources/spring-security-multiple-auth-providers.xml b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-multiple-auth-providers.xml similarity index 100% rename from spring-security-mvc-boot/src/main/resources/spring-security-multiple-auth-providers.xml rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-multiple-auth-providers.xml diff --git a/spring-security-mvc-boot/src/main/resources/spring-security-multiple-entry.xml b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-multiple-entry.xml similarity index 100% rename from spring-security-mvc-boot/src/main/resources/spring-security-multiple-entry.xml rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/spring-security-multiple-entry.xml diff --git a/spring-security-mvc-boot/src/main/resources/templates/403.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/403.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/403.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/403.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/adminPage.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/adminPage.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/adminPage.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/adminPage.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/index.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/index.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/index.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/index.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/login.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/login.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/login.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/login.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/loginAdmin.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/loginAdmin.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/loginAdmin.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/loginAdmin.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/loginUser.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/loginUser.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/loginUser.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/loginUser.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/login.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/login.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/login.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/login.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/loginWithWarning.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/loginWithWarning.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/loginWithWarning.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/loginWithWarning.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/multipleHttpLinks.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/multipleHttpLinks.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/multipleHttpLinks.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/multipleHttpLinks.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myAdminPage.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myAdminPage.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myAdminPage.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myAdminPage.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myGuestPage.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myGuestPage.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myGuestPage.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myGuestPage.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myPrivateUserPage.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myPrivateUserPage.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myPrivateUserPage.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myPrivateUserPage.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myUserPage.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myUserPage.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/multipleHttpElems/myUserPage.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/multipleHttpElems/myUserPage.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/private.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/private.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/private.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/private.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/protectedLinks.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/protectedLinks.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/protectedLinks.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/protectedLinks.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/home.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/home.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/home.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/home.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/login.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/login.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/login.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/login.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/protectedbyauthority.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/protectedbyauthority.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/protectedbyauthority.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/protectedbyauthority.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/protectedbynothing.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/protectedbynothing.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/protectedbynothing.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/protectedbynothing.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/protectedbyrole.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/protectedbyrole.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/rolesauthorities/protectedbyrole.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/rolesauthorities/protectedbyrole.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/ssl/welcome.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/ssl/welcome.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/ssl/welcome.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/ssl/welcome.html diff --git a/spring-security-mvc-boot/src/main/resources/templates/userPage.html b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/userPage.html similarity index 100% rename from spring-security-mvc-boot/src/main/resources/templates/userPage.html rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/main/resources/templates/userPage.html diff --git a/spring-security-mvc-boot/src/test/java/com/baeldung/relationships/SpringDataWithSecurityIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/com/baeldung/relationships/SpringDataWithSecurityIntegrationTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/com/baeldung/relationships/SpringDataWithSecurityIntegrationTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/com/baeldung/relationships/SpringDataWithSecurityIntegrationTest.java diff --git a/spring-security-mvc-boot/src/test/java/org/baeldung/SpringContextIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/SpringContextIntegrationTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/org/baeldung/SpringContextIntegrationTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/SpringContextIntegrationTest.java diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/jdbcauthentication/h2/web/UserControllerLiveTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/jdbcauthentication/h2/web/UserControllerLiveTest.java new file mode 100644 index 0000000000..638e9d7919 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/jdbcauthentication/h2/web/UserControllerLiveTest.java @@ -0,0 +1,35 @@ +package org.baeldung.jdbcauthentication.h2.web; + +import static io.restassured.RestAssured.given; +import static org.hamcrest.CoreMatchers.is; + +import org.junit.jupiter.api.Test; +import org.springframework.http.HttpStatus; + +import io.restassured.authentication.FormAuthConfig; +import io.restassured.filter.session.SessionFilter; + +/** + * This Live Test requires the H2JdbcAuthenticationApplication application to be up and running + */ +public class UserControllerLiveTest { + + private static final String PRINCIPAL_SVC_URL = "http://localhost:8082/principal"; + + @Test + public void givenExisting_whenRequestPrincipal_thenRetrieveData() throws Exception { + SessionFilter filter = new SessionFilter(); + given().auth() + .form("user", "pass", new FormAuthConfig("/login", "username", "password").withCsrfFieldName("_csrf")) + .and() + .filter(filter) + .when() + .get(PRINCIPAL_SVC_URL) + .then() + .statusCode(HttpStatus.OK.value()) + .and() + .body("authorities[0].authority", is("ROLE_USER")) + .body("principal.username", is("user")) + .body("name", is("user")); + } +} diff --git a/spring-security-mvc-boot/src/test/java/org/baeldung/web/ApplicationLiveTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/ApplicationLiveTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/org/baeldung/web/ApplicationLiveTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/ApplicationLiveTest.java diff --git a/spring-security-mvc-boot/src/test/java/org/baeldung/web/CustomUserDetailsServiceIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/CustomUserDetailsServiceIntegrationTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/org/baeldung/web/CustomUserDetailsServiceIntegrationTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/CustomUserDetailsServiceIntegrationTest.java diff --git a/spring-security-mvc-boot/src/test/java/org/baeldung/web/HttpsApplicationIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/HttpsApplicationIntegrationTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/org/baeldung/web/HttpsApplicationIntegrationTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/HttpsApplicationIntegrationTest.java diff --git a/spring-security-mvc-boot/src/test/java/org/baeldung/web/IpLiveTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/IpLiveTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/org/baeldung/web/IpLiveTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/IpLiveTest.java diff --git a/spring-security-mvc-boot/src/test/java/org/baeldung/web/MultipleAuthProvidersApplicationIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/MultipleAuthProvidersApplicationIntegrationTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/org/baeldung/web/MultipleAuthProvidersApplicationIntegrationTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/MultipleAuthProvidersApplicationIntegrationTest.java diff --git a/spring-security-mvc-boot/src/test/java/org/baeldung/web/MultipleEntryPointsIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/MultipleEntryPointsIntegrationTest.java similarity index 100% rename from spring-security-mvc-boot/src/test/java/org/baeldung/web/MultipleEntryPointsIntegrationTest.java rename to spring-security-mvc-boot/spring-security-mvc-boot-default/src/test/java/org/baeldung/web/MultipleEntryPointsIntegrationTest.java diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/pom.xml b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/pom.xml new file mode 100644 index 0000000000..765953c557 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/pom.xml @@ -0,0 +1,28 @@ + + + 4.0.0 + com.baeldung + spring-security-mvc-boot-mysql + 0.0.1-SNAPSHOT + spring-security-mvc-boot-mysql + jar + Spring Security MVC Boot using MySQL + + + spring-security-mvc-boot + com.baeldung + 0.0.1-SNAPSHOT + .. + + + + + mysql + mysql-connector-java + runtime + + + + diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/MySqlJdbcAuthenticationApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/MySqlJdbcAuthenticationApplication.java new file mode 100644 index 0000000000..238a48730c --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/MySqlJdbcAuthenticationApplication.java @@ -0,0 +1,13 @@ +package com.baeldung.jdbcauthentication.mysql; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +@SpringBootApplication +public class MySqlJdbcAuthenticationApplication { + + public static void main(String[] args) { + SpringApplication.run(MySqlJdbcAuthenticationApplication.class, args); + } + +} diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/config/SecurityConfiguration.java b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/config/SecurityConfiguration.java new file mode 100644 index 0000000000..a0584818cd --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/config/SecurityConfiguration.java @@ -0,0 +1,35 @@ +package com.baeldung.jdbcauthentication.mysql.config; + +import javax.sql.DataSource; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; +import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; +import org.springframework.security.crypto.password.PasswordEncoder; + +@Configuration +public class SecurityConfiguration { + + @Autowired + private DataSource dataSource; + + @Autowired + public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception { + auth.jdbcAuthentication() + .dataSource(dataSource) + .usersByUsernameQuery("select email,password,enabled " + + "from bael_users " + + "where email = ?") + .authoritiesByUsernameQuery("select email,authority " + + "from authorities " + + "where email = ?"); + } + + @Bean + public PasswordEncoder passwordEncoder() { + return new BCryptPasswordEncoder(); + } + +} \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/web/UserController.java b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/web/UserController.java new file mode 100644 index 0000000000..ed15f8bfe6 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/java/com/baeldung/jdbcauthentication/mysql/web/UserController.java @@ -0,0 +1,17 @@ +package com.baeldung.jdbcauthentication.mysql.web; + +import java.security.Principal; + +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +@RestController +@RequestMapping("/principal") +public class UserController { + + @GetMapping + public Principal retrievePrincipal(Principal principal) { + return principal; + } +} \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/application.properties b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/application.properties new file mode 100644 index 0000000000..2962475108 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/application.properties @@ -0,0 +1,8 @@ +server.port=8082 + +spring.datasource.url=jdbc:mysql://localhost:3306/jdbc_authentication +spring.datasource.username=root +spring.datasource.password=pass + +spring.datasource.initialization-mode=always +spring.jpa.hibernate.ddl-auto=none diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/data.sql b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/data.sql new file mode 100644 index 0000000000..8214fd8204 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/data.sql @@ -0,0 +1,4 @@ +-- User user@email.com/pass +INSERT INTO bael_users (name, email, password, enabled) values ('user', 'user@email.com', '$2a$10$8.UnVuG9HHgffUDAlk8qfOuVGkqRzgVymGe07xd00DMxs.AQubh4a', 1); + +INSERT INTO authorities (email, authority) values ('user@email.com', 'ROLE_USER'); \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/schema.sql b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/schema.sql new file mode 100644 index 0000000000..bb38c74366 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/main/resources/schema.sql @@ -0,0 +1,18 @@ +DROP TABLE IF EXISTS authorities; +DROP TABLE IF EXISTS bael_users; + +CREATE TABLE bael_users ( + name VARCHAR(50) NOT NULL, + email VARCHAR(50) NOT NULL, + password VARCHAR(100) NOT NULL, + enabled TINYINT NOT NULL DEFAULT 1, + PRIMARY KEY (email) +); + +CREATE TABLE authorities ( + email VARCHAR(50) NOT NULL, + authority VARCHAR(50) NOT NULL, + FOREIGN KEY (email) REFERENCES bael_users(email) +); + +CREATE UNIQUE INDEX ix_auth_email on authorities (email,authority); \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/SpringContextIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/SpringContextIntegrationTest.java new file mode 100644 index 0000000000..2c19e2c0ca --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/SpringContextIntegrationTest.java @@ -0,0 +1,15 @@ +package com.baeldung.jdbcauthentication.mysql; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.test.context.junit4.SpringRunner; + +@RunWith(SpringRunner.class) +@SpringBootTest(classes = MySqlJdbcAuthenticationApplication.class) +public class SpringContextIntegrationTest { + + @Test + public void whenSpringContextIsBootstrapped_thenNoExceptions() { + } +} diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/web/UserControllerLiveTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/web/UserControllerLiveTest.java new file mode 100644 index 0000000000..79bc84ea69 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-mysql/src/test/java/com/baeldung/jdbcauthentication/mysql/web/UserControllerLiveTest.java @@ -0,0 +1,35 @@ +package com.baeldung.jdbcauthentication.mysql.web; + +import static io.restassured.RestAssured.given; +import static org.hamcrest.CoreMatchers.is; + +import org.junit.jupiter.api.Test; +import org.springframework.http.HttpStatus; + +/** + * This Live Test requires: + * * a MySql instance running, that allows a 'root' user with password 'pass', and with a database named jdbc_authentication + * (e.g. with the following command `docker run -p 3306:3306 --name bael-mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=jdbc_authentication mysql:latest`) + * * the service up and running + * + */ +public class UserControllerLiveTest { + + private static final String PRINCIPAL_SVC_URL = "http://localhost:8082/principal"; + + @Test + public void givenExisting_whenRequestPrincipal_thenRetrieveData() throws Exception { + given().auth() + .preemptive() + .basic("user@email.com", "pass") + .when() + .get(PRINCIPAL_SVC_URL) + .then() + .statusCode(HttpStatus.OK.value()) + .and() + .body("authorities[0].authority", is("ROLE_USER")) + .body("principal.username", is("user@email.com")) + .body("name", is("user@email.com")); + } + +} diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/pom.xml b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/pom.xml new file mode 100644 index 0000000000..e68e47b596 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/pom.xml @@ -0,0 +1,28 @@ + + + 4.0.0 + com.baeldung + spring-security-mvc-boot-postgre + 0.0.1-SNAPSHOT + spring-security-mvc-boot-postgre + jar + Spring Security MVC Boot using PostgreSQL + + + spring-security-mvc-boot + com.baeldung + 0.0.1-SNAPSHOT + .. + + + + + org.postgresql + postgresql + runtime + + + + diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/PostgreJdbcAuthenticationApplication.java b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/PostgreJdbcAuthenticationApplication.java new file mode 100644 index 0000000000..d4b555e8c6 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/PostgreJdbcAuthenticationApplication.java @@ -0,0 +1,13 @@ +package com.baeldung.jdbcauthentication.postgre; + +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +@SpringBootApplication +public class PostgreJdbcAuthenticationApplication { + + public static void main(String[] args) { + SpringApplication.run(PostgreJdbcAuthenticationApplication.class, args); + } + +} diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/config/SecurityConfiguration.java b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/config/SecurityConfiguration.java new file mode 100644 index 0000000000..85dc9d364c --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/config/SecurityConfiguration.java @@ -0,0 +1,29 @@ +package com.baeldung.jdbcauthentication.postgre.config; + +import javax.sql.DataSource; + +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; +import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; +import org.springframework.security.crypto.password.PasswordEncoder; + +@Configuration +public class SecurityConfiguration { + + @Autowired + private DataSource dataSource; + + @Autowired + public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception { + auth.jdbcAuthentication() + .dataSource(dataSource); + } + + @Bean + public PasswordEncoder passwordEncoder() { + return new BCryptPasswordEncoder(); + } + +} \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/web/UserController.java b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/web/UserController.java new file mode 100644 index 0000000000..da85a46562 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/java/com/baeldung/jdbcauthentication/postgre/web/UserController.java @@ -0,0 +1,17 @@ +package com.baeldung.jdbcauthentication.postgre.web; + +import java.security.Principal; + +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +@RestController +@RequestMapping("/principal") +public class UserController { + + @GetMapping + public Principal retrievePrincipal(Principal principal) { + return principal; + } +} \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/application.properties b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/application.properties new file mode 100644 index 0000000000..2940c5121e --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/application.properties @@ -0,0 +1,8 @@ +server.port=8082 + +spring.datasource.url=jdbc:postgresql://localhost:5432/jdbc_authentication +spring.datasource.username=postgres +spring.datasource.password=pass + +spring.datasource.initialization-mode=always +spring.jpa.hibernate.ddl-auto=none diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/data.sql b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/data.sql new file mode 100644 index 0000000000..fcc6b54949 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/data.sql @@ -0,0 +1,4 @@ +-- User user/pass +INSERT INTO users (username, password, enabled) values ('user', '$2a$10$8.UnVuG9HHgffUDAlk8qfOuVGkqRzgVymGe07xd00DMxs.AQubh4a', true); + +INSERT INTO authorities (username, authority) values ('user', 'ROLE_USER'); \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/schema.sql b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/schema.sql new file mode 100644 index 0000000000..d78edfb528 --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/main/resources/schema.sql @@ -0,0 +1,16 @@ +DROP TABLE IF EXISTS authorities; +DROP TABLE IF EXISTS users; + +CREATE TABLE users ( + username varchar(50) NOT NULL PRIMARY KEY, + password varchar(100) NOT NULL, + enabled boolean not null DEFAULT true +); + +CREATE TABLE authorities ( + username varchar(50) NOT NULL, + authority varchar(50) NOT NULL, + CONSTRAINT foreign_authorities_users_1 foreign key(username) references users(username) +); + +CREATE UNIQUE INDEX ix_auth_username on authorities (username,authority); \ No newline at end of file diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/SpringContextIntegrationTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/SpringContextIntegrationTest.java new file mode 100644 index 0000000000..f133ef73be --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/SpringContextIntegrationTest.java @@ -0,0 +1,17 @@ +package com.baeldung.jdbcauthentication.postgre; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.test.context.junit4.SpringRunner; + +import com.baeldung.jdbcauthentication.postgre.PostgreJdbcAuthenticationApplication; + +@RunWith(SpringRunner.class) +@SpringBootTest(classes = PostgreJdbcAuthenticationApplication.class) +public class SpringContextIntegrationTest { + + @Test + public void whenSpringContextIsBootstrapped_thenNoExceptions() { + } +} diff --git a/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/web/UserControllerLiveTest.java b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/web/UserControllerLiveTest.java new file mode 100644 index 0000000000..b5f4379c0a --- /dev/null +++ b/spring-security-mvc-boot/spring-security-mvc-boot-postgre/src/test/java/com/baeldung/jdbcauthentication/postgre/web/UserControllerLiveTest.java @@ -0,0 +1,35 @@ +package com.baeldung.jdbcauthentication.postgre.web; + +import static io.restassured.RestAssured.given; +import static org.hamcrest.CoreMatchers.is; + +import org.junit.jupiter.api.Test; +import org.springframework.http.HttpStatus; + +/** + * This Live Test requires: + * * a PostgreSQL instance running, that allows a 'root' user with password 'pass', and with a database named jdbc_authentication + * (e.g. with the following command `docker run -p 5432:5432 --name bael-postgre -e POSTGRES_PASSWORD=pass -e POSTGRES_DB=jdbc_authentication postgres:latest`) + * * the service up and running + * + */ +public class UserControllerLiveTest { + + private static final String PRINCIPAL_SVC_URL = "http://localhost:8082/principal"; + + @Test + public void givenExisting_whenRequestPrincipal_thenRetrieveData() throws Exception { + given().auth() + .preemptive() + .basic("user", "pass") + .when() + .get(PRINCIPAL_SVC_URL) + .then() + .statusCode(HttpStatus.OK.value()) + .and() + .body("authorities[0].authority", is("ROLE_USER")) + .body("principal.username", is("user")) + .body("name", is("user")); + } + +} From f174fa0ae93e46820456607a141fa3fcfb52e53e Mon Sep 17 00:00:00 2001 From: Gerardo Roza Date: Mon, 29 Jul 2019 09:55:54 -0300 Subject: [PATCH 097/107] Fix test naming, now renamed as LiveTest --- ...onIntegrationTest.java => SessionConfigurationLiveTest.java} | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) rename spring-security-mvc/src/test/java/com/baeldung/session/{SessionConfigurationIntegrationTest.java => SessionConfigurationLiveTest.java} (98%) diff --git a/spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java b/spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationLiveTest.java similarity index 98% rename from spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java rename to spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationLiveTest.java index 5a9bf72077..7d9a03d5f6 100644 --- a/spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationIntegrationTest.java +++ b/spring-security-mvc/src/test/java/com/baeldung/session/SessionConfigurationLiveTest.java @@ -15,7 +15,7 @@ import io.restassured.specification.RequestSpecification; /** * This Live Test requires the service to be up and running. */ -public class SessionConfigurationIntegrationTest { +public class SessionConfigurationLiveTest { private static final String USER = "user1"; private static final String PASSWORD = "user1Pass"; From 8f5bb3c6a94e64660abac317e0a52bd54908996a Mon Sep 17 00:00:00 2001 From: Paul Latzelsperger <43503240+beardyinc@users.noreply.github.com> Date: Mon, 29 Jul 2019 22:38:42 +0200 Subject: [PATCH 098/107] Bael 3082 (#7446) * added example code for BAEL-3082 * added another test case, refactored method names * moved to basics module --- .../failure_vs_error/SimpleCalculator.java | 15 +++++++ .../SimpleCalculatorUnitTest.java | 39 +++++++++++++++++++ 2 files changed, 54 insertions(+) create mode 100644 testing-modules/junit-5-basics/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java create mode 100644 testing-modules/junit-5-basics/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java diff --git a/testing-modules/junit-5-basics/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java b/testing-modules/junit-5-basics/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java new file mode 100644 index 0000000000..d018aa939f --- /dev/null +++ b/testing-modules/junit-5-basics/src/main/java/com/baeldung/failure_vs_error/SimpleCalculator.java @@ -0,0 +1,15 @@ +package com.baeldung.failure_vs_error; + +/** + * @author paullatzelsperger + * @since 2019-07-17 + */ +public class SimpleCalculator { + + public static double divideNumbers(double dividend, double divisor) { + if (divisor == 0) { + throw new ArithmeticException("Division by zero!"); + } + return dividend / divisor; + } +} diff --git a/testing-modules/junit-5-basics/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java b/testing-modules/junit-5-basics/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java new file mode 100644 index 0000000000..6833834959 --- /dev/null +++ b/testing-modules/junit-5-basics/src/test/java/com/baeldung/failure_vs_error/SimpleCalculatorUnitTest.java @@ -0,0 +1,39 @@ +package com.baeldung.failure_vs_error; + +import org.junit.jupiter.api.Disabled; +import org.junit.jupiter.api.Test; + +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertThrows; + +/** + * @author paullatzelsperger + * @since 2019-07-17 + */ +class SimpleCalculatorUnitTest { + + @Test + void whenDivideByValidNumber_thenAssertCorrectResult() { + double result = SimpleCalculator.divideNumbers(6, 3); + assertEquals(2, result); + } + + @Test + @Disabled("test is expected to fail, disabled so that CI build still goes through") + void whenDivideNumbers_thenExpectWrongResult() { + double result = SimpleCalculator.divideNumbers(6, 3); + assertEquals(15, result); + } + + @Test + @Disabled("test is expected to raise an error, disabled so that CI build still goes through") + void whenDivideByZero_thenThrowsException() { + SimpleCalculator.divideNumbers(10, 0); + } + + @Test + void whenDivideByZero_thenAssertException(){ + assertThrows(ArithmeticException.class, () -> SimpleCalculator.divideNumbers(10, 0)); + } + +} From d9a20d17641f8a769cefe474684b955187de2b51 Mon Sep 17 00:00:00 2001 From: josephine-barboza Date: Tue, 30 Jul 2019 03:14:52 +0530 Subject: [PATCH 099/107] BAEL-2906 Functional Controllers in Spring MVC (#6972) * BAEL-2906 Functional Controllers in Spring MVC * BAEL-2906 Functional Controllers in Spring MVC * BAEL-2906 Functional Controllers in Spring MVC * BAEL-2906 Removed unnecessary files * BAEL-2906 Removed project * BAEL-2906 Removed comments --- spring-boot-mvc-2/.gitignore | 25 +++++++ spring-boot-mvc-2/README.md | 3 + spring-boot-mvc-2/pom.xml | 68 +++++++++++++++++ .../SpringBootMvcFnApplication.java | 74 +++++++++++++++++++ .../springbootmvc/ctrl/ProductController.java | 59 +++++++++++++++ .../baeldung/springbootmvc/model/Product.java | 72 ++++++++++++++++++ .../springbootmvc/svc/ProductService.java | 63 ++++++++++++++++ .../src/main/resources/application.properties | 1 + .../src/main/resources/logback.xml | 13 ++++ 9 files changed, 378 insertions(+) create mode 100644 spring-boot-mvc-2/.gitignore create mode 100644 spring-boot-mvc-2/README.md create mode 100644 spring-boot-mvc-2/pom.xml create mode 100644 spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/SpringBootMvcFnApplication.java create mode 100644 spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/ctrl/ProductController.java create mode 100644 spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/model/Product.java create mode 100644 spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/svc/ProductService.java create mode 100644 spring-boot-mvc-2/src/main/resources/application.properties create mode 100644 spring-boot-mvc-2/src/main/resources/logback.xml diff --git a/spring-boot-mvc-2/.gitignore b/spring-boot-mvc-2/.gitignore new file mode 100644 index 0000000000..82eca336e3 --- /dev/null +++ b/spring-boot-mvc-2/.gitignore @@ -0,0 +1,25 @@ +/target/ +!.mvn/wrapper/maven-wrapper.jar + +### STS ### +.apt_generated +.classpath +.factorypath +.project +.settings +.springBeans +.sts4-cache + +### IntelliJ IDEA ### +.idea +*.iws +*.iml +*.ipr + +### NetBeans ### +/nbproject/private/ +/build/ +/nbbuild/ +/dist/ +/nbdist/ +/.nb-gradle/ \ No newline at end of file diff --git a/spring-boot-mvc-2/README.md b/spring-boot-mvc-2/README.md new file mode 100644 index 0000000000..a405298cbe --- /dev/null +++ b/spring-boot-mvc-2/README.md @@ -0,0 +1,3 @@ +### Relevant Articles: + +- [Functional Controllers in Spring MVC]() \ No newline at end of file diff --git a/spring-boot-mvc-2/pom.xml b/spring-boot-mvc-2/pom.xml new file mode 100644 index 0000000000..18121325a5 --- /dev/null +++ b/spring-boot-mvc-2/pom.xml @@ -0,0 +1,68 @@ + + + 4.0.0 + spring-boot-mvc-2 + spring-boot-mvc-2 + jar + Module For Spring Boot MVC Web Fn + + + org.springframework.boot + spring-boot-starter-parent + 2.2.0.BUILD-SNAPSHOT + + + + + + org.springframework.boot + spring-boot-starter-web + + + + + + + org.springframework.boot + spring-boot-maven-plugin + + com.baeldung.springbootmvc.SpringBootMvcFnApplication + JAR + + + + + + + + spring-snapshots + Spring Snapshots + https://repo.spring.io/snapshot + + true + + + + spring-milestones + Spring Milestones + https://repo.spring.io/milestone + + + + + spring-snapshots + Spring Snapshots + https://repo.spring.io/snapshot + + true + + + + spring-milestones + Spring Milestones + https://repo.spring.io/milestone + + + \ No newline at end of file diff --git a/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/SpringBootMvcFnApplication.java b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/SpringBootMvcFnApplication.java new file mode 100644 index 0000000000..2a85550bd7 --- /dev/null +++ b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/SpringBootMvcFnApplication.java @@ -0,0 +1,74 @@ +package com.baeldung.springbootmvc; + +import static org.springframework.web.servlet.function.RouterFunctions.route; +import static org.springframework.web.servlet.function.ServerResponse.notFound; +import static org.springframework.web.servlet.function.ServerResponse.status; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; +import org.springframework.context.annotation.Bean; +import org.springframework.http.HttpStatus; +import org.springframework.web.servlet.function.RequestPredicates; +import org.springframework.web.servlet.function.RouterFunction; +import org.springframework.web.servlet.function.ServerResponse; + +import com.baeldung.springbootmvc.ctrl.ProductController; +import com.baeldung.springbootmvc.svc.ProductService; + +@SpringBootApplication +public class SpringBootMvcFnApplication { + + private static final Logger LOG = LoggerFactory.getLogger(SpringBootMvcFnApplication.class); + + public static void main(String[] args) { + SpringApplication.run(SpringBootMvcFnApplication.class, args); + } + + @Bean + RouterFunction productListing(ProductController pc, ProductService ps) { + return pc.productListing(ps); + } + + @Bean + RouterFunction allApplicationRoutes(ProductController pc, ProductService ps) { + return route().add(pc.remainingProductRoutes(ps)) + .before(req -> { + LOG.info("Found a route which matches " + req.uri() + .getPath()); + return req; + }) + .after((req, res) -> { + if (res.statusCode() == HttpStatus.OK) { + LOG.info("Finished processing request " + req.uri() + .getPath()); + } else { + LOG.info("There was an error while processing request" + req.uri()); + } + return res; + }) + .onError(Throwable.class, (e, res) -> { + LOG.error("Fatal exception has occurred", e); + return status(HttpStatus.INTERNAL_SERVER_ERROR).build(); + }) + .build() + .and(route(RequestPredicates.all(), req -> notFound().build())); + } + + public static class Error { + private String errorMessage; + + public Error(String message) { + this.errorMessage = message; + } + + public String getErrorMessage() { + return errorMessage; + } + + public void setErrorMessage(String errorMessage) { + this.errorMessage = errorMessage; + } + } +} diff --git a/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/ctrl/ProductController.java b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/ctrl/ProductController.java new file mode 100644 index 0000000000..6a77e72cea --- /dev/null +++ b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/ctrl/ProductController.java @@ -0,0 +1,59 @@ +package com.baeldung.springbootmvc.ctrl; + +import static org.springframework.web.servlet.function.RouterFunctions.route; +import static org.springframework.web.servlet.function.ServerResponse.ok; +import static org.springframework.web.servlet.function.ServerResponse.status; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.http.HttpStatus; +import org.springframework.stereotype.Component; +import org.springframework.web.servlet.function.EntityResponse; +import org.springframework.web.servlet.function.RequestPredicates; +import org.springframework.web.servlet.function.RouterFunction; +import org.springframework.web.servlet.function.ServerRequest; +import org.springframework.web.servlet.function.ServerResponse; + +import com.baeldung.springbootmvc.SpringBootMvcFnApplication.Error; +import com.baeldung.springbootmvc.model.Product; +import com.baeldung.springbootmvc.svc.ProductService; + +@Component +public class ProductController { + + public RouterFunction productListing(ProductService ps) { + return route().GET("/product", req -> ok().body(ps.findAll())) + .build(); + } + + public RouterFunction productSearch(ProductService ps) { + return route().nest(RequestPredicates.path("/product"), builder -> { + builder.GET("/name/{name}", req -> ok().body(ps.findByName(req.pathVariable("name")))) + .GET("/id/{id}", req -> ok().body(ps.findById(Integer.parseInt(req.pathVariable("id"))))); + }) + .onError(ProductService.ItemNotFoundException.class, (e, req) -> EntityResponse.fromObject(new Error(e.getMessage())) + .status(HttpStatus.NOT_FOUND) + .build()) + .build(); + } + + public RouterFunction adminFunctions(ProductService ps) { + return route().POST("/product", req -> ok().body(ps.save(req.body(Product.class)))) + .filter((req, next) -> authenticate(req) ? next.handle(req) : status(HttpStatus.UNAUTHORIZED).build()) + .onError(IllegalArgumentException.class, (e, req) -> EntityResponse.fromObject(new Error(e.getMessage())) + .status(HttpStatus.BAD_REQUEST) + .build()) + .build(); + } + + public RouterFunction remainingProductRoutes(ProductService ps) { + return route().add(productSearch(ps)) + .add(adminFunctions(ps)) + .build(); + } + + private boolean authenticate(ServerRequest req) { + return Boolean.TRUE; + } + +} diff --git a/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/model/Product.java b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/model/Product.java new file mode 100644 index 0000000000..1213b3c11e --- /dev/null +++ b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/model/Product.java @@ -0,0 +1,72 @@ +package com.baeldung.springbootmvc.model; + +public class Product { + private String name; + private double price; + private int id; + + public Product(String name, double price, int id) { + super(); + this.name = name; + this.price = price; + this.id = id; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public double getPrice() { + return price; + } + + public void setPrice(double price) { + this.price = price; + } + + public int getId() { + return id; + } + + public void setId(int id) { + this.id = id; + } + + @Override + public int hashCode() { + final int prime = 31; + int result = 1; + result = prime * result + id; + result = prime * result + ((name == null) ? 0 : name.hashCode()); + long temp; + temp = Double.doubleToLongBits(price); + result = prime * result + (int) (temp ^ (temp >>> 32)); + return result; + } + + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null) + return false; + if (getClass() != obj.getClass()) + return false; + Product other = (Product) obj; + if (id != other.id) + return false; + if (name == null) { + if (other.name != null) + return false; + } else if (!name.equals(other.name)) + return false; + if (Double.doubleToLongBits(price) != Double.doubleToLongBits(other.price)) + return false; + return true; + } + +} diff --git a/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/svc/ProductService.java b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/svc/ProductService.java new file mode 100644 index 0000000000..e2d281d54f --- /dev/null +++ b/spring-boot-mvc-2/src/main/java/com/baeldung/springbootmvc/svc/ProductService.java @@ -0,0 +1,63 @@ +package com.baeldung.springbootmvc.svc; + +import java.util.HashSet; +import java.util.Set; + +import org.springframework.stereotype.Service; +import org.springframework.util.StringUtils; + +import com.baeldung.springbootmvc.model.Product; + +@Service +public class ProductService { + + private final Set products = new HashSet<>(); + + { + products.add(new Product("Book", 23.90, 1)); + products.add(new Product("Pen", 44.34, 2)); + } + + public Product findById(int id) { + return products.stream() + .filter(obj -> obj.getId() == id) + .findFirst() + .orElseThrow(() -> new ItemNotFoundException("Product not found")); + } + + public Product findByName(String name) { + return products.stream() + .filter(obj -> obj.getName() + .equalsIgnoreCase(name)) + .findFirst() + .orElseThrow(() -> new ItemNotFoundException("Product not found")); + } + + public Set findAll() { + return products; + } + + public Product save(Product product) { + if (StringUtils.isEmpty(product.getName()) || product.getPrice() == 0.0) { + throw new IllegalArgumentException(); + } + int newId = products.stream() + .mapToInt(Product::getId) + .max() + .getAsInt() + 1; + product.setId(newId); + products.add(product); + return product; + } + + public static class ItemNotFoundException extends RuntimeException { + /** + * + */ + private static final long serialVersionUID = 1L; + + public ItemNotFoundException(String msg) { + super(msg); + } + } +} diff --git a/spring-boot-mvc-2/src/main/resources/application.properties b/spring-boot-mvc-2/src/main/resources/application.properties new file mode 100644 index 0000000000..709574239b --- /dev/null +++ b/spring-boot-mvc-2/src/main/resources/application.properties @@ -0,0 +1 @@ +spring.main.allow-bean-definition-overriding=true \ No newline at end of file diff --git a/spring-boot-mvc-2/src/main/resources/logback.xml b/spring-boot-mvc-2/src/main/resources/logback.xml new file mode 100644 index 0000000000..7d900d8ea8 --- /dev/null +++ b/spring-boot-mvc-2/src/main/resources/logback.xml @@ -0,0 +1,13 @@ + + + + + %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n + + + + + + + + \ No newline at end of file From 627fb4f1d114c81ceae4bbbbc04860ef026af182 Mon Sep 17 00:00:00 2001 From: maryarm <45322329+maryarm@users.noreply.github.com> Date: Tue, 30 Jul 2019 09:49:08 +0430 Subject: [PATCH 100/107] #BAEL-2888: Reloading Properties Files in Spring (#7427) -change package name to "com.baeldung.properties.reloading" -remove module 's ".gitignore" --- spring-boot-properties/.gitignore | 17 ----------------- .../SpringBootPropertiesApplication.java | 4 ++-- .../configs/PropertiesException.java | 2 +- .../configs/ReloadableProperties.java | 2 +- .../configs/ReloadablePropertySource.java | 2 +- .../configs/ReloadablePropertySourceConfig.java | 2 +- .../ReloadablePropertySourceFactory.java | 2 +- .../PropertiesReloadIntegrationTest.java | 10 +++++----- .../SpringBootPropertiesTestApplication.java | 4 ++-- ...onfigurationPropertiesRefreshConfigBean.java | 2 +- .../beans/EnvironmentConfigBean.java | 4 ++-- .../beans/PropertiesConfigBean.java | 2 +- .../beans/ValueRefreshConfigBean.java | 2 +- 13 files changed, 19 insertions(+), 36 deletions(-) delete mode 100644 spring-boot-properties/.gitignore rename spring-boot-properties/src/main/java/com/baeldung/properties/{ => reloading}/SpringBootPropertiesApplication.java (94%) rename spring-boot-properties/src/main/java/com/baeldung/properties/{ => reloading}/configs/PropertiesException.java (78%) rename spring-boot-properties/src/main/java/com/baeldung/properties/{ => reloading}/configs/ReloadableProperties.java (96%) rename spring-boot-properties/src/main/java/com/baeldung/properties/{ => reloading}/configs/ReloadablePropertySource.java (95%) rename spring-boot-properties/src/main/java/com/baeldung/properties/{ => reloading}/configs/ReloadablePropertySourceConfig.java (95%) rename spring-boot-properties/src/main/java/com/baeldung/properties/{ => reloading}/configs/ReloadablePropertySourceFactory.java (95%) rename spring-boot-properties/src/test/java/com/baeldung/properties/{ => reloading}/PropertiesReloadIntegrationTest.java (94%) rename spring-boot-properties/src/test/java/com/baeldung/properties/{ => reloading}/SpringBootPropertiesTestApplication.java (89%) rename spring-boot-properties/src/test/java/com/baeldung/properties/{ => reloading}/beans/ConfigurationPropertiesRefreshConfigBean.java (91%) rename spring-boot-properties/src/test/java/com/baeldung/properties/{ => reloading}/beans/EnvironmentConfigBean.java (85%) rename spring-boot-properties/src/test/java/com/baeldung/properties/{ => reloading}/beans/PropertiesConfigBean.java (90%) rename spring-boot-properties/src/test/java/com/baeldung/properties/{ => reloading}/beans/ValueRefreshConfigBean.java (81%) diff --git a/spring-boot-properties/.gitignore b/spring-boot-properties/.gitignore deleted file mode 100644 index 0532ef1888..0000000000 --- a/spring-boot-properties/.gitignore +++ /dev/null @@ -1,17 +0,0 @@ -*.class - -#folders# -/target -/neoDb* -/data -/src/main/webapp/WEB-INF/classes -*/META-INF/* - -# Packaged files # -*.jar -*.war -*.ear - -*.ipr -*.iml -*.iws diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/SpringBootPropertiesApplication.java b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/SpringBootPropertiesApplication.java similarity index 94% rename from spring-boot-properties/src/main/java/com/baeldung/properties/SpringBootPropertiesApplication.java rename to spring-boot-properties/src/main/java/com/baeldung/properties/reloading/SpringBootPropertiesApplication.java index 67bbddf9f1..6f76379a99 100644 --- a/spring-boot-properties/src/main/java/com/baeldung/properties/SpringBootPropertiesApplication.java +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/SpringBootPropertiesApplication.java @@ -1,6 +1,6 @@ -package com.baeldung.properties; +package com.baeldung.properties.reloading; -import com.baeldung.properties.configs.ReloadableProperties; +import com.baeldung.properties.reloading.configs.ReloadableProperties; import java.io.File; import java.util.Properties; import org.apache.commons.configuration.PropertiesConfiguration; diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/PropertiesException.java b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/PropertiesException.java similarity index 78% rename from spring-boot-properties/src/main/java/com/baeldung/properties/configs/PropertiesException.java rename to spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/PropertiesException.java index 5ec3a042f7..09c18aef33 100644 --- a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/PropertiesException.java +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/PropertiesException.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.configs; +package com.baeldung.properties.reloading.configs; public class PropertiesException extends RuntimeException { public PropertiesException() { diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadableProperties.java b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadableProperties.java similarity index 96% rename from spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadableProperties.java rename to spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadableProperties.java index 33d503b9bd..e90e68d09a 100644 --- a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadableProperties.java +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadableProperties.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.configs; +package com.baeldung.properties.reloading.configs; import java.io.FileReader; import java.io.IOException; diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySource.java b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySource.java similarity index 95% rename from spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySource.java rename to spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySource.java index 8a0cef955f..6d76a2e1e2 100644 --- a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySource.java +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySource.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.configs; +package com.baeldung.properties.reloading.configs; import org.apache.commons.configuration.PropertiesConfiguration; import org.apache.commons.configuration.reloading.FileChangedReloadingStrategy; diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceConfig.java b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySourceConfig.java similarity index 95% rename from spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceConfig.java rename to spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySourceConfig.java index 37e1a04839..dd70e3842e 100644 --- a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceConfig.java +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySourceConfig.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.configs; +package com.baeldung.properties.reloading.configs; import org.apache.commons.configuration.PropertiesConfiguration; import org.springframework.beans.factory.annotation.Autowired; diff --git a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceFactory.java b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySourceFactory.java similarity index 95% rename from spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceFactory.java rename to spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySourceFactory.java index 574362b3bf..2a620b0b2d 100644 --- a/spring-boot-properties/src/main/java/com/baeldung/properties/configs/ReloadablePropertySourceFactory.java +++ b/spring-boot-properties/src/main/java/com/baeldung/properties/reloading/configs/ReloadablePropertySourceFactory.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.configs; +package com.baeldung.properties.reloading.configs; import java.io.IOException; import org.springframework.core.env.PropertySource; diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/PropertiesReloadIntegrationTest.java b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/PropertiesReloadIntegrationTest.java similarity index 94% rename from spring-boot-properties/src/test/java/com/baeldung/properties/PropertiesReloadIntegrationTest.java rename to spring-boot-properties/src/test/java/com/baeldung/properties/reloading/PropertiesReloadIntegrationTest.java index a73311ded8..0c28cb085b 100644 --- a/spring-boot-properties/src/test/java/com/baeldung/properties/PropertiesReloadIntegrationTest.java +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/PropertiesReloadIntegrationTest.java @@ -1,9 +1,9 @@ -package com.baeldung.properties; +package com.baeldung.properties.reloading; -import com.baeldung.properties.beans.ConfigurationPropertiesRefreshConfigBean; -import com.baeldung.properties.beans.EnvironmentConfigBean; -import com.baeldung.properties.beans.PropertiesConfigBean; -import com.baeldung.properties.beans.ValueRefreshConfigBean; +import com.baeldung.properties.reloading.beans.ConfigurationPropertiesRefreshConfigBean; +import com.baeldung.properties.reloading.beans.EnvironmentConfigBean; +import com.baeldung.properties.reloading.beans.PropertiesConfigBean; +import com.baeldung.properties.reloading.beans.ValueRefreshConfigBean; import java.io.FileOutputStream; import org.junit.After; import org.junit.Assert; diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/SpringBootPropertiesTestApplication.java b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/SpringBootPropertiesTestApplication.java similarity index 89% rename from spring-boot-properties/src/test/java/com/baeldung/properties/SpringBootPropertiesTestApplication.java rename to spring-boot-properties/src/test/java/com/baeldung/properties/reloading/SpringBootPropertiesTestApplication.java index c572a6c053..50e8ef5b62 100644 --- a/spring-boot-properties/src/test/java/com/baeldung/properties/SpringBootPropertiesTestApplication.java +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/SpringBootPropertiesTestApplication.java @@ -1,6 +1,6 @@ -package com.baeldung.properties; +package com.baeldung.properties.reloading; -import com.baeldung.properties.beans.ValueRefreshConfigBean; +import com.baeldung.properties.reloading.beans.ValueRefreshConfigBean; import org.springframework.beans.factory.annotation.Value; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.cloud.context.config.annotation.RefreshScope; diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ConfigurationPropertiesRefreshConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/ConfigurationPropertiesRefreshConfigBean.java similarity index 91% rename from spring-boot-properties/src/test/java/com/baeldung/properties/beans/ConfigurationPropertiesRefreshConfigBean.java rename to spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/ConfigurationPropertiesRefreshConfigBean.java index 31f168fdcc..16892b904b 100644 --- a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ConfigurationPropertiesRefreshConfigBean.java +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/ConfigurationPropertiesRefreshConfigBean.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.beans; +package com.baeldung.properties.reloading.beans; import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.cloud.context.config.annotation.RefreshScope; diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/EnvironmentConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/EnvironmentConfigBean.java similarity index 85% rename from spring-boot-properties/src/test/java/com/baeldung/properties/beans/EnvironmentConfigBean.java rename to spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/EnvironmentConfigBean.java index fef12f8656..325e8c658e 100644 --- a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/EnvironmentConfigBean.java +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/EnvironmentConfigBean.java @@ -1,6 +1,6 @@ -package com.baeldung.properties.beans; +package com.baeldung.properties.reloading.beans; -import com.baeldung.properties.configs.ReloadablePropertySourceFactory; +import com.baeldung.properties.reloading.configs.ReloadablePropertySourceFactory; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.PropertySource; import org.springframework.core.env.Environment; diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/PropertiesConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/PropertiesConfigBean.java similarity index 90% rename from spring-boot-properties/src/test/java/com/baeldung/properties/beans/PropertiesConfigBean.java rename to spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/PropertiesConfigBean.java index da773b283a..8118f6156e 100644 --- a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/PropertiesConfigBean.java +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/PropertiesConfigBean.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.beans; +package com.baeldung.properties.reloading.beans; import java.util.Properties; import org.springframework.beans.factory.annotation.Autowired; diff --git a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ValueRefreshConfigBean.java b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/ValueRefreshConfigBean.java similarity index 81% rename from spring-boot-properties/src/test/java/com/baeldung/properties/beans/ValueRefreshConfigBean.java rename to spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/ValueRefreshConfigBean.java index d806938092..1018d7c9f5 100644 --- a/spring-boot-properties/src/test/java/com/baeldung/properties/beans/ValueRefreshConfigBean.java +++ b/spring-boot-properties/src/test/java/com/baeldung/properties/reloading/beans/ValueRefreshConfigBean.java @@ -1,4 +1,4 @@ -package com.baeldung.properties.beans; +package com.baeldung.properties.reloading.beans; public class ValueRefreshConfigBean { private String color; From 36ad6f15ef1b1f5db8aeb1e6d0257d12a1adccb2 Mon Sep 17 00:00:00 2001 From: Kumar Chandrakant Date: Tue, 30 Jul 2019 11:39:34 +0530 Subject: [PATCH 101/107] Adding code for the tutorial tracked under BAEL-3073. (#7442) --- .../baeldung/sasl/ClientCallbackHandler.java | 29 +++++++ .../baeldung/sasl/ServerCallbackHandler.java | 34 +++++++++ .../java/com/baeldung/sasl/SaslUnitTest.java | 76 +++++++++++++++++++ 3 files changed, 139 insertions(+) create mode 100644 core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ClientCallbackHandler.java create mode 100644 core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ServerCallbackHandler.java create mode 100644 core-java-modules/core-java-security/src/test/java/com/baeldung/sasl/SaslUnitTest.java diff --git a/core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ClientCallbackHandler.java b/core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ClientCallbackHandler.java new file mode 100644 index 0000000000..d73f2a2708 --- /dev/null +++ b/core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ClientCallbackHandler.java @@ -0,0 +1,29 @@ +package com.baeldung.sasl; + +import java.io.IOException; + +import javax.security.auth.callback.Callback; +import javax.security.auth.callback.CallbackHandler; +import javax.security.auth.callback.NameCallback; +import javax.security.auth.callback.PasswordCallback; +import javax.security.auth.callback.UnsupportedCallbackException; +import javax.security.sasl.RealmCallback; + +public class ClientCallbackHandler implements CallbackHandler { + + @Override + public void handle(Callback[] cbs) throws IOException, UnsupportedCallbackException { + for (Callback cb : cbs) { + if (cb instanceof NameCallback) { + NameCallback nc = (NameCallback) cb; + nc.setName("username"); + } else if (cb instanceof PasswordCallback) { + PasswordCallback pc = (PasswordCallback) cb; + pc.setPassword("password".toCharArray()); + } else if (cb instanceof RealmCallback) { + RealmCallback rc = (RealmCallback) cb; + rc.setText("myServer"); + } + } + } +} diff --git a/core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ServerCallbackHandler.java b/core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ServerCallbackHandler.java new file mode 100644 index 0000000000..3e071d68cc --- /dev/null +++ b/core-java-modules/core-java-security/src/main/java/com/baeldung/sasl/ServerCallbackHandler.java @@ -0,0 +1,34 @@ +package com.baeldung.sasl; + +import java.io.IOException; + +import javax.security.auth.callback.Callback; +import javax.security.auth.callback.CallbackHandler; +import javax.security.auth.callback.NameCallback; +import javax.security.auth.callback.PasswordCallback; +import javax.security.auth.callback.UnsupportedCallbackException; +import javax.security.sasl.AuthorizeCallback; +import javax.security.sasl.RealmCallback; + +public class ServerCallbackHandler implements CallbackHandler { + + @Override + public void handle(Callback[] cbs) throws IOException, UnsupportedCallbackException { + for (Callback cb : cbs) { + if (cb instanceof AuthorizeCallback) { + AuthorizeCallback ac = (AuthorizeCallback) cb; + ac.setAuthorized(true); + } else if (cb instanceof NameCallback) { + NameCallback nc = (NameCallback) cb; + nc.setName("username"); + + } else if (cb instanceof PasswordCallback) { + PasswordCallback pc = (PasswordCallback) cb; + pc.setPassword("password".toCharArray()); + } else if (cb instanceof RealmCallback) { + RealmCallback rc = (RealmCallback) cb; + rc.setText("myServer"); + } + } + } +} \ No newline at end of file diff --git a/core-java-modules/core-java-security/src/test/java/com/baeldung/sasl/SaslUnitTest.java b/core-java-modules/core-java-security/src/test/java/com/baeldung/sasl/SaslUnitTest.java new file mode 100644 index 0000000000..6601654781 --- /dev/null +++ b/core-java-modules/core-java-security/src/test/java/com/baeldung/sasl/SaslUnitTest.java @@ -0,0 +1,76 @@ +package com.baeldung.sasl; + +import static org.junit.Assert.assertTrue; +import static org.junit.jupiter.api.Assertions.assertEquals; + +import java.nio.charset.StandardCharsets; +import java.util.HashMap; +import java.util.Map; + +import javax.security.sasl.Sasl; +import javax.security.sasl.SaslClient; +import javax.security.sasl.SaslException; +import javax.security.sasl.SaslServer; + +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +public class SaslUnitTest { + + private static final String MECHANISM = "DIGEST-MD5"; + private static final String SERVER_NAME = "myServer"; + private static final String PROTOCOL = "myProtocol"; + private static final String AUTHORIZATION_ID = null; + private static final String QOP_LEVEL = "auth-conf"; + + private SaslServer saslServer; + private SaslClient saslClient; + + @Before + public void setUp() throws SaslException { + + ServerCallbackHandler serverHandler = new ServerCallbackHandler(); + ClientCallbackHandler clientHandler = new ClientCallbackHandler(); + + Map props = new HashMap<>(); + props.put(Sasl.QOP, QOP_LEVEL); + + saslServer = Sasl.createSaslServer(MECHANISM, PROTOCOL, SERVER_NAME, props, serverHandler); + saslClient = Sasl.createSaslClient(new String[] { MECHANISM }, AUTHORIZATION_ID, PROTOCOL, SERVER_NAME, props, clientHandler); + + } + + @Test + public void givenHandlers_whenStarted_thenAutenticationWorks() throws SaslException { + + byte[] challenge; + byte[] response; + + challenge = saslServer.evaluateResponse(new byte[0]); + response = saslClient.evaluateChallenge(challenge); + + challenge = saslServer.evaluateResponse(response); + response = saslClient.evaluateChallenge(challenge); + + assertTrue(saslServer.isComplete()); + assertTrue(saslClient.isComplete()); + + String qop = (String) saslClient.getNegotiatedProperty(Sasl.QOP); + assertEquals("auth-conf", qop); + + byte[] outgoing = "Baeldung".getBytes(); + byte[] secureOutgoing = saslClient.wrap(outgoing, 0, outgoing.length); + + byte[] secureIncoming = secureOutgoing; + byte[] incoming = saslServer.unwrap(secureIncoming, 0, secureIncoming.length); + assertEquals("Baeldung", new String(incoming, StandardCharsets.UTF_8)); + } + + @After + public void tearDown() throws SaslException { + saslClient.dispose(); + saslServer.dispose(); + } + +} From 8e3f2ae495116db8bfaf35f035351fe2c4d73218 Mon Sep 17 00:00:00 2001 From: Krzysztof Majewski Date: Tue, 30 Jul 2019 08:35:24 +0200 Subject: [PATCH 102/107] update --- persistence-modules/java-jpa-2/pom.xml | 96 +++++++++---------- .../java-jpa-2/src/main/resources/logback.xml | 13 --- 2 files changed, 48 insertions(+), 61 deletions(-) delete mode 100644 persistence-modules/java-jpa-2/src/main/resources/logback.xml diff --git a/persistence-modules/java-jpa-2/pom.xml b/persistence-modules/java-jpa-2/pom.xml index c8c9a24599..12586db1b7 100644 --- a/persistence-modules/java-jpa-2/pom.xml +++ b/persistence-modules/java-jpa-2/pom.xml @@ -19,11 +19,11 @@ hibernate-core ${hibernate.version} - - org.hibernate - hibernate-jpamodelgen - ${hibernate.version} - + + org.hibernate + hibernate-jpamodelgen + ${hibernate.version} + com.h2database h2 @@ -52,8 +52,8 @@
    - - + + org.apache.maven.plugins maven-compiler-plugin @@ -62,48 +62,48 @@ -proc:none - - org.bsc.maven - maven-processor-plugin - 3.3.3 - - - process - - process - - generate-sources - - target/metamodel - - org.hibernate.jpamodelgen.JPAMetaModelEntityProcessor - - - - - + + org.bsc.maven + maven-processor-plugin + 3.3.3 + + + process + + process + + generate-sources + + target/metamodel + + org.hibernate.jpamodelgen.JPAMetaModelEntityProcessor + + + + + - - org.codehaus.mojo - build-helper-maven-plugin - 3.0.0 - - - add-source - generate-sources - - add-source - - - - target/metamodel - - - - - - - + + org.codehaus.mojo + build-helper-maven-plugin + 3.0.0 + + + add-source + generate-sources + + add-source + + + + target/metamodel + + + + + + + 5.4.0.Final diff --git a/persistence-modules/java-jpa-2/src/main/resources/logback.xml b/persistence-modules/java-jpa-2/src/main/resources/logback.xml deleted file mode 100644 index 7d900d8ea8..0000000000 --- a/persistence-modules/java-jpa-2/src/main/resources/logback.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n - - - - - - - - \ No newline at end of file From 2aa2f078ddb720ebf555f84cdd98bc237a363012 Mon Sep 17 00:00:00 2001 From: "sreekanth.nair" Date: Tue, 30 Jul 2019 12:55:29 +0530 Subject: [PATCH 103/107] [BAEL-3121] Added source for finding number of lines in a file --- .../main/java/com/baeldung/files/Main.java | 24 ++++ .../baeldung/files/NumberOfLineFinder.java | 112 ++++++++++++++++++ .../file/NumberOfLineFinderUnitTest.java | 60 ++++++++++ 3 files changed, 196 insertions(+) create mode 100644 core-java-modules/core-java-io/src/main/java/com/baeldung/files/Main.java create mode 100644 core-java-modules/core-java-io/src/main/java/com/baeldung/files/NumberOfLineFinder.java create mode 100644 core-java-modules/core-java-io/src/test/java/com/baeldung/file/NumberOfLineFinderUnitTest.java diff --git a/core-java-modules/core-java-io/src/main/java/com/baeldung/files/Main.java b/core-java-modules/core-java-io/src/main/java/com/baeldung/files/Main.java new file mode 100644 index 0000000000..c3bcd048a4 --- /dev/null +++ b/core-java-modules/core-java-io/src/main/java/com/baeldung/files/Main.java @@ -0,0 +1,24 @@ +package com.baeldung.files; + +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingApacheCommonsIO; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingBufferedReader; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingGoogleGuava; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingLineNumberReader; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingNIOFileChannel; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingNIOFiles; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingScanner; + +public class Main { + + private static final String INPUT_FILE_NAME = "src/main/resources/input.txt"; + + public static void main(String... args) throws Exception { + System.out.printf("Total Number of Lines Using BufferedReader: %s%n", getTotalNumberOfLinesUsingBufferedReader(INPUT_FILE_NAME)); + System.out.printf("Total Number of Lines Using LineNumberReader: %s%n", getTotalNumberOfLinesUsingLineNumberReader(INPUT_FILE_NAME)); + System.out.printf("Total Number of Lines Using Scanner: %s%n", getTotalNumberOfLinesUsingScanner(INPUT_FILE_NAME)); + System.out.printf("Total Number of Lines Using NIO Files: %s%n", getTotalNumberOfLinesUsingNIOFiles(INPUT_FILE_NAME)); + System.out.printf("Total Number of Lines Using NIO FileChannel: %s%n", getTotalNumberOfLinesUsingNIOFileChannel(INPUT_FILE_NAME)); + System.out.printf("Total Number of Lines Using Apache Commons IO: %s%n", getTotalNumberOfLinesUsingApacheCommonsIO(INPUT_FILE_NAME)); + System.out.printf("Total Number of Lines Using NIO Google Guava: %s%n", getTotalNumberOfLinesUsingGoogleGuava(INPUT_FILE_NAME)); + } +} diff --git a/core-java-modules/core-java-io/src/main/java/com/baeldung/files/NumberOfLineFinder.java b/core-java-modules/core-java-io/src/main/java/com/baeldung/files/NumberOfLineFinder.java new file mode 100644 index 0000000000..076825d76c --- /dev/null +++ b/core-java-modules/core-java-io/src/main/java/com/baeldung/files/NumberOfLineFinder.java @@ -0,0 +1,112 @@ +package com.baeldung.files; + +import java.io.BufferedReader; +import java.io.File; +import java.io.FileReader; +import java.io.IOException; +import java.io.LineNumberReader; +import java.nio.ByteBuffer; +import java.nio.channels.FileChannel; +import java.nio.channels.FileChannel.MapMode; +import java.nio.charset.Charset; +import java.nio.file.Files; +import java.nio.file.Paths; +import java.nio.file.StandardOpenOption; +import java.util.List; +import java.util.Scanner; +import java.util.stream.Stream; + +import org.apache.commons.io.FileUtils; +import org.apache.commons.io.LineIterator; + +public class NumberOfLineFinder { + + public static int getTotalNumberOfLinesUsingBufferedReader(String fileName) { + int lines = 0; + try (BufferedReader reader = new BufferedReader(new FileReader(fileName))) { + while (reader.readLine() != null) { + lines++; + } + } catch (IOException ioe) { + ioe.printStackTrace(); + } + return lines; + } + + public static int getTotalNumberOfLinesUsingLineNumberReader(String fileName) { + int lines = 0; + try (LineNumberReader reader = new LineNumberReader(new FileReader(fileName))) { + reader.skip(Integer.MAX_VALUE); + lines = reader.getLineNumber() + 1; + } catch (IOException ioe) { + ioe.printStackTrace(); + } + return lines; + } + + public static int getTotalNumberOfLinesUsingScanner(String fileName) { + int lines = 0; + try (Scanner scanner = new Scanner(new FileReader(fileName))) { + while (scanner.hasNextLine()) { + scanner.nextLine(); + lines++; + } + } catch (IOException ioe) { + ioe.printStackTrace(); + } + return lines; + } + + public static int getTotalNumberOfLinesUsingNIOFiles(String fileName) { + int lines = 0; + try (Stream fileStream = Files.lines(Paths.get(fileName))) { + lines = (int) fileStream.count(); + } catch (IOException ioe) { + ioe.printStackTrace(); + } + return lines; + } + + public static int getTotalNumberOfLinesUsingNIOFileChannel(String fileName) { + int lines = 1; + try (FileChannel channel = FileChannel.open(Paths.get(fileName), StandardOpenOption.READ)) { + ByteBuffer byteBuffer = channel.map(MapMode.READ_ONLY, 0, channel.size()); + while (byteBuffer.hasRemaining()) { + byte currentChar = byteBuffer.get(); + if (currentChar == '\n') { + lines++; + } + } + } catch (IOException ioe) { + ioe.printStackTrace(); + } + return lines; + } + + public static int getTotalNumberOfLinesUsingApacheCommonsIO(String fileName) { + int lines = 0; + try { + LineIterator lineIterator = FileUtils.lineIterator(new File(fileName)); + while (lineIterator.hasNext()) { + lineIterator.nextLine(); + lines++; + } + } catch (IOException ioe) { + ioe.printStackTrace(); + } + return lines; + } + + public static int getTotalNumberOfLinesUsingGoogleGuava(String fileName) { + int lines = 0; + try { + List lineItems = com.google.common.io.Files.readLines(Paths.get(fileName) + .toFile(), Charset.defaultCharset()); + lines = lineItems.size(); + } catch (IOException ioe) { + ioe.printStackTrace(); + } + return lines; + } + +} diff --git a/core-java-modules/core-java-io/src/test/java/com/baeldung/file/NumberOfLineFinderUnitTest.java b/core-java-modules/core-java-io/src/test/java/com/baeldung/file/NumberOfLineFinderUnitTest.java new file mode 100644 index 0000000000..6f0427ebd2 --- /dev/null +++ b/core-java-modules/core-java-io/src/test/java/com/baeldung/file/NumberOfLineFinderUnitTest.java @@ -0,0 +1,60 @@ +package com.baeldung.file; + +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingApacheCommonsIO; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingBufferedReader; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingGoogleGuava; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingLineNumberReader; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingNIOFileChannel; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingNIOFiles; +import static com.baeldung.files.NumberOfLineFinder.getTotalNumberOfLinesUsingScanner; +import static org.junit.Assert.assertEquals; + +import org.junit.Test; + +public class NumberOfLineFinderUnitTest { + private static final String INPUT_FILE_NAME = "src/main/resources/input.txt"; + private static final int ACTUAL_LINE_COUNT = 45; + + @Test + public void whenUsingBufferedReader_thenReturnTotalNumberOfLines() { + int lines = getTotalNumberOfLinesUsingBufferedReader(INPUT_FILE_NAME); + assertEquals(ACTUAL_LINE_COUNT, lines); + } + + @Test + public void whenUsingLineNumberReader_thenReturnTotalNumberOfLines() { + int lines = getTotalNumberOfLinesUsingLineNumberReader(INPUT_FILE_NAME); + assertEquals(ACTUAL_LINE_COUNT, lines); + } + + @Test + public void whenUsingScanner_thenReturnTotalNumberOfLines() { + int lines = getTotalNumberOfLinesUsingScanner(INPUT_FILE_NAME); + assertEquals(ACTUAL_LINE_COUNT, lines); + } + + @Test + public void whenUsingNIOFiles_thenReturnTotalNumberOfLines() { + int lines = getTotalNumberOfLinesUsingNIOFiles(INPUT_FILE_NAME); + assertEquals(ACTUAL_LINE_COUNT, lines); + } + + @Test + public void whenUsingNIOFileChannel_thenReturnTotalNumberOfLines() { + int lines = getTotalNumberOfLinesUsingNIOFileChannel(INPUT_FILE_NAME); + assertEquals(ACTUAL_LINE_COUNT, lines); + } + + @Test + public void whenUsingApacheCommonsIO_thenReturnTotalNumberOfLines() { + int lines = getTotalNumberOfLinesUsingApacheCommonsIO(INPUT_FILE_NAME); + assertEquals(ACTUAL_LINE_COUNT, lines); + } + + @Test + public void whenUsingGoogleGuava_thenReturnTotalNumberOfLines() { + int lines = getTotalNumberOfLinesUsingGoogleGuava(INPUT_FILE_NAME); + assertEquals(ACTUAL_LINE_COUNT, lines); + } + +} From 19d73e961173a82aa8822589986d113f75355b68 Mon Sep 17 00:00:00 2001 From: Alessio Stalla Date: Tue, 30 Jul 2019 14:36:32 +0200 Subject: [PATCH 104/107] Fix parent POM --- persistence-modules/java-sql2o/pom.xml | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/persistence-modules/java-sql2o/pom.xml b/persistence-modules/java-sql2o/pom.xml index 54838c32cb..fe5a0e5dc8 100644 --- a/persistence-modules/java-sql2o/pom.xml +++ b/persistence-modules/java-sql2o/pom.xml @@ -2,7 +2,6 @@ 4.0.0 - com.baeldung java-sql2o 1.0-SNAPSHOT @@ -19,12 +18,12 @@ java-sql2o - + From db90a53e38b269698646678c4a6c20ad2d69cbc7 Mon Sep 17 00:00:00 2001 From: Justin Albano Date: Tue, 30 Jul 2019 15:54:17 -0400 Subject: [PATCH 105/107] BAEL-3141: Added test cases for String to Double conversion. (#7448) These tests exercise the conversion of Strings that can be converted to Doubles, as well as the exceptions that are thrown for invalid Strings. --- .../StringToDoubleConversionUnitTest.java | 56 +++++++++++++++++++ 1 file changed, 56 insertions(+) create mode 100644 java-strings-2/src/test/java/com/baeldung/string/todouble/StringToDoubleConversionUnitTest.java diff --git a/java-strings-2/src/test/java/com/baeldung/string/todouble/StringToDoubleConversionUnitTest.java b/java-strings-2/src/test/java/com/baeldung/string/todouble/StringToDoubleConversionUnitTest.java new file mode 100644 index 0000000000..9abb7ac453 --- /dev/null +++ b/java-strings-2/src/test/java/com/baeldung/string/todouble/StringToDoubleConversionUnitTest.java @@ -0,0 +1,56 @@ +package com.baeldung.string.todouble; + +import static org.junit.Assert.assertEquals; + +import java.text.DecimalFormat; +import java.text.ParseException; + +import org.junit.Test; + +public class StringToDoubleConversionUnitTest { + + @Test + public void givenValidString_WhenParseDouble_ThenResultIsPrimitiveDouble() { + assertEquals(1.23, Double.parseDouble("1.23"), 0.000001); + } + + @Test(expected = NullPointerException.class) + public void givenNullString_WhenParseDouble_ThenNullPointerExceptionIsThrown() { + Double.parseDouble(null); + } + + @Test(expected = NumberFormatException.class) + public void givenInalidString_WhenParseDouble_ThenNumberFormatExceptionIsThrown() { + Double.parseDouble("&"); + } + + @Test + public void givenValidString_WhenValueOf_ThenResultIsPrimitiveDouble() { + assertEquals(1.23, Double.valueOf("1.23"), 0.000001); + } + + @Test(expected = NullPointerException.class) + public void givenNullString_WhenValueOf_ThenNullPointerExceptionIsThrown() { + Double.valueOf(null); + } + + @Test(expected = NumberFormatException.class) + public void givenInalidString_WhenValueOf_ThenNumberFormatExceptionIsThrown() { + Double.valueOf("&"); + } + + @Test + public void givenValidString_WhenDecimalFormat_ThenResultIsValidDouble() throws ParseException { + assertEquals(1.23, new DecimalFormat("#").parse("1.23").doubleValue(), 0.000001); + } + + @Test(expected = NullPointerException.class) + public void givenNullString_WhenDecimalFormat_ThenNullPointerExceptionIsThrown() throws ParseException { + new DecimalFormat("#").parse(null); + } + + @Test(expected = ParseException.class) + public void givenInvalidString_WhenDecimalFormat_ThenParseExceptionIsThrown() throws ParseException { + new DecimalFormat("#").parse("&"); + } +} From ecf8bd76cc7232e6d1a23cc16a651fea7abeb435 Mon Sep 17 00:00:00 2001 From: Sumeet Gajbhar Date: Wed, 31 Jul 2019 01:42:25 +0530 Subject: [PATCH 106/107] BAEL-3027 binary number arithmetic operations (#7437) * BAEL-3027 binary number arithmetic operations * BAEL-3127 updated the unit test case names * added unit test cases for built-in java functions * updated function name * BAEL-3127 updated unit test case names * BAEL-3127 removed comments from code --- .../baeldung/binarynumbers/BinaryNumbers.java | 148 ++++++++++++++++++ .../binarynumbers/BinaryNumbersUnitTest.java | 73 +++++++++ 2 files changed, 221 insertions(+) create mode 100644 java-numbers-2/src/main/java/com/baeldung/binarynumbers/BinaryNumbers.java create mode 100644 java-numbers-2/src/test/java/com/baeldung/binarynumbers/BinaryNumbersUnitTest.java diff --git a/java-numbers-2/src/main/java/com/baeldung/binarynumbers/BinaryNumbers.java b/java-numbers-2/src/main/java/com/baeldung/binarynumbers/BinaryNumbers.java new file mode 100644 index 0000000000..effdee07ad --- /dev/null +++ b/java-numbers-2/src/main/java/com/baeldung/binarynumbers/BinaryNumbers.java @@ -0,0 +1,148 @@ +package com.baeldung.binarynumbers; + +public class BinaryNumbers { + + /** + * This method takes a decimal number and convert it into a binary number. + * example:- input:10, output:1010 + * + * @param decimalNumber + * @return binary number + */ + public Integer convertDecimalToBinary(Integer decimalNumber) { + + if (decimalNumber == 0) { + return decimalNumber; + } + + StringBuilder binaryNumber = new StringBuilder(); + + while (decimalNumber > 0) { + + int remainder = decimalNumber % 2; + int result = decimalNumber / 2; + + binaryNumber.append(remainder); + decimalNumber = result; + } + + binaryNumber = binaryNumber.reverse(); + + return Integer.valueOf(binaryNumber.toString()); + } + + /** + * This method takes a binary number and convert it into a decimal number. + * example:- input:101, output:5 + * + * @param binary number + * @return decimal Number + */ + public Integer convertBinaryToDecimal(Integer binaryNumber) { + + Integer result = 0; + Integer base = 1; + + while (binaryNumber > 0) { + + int lastDigit = binaryNumber % 10; + binaryNumber = binaryNumber / 10; + + result += lastDigit * base; + + base = base * 2; + } + return result; + } + + /** + * This method accepts two binary numbers and returns sum of input numbers. + * Example:- firstNum: 101, secondNum: 100, output: 1001 + * + * @param firstNum + * @param secondNum + * @return addition of input numbers + */ + public Integer addBinaryNumber(Integer firstNum, Integer secondNum) { + + StringBuilder output = new StringBuilder(); + + int carry = 0; + int temp; + + while (firstNum != 0 || secondNum != 0) { + + temp = (firstNum % 10 + secondNum % 10 + carry) % 2; + output.append(temp); + + carry = (firstNum % 10 + secondNum % 10 + carry) / 2; + + firstNum = firstNum / 10; + secondNum = secondNum / 10; + } + + if (carry != 0) { + output.append(carry); + } + + return Integer.valueOf(output.reverse() + .toString()); + } + + /** + * This method takes two binary number as input and subtract second number from the first number. + * example:- firstNum: 1000, secondNum: 11, output: 101 + * @param firstNum + * @param secondNum + * @return Result of subtraction of secondNum from first + */ + public Integer substractBinaryNumber(Integer firstNum, Integer secondNum) { + + int onesComplement = Integer.valueOf(getOnesComplement(secondNum)); + + StringBuilder output = new StringBuilder(); + + int carry = 0; + int temp; + + while (firstNum != 0 || onesComplement != 0) { + + temp = (firstNum % 10 + onesComplement % 10 + carry) % 2; + output.append(temp); + + carry = (firstNum % 10 + onesComplement % 10 + carry) / 2; + + firstNum = firstNum / 10; + onesComplement = onesComplement / 10; + } + + String additionOfFirstNumAndOnesComplement = output.reverse() + .toString(); + + if (carry == 1) { + return addBinaryNumber(Integer.valueOf(additionOfFirstNumAndOnesComplement), carry); + } else { + return getOnesComplement(Integer.valueOf(additionOfFirstNumAndOnesComplement)); + } + + } + + public Integer getOnesComplement(Integer num) { + + StringBuilder onesComplement = new StringBuilder(); + + while (num > 0) { + int lastDigit = num % 10; + if (lastDigit == 0) { + onesComplement.append(1); + } else { + onesComplement.append(0); + } + num = num / 10; + } + + return Integer.valueOf(onesComplement.reverse() + .toString()); + } + +} diff --git a/java-numbers-2/src/test/java/com/baeldung/binarynumbers/BinaryNumbersUnitTest.java b/java-numbers-2/src/test/java/com/baeldung/binarynumbers/BinaryNumbersUnitTest.java new file mode 100644 index 0000000000..ca6022261d --- /dev/null +++ b/java-numbers-2/src/test/java/com/baeldung/binarynumbers/BinaryNumbersUnitTest.java @@ -0,0 +1,73 @@ +package com.baeldung.binarynumbers; + +import static org.junit.Assert.assertEquals; + +import org.junit.Test; + +public class BinaryNumbersUnitTest { + + private BinaryNumbers binaryNumbers = new BinaryNumbers(); + + @Test + public void given_decimalNumber_then_returnBinaryNumber() { + assertEquals(Integer.valueOf(1000), binaryNumbers.convertDecimalToBinary(8)); + assertEquals(Integer.valueOf(10100), binaryNumbers.convertDecimalToBinary(20)); + } + + @Test + public void given_decimalNumber_then_convertToBinaryNumber() { + assertEquals("1000", Integer.toBinaryString(8)); + assertEquals("10100", Integer.toBinaryString(20)); + } + + @Test + public void given_binaryNumber_then_ConvertToDecimalNumber() { + assertEquals(8, Integer.parseInt("1000", 2)); + assertEquals(20, Integer.parseInt("10100", 2)); + } + + @Test + public void given_binaryNumber_then_returnDecimalNumber() { + assertEquals(Integer.valueOf(8), binaryNumbers.convertBinaryToDecimal(1000)); + assertEquals(Integer.valueOf(20), binaryNumbers.convertBinaryToDecimal(10100)); + } + + @Test + public void given_twoBinaryNumber_then_returnAddition() { + // adding 4 and 10 + assertEquals(Integer.valueOf(1110), binaryNumbers.addBinaryNumber(100, 1010)); + + // adding 26 and 14 + assertEquals(Integer.valueOf(101000), binaryNumbers.addBinaryNumber(11010, 1110)); + } + + @Test + public void given_twoBinaryNumber_then_returnSubtraction() { + // subtracting 16 from 25 + assertEquals(Integer.valueOf(1001), binaryNumbers.substractBinaryNumber(11001, 10000)); + + // subtracting 29 from 16, the output here is negative + assertEquals(Integer.valueOf(1101), binaryNumbers.substractBinaryNumber(10000, 11101)); + } + + @Test + public void given_binaryLiteral_thenReturnDecimalValue() { + + byte five = 0b101; + assertEquals((byte) 5, five); + + short three = 0b11; + assertEquals((short) 3, three); + + int nine = 0B1001; + assertEquals(9, nine); + + long twentyNine = 0B11101; + assertEquals(29, twentyNine); + + int minusThirtySeven = -0B100101; + assertEquals(-37, minusThirtySeven); + + } + +} From 970889ad14d80da42f3b7eff5c23f48fb17f3141 Mon Sep 17 00:00:00 2001 From: Eugen Paraschiv Date: Wed, 31 Jul 2019 12:04:14 +0300 Subject: [PATCH 107/107] minor cleanup work --- pom.xml | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/pom.xml b/pom.xml index 5b5058763d..f66250a8fd 100644 --- a/pom.xml +++ b/pom.xml @@ -10,10 +10,6 @@ parent-modules pom - - quarkus - - @@ -1589,4 +1585,5 @@ 1.16.12 1.4.197 +