How to make spring batch to catch exception and continue with work without complete job? - spring

I want to catch an exception in the item processor, do something and continue to work with the job without completing the job. And if it is possible with this to have JdbcPagingItemReader to avoid possible thread issue when reading.
Configuration:
#Configuration
#EnableJpaRepositories
#Slf4j
public class AppConfig {
private final ProcessorVerificationSkipper processorVerificationSkipper;
private final WriterVerificationSkipper writerVerificationSkipper;
private final JobBuilderFactory jobBuilderFactory;
private final StepBuilderFactory stepBuilderFactory;
private final MyProcessor myProcessor;
private final MyWriter myWriter;
private final DataSource dataSource;
public AppConfig (
JobBuilderFactory jobBuilderFactory,
StepBuilderFactory stepBuilderFactory,
MyProcessor myProcessor,
MyWriter myWriter,
DataSource dataSource,
ProcessorVerificationSkipper processorVerificationSkipper,
WriterVerificationSkipper writerVerificationSkipper) {
this.processorVerificationSkipper = processorVerificationSkipper;
this.writerVerificationSkipper = writerVerificationSkipper;
this.jobBuilderFactory = jobBuilderFactory;
this.stepBuilderFactory = stepBuilderFactory;
this.myProcessor = myProcessor;
this.myWriter= myWriter;
this.dataSource = dataSource;
}
/* Without pagination
#Bean
public ItemReader<MyTable> itemReader() {
JdbcCursorItemReader contactJdbcCursorItemReader = new JdbcCursorItemReader<>();
contactJdbcCursorItemReader.setSql("SELECT * FROM MYTABLE");
contactJdbcCursorItemReader.setDataSource(dataSource);
contactJdbcCursorItemReader.setRowMapper(new BeanPropertyRowMapper<>(MyTable.class));
return contactJdbcCursorItemReader;
}*/
// with pagination
#Bean
public JdbcPagingItemReader<MyTable> itemReader() throws Exception {
return new JdbcPagingItemReaderBuilder<Object>()
.dataSource(dataSource)
.saveState(false)
.queryProvider(queryProvider())
.rowMapper(new BeanPropertyRowMapper<>(MyTable.class))
.pageSize(10)
.fetchSize(10)
.build();
}
#Bean
public PagingQueryProvider queryProvider() throws Exception {
SqlPagingQueryProviderFactoryBean provider = new SqlPagingQueryProviderFactoryBean();
provider.setDataSource(dataSource);
provider.setSelectClause("SELECT *");
provider.setFromClause("FROM MYTABLE");
provider.setSortKey("ID");
return (PagingQueryProvider)provider.getObject();
}
#Bean
TaskExecutor taskExecutorStepPush() {
ThreadPoolTaskExecutor taskExecutor = new ThreadPoolTaskExecutor();
taskExecutor.setCorePoolSize(2);
taskExecutor.setMaxPoolSize(20);
taskExecutor.setQueueCapacity(4);
taskExecutor.setAllowCoreThreadTimeOut(true);
taskExecutor.setWaitForTasksToCompleteOnShutdown(true);
return taskExecutor;
}
#Bean
public Step step() throws Exception {
DefaultTransactionAttribute attribute = new DefaultTransactionAttribute();
attribute.setPropagationBehavior(Propagation.REQUIRED.value());
attribute.setIsolationLevel(Isolation.READ_COMMITTED.value());
// return
SimpleStepBuilder<MyTable, MyTable> builder =
(SimpleStepBuilder<MyTable, MyTable>)stepBuilderFactory.get("stepName")
.<MyTable, MyTable >chunk(10)
.reader(itemReader())
.processor(myProcessor)
.faultTolerant()
.skipLimit(Integer.parseInt(env.getProperty(CHUNK_SIZE)))
.skip(Exception.class)
.skipPolicy(processorVerificationSkipper)
.writer(myWriter)
.faultTolerant()
.skip(Exception.class)
.skipPolicy(writerVerificationSkipper)
.noRetry(Exception.class)
.noRollback(Exception.class)
.transactionAttribute(attribute);
return builder.build();
}
ProcessorVerificationSkipper.java
#Component
public class ProcessorVerificationSkipper implements SkipPolicy {
#Override
public boolean shouldSkip(Throwable throwable, int i) throws SkipLimitExceededException {
return true;
}
}
WriterVerificationSkipper.java
#Component
public class WriterVerificationSkipper implements SkipPolicy {
#Override
public boolean shouldSkip(Throwable throwable, int i) throws SkipLimitExceededException {
return true;
}
}
MyTable.java
#Getter
#Setter
#Entity(name = "MYTABLE")
public class MyTable{
#Id
#Column(name = "ID", nullable = false, precision = 0)
private Long sourceId;
#Basic
#Column(name = "A", nullable = true, length = 10)
private String a;
}
application.properties:
spring.batch.job.enabled=false
job.delay.fixed=120000
## Actuator When to show full health details.
management.endpoint.health.show-details=always
spring.main.allow-bean-definition-overriding=true
## Actuator - Endpoint IDs that should be included or '*' for all.
management.endpoints.web.exposure.include=*
management.endpoints.web.exposure.exclude=shutdown,flyway
java.naming.factory.initial=weblogic.jndi.WLInitialContextFactory
spring.datasource.jndi-name=jdbc/MyDS
spring.datasource.driver-class-name=oracle.jdbc.OracleDriver
spring.datasource.auto-commit=false
spring.jpa.show-sql=true
spring.jpa.properties.hibernate.show_sql=true
spring.jpa.properties.hibernate.use_sql_comments=true
spring.jpa.properties.hibernate.format_sql=true
logging.level.org.hibernate.SQL=DEBUG
logging.level.org.hibernate.type.descriptor.sql.BasicBinder=TRACE
MyProcessor.java:
#Slf4j
#Component
public class MyProcessor implements ItemProcessor<MyTable, MyTable> {
#Override
public Object process(MyTable myTable) {
return doSomething(myTable);
}
private Object doSomething(MyTable myTable) {
try {
myTable.setA("a");
// do something
}
catch(Exception1 e) {
myTable.setA("e1");
}
catch(Exception e) {
myTable.setA("e2");
}
return object;
}
}
MyWriter.java
#Component
public class MyWriter implements ItemWriter<MyTable> {
private final NamedParameterJdbcTemplate namedParameterJdbcTemplate;
public DocumentWriter(NamedParameterJdbcTemplate namedParameterJdbcTemplate) {
this.namedParameterJdbcTemplate = namedParameterJdbcTemplate;
}
#Override
public void write(List<? extends MyTable> list) {
SqlParameterSource[] batch = SqlParameterSourceUtils.createBatch(list.toArray());
int[] updateCounts = namedParameterJdbcTemplate.batchUpdate("UPDATE MYTABLE SET A = :a, batch);
}
pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.9.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.myapp</groupId>
<artifactId>my-app</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>war</packaging>
<properties>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven-compiler-plugin.version>3.8.0</maven-compiler-plugin.version>
<oracle-ojdbc8.version>12.2.0.1</oracle-ojdbc8.version>
<maven-jaxws-plugin.version>2.5</maven-jaxws-plugin.version>
<maven-jaxb2-plugin.version>2.4</maven-jaxb2-plugin.version>
<jupiter.version>5.5.0</jupiter.version>
<mockito.version>2.23.0</mockito.version>
<maven-surefire-plugin.version>2.22.1</maven-surefire-plugin.version>
<maven-war-plugin.version>3.2.2</maven-war-plugin.version>
<weblogic-wlclient.version>12.1.1</weblogic-wlclient.version>
<lombok.version>1.16.20</lombok.version>
<oracle-ojdbc.version>12.2.0.1</oracle-ojdbc.version>
<appache.http-client.version>4.5.9</appache.http-client.version>
<mockito.version>3.0.0</mockito.version>
</properties>
<dependencies>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-nop</artifactId>
<version>1.7.28</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
</dependency>
<dependency>
<groupId>commons-collections</groupId>
<artifactId>commons-collections</artifactId>
<version>3.2.1</version>
</dependency>
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.6</version>
</dependency>
<dependency>
<groupId>com.oracle.jdbc</groupId>
<artifactId>ojdbc8</artifactId>
<version>12.2.0.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-batch</artifactId>
</dependency>
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
<version>${appache.http-client.version}</version>
<exclusions>
<exclusion>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
</dependencies>
<profiles>
</profiles>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven-compiler-plugin.version}</version>
<configuration>
<source>${java.version}</source>
<target>${java.version}</target>
</configuration>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>2.1.3.RELEASE</version>
</plugin>
<plugin>
<artifactId>maven-surefire-plugin</artifactId>
<version>${maven-surefire-plugin.version}</version>
<configuration>
<classpathDependencyExcludes>
<classpathDependencyExcludes>ch.qos.logback:logback-classic</classpathDependencyExcludes>
</classpathDependencyExcludes>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>${maven-war-plugin.version}</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
<archive>
<index>true</index>
<manifest>
<addDefaultSpecificationEntries>true</addDefaultSpecificationEntries>
<addClasspath>true</addClasspath>
</manifest>
<manifestEntries>
<Implementation-Version>${project.version}</Implementation-Version>
<Implementation-Vendor-Id>${project.groupId}</Implementation-Vendor-Id>
<Implementation-URL>${project.url}</Implementation-URL>
<Build-Time>${maven.build.timestamp}</Build-Time>
</manifestEntries>
</archive>
</configuration>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<goals>
<goal>build-info</goal>
</goals>
<configuration>
<additionalProperties>
<version>${project.version}(${build.number})</version>
<Implementation-Version>${project.version}(${build.number})</Implementation-Version>
<BuildNumber>${build.number}</BuildNumber>
<BuildURL>${build.url}</BuildURL>
</additionalProperties>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
With this when an exception occurs job finished as COMPLETED which I don't want. I want to go for all selected records to the end, no matter of exceptions, just to set the value of the property depending on the type of exception.
Is this possible?
How to configure a job?

Related

Parse csv file by using Spring Batch and print it on console in spring Boot

My goal of the Project :
I have to read csv file by using Spring Batch and extract the specific column information like (Column Name :"msdin") "msdin" can print it on console. But my application is showing failed to start the application.
Well it is asking me to configure the data Source.Why we need to configure the data source in case of spring batch if my requirement is to read the csv file and print it on console.
I tried to identify the issues but not able to resolve. Can anybody help me how to resolve this issues?
Domain Class
public class Customer implements Serializable {
private Long id_type;
private String id_number;
private String customer_name;
private String email_address;
private LocalDate birthday;
private String citizenship;
private String address;
private Long msisdn;
private LocalDate kyc_date;
private String kyc_level;
private String goalscore;
private String mobile_network;
public Long getId_type() {
return id_type;
}
public void setId_type(Long id_type) {
this.id_type = id_type;
}
public String getId_number() {
return id_number;
}
public void setId_number(String id_number) {
this.id_number = id_number;
}
public String getCustomer_name() {
return customer_name;
}
public void setCustomer_name(String customer_name) {
this.customer_name = customer_name;
}
public String getEmail_address() {
return email_address;
}
public void setEmail_address(String email_address) {
this.email_address = email_address;
}
public LocalDate getBirthday() {
return birthday;
}
public void setBirthday(LocalDate birthday) {
this.birthday = birthday;
}
public String getCitizenship() {
return citizenship;
}
public void setCitizenship(String citizenship) {
this.citizenship = citizenship;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public Long getMsisdn() {
return msisdn;
}
public void setMsisdn(Long msisdn) {
this.msisdn = msisdn;
}
public LocalDate getKyc_date() {
return kyc_date;
}
public void setKyc_date(LocalDate kyc_date) {
this.kyc_date = kyc_date;
}
public String getKyc_level() {
return kyc_level;
}
public void setKyc_level(String kyc_level) {
this.kyc_level = kyc_level;
}
public String getGoalscore() {
return goalscore;
}
public void setGoalscore(String goalscore) {
this.goalscore = goalscore;
}
public String getMobile_network() {
return mobile_network;
}
public void setMobile_network(String mobile_network) {
this.mobile_network = mobile_network;
}
}
BatchConfiguration class
#Configuration
#EnableBatchProcessing
public class BatchConfiguration {
#Autowired
public JobBuilderFactory jobBuilderFactory;
#Autowired
public StepBuilderFactory stepBuilderFactory;
#Value("classPath:/data/gcash.csv")
private Resource inputResource;
public ItemReader<Customer> itemReader() {
FlatFileItemReader<Customer> customerItemReader = new FlatFileItemReader<>();
customerItemReader.setLineMapper(linemapper());
customerItemReader.setLinesToSkip(1);
customerItemReader.setResource(inputResource);
return customerItemReader;
}
#Bean
public LineMapper<Customer> linemapper() {
DefaultLineMapper<Customer> linemapper = new DefaultLineMapper<>();
final DelimitedLineTokenizer tokenizer = new DelimitedLineTokenizer();
tokenizer.setDelimiter(";");
tokenizer.setStrict(false);
tokenizer.setNames(new String[] { "id_type", "id_number", "customer_name", "email_address", "birthday",
"citizenship", "address", "msisdn", "kyc_date", "kyc_level", "goalscore", "mobile_network" });
linemapper.setFieldSetMapper(new BeanWrapperFieldSetMapper<Customer>() {
{
setTargetType(Customer.class);
}
});
return linemapper;
}
}
Error Stack
Error starting ApplicationContext. To display the conditions report re-run your application with 'debug' enabled.
2021-04-27 11:05:46.235 ERROR 22368 --- [ restartedMain] o.s.b.d.LoggingFailureAnalysisReporter :
***************************
APPLICATION FAILED TO START
***************************
Description:
Failed to configure a DataSource: 'url' attribute is not specified and no embedded datasource could be configured.
Reason: Failed to determine a suitable driver class
Action:
Consider the following:
If you want an embedded database (H2, HSQL or Derby), please put it on the classpath.
If you have database settings to be loaded from a particular profile you may need to activate it (no profiles are currently active).
pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.4.3</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<groupId>com.gcash.milo</groupId>
<artifactId>GCash_Milo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>GCash_Milo</name>
<description>Developing Milo project for GCash banking application.
</description>
<properties>
<java.version>8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<scope>runtime</scope>
</dependency>
<!-- https://mvnrepository.com/artifact/commons-io/commons-io -->
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.5</version>
</dependency>
<dependency>
<groupId>com.opencsv</groupId>
<artifactId>opencsv</artifactId>
<version>4.0</version>
</dependency>
<dependency>
<groupId>com.jcraft</groupId>
<artifactId>jsch</artifactId>
<version>0.1.54</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
</dependency>
<dependency>
<groupId>joda-time</groupId>
<artifactId>joda-time</artifactId>
<version>2.10</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-integration</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-batch</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.integration</groupId>
<artifactId>spring-integration-sftp</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.integration</groupId>
<artifactId>spring-integration-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.19.1</version>
<configuration>
<testFailureIgnore>true</testFailureIgnore>
</configuration>
</plugin>
</plugins>
</build>
</project>
in your spring boot application class, add the following snippet to #SpringBootApplication annotation:
#SpringBootApplication(exclude = {DataSourceAutoConfiguration.class })
#SpringBootApplcation annotation uses #EnableAutoConfiguration, which expects a datasource to be configured

Springboot app deployed in CloudFoundry - Get and Post operation on db fail

I am building a sample Spring application that will expose a REST
API to get and post data to a table in a database. Building the basic stuff.
I am using PostgreSQL for the data source in Cloud Foundry.
The GET API which returns a string works fine. The API which does POST returns 404 Not Found. The API which returns the entries in the table throws an exception.
Type Exception Report
Message Request processing failed; nested exception is org.springframework.orm.jpa.JpaSystemException: Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.6.2.v20151217-774c696): org.eclipse.persistence.exceptions.DatabaseException
Description:
The server encountered an unexpected condition that prevented it from fulfilling the request.
Exception
org.springframework.web.util.NestedServletException: Request processing failed; nested exception is org.springframework.orm.jpa.JpaSystemException: Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.6.2.v20151217-774c696): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: org.postgresql.util.PSQLException: ERROR: syntax error at or near "GROUP"
++++++++++++++++++++++++++++++++++++++++++++++++++++++++
#Configuration
#EnableJpaRepositories(basePackageClasses =
CustomerFeedbackRepository.class)
#Profile("cloud")
public class CloudDatabaseConfig extends AbstractCloudConfig {
#Bean
public DataSource dataSource() {
List<String> dataSourceNames =
Arrays.asList("BasicDbcpPooledDataSourceCreator","TomcatJdbcPooledDataSourceCreator","HikariCpPooledDataSourceCreator","TomcatDbcpPooledDataSourceCreator");
DataSourceConfig dbConfig = new DataSourceConfig(dataSourceNames);
return connectionFactory().dataSource(dbConfig);
}
#Bean(name = "entityManagerFactory")
public LocalContainerEntityManagerFactoryBean entityManagerFactory(DataSource dataSource) {
return EntityManagerFactoryProvider.get(dataSource, CustomerFeedback.class.getPackage().getName());
}
#Bean(name = "transactionManager")
public JpaTransactionManager transactionManager(EntityManagerFactory entityManagerFactory) {
return new JpaTransactionManager(entityManagerFactory);
}
}
#PostMapping("/capturecf")
#RequestMapping(value ="CustomerFeedback", method = RequestMethod.POST)
public CustomerFeedback addFeedback(#RequestBody CustomerFeedback custfeedback)
{
return customerfeedbackrepo.save(custfeedback);
}
#PostMapping("/captureua")
#RequestMapping(value = "UsageActivity", method = RequestMethod.POST)
public UsageActivity addUsageTracking(#Valid #RequestBody UsageActivity usageActivity)
{
return usageactivityrepository.save(usageActivity);
}
#GetMapping("/usageactivity")
public List<UsageActivity> getAllNotes() {
return usageactivityrepository.findAll();`enter code here`
}
<dependencies>
<!-- APIs for servlets and injection -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.0.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.inject</groupId>
<artifactId>javax.inject</artifactId>
<version>1</version>
</dependency>
<!-- Spring Framework and Spring WebMVC -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${spring.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${spring.version}</version>
</dependency>
<!-- Logging library -->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>${logback.version}</version>
</dependency>
<dependency>
<groupId>com.sap.hcp.cf.logging</groupId>
<artifactId>cf-java-logging-support-logback</artifactId>
<version>${sap.logging.version}</version>
</dependency>
<dependency>
<groupId>com.sap.hcp.cf.logging</groupId>
<artifactId>cf-java-logging-support-servlet</artifactId>
<version>${sap.logging.version}</version>
</dependency>
<!-- JSON conversion -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.8.1</version>
</dependency>
<!-- Actuator for adding management endpoints -->
<dependency>
<groupId> org.springframework.boot</groupId>
<artifactId>spring-boot-actuator</artifactId>
<version>1.2.5.RELEASE</version>
</dependency>
<!-- Bean validation (#NotNull etc.) -->
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator</artifactId>
<version>5.2.1.Final</version>
</dependency>
<!-- MethodValidationPostProcessor relies on Expression Language -->
<dependency>
<groupId>javax.el</groupId>
<artifactId>javax.el-api</artifactId>
<version>3.0.1-b04</version>
</dependency>
<!-- Spring Cloud Connector -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-spring-service-connector</artifactId>
<version>1.2.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-cloudfoundry-connector</artifactId>
<version>1.2.1.RELEASE</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-jpa</artifactId>
<version>1.9.2.RELEASE</version>
<exclusions>
<exclusion>
<!-- We need spring-core 4.2 or later, but spring-data includes 4.1.9 -->
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- EclipseLink as JPA implementation -->
<dependency>
<groupId>org.eclipse.persistence</groupId>
<artifactId>org.eclipse.persistence.jpa</artifactId>
<version>2.6.2</version>
</dependency>
<!-- PostgreSQL database implementations -->
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>9.4-1206-jdbc41</version>
<scope>runtime</scope>
</dependency>
<!-- connection pooling -->
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-dbcp2</artifactId>
<version>2.1.1</version>
<scope>runtime</scope>
</dependency>
<!-- Testing -->
<dependency>
<groupId>org.hamcrest</groupId>
<artifactId>hamcrest-library</artifactId>
<version>1.3</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-core</artifactId>
<version>1.10.19</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>${spring.version}</version>
<scope>test</scope>
</dependency>
<!-- Use MockMvcResultMatchers.jsonPath to assert the JSON body -->
<dependency>
<groupId>com.jayway.jsonpath</groupId>
<artifactId>json-path</artifactId>
<version>2.2.0</version>
<scope>test</scope>
</dependency>
<!-- H2 (in-memory) database implementation -->
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>1.4.184</version>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<finalName>customerconnect</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.3</version>
<configuration>
<source>${java.version}</source>
<target>${java.version}</target>
</configuration>
</plugin>
<plugin>
<!-- Provides the application at http://localhost:8080/ using an embedded
Tomcat server with a pre-configured environment referencing the SAP proxy -->
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<version>2.2</version>
<configuration>
<port>${maven.tomcat.port}</port>
<path>/</path>
<systemProperties>
<http.proxyHost>${http.proxyHost}</http.proxyHost>
<http.proxyPort>${http.proxyPort}</http.proxyPort>
</systemProperties>
</configuration>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>findbugs-maven-plugin</artifactId>
<version>3.0.2</version>
<executions>
<execution>
<phase>verify</phase>
<goals>
<goal>findbugs</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-pmd-plugin</artifactId>
<version>3.5</version>
<executions>
<execution>
<phase>verify</phase>
<goals>
<goal>pmd</goal>
<goal>cpd</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.18.1</version>
</plugin>
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>0.7.5.201505241946</version>
<executions>
<execution>
<id>default-prepare-agent</id>
<goals>
<goal>prepare-agent</goal>
</goals>
</execution>
<execution>
<id>default-report</id>
<phase>prepare-package</phase>
<goals>
<goal>report</goal>
</goals>
</execution>
<execution>
<id>default-check</id>
<goals>
<goal>check</goal>
</goals>
<configuration>
<rules>
</rules>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
<reporting>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jxr-plugin</artifactId>
<version>2.5</version>
</plugin>
</plugins>
</reporting>
</project>
package com.sap.customerconnect.ads.repositories;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.repository.CrudRepository;
import org.springframework.stereotype.Component;
import org.springframework.stereotype.Repository;
import com.sap.customerconnect.ads.models.UsageActivity;
import com.sap.customerconnect.ads.models.UsageActivityPK;
#Component
#Repository
public interface UsageActivityRepository extends JpaRepository<UsageActivity, UsageActivityPK> {
}
package com.sap.customerconnect.ads.repositories;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.stereotype.Component;
import org.springframework.stereotype.Repository;
import com.sap.customerconnect.ads.models.CustomerFeedback;
import com.sap.customerconnect.ads.models.CustomerFeedbackPK;
#Component
#Repository
public interface CustomerFeedbackRepository extends JpaRepository<CustomerFeedback, CustomerFeedbackPK>{
}
package com.sap.customerconnect.ads.models;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.IdClass;
import javax.persistence.Table;
#IdClass(UsageActivityPK.class)
#Entity
#Table(name = "UsageActivity")
public class UsageActivity {
#Id
#Column(name = "PRODUCT_ID")
private String ProductId;
#Id
#Column(name = "CUSTOMER_ID")
private String CustomerId;
#Id
#Column(name = "SCREEN_ID")
private String ScreenId;
#Column(name = "GROUP")
private String Group;
#Column(name = "ACTION")
private String Action;
#Column(name = "DESCRIPTION")
private String Description;
#Column(name = "COUNT")
private Integer Count;
public UsageActivity() {
}
public String getProductId() {
return ProductId;
}
public void setProductId(String productId) {
ProductId = productId;
}
public String getCustomerId() {
return CustomerId;
}
public void setCustomerId(String customerId) {
CustomerId = customerId;
}
public String getScreenId() {
return ScreenId;
}
public void setScreenId(String screenId) {
ScreenId = screenId;
}
public String getGroup() {
return Group;
}
public void setGroup(String group) {
Group = group;
}
public String getAction() {
return Action;
}
public void setAction(String action) {
Action = action;
}
public String getDescription() {
return Description;
}
public void setDescription(String description) {
Description = description;
}
public Integer getCount() {
return Count;
}
public void setCount(Integer count) {
Count = count;
}
public UsageActivity(String productId, String customerId, String screenId, String group, String action,
String description, Integer count) {
super();
ProductId = productId;
CustomerId = customerId;
ScreenId = screenId;
Group = group;
Action = action;
Description = description;
Count = count;
}
}
package com.sap.customerconnect.ads.models;
import java.io.Serializable;
import javax.persistence.Column;
import javax.persistence.Embeddable;
#Embeddable
public class UsageActivityPK implements Serializable{
private static final long serialVersionUID = 1L;
#Column(name = "PRODUCT_ID")
private String ProductId;
#Column(name = "CUSTOMER_ID")
private String CustomerId;
#Column(name = "SCREEN_ID")
private String ScreenId;
}
The POST and GET operations on the repository does not work.

Spring Boot #Controller not working when deploy on Tomcat standalone

I have an Spring Boot Application + ThymeLeaf, with #RestController and #Controller, everything work fine with tomcat embedded but when I deploy my app with war file to Tomcat 8.5 #Controller class not working #RestController is working fine, when I go to any page with controller use #Controller I have 404 error.
This is my pom.xml:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.example.boot</groupId>
<artifactId>boot-parent</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>api</artifactId>
<packaging>war</packaging>
<properties>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
<version>2.1.2.RELEASE</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.springframework/spring-context -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
</dependency>
<dependency>
<groupId>com.example.boot</groupId>
<artifactId>web</artifactId>
<version>${project.version}</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.14</version>
<scope>provided</scope>
</dependency>
<!-- https://mvnrepository.com/artifact/mysql/mysql-connector-java -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>[5.0.2,5.1.47)</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-cas</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-ldap</artifactId>
<version>${spring-security.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
<scope>provided</scope>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<fork>true</fork>
<skip>false</skip>
</configuration>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.8</source>
<target>1.8</target>
<showDeprecation>true</showDeprecation>
<showWarnings>true</showWarnings>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<configuration>
<packagingExcludes>WEB-INF/lib/tomcat-*.jar</packagingExcludes>
<warName>skillinventory</warName>
</configuration>
</plugin>
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<executions>
<execution>
<id>copy-resources</id>
<phase>validate</phase>
<goals>
<goal>copy-resources</goal>
</goals>
<configuration>
<outputDirectory>${project.build.directory}/classes/resources/</outputDirectory>
<resources>
<resource>
<directory>${project.parent.basedir}/web-si/src/main/web/dist/FrontEnd/</directory>
</resource>
</resources>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
This is my Spring Boot app class:
#SpringBootApplication
#EnableScheduling
#PropertySource("classpath:application.properties")
public class Application extends SpringBootServletInitializer {
#Value("${cas.service}")
private String service;
#Value("${cas.loginUrl}")
private String loginUrl;
#Value("${cas.cas30ServiceTicketValidator}")
private String cas30ServiceTicketValidator;
#Value("${cas.createAuthorityList}")
private String createAuthorityList;
#Value("${cas.key}")
private String key;
#Value("${cas.logoutFilterLink}")
private String logoutFilterLink;
#Value("${cas.setFilterProcessesUrl}")
private String setFilterProcessesUrl;
#Value("${cas.setCasServerUrlPrefix}")
private String setCasServerUrlPrefix;
#Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
return application.sources(Application.class);
}
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
#Bean
public ServiceProperties serviceProperties() {
ServiceProperties serviceProperties = new ServiceProperties();
serviceProperties.setService(service);
serviceProperties.setSendRenew(false);
return serviceProperties;
}
#Bean
#Primary
public AuthenticationEntryPoint authenticationEntryPoint(ServiceProperties sP) {
CasAuthenticationEntryPoint entryPoint = new CasAuthenticationEntryPoint();
entryPoint.setLoginUrl(loginUrl);
entryPoint.setServiceProperties(sP);
return entryPoint;
}
#Bean
public TicketValidator ticketValidator() {
return new Cas30ServiceTicketValidator(cas30ServiceTicketValidator);
}
#Bean
public CasAuthenticationProvider casAuthenticationProvider() {
CasAuthenticationProvider provider = new CasAuthenticationProvider();
provider.setAuthenticationUserDetailsService(customUserDetailsService());
provider.setKey(key);
return provider;
}
#Bean
public AuthenticationUserDetailsService<CasAssertionAuthenticationToken> customUserDetailsService() {
return token -> {
AttributePrincipal principal = token.getAssertion().getPrincipal();
String name = principal.getName();
return new User(name, "pwd", AuthorityUtils.createAuthorityList(createAuthorityList));
};
}
#Bean
public SecurityContextLogoutHandler securityContextLogoutHandler() {
return new SecurityContextLogoutHandler();
}
#Bean
public LogoutFilter logoutFilter() {
LogoutFilter logoutFilter = new LogoutFilter(logoutFilterLink, securityContextLogoutHandler());
logoutFilter.setFilterProcessesUrl(setFilterProcessesUrl);
return logoutFilter;
}
#Bean
public SingleSignOutFilter singleSignOutFilter() {
SingleSignOutFilter singleSignOutFilter = new SingleSignOutFilter();
singleSignOutFilter.setCasServerUrlPrefix(setCasServerUrlPrefix);
singleSignOutFilter.setIgnoreInitConfiguration(true);
return singleSignOutFilter;
}
#EventListener
public SingleSignOutHttpSessionListener singleSignOutHttpSessionListener(HttpSessionEvent event) {
return new SingleSignOutHttpSessionListener();
}
}
My security config:
#EnableWebSecurity
#Configuration
public class SpringSecurityConfig extends WebSecurityConfigurerAdapter {
private AuthenticationProvider authenticationProvider;
private AuthenticationEntryPoint authenticationEntryPoint;
#Autowired
public SpringSecurityConfig(CasAuthenticationProvider
casAuthenticationProvider,
AuthenticationEntryPoint authenticationEntryPoint) {
this.authenticationProvider = casAuthenticationProvider;
this.authenticationEntryPoint = authenticationEntryPoint;
}
#Override
protected void configure(HttpSecurity http) throws Exception {
http
.csrf().disable()
.authorizeRequests()
.antMatchers("/v1/datas/**")
.permitAll()
.and()
.authorizeRequests()
.regexMatchers("/")
.authenticated()
.and()
.authorizeRequests()
.regexMatchers("/")
.permitAll()
.and()
.httpBasic()
.authenticationEntryPoint(authenticationEntryPoint);
}
#Override
protected void configure(AuthenticationManagerBuilder auth) throws
Exception {
auth.authenticationProvider(authenticationProvider);
}
#Override
protected AuthenticationManager authenticationManager() throws Exception {
return new ProviderManager(Arrays.asList(authenticationProvider));
}
#Bean
public CasAuthenticationFilter casAuthenticationFilter(ServiceProperties serviceProperties) throws Exception {
CasAuthenticationFilter filter = new CasAuthenticationFilter();
filter.setServiceProperties(serviceProperties);
filter.setAuthenticationManager(authenticationManager());
return filter;
}
My controller with #Controller :
#Controller
public class ManagerDataController {
#Value("${theme.root}")
private String themeRoot;
#RequestMapping(value = "/hr/skilldatas", method = RequestMethod.GET)
public String goProgessData(Model model) {
model.addAttribute("themeRoot", themeRoot);
return "data-process";
}
#RequestMapping(value = "/hr/datas", method = RequestMethod.GET)
public String goDataManager(Model model) {
model.addAttribute("themeRoot", themeRoot);
return "datamanager";
}
}
I don't know why it working fine with tomcat embeded but tomcat standalone?
It turn out that because I declare thymeleaf dependency scope is provided, it not Spring false, after I change scope to compile it working now.

Spring 5 MVC - InternalResourceViewResolver and Spring Security

I'm learning Spring, and I've got stuck on some issues i can't resolve. I run it on a GlassFish Server.
I'm implementing a simple WebMvcConfigurer which has an InternalResourceViewResolver, it looks like this:
#Configuration
#EnableWebMvc
public class WebMvcConfig implements WebMvcConfigurer {
#Bean
public InternalResourceViewResolver resolver() {
InternalResourceViewResolver resolver = new InternalResourceViewResolver();
resolver.setViewClass(JstlView.class);
resolver.setPrefix("/WEB-INF/views/");
resolver.setSuffix(".jsp");
return resolver;
}
#Bean
public MessageSource messageSource() {
ResourceBundleMessageSource source = new ResourceBundleMessageSource();
source.setBasename("messages");
return source;
}
#Override
public Validator getValidator() {
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
validator.setValidationMessageSource(messageSource());
return validator;
}
}
and my Controller:
#WebServlet(value = "/")
#Controller
public class HomeController extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.getRequestDispatcher("index.jsp").forward(request,response);
}
}
I would assume that when I run the app, it would open the index.jsp file, but it doesn't, instead I get a 404. When I change it to
request.getRequestDispatcher("/WEB-INF/views/index.jsp").forward(request,response);
it opens it.
Also, I've followed the documentation on Spring Security and implemented simple security. From my understanding, every request should be authenticated and it should redirect the user to a login page, but it doesn't.
Here is the code:
#EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
#Bean
public UserDetailsService userDetailsService() {
InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
manager.createUser(User.withUsername("user").password("user").roles("USER").build());
manager.createUser(User.withUsername("admin").password("admin").roles("USER", "ADMIN").build());
return manager;
}
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.anyRequest().authenticated()
.and()
.formLogin()
.and()
.httpBasic();
}
}
public class WebAppInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected String[] getServletMappings() {
return new String[]{"/"};
}
#Override
protected Class<?>[] getRootConfigClasses() {
return new Class<?>[]{ApplicationConfig.class, WebSecurityConfig.class};
}
#Override
protected Class<?>[] getServletConfigClasses() {
return new Class[] { WebMvcConfig.class };
}
#Override
protected Filter[] getServletFilters() {
CharacterEncodingFilter characterEncodingFilter = new CharacterEncodingFilter();
characterEncodingFilter.setEncoding("UTF-8");
characterEncodingFilter.setForceEncoding(true);
// you might want to add stuff to enable spring security
return new Filter[]{characterEncodingFilter};
}
}
#Configuration
public class ApplicationConfig {
#Bean
public static PropertySourcesPlaceholderConfigurer propertySourcesPlaceholderConfigurer() {
return new PropertySourcesPlaceholderConfigurer();
}
}
I'm suspecting that the issues are related, but can't see what I'm missing here. When i change the path in the Controller as mentioned above, I do not get redirected to the login page.
Here is the pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.vives</groupId>
<artifactId>spring-mvc-quickstart</artifactId>
<version>1.0-SNAPSHOT</version>
<packaging>war</packaging>
<name>spring-mvc-quickstart</name>
<properties>
<endorsed.dir>${project.build.directory}/endorsed</endorsed.dir>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<java-version>1.8</java-version>
<!-- Override Spring version -->
<spring.version>5.0.0.RELEASE</spring.version>
<jackson.version>2.9.1</jackson.version>
<thymeleaf-extras-java8time-version>3.0.1.RELEASE</thymeleaf-extras-java8time-version>
<!-- AssertJ is not a part of Spring IO platform, so the version must be provided explicitly -->
<assertj-core-version>3.8.0</assertj-core-version>
</properties>
<dependencies>
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-web-api</artifactId>
<version>7.0</version>
<scope>provided</scope>
</dependency>
<!-- Spring -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.0.1.RELEASE</version>
</dependency>
<!-- Security -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-config</artifactId>
<version>4.2.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-web</artifactId>
<version>4.2.3.RELEASE</version>
</dependency>
<dependency>
<groupId>jstl</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
<version>5.0.1.RELEASE</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.9.2</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-entitymanager</artifactId>
<!-- Avoid issue #72 Could not initialize class org.thymeleaf.templateresolver.ServletContextTemplateResolver due to 'validation is not supported' -->
<exclusions>
<exclusion>
<artifactId>pull-parser</artifactId>
<groupId>pull-parser</groupId>
</exclusion>
</exclusions>
<version>5.2.9.Final</version>
</dependency>
</dependencies>
<repositories>
<repository>
<id>spring-release</id>
<name>Spring Release Repository</name>
<url>https://repo.spring.io/release</url>
</repository>
</repositories>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.1</version>
<configuration>
<source>1.7</source>
<target>1.7</target>
<compilerArguments>
<endorseddirs>${endorsed.dir}</endorseddirs>
</compilerArguments>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.3</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<version>2.6</version>
<executions>
<execution>
<phase>validate</phase>
<goals>
<goal>copy</goal>
</goals>
<configuration>
<outputDirectory>${endorsed.dir}</outputDirectory>
<silent>true</silent>
<artifactItems>
<artifactItem>
<groupId>javax</groupId>
<artifactId>javaee-endorsed-api</artifactId>
<version>7.0</version>
<type>jar</type>
</artifactItem>
</artifactItems>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
Can someone explain to me what is happening or what I'm doing wrong?
I've finally resolved the issues I had.
As for security, i forgot to add SecurityWebApplicationInitializer and as for navigation, this link helped me.

How to configure Spring Security + OAuth2

I'm building a REST Application using Spring Security + OAuth2.
If i use
curl -u clientapp:123456 -X POST http://localhost:8080/oauth/token -H "Accept:application/json" -d "username=admin&password=123456&grant_type=password"
I do not get the response
But if i add the application contextpath i am able to.
curl -u clientapp:123456 -X POST http://localhost:8080/demoproject/oauth/token -H "Accept:application/json" -d "username=admin&password=123456&grant_type=password"
Also getting success response
{"access_token":"dc86814f-94a5-43b7-9e8d-73b143b28c64","token_type":"bearer","re
fresh_token":"09c7e31e-b8e7-4bf2-a839-9e8d4702b822","expires_in":2837,"scope":"r
ead write"}
But when use the access token to request a secured API, I'm getting login page as response because of Spring Security Configuration.
Here is my Configration:
WebMvcInitializer.java
import org.springframework.web.servlet.support.AbstractAnnotationConfigDispatcherServletInitializer;
public class WebMvcInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
#Override
protected Class<?>[] getRootConfigClasses() {
return new Class[] {
WebConfig.class,
WebSecurityConfiguration.class,
Oauth2ServerConfiguration.AuthConfig.class };
}
#Override
protected Class<?>[] getServletConfigClasses() {
return null;
}
#Override
protected String[] getServletMappings() {
return new String[] { "/" };
}
}
WebSecurityConfiguration .java
#Configuration
#EnableWebSecurity
#EnableWebMvcSecurity
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {
#Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.inMemoryAuthentication().withUser("admin").password("123456").roles("USER", "ADMIN");
}
#Override
#Bean
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
#Bean
public PasswordEncoder passwordEncoder() {
PasswordEncoder encoder = new BCryptPasswordEncoder();
return encoder;
}
#Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests().anyRequest().hasRole("USER");
//super.configure(http);
}
}
WebConfig.java
#Configuration
#EnableWebMvc
#ComponentScan(basePackages = "edu.demo.springoauth")
public class WebConfig extends WebMvcConfigurerAdapter {
#Bean
public ViewResolver viewResolver() {
InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
viewResolver.setViewClass(JstlView.class);
viewResolver.setPrefix("/WEB-INF/views/");
viewResolver.setSuffix(".jsp");
return viewResolver;
}
#Override
public void addResourceHandlers(ResourceHandlerRegistry registry) {
registry.addResourceHandler("/static/**").addResourceLocations("/static/");
}
}
SecurityInitializer.java
import org.springframework.security.web.context.AbstractSecurityWebApplicationInitializer;
public class SecurityInitializer extends AbstractSecurityWebApplicationInitializer {
}
Oauth2ServerConfiguration.java
#Configuration
public class Oauth2ServerConfiguration {
private static final String SERVER_RESOURCE_ID = "oauthdemo";
private static InMemoryTokenStore tokenStore = new InMemoryTokenStore();
#Configuration
#EnableResourceServer
protected static class ResourceServer extends ResourceServerConfigurerAdapter {
#Override
public void configure(ResourceServerSecurityConfigurer resources) throws Exception {
resources.resourceId(SERVER_RESOURCE_ID);
}
#Override
#Order(Ordered.HIGHEST_PRECEDENCE)
public void configure(HttpSecurity http) throws Exception {
http.requestMatchers().antMatchers("/oauth/**" , "/noauth/**" , "/api/r/**")
.and()
.authorizeRequests().antMatchers("/api/w/**").hasAuthority("ROLE_USER");
}
}
#Configuration
#EnableAuthorizationServer
protected static class AuthConfig extends AuthorizationServerConfigurerAdapter {
#Autowired
#Qualifier("authenticationManagerBean")
private AuthenticationManager authenticationManager;
#Override
public void configure(AuthorizationServerSecurityConfigurer oauthServer) throws Exception {
oauthServer.allowFormAuthenticationForClients();
}
#Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
endpoints.authenticationManager(authenticationManager);
}
#Override
public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
clients.inMemory().withClient("clientapp").authorizedGrantTypes("password","client_credentials", "authorization_code", "refresh_token", "implicit")
.authorities("ROLE_CLIENT", "ROLE_TRUSTED_CLIENT", "ROLE_USER")
.scopes("read", "write").resourceIds(SERVER_RESOURCE_ID).secret("123456").accessTokenValiditySeconds(3600);
}
#Bean
#Primary
public DefaultTokenServices tokenServices() {
DefaultTokenServices tokenServices = new DefaultTokenServices();
tokenServices.setSupportRefreshToken(true);
tokenServices.setTokenStore(tokenStore);
return tokenServices;
}
}
}
Pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>edu.demo</groupId>
<artifactId>springoauth</artifactId>
<name>springoauth</name>
<packaging>war</packaging>
<version>1.0.0-BUILD-SNAPSHOT</version>
<properties>
<build.profile.id>dev</build.profile.id>
<java-version>1.8</java-version>
<spring.security.oauth2.version>2.0.1.RELEASE</spring.security.oauth2.version>
<spring-security.version>3.2.4.RELEASE</spring-security.version>
<spring.version>4.0.5.RELEASE</spring.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-framework-bom</artifactId>
<version>${spring.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>3.8.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.7</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-web</artifactId>
<version>${spring-security.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-core</artifactId>
<version>${spring-security.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-config</artifactId>
<version>${spring-security.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.security.oauth</groupId>
<artifactId>spring-security-oauth2</artifactId>
<version>${spring.security.oauth2.version}</version>
</dependency>
<dependency>
<groupId>org.codehaus.jackson</groupId>
<artifactId>jackson-mapper-asl</artifactId>
<version>1.9.13</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
</dependency>
<dependency>
<groupId>org.apache.tomcat</groupId>
<artifactId>tomcat-dbcp</artifactId>
<version>7.0.47</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-orm</artifactId>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-core</artifactId>
<version>4.1.8.Final</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.22</version>
</dependency>
</dependencies>
<profiles>
<profile>
<id>dev</id>
<properties>
<build.profile.id>dev</build.profile.id>
</properties>
</profile>
</profiles>
<build>
<finalName>springoauth</finalName>
<filters>
<filter>profiles/${build.profile.id}/config.properties</filter>
</filters>
<resources>
<resource>
<filtering>true</filtering>
<directory>src/main/resources</directory>
<excludes>
<exclude>**/messages*.properties</exclude>
</excludes>
</resource>
<resource>
<filtering>false</filtering>
<directory>src/main/resources</directory>
<includes>
<include>**/messages*.properties</include>
</includes>
</resource>
</resources>
<plugins>
<plugin>
<artifactId>maven-eclipse-plugin</artifactId>
<version>2.9</version>
<configuration>
<additionalProjectnatures>
<projectnature>org.springframework.ide.eclipse.core.springnature</projectnature>
</additionalProjectnatures>
<additionalBuildcommands>
<buildcommand>org.springframework.ide.eclipse.core.springbuilder</buildcommand>
</additionalBuildcommands>
<downloadSources>true</downloadSources>
<downloadJavadocs>true</downloadJavadocs>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>2.5.1</version>
<configuration>
<source>${java-version}</source>
<target>${java-version}</target>
<compilerArgument>-Xlint:all</compilerArgument>
<showWarnings>true</showWarnings>
<showDeprecation>true</showDeprecation>
</configuration>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>exec-maven-plugin</artifactId>
<version>1.2.1</version>
<configuration>
<mainClass>org.test.int1.Main</mainClass>
</configuration>
</plugin>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
</plugins>
</build>
</project>
Is there something in spring configuration that I'm doing wrong?

Resources