diff --git a/.travis.yml b/.travis.yml
index 4df8a96f6d..5e2d690b4e 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -4,7 +4,7 @@ before_install:
- echo "MAVEN_OPTS='-Xmx2048M -Xss128M -XX:+CMSClassUnloadingEnabled -XX:+UseG1GC -XX:-UseGCOverheadLimit'" > ~/.mavenrc
install: skip
-script: travis_wait 60 mvn -q install
+script: travis_wait 60 mvn -q install -Pdefault
sudo: required
diff --git a/apache-avro/pom.xml b/apache-avro/pom.xml
new file mode 100644
index 0000000000..39da518269
--- /dev/null
+++ b/apache-avro/pom.xml
@@ -0,0 +1,88 @@
+
+
+ 4.0.0
+ com.baeldung
+ apache-avro-tutorial
+ 0.0.1-SNAPSHOT
+
+
+ UTF-8
+ 3.5
+ 1.8.2
+ 1.8
+ 1.7.25
+
+
+
+ com.baeldung
+ parent-modules
+ 1.0.0-SNAPSHOT
+
+
+
+
+ junit
+ junit
+ 4.10
+ test
+
+
+ org.slf4j
+ slf4j-simple
+ ${slf4j.version}
+ compile
+
+
+ org.apache.avro
+ avro
+ ${avro.version}
+
+
+ org.apache.avro
+ avro-compiler
+ ${avro.version}
+
+
+
+ org.apache.avro
+ avro-maven-plugin
+ ${avro.version}
+
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ ${compiler-plugin.version}
+
+ ${java.version}
+ ${java.version}
+
+
+
+ org.apache.avro
+ avro-maven-plugin
+ ${avro.version}
+
+
+ schemas
+ generate-sources
+
+ schema
+ protocol
+ idl-protocol
+
+
+ ${project.basedir}/src/main/resources/
+ ${project.basedir}/src/main/java/
+
+
+
+
+
+
+
diff --git a/apache-avro/src/main/java/com/baeldung/avro/util/AvroClassGenerator.java b/apache-avro/src/main/java/com/baeldung/avro/util/AvroClassGenerator.java
new file mode 100644
index 0000000000..718b62a752
--- /dev/null
+++ b/apache-avro/src/main/java/com/baeldung/avro/util/AvroClassGenerator.java
@@ -0,0 +1,14 @@
+package com.baeldung.avro.util;
+
+import org.apache.avro.Schema;
+import org.apache.avro.compiler.specific.SpecificCompiler;
+
+import java.io.File;
+import java.io.IOException;
+
+public class AvroClassGenerator {
+ public void generateAvroClasses() throws IOException {
+ SpecificCompiler compiler = new SpecificCompiler(new Schema.Parser().parse(new File("src/main/resources/avroHttpRequest-schema.avsc")));
+ compiler.compileToDestination(new File("src/main/resources"), new File("src/main/java"));
+ }
+}
diff --git a/apache-avro/src/main/java/com/baeldung/avro/util/AvroSchemaBuilder.java b/apache-avro/src/main/java/com/baeldung/avro/util/AvroSchemaBuilder.java
new file mode 100644
index 0000000000..4a1314cd00
--- /dev/null
+++ b/apache-avro/src/main/java/com/baeldung/avro/util/AvroSchemaBuilder.java
@@ -0,0 +1,24 @@
+package com.baeldung.avro.util;
+
+
+import org.apache.avro.Schema;
+import org.apache.avro.SchemaBuilder;
+
+public class AvroSchemaBuilder {
+
+ public Schema createAvroHttpRequestSchema(){
+
+ Schema clientIdentifier = SchemaBuilder.record("ClientIdentifier").namespace("com.baeldung.avro.model")
+ .fields().requiredString("hostName").requiredString("ipAddress").endRecord();
+
+ Schema avroHttpRequest = SchemaBuilder.record("AvroHttpRequest").namespace("com.baeldung.avro.model").fields()
+ .requiredLong("requestTime")
+ .name("clientIdentifier").type(clientIdentifier).noDefault()
+ .name("employeeNames").type().array().items().stringType().arrayDefault(null)
+ .name("active").type().enumeration("Active").symbols("YES", "NO").noDefault()
+ .endRecord();
+ return avroHttpRequest;
+ }
+}
+
+
diff --git a/apache-avro/src/main/java/com/baeldung/avro/util/model/Active.java b/apache-avro/src/main/java/com/baeldung/avro/util/model/Active.java
new file mode 100644
index 0000000000..3ae0508394
--- /dev/null
+++ b/apache-avro/src/main/java/com/baeldung/avro/util/model/Active.java
@@ -0,0 +1,13 @@
+/**
+ * Autogenerated by Avro
+ *
+ * DO NOT EDIT DIRECTLY
+ */
+package com.baeldung.avro.util.model;
+@SuppressWarnings("all")
+@org.apache.avro.specific.AvroGenerated
+public enum Active {
+ YES, NO ;
+ public static final org.apache.avro.Schema SCHEMA$ = new org.apache.avro.Schema.Parser().parse("{\"type\":\"enum\",\"name\":\"Active\",\"namespace\":\"com.baeldung.avro.model\",\"symbols\":[\"YES\",\"NO\"]}");
+ public static org.apache.avro.Schema getClassSchema() { return SCHEMA$; }
+}
diff --git a/apache-avro/src/main/java/com/baeldung/avro/util/model/AvroHttpRequest.java b/apache-avro/src/main/java/com/baeldung/avro/util/model/AvroHttpRequest.java
new file mode 100644
index 0000000000..56b36050a5
--- /dev/null
+++ b/apache-avro/src/main/java/com/baeldung/avro/util/model/AvroHttpRequest.java
@@ -0,0 +1,491 @@
+/**
+ * Autogenerated by Avro
+ *
+ * DO NOT EDIT DIRECTLY
+ */
+package com.baeldung.avro.util.model;
+
+import org.apache.avro.specific.SpecificData;
+import org.apache.avro.message.BinaryMessageEncoder;
+import org.apache.avro.message.BinaryMessageDecoder;
+import org.apache.avro.message.SchemaStore;
+
+@SuppressWarnings("all")
+@org.apache.avro.specific.AvroGenerated
+public class AvroHttpRequest extends org.apache.avro.specific.SpecificRecordBase implements org.apache.avro.specific.SpecificRecord {
+ private static final long serialVersionUID = -8649010116827875312L;
+ public static final org.apache.avro.Schema SCHEMA$ = new org.apache.avro.Schema.Parser().parse("{\"type\":\"record\",\"name\":\"AvroHttpRequest\",\"namespace\":\"com.baeldung.avro.model\",\"fields\":[{\"name\":\"requestTime\",\"type\":\"long\"},{\"name\":\"clientIdentifier\",\"type\":{\"type\":\"record\",\"name\":\"ClientIdentifier\",\"fields\":[{\"name\":\"hostName\",\"type\":\"string\"},{\"name\":\"ipAddress\",\"type\":\"string\"}]}},{\"name\":\"employeeNames\",\"type\":{\"type\":\"array\",\"items\":\"string\"},\"default\":null},{\"name\":\"active\",\"type\":{\"type\":\"enum\",\"name\":\"Active\",\"symbols\":[\"YES\",\"NO\"]}}]}");
+ public static org.apache.avro.Schema getClassSchema() { return SCHEMA$; }
+
+ private static SpecificData MODEL$ = new SpecificData();
+
+ private static final BinaryMessageEncoder ENCODER =
+ new BinaryMessageEncoder(MODEL$, SCHEMA$);
+
+ private static final BinaryMessageDecoder DECODER =
+ new BinaryMessageDecoder(MODEL$, SCHEMA$);
+
+ /**
+ * Return the BinaryMessageDecoder instance used by this class.
+ */
+ public static BinaryMessageDecoder getDecoder() {
+ return DECODER;
+ }
+
+ /**
+ * Create a new BinaryMessageDecoder instance for this class that uses the specified {@link SchemaStore}.
+ * @param resolver a {@link SchemaStore} used to find schemas by fingerprint
+ */
+ public static BinaryMessageDecoder createDecoder(SchemaStore resolver) {
+ return new BinaryMessageDecoder(MODEL$, SCHEMA$, resolver);
+ }
+
+ /** Serializes this AvroHttpRequest to a ByteBuffer. */
+ public java.nio.ByteBuffer toByteBuffer() throws java.io.IOException {
+ return ENCODER.encode(this);
+ }
+
+ /** Deserializes a AvroHttpRequest from a ByteBuffer. */
+ public static AvroHttpRequest fromByteBuffer(
+ java.nio.ByteBuffer b) throws java.io.IOException {
+ return DECODER.decode(b);
+ }
+
+ @Deprecated public long requestTime;
+ @Deprecated public ClientIdentifier clientIdentifier;
+ @Deprecated public java.util.List employeeNames;
+ @Deprecated public Active active;
+
+ /**
+ * Default constructor. Note that this does not initialize fields
+ * to their default values from the schema. If that is desired then
+ * one should use newBuilder()
.
+ */
+ public AvroHttpRequest() {}
+
+ /**
+ * All-args constructor.
+ * @param requestTime The new value for requestTime
+ * @param clientIdentifier The new value for clientIdentifier
+ * @param employeeNames The new value for employeeNames
+ * @param active The new value for active
+ */
+ public AvroHttpRequest(java.lang.Long requestTime, ClientIdentifier clientIdentifier, java.util.List employeeNames, Active active) {
+ this.requestTime = requestTime;
+ this.clientIdentifier = clientIdentifier;
+ this.employeeNames = employeeNames;
+ this.active = active;
+ }
+
+ public org.apache.avro.Schema getSchema() { return SCHEMA$; }
+ // Used by DatumWriter. Applications should not call.
+ public java.lang.Object get(int field$) {
+ switch (field$) {
+ case 0: return requestTime;
+ case 1: return clientIdentifier;
+ case 2: return employeeNames;
+ case 3: return active;
+ default: throw new org.apache.avro.AvroRuntimeException("Bad index");
+ }
+ }
+
+ // Used by DatumReader. Applications should not call.
+ @SuppressWarnings(value="unchecked")
+ public void put(int field$, java.lang.Object value$) {
+ switch (field$) {
+ case 0: requestTime = (java.lang.Long)value$; break;
+ case 1: clientIdentifier = (ClientIdentifier)value$; break;
+ case 2: employeeNames = (java.util.List)value$; break;
+ case 3: active = (Active)value$; break;
+ default: throw new org.apache.avro.AvroRuntimeException("Bad index");
+ }
+ }
+
+ /**
+ * Gets the value of the 'requestTime' field.
+ * @return The value of the 'requestTime' field.
+ */
+ public java.lang.Long getRequestTime() {
+ return requestTime;
+ }
+
+ /**
+ * Sets the value of the 'requestTime' field.
+ * @param value the value to set.
+ */
+ public void setRequestTime(java.lang.Long value) {
+ this.requestTime = value;
+ }
+
+ /**
+ * Gets the value of the 'clientIdentifier' field.
+ * @return The value of the 'clientIdentifier' field.
+ */
+ public ClientIdentifier getClientIdentifier() {
+ return clientIdentifier;
+ }
+
+ /**
+ * Sets the value of the 'clientIdentifier' field.
+ * @param value the value to set.
+ */
+ public void setClientIdentifier(ClientIdentifier value) {
+ this.clientIdentifier = value;
+ }
+
+ /**
+ * Gets the value of the 'employeeNames' field.
+ * @return The value of the 'employeeNames' field.
+ */
+ public java.util.List getEmployeeNames() {
+ return employeeNames;
+ }
+
+ /**
+ * Sets the value of the 'employeeNames' field.
+ * @param value the value to set.
+ */
+ public void setEmployeeNames(java.util.List value) {
+ this.employeeNames = value;
+ }
+
+ /**
+ * Gets the value of the 'active' field.
+ * @return The value of the 'active' field.
+ */
+ public Active getActive() {
+ return active;
+ }
+
+ /**
+ * Sets the value of the 'active' field.
+ * @param value the value to set.
+ */
+ public void setActive(Active value) {
+ this.active = value;
+ }
+
+ /**
+ * Creates a new AvroHttpRequest RecordBuilder.
+ * @return A new AvroHttpRequest RecordBuilder
+ */
+ public static AvroHttpRequest.Builder newBuilder() {
+ return new AvroHttpRequest.Builder();
+ }
+
+ /**
+ * Creates a new AvroHttpRequest RecordBuilder by copying an existing Builder.
+ * @param other The existing builder to copy.
+ * @return A new AvroHttpRequest RecordBuilder
+ */
+ public static AvroHttpRequest.Builder newBuilder(AvroHttpRequest.Builder other) {
+ return new AvroHttpRequest.Builder(other);
+ }
+
+ /**
+ * Creates a new AvroHttpRequest RecordBuilder by copying an existing AvroHttpRequest instance.
+ * @param other The existing instance to copy.
+ * @return A new AvroHttpRequest RecordBuilder
+ */
+ public static AvroHttpRequest.Builder newBuilder(AvroHttpRequest other) {
+ return new AvroHttpRequest.Builder(other);
+ }
+
+ /**
+ * RecordBuilder for AvroHttpRequest instances.
+ */
+ public static class Builder extends org.apache.avro.specific.SpecificRecordBuilderBase
+ implements org.apache.avro.data.RecordBuilder {
+
+ private long requestTime;
+ private ClientIdentifier clientIdentifier;
+ private ClientIdentifier.Builder clientIdentifierBuilder;
+ private java.util.List employeeNames;
+ private Active active;
+
+ /** Creates a new Builder */
+ private Builder() {
+ super(SCHEMA$);
+ }
+
+ /**
+ * Creates a Builder by copying an existing Builder.
+ * @param other The existing Builder to copy.
+ */
+ private Builder(AvroHttpRequest.Builder other) {
+ super(other);
+ if (isValidValue(fields()[0], other.requestTime)) {
+ this.requestTime = data().deepCopy(fields()[0].schema(), other.requestTime);
+ fieldSetFlags()[0] = true;
+ }
+ if (isValidValue(fields()[1], other.clientIdentifier)) {
+ this.clientIdentifier = data().deepCopy(fields()[1].schema(), other.clientIdentifier);
+ fieldSetFlags()[1] = true;
+ }
+ if (other.hasClientIdentifierBuilder()) {
+ this.clientIdentifierBuilder = ClientIdentifier.newBuilder(other.getClientIdentifierBuilder());
+ }
+ if (isValidValue(fields()[2], other.employeeNames)) {
+ this.employeeNames = data().deepCopy(fields()[2].schema(), other.employeeNames);
+ fieldSetFlags()[2] = true;
+ }
+ if (isValidValue(fields()[3], other.active)) {
+ this.active = data().deepCopy(fields()[3].schema(), other.active);
+ fieldSetFlags()[3] = true;
+ }
+ }
+
+ /**
+ * Creates a Builder by copying an existing AvroHttpRequest instance
+ * @param other The existing instance to copy.
+ */
+ private Builder(AvroHttpRequest other) {
+ super(SCHEMA$);
+ if (isValidValue(fields()[0], other.requestTime)) {
+ this.requestTime = data().deepCopy(fields()[0].schema(), other.requestTime);
+ fieldSetFlags()[0] = true;
+ }
+ if (isValidValue(fields()[1], other.clientIdentifier)) {
+ this.clientIdentifier = data().deepCopy(fields()[1].schema(), other.clientIdentifier);
+ fieldSetFlags()[1] = true;
+ }
+ this.clientIdentifierBuilder = null;
+ if (isValidValue(fields()[2], other.employeeNames)) {
+ this.employeeNames = data().deepCopy(fields()[2].schema(), other.employeeNames);
+ fieldSetFlags()[2] = true;
+ }
+ if (isValidValue(fields()[3], other.active)) {
+ this.active = data().deepCopy(fields()[3].schema(), other.active);
+ fieldSetFlags()[3] = true;
+ }
+ }
+
+ /**
+ * Gets the value of the 'requestTime' field.
+ * @return The value.
+ */
+ public java.lang.Long getRequestTime() {
+ return requestTime;
+ }
+
+ /**
+ * Sets the value of the 'requestTime' field.
+ * @param value The value of 'requestTime'.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder setRequestTime(long value) {
+ validate(fields()[0], value);
+ this.requestTime = value;
+ fieldSetFlags()[0] = true;
+ return this;
+ }
+
+ /**
+ * Checks whether the 'requestTime' field has been set.
+ * @return True if the 'requestTime' field has been set, false otherwise.
+ */
+ public boolean hasRequestTime() {
+ return fieldSetFlags()[0];
+ }
+
+
+ /**
+ * Clears the value of the 'requestTime' field.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder clearRequestTime() {
+ fieldSetFlags()[0] = false;
+ return this;
+ }
+
+ /**
+ * Gets the value of the 'clientIdentifier' field.
+ * @return The value.
+ */
+ public ClientIdentifier getClientIdentifier() {
+ return clientIdentifier;
+ }
+
+ /**
+ * Sets the value of the 'clientIdentifier' field.
+ * @param value The value of 'clientIdentifier'.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder setClientIdentifier(ClientIdentifier value) {
+ validate(fields()[1], value);
+ this.clientIdentifierBuilder = null;
+ this.clientIdentifier = value;
+ fieldSetFlags()[1] = true;
+ return this;
+ }
+
+ /**
+ * Checks whether the 'clientIdentifier' field has been set.
+ * @return True if the 'clientIdentifier' field has been set, false otherwise.
+ */
+ public boolean hasClientIdentifier() {
+ return fieldSetFlags()[1];
+ }
+
+ /**
+ * Gets the Builder instance for the 'clientIdentifier' field and creates one if it doesn't exist yet.
+ * @return This builder.
+ */
+ public ClientIdentifier.Builder getClientIdentifierBuilder() {
+ if (clientIdentifierBuilder == null) {
+ if (hasClientIdentifier()) {
+ setClientIdentifierBuilder(ClientIdentifier.newBuilder(clientIdentifier));
+ } else {
+ setClientIdentifierBuilder(ClientIdentifier.newBuilder());
+ }
+ }
+ return clientIdentifierBuilder;
+ }
+
+ /**
+ * Sets the Builder instance for the 'clientIdentifier' field
+ * @param value The builder instance that must be set.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder setClientIdentifierBuilder(ClientIdentifier.Builder value) {
+ clearClientIdentifier();
+ clientIdentifierBuilder = value;
+ return this;
+ }
+
+ /**
+ * Checks whether the 'clientIdentifier' field has an active Builder instance
+ * @return True if the 'clientIdentifier' field has an active Builder instance
+ */
+ public boolean hasClientIdentifierBuilder() {
+ return clientIdentifierBuilder != null;
+ }
+
+ /**
+ * Clears the value of the 'clientIdentifier' field.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder clearClientIdentifier() {
+ clientIdentifier = null;
+ clientIdentifierBuilder = null;
+ fieldSetFlags()[1] = false;
+ return this;
+ }
+
+ /**
+ * Gets the value of the 'employeeNames' field.
+ * @return The value.
+ */
+ public java.util.List getEmployeeNames() {
+ return employeeNames;
+ }
+
+ /**
+ * Sets the value of the 'employeeNames' field.
+ * @param value The value of 'employeeNames'.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder setEmployeeNames(java.util.List value) {
+ validate(fields()[2], value);
+ this.employeeNames = value;
+ fieldSetFlags()[2] = true;
+ return this;
+ }
+
+ /**
+ * Checks whether the 'employeeNames' field has been set.
+ * @return True if the 'employeeNames' field has been set, false otherwise.
+ */
+ public boolean hasEmployeeNames() {
+ return fieldSetFlags()[2];
+ }
+
+
+ /**
+ * Clears the value of the 'employeeNames' field.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder clearEmployeeNames() {
+ employeeNames = null;
+ fieldSetFlags()[2] = false;
+ return this;
+ }
+
+ /**
+ * Gets the value of the 'active' field.
+ * @return The value.
+ */
+ public Active getActive() {
+ return active;
+ }
+
+ /**
+ * Sets the value of the 'active' field.
+ * @param value The value of 'active'.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder setActive(Active value) {
+ validate(fields()[3], value);
+ this.active = value;
+ fieldSetFlags()[3] = true;
+ return this;
+ }
+
+ /**
+ * Checks whether the 'active' field has been set.
+ * @return True if the 'active' field has been set, false otherwise.
+ */
+ public boolean hasActive() {
+ return fieldSetFlags()[3];
+ }
+
+
+ /**
+ * Clears the value of the 'active' field.
+ * @return This builder.
+ */
+ public AvroHttpRequest.Builder clearActive() {
+ active = null;
+ fieldSetFlags()[3] = false;
+ return this;
+ }
+
+ @Override
+ @SuppressWarnings("unchecked")
+ public AvroHttpRequest build() {
+ try {
+ AvroHttpRequest record = new AvroHttpRequest();
+ record.requestTime = fieldSetFlags()[0] ? this.requestTime : (java.lang.Long) defaultValue(fields()[0]);
+ if (clientIdentifierBuilder != null) {
+ record.clientIdentifier = this.clientIdentifierBuilder.build();
+ } else {
+ record.clientIdentifier = fieldSetFlags()[1] ? this.clientIdentifier : (ClientIdentifier) defaultValue(fields()[1]);
+ }
+ record.employeeNames = fieldSetFlags()[2] ? this.employeeNames : (java.util.List) defaultValue(fields()[2]);
+ record.active = fieldSetFlags()[3] ? this.active : (Active) defaultValue(fields()[3]);
+ return record;
+ } catch (java.lang.Exception e) {
+ throw new org.apache.avro.AvroRuntimeException(e);
+ }
+ }
+ }
+
+ @SuppressWarnings("unchecked")
+ private static final org.apache.avro.io.DatumWriter
+ WRITER$ = (org.apache.avro.io.DatumWriter)MODEL$.createDatumWriter(SCHEMA$);
+
+ @Override public void writeExternal(java.io.ObjectOutput out)
+ throws java.io.IOException {
+ WRITER$.write(this, SpecificData.getEncoder(out));
+ }
+
+ @SuppressWarnings("unchecked")
+ private static final org.apache.avro.io.DatumReader
+ READER$ = (org.apache.avro.io.DatumReader)MODEL$.createDatumReader(SCHEMA$);
+
+ @Override public void readExternal(java.io.ObjectInput in)
+ throws java.io.IOException {
+ READER$.read(this, SpecificData.getDecoder(in));
+ }
+
+}
diff --git a/apache-avro/src/main/java/com/baeldung/avro/util/model/ClientIdentifier.java b/apache-avro/src/main/java/com/baeldung/avro/util/model/ClientIdentifier.java
new file mode 100644
index 0000000000..503dde40df
--- /dev/null
+++ b/apache-avro/src/main/java/com/baeldung/avro/util/model/ClientIdentifier.java
@@ -0,0 +1,308 @@
+/**
+ * Autogenerated by Avro
+ *
+ * DO NOT EDIT DIRECTLY
+ */
+package com.baeldung.avro.util.model;
+
+import org.apache.avro.specific.SpecificData;
+import org.apache.avro.message.BinaryMessageEncoder;
+import org.apache.avro.message.BinaryMessageDecoder;
+import org.apache.avro.message.SchemaStore;
+
+@SuppressWarnings("all")
+@org.apache.avro.specific.AvroGenerated
+public class ClientIdentifier extends org.apache.avro.specific.SpecificRecordBase implements org.apache.avro.specific.SpecificRecord {
+ private static final long serialVersionUID = 8754570983127295424L;
+ public static final org.apache.avro.Schema SCHEMA$ = new org.apache.avro.Schema.Parser().parse("{\"type\":\"record\",\"name\":\"ClientIdentifier\",\"namespace\":\"com.baeldung.avro.model\",\"fields\":[{\"name\":\"hostName\",\"type\":\"string\"},{\"name\":\"ipAddress\",\"type\":\"string\"}]}");
+ public static org.apache.avro.Schema getClassSchema() { return SCHEMA$; }
+
+ private static SpecificData MODEL$ = new SpecificData();
+
+ private static final BinaryMessageEncoder ENCODER =
+ new BinaryMessageEncoder(MODEL$, SCHEMA$);
+
+ private static final BinaryMessageDecoder DECODER =
+ new BinaryMessageDecoder(MODEL$, SCHEMA$);
+
+ /**
+ * Return the BinaryMessageDecoder instance used by this class.
+ */
+ public static BinaryMessageDecoder getDecoder() {
+ return DECODER;
+ }
+
+ /**
+ * Create a new BinaryMessageDecoder instance for this class that uses the specified {@link SchemaStore}.
+ * @param resolver a {@link SchemaStore} used to find schemas by fingerprint
+ */
+ public static BinaryMessageDecoder createDecoder(SchemaStore resolver) {
+ return new BinaryMessageDecoder(MODEL$, SCHEMA$, resolver);
+ }
+
+ /** Serializes this ClientIdentifier to a ByteBuffer. */
+ public java.nio.ByteBuffer toByteBuffer() throws java.io.IOException {
+ return ENCODER.encode(this);
+ }
+
+ /** Deserializes a ClientIdentifier from a ByteBuffer. */
+ public static ClientIdentifier fromByteBuffer(
+ java.nio.ByteBuffer b) throws java.io.IOException {
+ return DECODER.decode(b);
+ }
+
+ @Deprecated public java.lang.CharSequence hostName;
+ @Deprecated public java.lang.CharSequence ipAddress;
+
+ /**
+ * Default constructor. Note that this does not initialize fields
+ * to their default values from the schema. If that is desired then
+ * one should use newBuilder()
.
+ */
+ public ClientIdentifier() {}
+
+ /**
+ * All-args constructor.
+ * @param hostName The new value for hostName
+ * @param ipAddress The new value for ipAddress
+ */
+ public ClientIdentifier(java.lang.CharSequence hostName, java.lang.CharSequence ipAddress) {
+ this.hostName = hostName;
+ this.ipAddress = ipAddress;
+ }
+
+ public org.apache.avro.Schema getSchema() { return SCHEMA$; }
+ // Used by DatumWriter. Applications should not call.
+ public java.lang.Object get(int field$) {
+ switch (field$) {
+ case 0: return hostName;
+ case 1: return ipAddress;
+ default: throw new org.apache.avro.AvroRuntimeException("Bad index");
+ }
+ }
+
+ // Used by DatumReader. Applications should not call.
+ @SuppressWarnings(value="unchecked")
+ public void put(int field$, java.lang.Object value$) {
+ switch (field$) {
+ case 0: hostName = (java.lang.CharSequence)value$; break;
+ case 1: ipAddress = (java.lang.CharSequence)value$; break;
+ default: throw new org.apache.avro.AvroRuntimeException("Bad index");
+ }
+ }
+
+ /**
+ * Gets the value of the 'hostName' field.
+ * @return The value of the 'hostName' field.
+ */
+ public java.lang.CharSequence getHostName() {
+ return hostName;
+ }
+
+ /**
+ * Sets the value of the 'hostName' field.
+ * @param value the value to set.
+ */
+ public void setHostName(java.lang.CharSequence value) {
+ this.hostName = value;
+ }
+
+ /**
+ * Gets the value of the 'ipAddress' field.
+ * @return The value of the 'ipAddress' field.
+ */
+ public java.lang.CharSequence getIpAddress() {
+ return ipAddress;
+ }
+
+ /**
+ * Sets the value of the 'ipAddress' field.
+ * @param value the value to set.
+ */
+ public void setIpAddress(java.lang.CharSequence value) {
+ this.ipAddress = value;
+ }
+
+ /**
+ * Creates a new ClientIdentifier RecordBuilder.
+ * @return A new ClientIdentifier RecordBuilder
+ */
+ public static ClientIdentifier.Builder newBuilder() {
+ return new ClientIdentifier.Builder();
+ }
+
+ /**
+ * Creates a new ClientIdentifier RecordBuilder by copying an existing Builder.
+ * @param other The existing builder to copy.
+ * @return A new ClientIdentifier RecordBuilder
+ */
+ public static ClientIdentifier.Builder newBuilder(ClientIdentifier.Builder other) {
+ return new ClientIdentifier.Builder(other);
+ }
+
+ /**
+ * Creates a new ClientIdentifier RecordBuilder by copying an existing ClientIdentifier instance.
+ * @param other The existing instance to copy.
+ * @return A new ClientIdentifier RecordBuilder
+ */
+ public static ClientIdentifier.Builder newBuilder(ClientIdentifier other) {
+ return new ClientIdentifier.Builder(other);
+ }
+
+ /**
+ * RecordBuilder for ClientIdentifier instances.
+ */
+ public static class Builder extends org.apache.avro.specific.SpecificRecordBuilderBase
+ implements org.apache.avro.data.RecordBuilder {
+
+ private java.lang.CharSequence hostName;
+ private java.lang.CharSequence ipAddress;
+
+ /** Creates a new Builder */
+ private Builder() {
+ super(SCHEMA$);
+ }
+
+ /**
+ * Creates a Builder by copying an existing Builder.
+ * @param other The existing Builder to copy.
+ */
+ private Builder(ClientIdentifier.Builder other) {
+ super(other);
+ if (isValidValue(fields()[0], other.hostName)) {
+ this.hostName = data().deepCopy(fields()[0].schema(), other.hostName);
+ fieldSetFlags()[0] = true;
+ }
+ if (isValidValue(fields()[1], other.ipAddress)) {
+ this.ipAddress = data().deepCopy(fields()[1].schema(), other.ipAddress);
+ fieldSetFlags()[1] = true;
+ }
+ }
+
+ /**
+ * Creates a Builder by copying an existing ClientIdentifier instance
+ * @param other The existing instance to copy.
+ */
+ private Builder(ClientIdentifier other) {
+ super(SCHEMA$);
+ if (isValidValue(fields()[0], other.hostName)) {
+ this.hostName = data().deepCopy(fields()[0].schema(), other.hostName);
+ fieldSetFlags()[0] = true;
+ }
+ if (isValidValue(fields()[1], other.ipAddress)) {
+ this.ipAddress = data().deepCopy(fields()[1].schema(), other.ipAddress);
+ fieldSetFlags()[1] = true;
+ }
+ }
+
+ /**
+ * Gets the value of the 'hostName' field.
+ * @return The value.
+ */
+ public java.lang.CharSequence getHostName() {
+ return hostName;
+ }
+
+ /**
+ * Sets the value of the 'hostName' field.
+ * @param value The value of 'hostName'.
+ * @return This builder.
+ */
+ public ClientIdentifier.Builder setHostName(java.lang.CharSequence value) {
+ validate(fields()[0], value);
+ this.hostName = value;
+ fieldSetFlags()[0] = true;
+ return this;
+ }
+
+ /**
+ * Checks whether the 'hostName' field has been set.
+ * @return True if the 'hostName' field has been set, false otherwise.
+ */
+ public boolean hasHostName() {
+ return fieldSetFlags()[0];
+ }
+
+
+ /**
+ * Clears the value of the 'hostName' field.
+ * @return This builder.
+ */
+ public ClientIdentifier.Builder clearHostName() {
+ hostName = null;
+ fieldSetFlags()[0] = false;
+ return this;
+ }
+
+ /**
+ * Gets the value of the 'ipAddress' field.
+ * @return The value.
+ */
+ public java.lang.CharSequence getIpAddress() {
+ return ipAddress;
+ }
+
+ /**
+ * Sets the value of the 'ipAddress' field.
+ * @param value The value of 'ipAddress'.
+ * @return This builder.
+ */
+ public ClientIdentifier.Builder setIpAddress(java.lang.CharSequence value) {
+ validate(fields()[1], value);
+ this.ipAddress = value;
+ fieldSetFlags()[1] = true;
+ return this;
+ }
+
+ /**
+ * Checks whether the 'ipAddress' field has been set.
+ * @return True if the 'ipAddress' field has been set, false otherwise.
+ */
+ public boolean hasIpAddress() {
+ return fieldSetFlags()[1];
+ }
+
+
+ /**
+ * Clears the value of the 'ipAddress' field.
+ * @return This builder.
+ */
+ public ClientIdentifier.Builder clearIpAddress() {
+ ipAddress = null;
+ fieldSetFlags()[1] = false;
+ return this;
+ }
+
+ @Override
+ @SuppressWarnings("unchecked")
+ public ClientIdentifier build() {
+ try {
+ ClientIdentifier record = new ClientIdentifier();
+ record.hostName = fieldSetFlags()[0] ? this.hostName : (java.lang.CharSequence) defaultValue(fields()[0]);
+ record.ipAddress = fieldSetFlags()[1] ? this.ipAddress : (java.lang.CharSequence) defaultValue(fields()[1]);
+ return record;
+ } catch (java.lang.Exception e) {
+ throw new org.apache.avro.AvroRuntimeException(e);
+ }
+ }
+ }
+
+ @SuppressWarnings("unchecked")
+ private static final org.apache.avro.io.DatumWriter
+ WRITER$ = (org.apache.avro.io.DatumWriter)MODEL$.createDatumWriter(SCHEMA$);
+
+ @Override public void writeExternal(java.io.ObjectOutput out)
+ throws java.io.IOException {
+ WRITER$.write(this, SpecificData.getEncoder(out));
+ }
+
+ @SuppressWarnings("unchecked")
+ private static final org.apache.avro.io.DatumReader
+ READER$ = (org.apache.avro.io.DatumReader)MODEL$.createDatumReader(SCHEMA$);
+
+ @Override public void readExternal(java.io.ObjectInput in)
+ throws java.io.IOException {
+ READER$.read(this, SpecificData.getDecoder(in));
+ }
+
+}
diff --git a/apache-avro/src/main/java/com/baeldung/avro/util/serealization/AvroDeSerealizer.java b/apache-avro/src/main/java/com/baeldung/avro/util/serealization/AvroDeSerealizer.java
new file mode 100644
index 0000000000..d2219a45f2
--- /dev/null
+++ b/apache-avro/src/main/java/com/baeldung/avro/util/serealization/AvroDeSerealizer.java
@@ -0,0 +1,33 @@
+package com.baeldung.avro.util.serealization;
+
+import com.baeldung.avro.util.model.AvroHttpRequest;
+import org.apache.avro.io.DatumReader;
+import org.apache.avro.io.Decoder;
+import org.apache.avro.io.DecoderFactory;
+import org.apache.avro.specific.SpecificDatumReader;
+
+import java.io.IOException;
+
+public class AvroDeSerealizer {
+
+public AvroHttpRequest deSerealizeAvroHttpRequestJSON(byte[] data){
+ DatumReader reader = new SpecificDatumReader<>(AvroHttpRequest.class);
+ Decoder decoder = null;
+ try {
+ decoder = DecoderFactory.get().jsonDecoder(AvroHttpRequest.getClassSchema(), new String(data));
+ return reader.read(null, decoder);
+ } catch (IOException e) {
+ return null;
+ }
+}
+
+public AvroHttpRequest deSerealizeAvroHttpRequestBinary(byte[] data){
+ DatumReader employeeReader = new SpecificDatumReader<>(AvroHttpRequest.class);
+ Decoder decoder = DecoderFactory.get().binaryDecoder(data, null);
+ try {
+ return employeeReader.read(null, decoder);
+ } catch (IOException e) {
+ return null;
+ }
+}
+}
diff --git a/apache-avro/src/main/java/com/baeldung/avro/util/serealization/AvroSerealizer.java b/apache-avro/src/main/java/com/baeldung/avro/util/serealization/AvroSerealizer.java
new file mode 100644
index 0000000000..f56c89e201
--- /dev/null
+++ b/apache-avro/src/main/java/com/baeldung/avro/util/serealization/AvroSerealizer.java
@@ -0,0 +1,44 @@
+package com.baeldung.avro.util.serealization;
+
+import com.baeldung.avro.util.model.AvroHttpRequest;
+import org.apache.avro.io.*;
+import org.apache.avro.specific.SpecificDatumWriter;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+
+public class AvroSerealizer {
+
+public byte[] serealizeAvroHttpRequestJSON(AvroHttpRequest request){
+ DatumWriter writer = new SpecificDatumWriter<>(AvroHttpRequest.class);
+ byte[] data = new byte[0];
+ ByteArrayOutputStream stream = new ByteArrayOutputStream();
+ Encoder jsonEncoder = null;
+ try {
+ jsonEncoder = EncoderFactory.get().jsonEncoder(AvroHttpRequest.getClassSchema(), stream);
+ writer.write(request, jsonEncoder);
+ jsonEncoder.flush();
+ data = stream.toByteArray();
+ } catch (IOException e) {
+ data =null;
+ }
+ return data;
+}
+
+public byte[] serealizeAvroHttpRequestBinary(AvroHttpRequest request){
+ DatumWriter writer = new SpecificDatumWriter<>(AvroHttpRequest.class);
+ byte[] data = new byte[0];
+ ByteArrayOutputStream stream = new ByteArrayOutputStream();
+ Encoder jsonEncoder = EncoderFactory.get().binaryEncoder(stream,null);
+ try {
+ writer.write(request, jsonEncoder);
+ jsonEncoder.flush();
+ data = stream.toByteArray();
+ } catch (IOException e) {
+ data = null;
+ }
+
+ return data;
+}
+
+}
diff --git a/apache-avro/src/main/resources/avroHttpRequest-schema.avsc b/apache-avro/src/main/resources/avroHttpRequest-schema.avsc
new file mode 100644
index 0000000000..18179a9cde
--- /dev/null
+++ b/apache-avro/src/main/resources/avroHttpRequest-schema.avsc
@@ -0,0 +1,47 @@
+{
+ "type":"record",
+ "name":"AvroHttpRequest",
+ "namespace":"com.baeldung.avro.model",
+ "fields":[
+ {
+ "name":"requestTime",
+ "type":"long"
+ },
+ {
+ "name":"clientIdentifier",
+ "type":{
+ "type":"record",
+ "name":"ClientIdentifier",
+ "fields":[
+ {
+ "name":"hostName",
+ "type":"string"
+ },
+ {
+ "name":"ipAddress",
+ "type":"string"
+ }
+ ]
+ }
+ },
+ {
+ "name":"employeeNames",
+ "type":{
+ "type":"array",
+ "items":"string"
+ },
+ "default":null
+ },
+ {
+ "name":"active",
+ "type":{
+ "type":"enum",
+ "name":"Active",
+ "symbols":[
+ "YES",
+ "NO"
+ ]
+ }
+ }
+ ]
+}
\ No newline at end of file
diff --git a/apache-avro/src/test/java/com/baeldung/avro/util/serealization/AvroSerealizerDeSerealizerTest.java b/apache-avro/src/test/java/com/baeldung/avro/util/serealization/AvroSerealizerDeSerealizerTest.java
new file mode 100644
index 0000000000..937a4ae650
--- /dev/null
+++ b/apache-avro/src/test/java/com/baeldung/avro/util/serealization/AvroSerealizerDeSerealizerTest.java
@@ -0,0 +1,75 @@
+package com.baeldung.avro.util.serealization;
+
+import com.baeldung.avro.util.model.Active;
+import com.baeldung.avro.util.model.AvroHttpRequest;
+import com.baeldung.avro.util.model.ClientIdentifier;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Objects;
+
+import static org.junit.Assert.*;
+
+public class AvroSerealizerDeSerealizerTest {
+
+ AvroSerealizer serealizer;
+ AvroDeSerealizer deSerealizer;
+ AvroHttpRequest request;
+
+ @Before
+ public void setUp() throws Exception {
+ serealizer = new AvroSerealizer();
+ deSerealizer = new AvroDeSerealizer();
+
+ ClientIdentifier clientIdentifier = ClientIdentifier.newBuilder().
+ setHostName("localhost").setIpAddress("255.255.255.0").build();
+
+ List employees = new ArrayList();
+ employees.add("James");
+ employees.add("Alice");
+ employees.add("David");
+ employees.add("Han");
+
+ request = AvroHttpRequest.newBuilder().setRequestTime(01l)
+ .setActive(Active.YES).setClientIdentifier(clientIdentifier)
+ .setEmployeeNames(employees).build();
+ }
+
+ @After
+ public void tearDown() throws Exception {
+ }
+
+@Test
+public void WhenSerialized_UsingJSONEncoder_ObjectGetsSerialized(){
+ byte[] data = serealizer.serealizeAvroHttpRequestJSON(request);
+ assertTrue(Objects.nonNull(data));
+ assertTrue(data.length > 0);
+}
+
+@Test
+public void WhenSerialized_UsingBinaryEncoder_ObjectGetsSerialized(){
+ byte[] data = serealizer.serealizeAvroHttpRequestBinary(request);
+ assertTrue(Objects.nonNull(data));
+ assertTrue(data.length > 0);
+}
+
+@Test
+public void WhenDeserialize_UsingJSONDecoder_ActualAndExpectedObjectsAreEqual(){
+ byte[] data = serealizer.serealizeAvroHttpRequestJSON(request);
+ AvroHttpRequest actualRequest = deSerealizer.deSerealizeAvroHttpRequestJSON(data);
+ assertEquals(actualRequest,request);
+ assertTrue(actualRequest.getRequestTime().equals(request.getRequestTime()));
+}
+
+@Test
+public void WhenDeserialize_UsingBinaryecoder_ActualAndExpectedObjectsAreEqual(){
+ byte[] data = serealizer.serealizeAvroHttpRequestBinary(request);
+ AvroHttpRequest actualRequest = deSerealizer.deSerealizeAvroHttpRequestBinary(data);
+ assertEquals(actualRequest,request);
+ assertTrue(actualRequest.getRequestTime().equals(request.getRequestTime()));
+}
+}
+
diff --git a/core-java-8/src/main/java/com/baeldung/convertlisttomap/Animal.java b/core-java-8/src/main/java/com/baeldung/convertlisttomap/Animal.java
new file mode 100644
index 0000000000..b8eddf71a5
--- /dev/null
+++ b/core-java-8/src/main/java/com/baeldung/convertlisttomap/Animal.java
@@ -0,0 +1,27 @@
+package com.baeldung.convertlisttomap;
+
+public class Animal {
+ private int id;
+ private String name;
+
+ public Animal(int id, String name) {
+ this.id = id;
+ this.setName(name);
+ }
+
+ public int getId() {
+ return id;
+ }
+
+ public void setId(int id) {
+ this.id = id;
+ }
+
+ public String getName() {
+ return name;
+ }
+
+ public void setName(String name) {
+ this.name = name;
+ }
+}
diff --git a/core-java-8/src/main/java/com/baeldung/convertlisttomap/ConvertListToMapService.java b/core-java-8/src/main/java/com/baeldung/convertlisttomap/ConvertListToMapService.java
new file mode 100644
index 0000000000..679e753c56
--- /dev/null
+++ b/core-java-8/src/main/java/com/baeldung/convertlisttomap/ConvertListToMapService.java
@@ -0,0 +1,52 @@
+package com.baeldung.convertlisttomap;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+import org.apache.commons.collections4.IterableUtils;
+import org.apache.commons.collections4.MapUtils;
+import com.google.common.collect.Maps;
+
+public class ConvertListToMapService {
+
+ public Map convertListBeforeJava8(List list) {
+ Map map = new HashMap();
+ for (Animal animal : list) {
+ map.put(animal.getId(), animal);
+ }
+ return map;
+ }
+
+ public Map convertListAfterJava8(List list) {
+ Map map = list.stream().collect(Collectors.toMap(Animal::getId, animal -> animal));
+ return map;
+ }
+
+ public Map convertListWithGuava(List list) {
+
+ Map map = Maps.uniqueIndex(list, Animal::getId);
+ return map;
+ }
+
+ public Map convertListWithApacheCommons1(List list) {
+
+ Map map = new HashMap();
+
+ IterableUtils.forEach(list, animal -> {
+ map.put(animal.getId(), animal);
+ });
+
+ return map;
+ }
+
+ public Map convertListWithApacheCommons2(List list) {
+
+ Map map = new HashMap();
+
+ MapUtils.populateMap(map, list, Animal::getId);
+
+ return map;
+ }
+}
diff --git a/core-java-8/src/test/java/com/baeldung/convertlisttomap/ConvertListToMapServiceUnitTest.java b/core-java-8/src/test/java/com/baeldung/convertlisttomap/ConvertListToMapServiceUnitTest.java
new file mode 100644
index 0000000000..4e78af08cd
--- /dev/null
+++ b/core-java-8/src/test/java/com/baeldung/convertlisttomap/ConvertListToMapServiceUnitTest.java
@@ -0,0 +1,73 @@
+package com.baeldung.convertlisttomap;
+
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.*;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+
+import org.junit.Before;
+import org.junit.Test;
+
+public class ConvertListToMapServiceUnitTest {
+ List list;
+
+ private ConvertListToMapService convertListService;
+
+ @Before
+ public void init() {
+ this.convertListService = new ConvertListToMapService();
+ this.list = new ArrayList<>();
+
+ Animal cat = new Animal(1, "Cat");
+ list.add(cat);
+ Animal dog = new Animal(2, "Dog");
+ list.add(dog);
+ Animal pig = new Animal(3, "Pig");
+ list.add(pig);
+ Animal cow = new Animal(4, "Cow");
+ list.add(cow);
+ Animal goat = new Animal(5, "Goat");
+ list.add(goat);
+ }
+
+ @Test
+ public void givenAList_whenConvertBeforeJava8_thenReturnMapWithTheSameElements() {
+
+ Map map = convertListService.convertListBeforeJava8(list);
+
+ assertThat(map.values(), containsInAnyOrder(list.toArray()));
+ }
+
+ @Test
+ public void givenAList_whenConvertAfterJava8_thenReturnMapWithTheSameElements() {
+
+ Map map = convertListService.convertListAfterJava8(list);
+
+ assertThat(map.values(), containsInAnyOrder(list.toArray()));
+ }
+
+ @Test
+ public void givenAList_whenConvertWithGuava_thenReturnMapWithTheSameElements() {
+
+ Map map = convertListService.convertListWithGuava(list);
+
+ assertThat(map.values(), containsInAnyOrder(list.toArray()));
+ }
+
+ @Test
+ public void givenAList_whenConvertWithApacheCommons1_thenReturnMapWithTheSameElements() {
+
+ Map map = convertListService.convertListWithApacheCommons1(list);
+
+ assertThat(map.values(), containsInAnyOrder(list.toArray()));
+ }
+
+ @Test
+ public void givenAList_whenConvertWithApacheCommons2_thenReturnMapWithTheSameElements() {
+
+ Map map = convertListService.convertListWithApacheCommons2(list);
+
+ assertThat(map.values(), containsInAnyOrder(list.toArray()));
+ }
+}
diff --git a/core-java-collections/src/test/java/com/baeldung/java/set/HashSetInitalizingUnitTest.java b/core-java-collections/src/test/java/com/baeldung/java/set/HashSetInitalizingUnitTest.java
index 13df09b597..2e736501cf 100644
--- a/core-java-collections/src/test/java/com/baeldung/java/set/HashSetInitalizingUnitTest.java
+++ b/core-java-collections/src/test/java/com/baeldung/java/set/HashSetInitalizingUnitTest.java
@@ -50,22 +50,9 @@ public class HashSetInitalizingUnitTest {
@Test
public void whenUsingJava8_usingCollectOnStream_thenCorrectSize() {
- Set set = Stream.of("a", "b", "c").collect(Collectors.toSet());
+ Set set = Stream.of("a", "b", "c").collect(Collectors.toCollection(HashSet::new));
assertEquals(3, set.size());
}
- @Test
- public void whenUsingJava8_fromStringArray_thenCorrectSize() {
- String[] stringArray = {"a","b","c"};
- Set set = Arrays.stream(stringArray).collect(Collectors.toCollection(HashSet::new));
- assertEquals(3, set.size());
- }
-
- // Requires Java9 - uncomment if you are using Java 9 or higher
- /*@Test
- public void whenUsingJava9_usingCollectOnStream_thenCorrectSize() {
- Set set = Set.of("a", "b", "c");
- assertEquals(3, set.size());
- }*/
@Test
public void whenUsingGoogleGuava_createMutableSet_thenCorrectSize() {
@@ -78,4 +65,6 @@ public class HashSetInitalizingUnitTest {
Set set = ImmutableSet.of("a", "b", "c");
assertEquals(3, set.size());
}
+
}
+
diff --git a/core-kotlin/pom.xml b/core-kotlin/pom.xml
index fa16dad496..afa7d8a963 100644
--- a/core-kotlin/pom.xml
+++ b/core-kotlin/pom.xml
@@ -60,7 +60,6 @@
org.jetbrains.kotlin
kotlin-reflect
${kotlin-reflect.version}
- test
org.jetbrains.kotlinx
@@ -224,10 +223,11 @@
- 1.2.41
- 1.2.41
- 1.2.41
- 1.2.41
+ UTF-8
+ 1.2.51
+ 1.2.51
+ 1.2.51
+ 1.2.51
0.22.5
0.9.2
1.5.0
diff --git a/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsExtensionOnAny.kt b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsExtensionOnAny.kt
new file mode 100644
index 0000000000..32d968fff5
--- /dev/null
+++ b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsExtensionOnAny.kt
@@ -0,0 +1,30 @@
+package com.baeldung.kotlin.logging
+
+import org.slf4j.Logger
+
+open class LoggerAsExtensionOnAny {
+ val logger = logger()
+
+ fun log(s: String) {
+ logger().info(s)
+ logger.info(s)
+ }
+}
+
+class ExtensionSubclass : LoggerAsExtensionOnAny()
+
+fun T.logger(): Logger = getLogger(getClassForLogging(javaClass))
+
+fun main(args: Array) {
+ LoggerAsExtensionOnAny().log("test")
+ ExtensionSubclass().log("sub")
+ "foo".logger().info("foo")
+ 1.logger().info("uh-oh!")
+ SomeOtherClass().logger()
+}
+
+class SomeOtherClass {
+ fun logger(): String {
+ return "foo"
+ }
+}
\ No newline at end of file
diff --git a/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsExtensionOnMarkerInterface.kt b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsExtensionOnMarkerInterface.kt
new file mode 100644
index 0000000000..b33d4c9f93
--- /dev/null
+++ b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsExtensionOnMarkerInterface.kt
@@ -0,0 +1,30 @@
+package com.baeldung.kotlin.logging
+
+import org.slf4j.Logger
+import org.slf4j.LoggerFactory
+
+interface Logging
+
+inline fun T.logger(): Logger =
+ //Wrong logger name!
+ //LoggerFactory.getLogger(javaClass.name + " w/interface")
+ LoggerFactory.getLogger(getClassForLogging(T::class.java).name + " w/interface")
+
+open class LoggerAsExtensionOnMarkerInterface : Logging {
+ companion object : Logging {
+ val logger = logger()
+ }
+
+ fun log(s: String) {
+ logger().info(s)
+ logger.info(s)
+ }
+}
+
+class MarkerExtensionSubclass : LoggerAsExtensionOnMarkerInterface()
+
+fun main(args: Array) {
+ LoggerAsExtensionOnMarkerInterface().log("test")
+ MarkerExtensionSubclass().log("sub")
+ "foo".logger().info("foo")
+}
\ No newline at end of file
diff --git a/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsProperty.kt b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsProperty.kt
new file mode 100644
index 0000000000..979b3b3a10
--- /dev/null
+++ b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsProperty.kt
@@ -0,0 +1,17 @@
+package com.baeldung.kotlin.logging
+
+open class LoggerAsProperty {
+ private val logger = getLogger(javaClass)
+
+ fun log(s: String) {
+ logger.info(s)
+ }
+
+}
+
+class PropertySubclass : LoggerAsProperty()
+
+fun main(args: Array) {
+ LoggerAsProperty().log("test")
+ PropertySubclass().log("sub")
+}
\ No newline at end of file
diff --git a/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsPropertyDelegate.kt b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsPropertyDelegate.kt
new file mode 100644
index 0000000000..23f04722be
--- /dev/null
+++ b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerAsPropertyDelegate.kt
@@ -0,0 +1,47 @@
+package com.baeldung.kotlin.logging
+
+import org.slf4j.Logger
+import kotlin.properties.ReadOnlyProperty
+import kotlin.reflect.KProperty
+
+open class LoggerAsPropertyDelegate {
+ private val lazyLogger by lazyLogger()
+ protected val logger by LoggerDelegate()
+ private val logger2 = logger
+
+ companion object {
+ private val lazyLoggerComp by lazyLogger()
+ private val loggerComp by LoggerDelegate()
+ }
+
+ open fun log(s: String) {
+ logger.info(s)
+ logger2.info(s)
+ lazyLogger.info(s)
+ loggerComp.info(s)
+ lazyLoggerComp.info(s)
+ }
+
+}
+
+class DelegateSubclass : LoggerAsPropertyDelegate() {
+ override fun log(s: String) {
+ logger.info("-- in sub")
+ super.log(s)
+ }
+}
+
+fun lazyLogger(forClass: Class<*>): Lazy =
+ lazy { getLogger(getClassForLogging(forClass)) }
+
+fun T.lazyLogger(): Lazy = lazyLogger(javaClass)
+
+fun main(args: Array) {
+ LoggerAsPropertyDelegate().log("test")
+ DelegateSubclass().log("sub")
+}
+
+class LoggerDelegate : ReadOnlyProperty {
+ override fun getValue(thisRef: R, property: KProperty<*>) =
+ getLogger(getClassForLogging(thisRef.javaClass))
+}
diff --git a/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerInCompanionObject.kt b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerInCompanionObject.kt
new file mode 100644
index 0000000000..f973606369
--- /dev/null
+++ b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/LoggerInCompanionObject.kt
@@ -0,0 +1,44 @@
+package com.baeldung.kotlin.logging
+
+open class LoggerInCompanionObject {
+ companion object {
+ private val loggerWithExplicitClass = getLogger(LoggerInCompanionObject::class.java)
+ @Suppress("JAVA_CLASS_ON_COMPANION")
+ private val loggerWithWrongClass = getLogger(javaClass)
+ @Suppress("JAVA_CLASS_ON_COMPANION")
+ private val logger = getLogger(javaClass.enclosingClass)
+ }
+
+ fun log(s: String) {
+ loggerWithExplicitClass.info(s)
+ loggerWithWrongClass.info(s)
+ logger.info(s)
+ }
+
+ class Inner {
+ companion object {
+ private val loggerWithExplicitClass = getLogger(Inner::class.java)
+ @Suppress("JAVA_CLASS_ON_COMPANION")
+ @JvmStatic
+ private val loggerWithWrongClass = getLogger(javaClass)
+ @Suppress("JAVA_CLASS_ON_COMPANION")
+ @JvmStatic
+ private val logger = getLogger(javaClass.enclosingClass)
+ }
+
+ fun log(s: String) {
+ loggerWithExplicitClass.info(s)
+ loggerWithWrongClass.info(s)
+ logger.info(s)
+ }
+ }
+
+}
+
+class CompanionSubclass : LoggerInCompanionObject()
+
+fun main(args: Array) {
+ LoggerInCompanionObject().log("test")
+ LoggerInCompanionObject.Inner().log("test")
+ CompanionSubclass().log("sub")
+}
\ No newline at end of file
diff --git a/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/Util.kt b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/Util.kt
new file mode 100644
index 0000000000..b9c0d9e34c
--- /dev/null
+++ b/core-kotlin/src/main/kotlin/com/baeldung/kotlin/logging/Util.kt
@@ -0,0 +1,13 @@
+package com.baeldung.kotlin.logging
+
+import org.slf4j.Logger
+import org.slf4j.LoggerFactory
+import kotlin.reflect.full.companionObject
+
+fun getLogger(forClass: Class<*>): Logger = LoggerFactory.getLogger(forClass)
+
+fun getClassForLogging(javaClass: Class): Class<*> {
+ return javaClass.enclosingClass?.takeIf {
+ it.kotlin.companionObject?.java == javaClass
+ } ?: javaClass
+}
\ No newline at end of file
diff --git a/jhipster/jhipster-monolithic/pom.xml b/jhipster/jhipster-monolithic/pom.xml
index 6ac756c807..0536f80ada 100644
--- a/jhipster/jhipster-monolithic/pom.xml
+++ b/jhipster/jhipster-monolithic/pom.xml
@@ -6,7 +6,7 @@
jhipster-monolithic
0.0.1-SNAPSHOT
war
- JHipster Monolithic Application
+ JHipster Monolithic Application
parent-boot-1
diff --git a/jhipster/jhipster-monolithic/src/main/resources/logback-spring.xml b/jhipster/jhipster-monolithic/src/main/resources/logback-spring.xml
index 3c62a70c31..2fda7cc968 100644
--- a/jhipster/jhipster-monolithic/src/main/resources/logback-spring.xml
+++ b/jhipster/jhipster-monolithic/src/main/resources/logback-spring.xml
@@ -3,28 +3,9 @@
-
-
-
-
-
-
+
diff --git a/libraries/src/test/java/com/baeldung/hoverfly/HoverflyApiIntegrationTest.java b/libraries/src/test/java/com/baeldung/hoverfly/HoverflyApiLiveTest.java
similarity index 99%
rename from libraries/src/test/java/com/baeldung/hoverfly/HoverflyApiIntegrationTest.java
rename to libraries/src/test/java/com/baeldung/hoverfly/HoverflyApiLiveTest.java
index 09d31eac21..8d60b40bb0 100644
--- a/libraries/src/test/java/com/baeldung/hoverfly/HoverflyApiIntegrationTest.java
+++ b/libraries/src/test/java/com/baeldung/hoverfly/HoverflyApiLiveTest.java
@@ -31,7 +31,7 @@ import org.springframework.web.client.RestTemplate;
import io.specto.hoverfly.junit.core.SimulationSource;
import io.specto.hoverfly.junit.rule.HoverflyRule;
-public class HoverflyApiIntegrationTest {
+public class HoverflyApiLiveTest {
private static final SimulationSource source = dsl(service("http://www.baeldung.com").get("/api/courses/1").willReturn(success().body(jsonWithSingleQuotes("{'id':'1','name':'HCI'}")))
diff --git a/libraries/src/test/java/com/baeldung/infinispan/service/HelloWorldServiceIntegrationTest.java b/libraries/src/test/java/com/baeldung/infinispan/service/HelloWorldServiceTemporaryLiveTest.java
similarity index 96%
rename from libraries/src/test/java/com/baeldung/infinispan/service/HelloWorldServiceIntegrationTest.java
rename to libraries/src/test/java/com/baeldung/infinispan/service/HelloWorldServiceTemporaryLiveTest.java
index 75dae2b2fa..46cc77cbba 100644
--- a/libraries/src/test/java/com/baeldung/infinispan/service/HelloWorldServiceIntegrationTest.java
+++ b/libraries/src/test/java/com/baeldung/infinispan/service/HelloWorldServiceTemporaryLiveTest.java
@@ -5,7 +5,7 @@ import org.junit.Test;
import static org.assertj.core.api.Java6Assertions.assertThat;
-public class HelloWorldServiceIntegrationTest extends AbstractIntegrationTest {
+public class HelloWorldServiceTemporaryLiveTest extends AbstractIntegrationTest {
@Test
public void whenGetIsCalledTwoTimes_thenTheSecondShouldHitTheCache() {
diff --git a/micronaut/hello-world/.mvn/jvm.config b/micronaut/.mvn/jvm.config
similarity index 100%
rename from micronaut/hello-world/.mvn/jvm.config
rename to micronaut/.mvn/jvm.config
diff --git a/micronaut/hello-world/.mvn/wrapper/MavenWrapperDownloader.java b/micronaut/.mvn/wrapper/MavenWrapperDownloader.java
similarity index 99%
rename from micronaut/hello-world/.mvn/wrapper/MavenWrapperDownloader.java
rename to micronaut/.mvn/wrapper/MavenWrapperDownloader.java
index d475a89ce1..66a3132a52 100644
--- a/micronaut/hello-world/.mvn/wrapper/MavenWrapperDownloader.java
+++ b/micronaut/.mvn/wrapper/MavenWrapperDownloader.java
@@ -106,5 +106,4 @@ public class MavenWrapperDownloader {
fos.close();
rbc.close();
}
-
}
diff --git a/micronaut/hello-world/.mvn/wrapper/maven-wrapper.jar b/micronaut/.mvn/wrapper/maven-wrapper.jar
similarity index 100%
rename from micronaut/hello-world/.mvn/wrapper/maven-wrapper.jar
rename to micronaut/.mvn/wrapper/maven-wrapper.jar
diff --git a/micronaut/hello-world/.mvn/wrapper/maven-wrapper.properties b/micronaut/.mvn/wrapper/maven-wrapper.properties
similarity index 100%
rename from micronaut/hello-world/.mvn/wrapper/maven-wrapper.properties
rename to micronaut/.mvn/wrapper/maven-wrapper.properties
diff --git a/micronaut/hello-world/Dockerfile b/micronaut/Dockerfile
similarity index 100%
rename from micronaut/hello-world/Dockerfile
rename to micronaut/Dockerfile
diff --git a/micronaut/hello-world/micronaut-cli.yml b/micronaut/micronaut-cli.yml
similarity index 100%
rename from micronaut/hello-world/micronaut-cli.yml
rename to micronaut/micronaut-cli.yml
diff --git a/micronaut/hello-world/mvnw b/micronaut/mvnw
similarity index 100%
rename from micronaut/hello-world/mvnw
rename to micronaut/mvnw
diff --git a/micronaut/hello-world/mvnw.cmd b/micronaut/mvnw.cmd
similarity index 100%
rename from micronaut/hello-world/mvnw.cmd
rename to micronaut/mvnw.cmd
diff --git a/micronaut/hello-world/pom.xml b/micronaut/pom.xml
similarity index 100%
rename from micronaut/hello-world/pom.xml
rename to micronaut/pom.xml
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClient.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClient.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClient.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClient.java
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/client/GreetingClient.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/client/GreetingClient.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/client/GreetingClient.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/client/GreetingClient.java
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/ServerApplication.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/ServerApplication.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/ServerApplication.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/ServerApplication.java
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/controller/AsyncGreetController.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/controller/AsyncGreetController.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/controller/AsyncGreetController.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/controller/AsyncGreetController.java
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/controller/GreetController.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/controller/GreetController.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/controller/GreetController.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/controller/GreetController.java
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/service/EnglishGreetingService.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/service/EnglishGreetingService.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/service/EnglishGreetingService.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/service/EnglishGreetingService.java
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/service/GreetingService.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/service/GreetingService.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/service/GreetingService.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/service/GreetingService.java
diff --git a/micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/service/SpanishGreetingService.java b/micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/service/SpanishGreetingService.java
similarity index 100%
rename from micronaut/hello-world/src/main/java/com/baeldung/micronaut/helloworld/server/service/SpanishGreetingService.java
rename to micronaut/src/main/java/com/baeldung/micronaut/helloworld/server/service/SpanishGreetingService.java
diff --git a/micronaut/hello-world/src/main/resources/application.yml b/micronaut/src/main/resources/application.yml
similarity index 100%
rename from micronaut/hello-world/src/main/resources/application.yml
rename to micronaut/src/main/resources/application.yml
diff --git a/micronaut/hello-world/src/main/resources/logback.xml b/micronaut/src/main/resources/logback.xml
similarity index 100%
rename from micronaut/hello-world/src/main/resources/logback.xml
rename to micronaut/src/main/resources/logback.xml
diff --git a/micronaut/hello-world/src/test/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClientTest.java b/micronaut/src/test/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClientTest.java
similarity index 100%
rename from micronaut/hello-world/src/test/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClientTest.java
rename to micronaut/src/test/java/com/baeldung/micronaut/helloworld/client/ConcreteGreetingClientTest.java
diff --git a/micronaut/hello-world/src/test/java/com/baeldung/micronaut/helloworld/client/GreetingClientTest.java b/micronaut/src/test/java/com/baeldung/micronaut/helloworld/client/GreetingClientTest.java
similarity index 100%
rename from micronaut/hello-world/src/test/java/com/baeldung/micronaut/helloworld/client/GreetingClientTest.java
rename to micronaut/src/test/java/com/baeldung/micronaut/helloworld/client/GreetingClientTest.java
diff --git a/msf4j/pom.xml b/msf4j/pom.xml
index f2cfe10f57..cca8281764 100644
--- a/msf4j/pom.xml
+++ b/msf4j/pom.xml
@@ -1,33 +1,33 @@
-
- 4.0.0
- com.baeldung.msf4j
- msf4j
- 0.0.1-SNAPSHOT
- WSO2 MSF4J Microservice
+
+ 4.0.0
+ com.baeldung.msf4j
+ msf4j
+ 0.0.1-SNAPSHOT
-
- org.wso2.msf4j
- msf4j-service
- 2.6.0
-
+
+ org.wso2.msf4j
+ msf4j-service
+ 2.6.0
+
-
-
- org.wso2.msf4j
- msf4j-spring
- ${msf4j.version}
-
-
- org.wso2.msf4j
- msf4j-mustache-template
- ${msf4j.version}
-
-
+
+
+ org.wso2.msf4j
+ msf4j-spring
+ ${msf4j.version}
+
+
+ org.wso2.msf4j
+ msf4j-mustache-template
+ ${msf4j.version}
+
+
-
- com.baeldung.msf4j.msf4jintro.Application
- 2.6.1
-
+
+ com.baeldung.msf4j.msf4jintro.Application
+ 2.6.1
+
\ No newline at end of file
diff --git a/parent-boot-2/pom.xml b/parent-boot-2/pom.xml
index 2d45120f32..ab6162a5a5 100644
--- a/parent-boot-2/pom.xml
+++ b/parent-boot-2/pom.xml
@@ -5,8 +5,7 @@
parent-boot-2
0.0.1-SNAPSHOT
pom
- Parent Boot 2
- Parent for all spring boot 2 modules
+ Parent for all Spring Boot 2 modules
org.springframework.boot
diff --git a/pom.xml b/pom.xml
index 798d4edd00..8a577682ea 100644
--- a/pom.xml
+++ b/pom.xml
@@ -10,273 +10,6 @@
parent-modules
pom
-
- parent-boot-1
- parent-boot-2
- parent-spring-4
- parent-spring-5
- parent-java
- asm
- atomix
- apache-cayenne
- aws
- aws-lambda
- akka-streams
- algorithms
- annotations
- apache-cxf
- apache-fop
- apache-poi
- apache-tika
- apache-thrift
- apache-curator
- apache-zookeeper
- apache-opennlp
- autovalue
- axon
- azure
- bootique
- cdi
-
- core-java
- core-java-collections
- core-java-io
- core-java-8
- core-kotlin
- core-groovy
- core-java-concurrency
- couchbase
- deltaspike
- dozer
- ethereum
- ejb
- feign
- flips
- testing-modules/gatling
- geotools
- testing-modules/groovy-spock
- google-cloud
- google-web-toolkit
- gson
- guava
- guava-modules/guava-18
- guava-modules/guava-19
- guava-modules/guava-21
- guice
- disruptor
- spring-static-resources
- hazelcast
- hbase
- hibernate5
- httpclient
- hystrix
- image-processing
- immutables
- influxdb
- jackson
- persistence-modules/java-cassandra
- vavr
- java-lite
- java-numbers
- java-rmi
- java-vavr-stream
- javax-servlets
- javaxval
- jaxb
- javafx
- jgroups
- jee-7
- jhipster/jhipster-monolithic
- jjwt
- jpa-storedprocedure
- jsf
- json-path
- json
- jsoup
- testing-modules/junit-5
- jws
- libraries
- libraries-data
- linkrest
- logging-modules/log-mdc
- logging-modules/log4j
- logging-modules/log4j2
- logging-modules/logback
- lombok
- mapstruct
- metrics
- maven
- mesos-marathon
- msf4j
- testing-modules/mockito
- testing-modules/mockito-2
- testing-modules/mocks
- mustache
- mvn-wrapper
- noexception
- orientdb
- osgi
- orika
- patterns
- pdf
- protobuffer
- persistence-modules/querydsl
- reactor-core
- persistence-modules/redis
- testing-modules/rest-assured
- testing-modules/rest-testing
- resteasy
- rxjava
- spring-swagger-codegen
- testing-modules/selenium-junit-testng
- persistence-modules/solr
- spark-java
- spring-4
- spring-5
- spring-5-reactive
- spring-5-mvc
- spring-5-security
- spring-activiti
- spring-akka
- spring-amqp
- spring-all
- spring-amqp-simple
- spring-apache-camel
- spring-batch
- spring-bom
- spring-boot
- spring-boot-keycloak
- spring-boot-bootstrap
- spring-boot-admin
- spring-boot-ops
- spring-boot-persistence
- spring-boot-security
- spring-boot-mvc
- spring-boot-logging-log4j2
- spring-cloud-data-flow
- spring-cloud
- spring-core
- spring-cucumber
- spring-ejb
- spring-aop
- persistence-modules/spring-data-cassandra
- spring-data-couchbase-2
- persistence-modules/spring-data-dynamodb
- spring-data-elasticsearch
- spring-data-keyvalue
- spring-data-mongodb
- persistence-modules/spring-data-neo4j
- persistence-modules/spring-data-redis
- spring-data-rest
- persistence-modules/spring-data-solr
- spring-dispatcher-servlet
- spring-exceptions
- spring-freemarker
- persistence-modules/spring-hibernate-3
- spring-hibernate4
- persistence-modules/spring-hibernate-5
- persistence-modules/spring-data-eclipselink
- spring-integration
- spring-jenkins-pipeline
- spring-jersey
- jmeter
- spring-jms
- spring-jooq
- persistence-modules/spring-jpa
- spring-kafka
- spring-katharsis
- spring-ldap
- spring-mockito
- spring-mvc-forms-jsp
- spring-mvc-forms-thymeleaf
- spring-mvc-java
- spring-mvc-velocity
- spring-mvc-webflow
- spring-mvc-xml
- spring-mvc-kotlin
- spring-protobuf
- spring-quartz
- spring-rest-angular
- spring-rest-full
- spring-rest-query-language
- spring-rest
- spring-rest-simple
- spring-security-acl
- spring-security-cache-control
- spring-security-client/spring-security-jsp-authentication
- spring-security-client/spring-security-jsp-authorize
- spring-security-client/spring-security-jsp-config
- spring-security-client/spring-security-mvc
- spring-security-client/spring-security-thymeleaf-authentication
- spring-security-client/spring-security-thymeleaf-authorize
- spring-security-client/spring-security-thymeleaf-config
- spring-security-core
- spring-security-mvc-boot
- spring-security-mvc-custom
- spring-security-mvc-digest-auth
- spring-security-mvc-ldap
- spring-security-mvc-login
- spring-security-mvc-persisted-remember-me
- spring-security-mvc-session
- spring-security-mvc-socket
- spring-security-openid
-
- spring-security-rest-basic-auth
- spring-security-rest-custom
- spring-security-rest
- spring-security-sso
- spring-security-x509
- spring-session
- spring-sleuth
- spring-social-login
- spring-spel
- spring-state-machine
- spring-thymeleaf
- spring-userservice
- spring-zuul
- spring-reactor
- spring-vertx
- spring-jinq
- spring-rest-embedded-tomcat
- testing-modules/testing
- testing-modules/testng
- video-tutorials
- xml
- xmlunit-2
- struts-2
- apache-velocity
- apache-solrj
- rabbitmq
- vertx
- persistence-modules/spring-data-gemfire
- mybatis
- spring-drools
- drools
- persistence-modules/liquibase
- spring-boot-property-exp
- testing-modules/mockserver
- testing-modules/test-containers
- undertow
- vertx-and-rxjava
- saas
- deeplearning4j
- lucene
- vraptor
- persistence-modules/java-cockroachdb
- spring-security-thymeleaf
- persistence-modules/java-jdbi
- jersey
- java-spi
- performance-tests
- twilio
- spring-boot-ctx-fluent
- java-ee-8-security-api
- spring-webflux-amqp
- antlr
- maven-archetype
- apache-meecrowave
-
-
@@ -465,8 +198,9 @@
+
- integration
+ default
@@ -500,15 +234,11 @@
-
parent-boot-1
parent-boot-2
parent-spring-4
parent-spring-5
parent-java
-
-
-
asm
atomix
apache-cayenne
@@ -530,6 +260,7 @@
azure
bootique
cdi
+
core-java
core-java-collections
core-java-io
@@ -544,9 +275,9 @@
ejb
feign
flips
+ testing-modules/gatling
geotools
testing-modules/groovy-spock
- testing-modules/gatling
google-cloud
google-web-toolkit
gson
@@ -600,10 +331,7 @@
maven
mesos-marathon
msf4j
-
-
-
-
+ spring-rest-simple
+ spring-security-acl
+ spring-security-cache-control
+ spring-security-client/spring-security-jsp-authentication
+ spring-security-client/spring-security-jsp-authorize
+ spring-security-client/spring-security-jsp-config
+ spring-security-client/spring-security-mvc
+ spring-security-client/spring-security-thymeleaf-authentication
+ spring-security-client/spring-security-thymeleaf-authorize
+ spring-security-client/spring-security-thymeleaf-config
+ spring-security-core
+ spring-security-mvc-boot
+ spring-security-mvc-custom
+ spring-security-mvc-digest-auth
+ spring-security-mvc-ldap
+ spring-security-mvc-login
+ spring-security-mvc-persisted-remember-me
+ spring-security-mvc-session
+ spring-security-mvc-socket
+ spring-security-openid
+
+ spring-security-rest-basic-auth
+ spring-security-rest-custom
+ spring-security-rest
+ spring-security-sso
+ spring-security-x509
+ spring-session
+ spring-sleuth
+ spring-social-login
+ spring-spel
+ spring-state-machine
+ spring-thymeleaf
+ spring-userservice
+ spring-zuul
+ spring-reactor
+ spring-vertx
+ spring-jinq
+ spring-rest-embedded-tomcat
+ testing-modules/testing
+ testing-modules/testng
+ video-tutorials
+ xml
+ xmlunit-2
+ struts-2
+ apache-velocity
+ apache-solrj
+ rabbitmq
+ vertx
+ persistence-modules/spring-data-gemfire
+ mybatis
+ spring-drools
+ drools
+ persistence-modules/liquibase
+ spring-boot-property-exp
+ testing-modules/mockserver
+ testing-modules/test-containers
+ undertow
+ vertx-and-rxjava
+ saas
+ deeplearning4j
+ lucene
+ vraptor
+ persistence-modules/java-cockroachdb
+ spring-security-thymeleaf
+ persistence-modules/java-jdbi
+ jersey
+ java-spi
+ performance-tests
+ twilio
+ spring-boot-ctx-fluent
+ java-ee-8-security-api
+ spring-webflux-amqp
+ antlr
+ maven-archetype
+ apache-meecrowave
+
+
+
+
+
+ integration
+
+
+
+ org.apache.maven.plugins
+ maven-surefire-plugin
+
+
+ integration-test
+
+ test
+
+
+
+ **/*ManualTest.java
+ **/*LiveTest.java
+
+
+ **/*IntegrationTest.java
+ **/*IntTest.java
+
+
+
+
+
+
+ json
+
+
+
+
+
+
+
+
+ parent-boot-1
+ parent-boot-2
+ parent-spring-4
+ parent-spring-5
+ parent-java
+
+
+
+
+
+
+
+
-
+
+
+
+
+
+
+
+
+
+
+
+ persistence-modules/spring-data-solr
+ spring-dispatcher-servlet
+ spring-exceptions
+ spring-freemarker
+ persistence-modules/spring-hibernate-3
+ spring-hibernate4
+ persistence-modules/spring-hibernate-5
+ persistence-modules/spring-data-eclipselink
+ spring-integration
+ spring-jenkins-pipeline
+ spring-jersey
+ spring-jms
+ spring-jooq
+ persistence-modules/spring-jpa
+ spring-kafka
+ spring-katharsis
+ spring-ldap
+ spring-mockito
+ spring-mvc-forms-jsp
+ spring-mvc-forms-thymeleaf
+ spring-mvc-java
+ spring-mvc-velocity
+ spring-mvc-webflow
+ spring-mvc-xml
+ spring-mvc-kotlin
+ spring-protobuf
+ spring-quartz
+ spring-rest-angular
+ spring-rest-full
+ spring-rest-query-language
+ spring-rest
+ spring-rest-simple
+
+
+
+
+
+
+
+
+
+
+
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/CorsOnAnnotatedElementsApplication.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/CorsOnAnnotatedElementsApplication.java
new file mode 100644
index 0000000000..87efe72a1b
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/CorsOnAnnotatedElementsApplication.java
@@ -0,0 +1,25 @@
+package com.baeldung.reactive.cors.annotated;
+
+import java.util.Collections;
+
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+import org.springframework.boot.autoconfigure.data.mongo.MongoDataAutoConfiguration;
+import org.springframework.boot.autoconfigure.data.mongo.MongoReactiveDataAutoConfiguration;
+import org.springframework.boot.autoconfigure.mongo.MongoAutoConfiguration;
+import org.springframework.boot.autoconfigure.mongo.MongoReactiveAutoConfiguration;
+
+@SpringBootApplication(exclude = { MongoAutoConfiguration.class,
+ MongoDataAutoConfiguration.class,
+ MongoReactiveDataAutoConfiguration.class,
+ MongoReactiveAutoConfiguration.class }
+)
+public class CorsOnAnnotatedElementsApplication {
+
+ public static void main(String[] args) {
+ SpringApplication app = new SpringApplication(CorsOnAnnotatedElementsApplication.class);
+ app.setDefaultProperties(Collections.singletonMap("server.port", "8081"));
+ app.run(args);
+ }
+
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/controllers/CorsOnClassController.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/controllers/CorsOnClassController.java
new file mode 100644
index 0000000000..00bc93a101
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/controllers/CorsOnClassController.java
@@ -0,0 +1,49 @@
+package com.baeldung.reactive.cors.annotated.controllers;
+
+import org.springframework.web.bind.annotation.CrossOrigin;
+import org.springframework.web.bind.annotation.PutMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import reactor.core.publisher.Mono;
+
+@CrossOrigin(value = { "http://allowed-origin.com" }, allowedHeaders = { "Baeldung-Another-Allowed" }, maxAge = 900)
+@RestController
+@RequestMapping("/cors-on-controller")
+public class CorsOnClassController {
+
+ @PutMapping("/regular-endpoint")
+ public Mono corsDisabledEndpoint() {
+ return Mono.just("Regular endpoint");
+ }
+
+ @CrossOrigin
+ @PutMapping("/cors-enabled-endpoint")
+ public Mono corsEnabledEndpoint() {
+ return Mono.just("CORS enabled endpoint");
+ }
+
+ @CrossOrigin({ "http://another-allowed-origin.com" })
+ @PutMapping("/cors-enabled-origin-restrictive-endpoint")
+ public Mono corsEnabledOriginRestrictiveEndpoint() {
+ return Mono.just("CORS enabled endpoint - Origin Restrictive");
+ }
+
+ @CrossOrigin(allowedHeaders = { "Baeldung-Allowed" })
+ @PutMapping("/cors-enabled-header-restrictive-endpoint")
+ public Mono corsEnabledHeaderRestrictiveEndpoint() {
+ return Mono.just("CORS enabled endpoint - Header Restrictive");
+ }
+
+ @CrossOrigin(exposedHeaders = { "Baeldung-Exposed" })
+ @PutMapping("/cors-enabled-exposed-header-endpoint")
+ public Mono corsEnabledExposedHeadersEndpoint() {
+ return Mono.just("CORS enabled endpoint - Exposed Header");
+ }
+
+ @PutMapping("/cors-enabled-mixed-config-endpoint")
+ @CrossOrigin(allowedHeaders = { "Baeldung-Allowed", "Baeldung-Other-Allowed" }, exposedHeaders = { "Baeldung-Allowed", "Baeldung-Exposed" }, maxAge = 3600)
+ public Mono corsEnabledHeaderExposedEndpoint() {
+ return Mono.just("CORS enabled endpoint - Mixed Config");
+ }
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/controllers/CorsOnMethodsController.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/controllers/CorsOnMethodsController.java
new file mode 100644
index 0000000000..3c72d25840
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/annotated/controllers/CorsOnMethodsController.java
@@ -0,0 +1,48 @@
+package com.baeldung.reactive.cors.annotated.controllers;
+
+import org.springframework.web.bind.annotation.CrossOrigin;
+import org.springframework.web.bind.annotation.PutMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import reactor.core.publisher.Mono;
+
+@RestController
+@RequestMapping("/cors-on-methods")
+public class CorsOnMethodsController {
+
+ @PutMapping("/cors-disabled-endpoint")
+ public Mono corsDisabledEndpoint() {
+ return Mono.just("CORS disabled endpoint");
+ }
+
+ @CrossOrigin
+ @PutMapping("/cors-enabled-endpoint")
+ public Mono corsEnabledEndpoint() {
+ return Mono.just("CORS enabled endpoint");
+ }
+
+ @CrossOrigin({ "http://allowed-origin.com" })
+ @PutMapping("/cors-enabled-origin-restrictive-endpoint")
+ public Mono corsEnabledOriginRestrictiveEndpoint() {
+ return Mono.just("CORS enabled endpoint - Origin Restrictive");
+ }
+
+ @CrossOrigin(allowedHeaders = { "Baeldung-Allowed" })
+ @PutMapping("/cors-enabled-header-restrictive-endpoint")
+ public Mono corsEnabledHeaderRestrictiveEndpoint() {
+ return Mono.just("CORS enabled endpoint - Header Restrictive");
+ }
+
+ @CrossOrigin(exposedHeaders = { "Baeldung-Exposed" })
+ @PutMapping("/cors-enabled-exposed-header-endpoint")
+ public Mono corsEnabledExposedHeadersEndpoint() {
+ return Mono.just("CORS enabled endpoint - Exposed Header");
+ }
+
+ @PutMapping("/cors-enabled-mixed-config-endpoint")
+ @CrossOrigin(allowedHeaders = { "Baeldung-Allowed", "Baeldung-Other-Allowed" }, exposedHeaders = { "Baeldung-Allowed", "Baeldung-Exposed" }, maxAge = 3600)
+ public Mono corsEnabledHeaderExposedEndpoint() {
+ return Mono.just("CORS enabled endpoint - Mixed Config");
+ }
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/CorsGlobalConfigApplication.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/CorsGlobalConfigApplication.java
new file mode 100644
index 0000000000..8228944569
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/CorsGlobalConfigApplication.java
@@ -0,0 +1,25 @@
+package com.baeldung.reactive.cors.global;
+
+import java.util.Collections;
+
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+import org.springframework.boot.autoconfigure.data.mongo.MongoDataAutoConfiguration;
+import org.springframework.boot.autoconfigure.data.mongo.MongoReactiveDataAutoConfiguration;
+import org.springframework.boot.autoconfigure.mongo.MongoAutoConfiguration;
+import org.springframework.boot.autoconfigure.mongo.MongoReactiveAutoConfiguration;
+
+@SpringBootApplication(exclude = { MongoAutoConfiguration.class,
+ MongoDataAutoConfiguration.class,
+ MongoReactiveDataAutoConfiguration.class,
+ MongoReactiveAutoConfiguration.class }
+)
+public class CorsGlobalConfigApplication {
+
+ public static void main(String[] args) {
+ SpringApplication app = new SpringApplication(CorsGlobalConfigApplication.class);
+ app.setDefaultProperties(Collections.singletonMap("server.port", "8082"));
+ app.run(args);
+ }
+
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/config/CorsGlobalConfiguration.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/config/CorsGlobalConfiguration.java
new file mode 100644
index 0000000000..92cd6ec50a
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/config/CorsGlobalConfiguration.java
@@ -0,0 +1,22 @@
+package com.baeldung.reactive.cors.global.config;
+
+import org.springframework.context.annotation.Configuration;
+import org.springframework.web.reactive.config.CorsRegistry;
+import org.springframework.web.reactive.config.EnableWebFlux;
+import org.springframework.web.reactive.config.WebFluxConfigurer;
+
+@Configuration
+@EnableWebFlux
+public class CorsGlobalConfiguration implements WebFluxConfigurer {
+
+ @Override
+ public void addCorsMappings(CorsRegistry corsRegistry) {
+ corsRegistry.addMapping("/**")
+ .allowedOrigins("http://allowed-origin.com")
+ .allowedMethods("PUT")
+ .allowedHeaders("Baeldung-Allowed", "Baledung-Another-Allowed")
+ .exposedHeaders("Baeldung-Allowed", "Baeldung-Exposed")
+ .maxAge(3600);
+ }
+
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/controllers/FurtherCorsConfigsController.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/controllers/FurtherCorsConfigsController.java
new file mode 100644
index 0000000000..b6341c9af1
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/controllers/FurtherCorsConfigsController.java
@@ -0,0 +1,24 @@
+package com.baeldung.reactive.cors.global.controllers;
+
+import org.springframework.web.bind.annotation.CrossOrigin;
+import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.RestController;
+
+import reactor.core.publisher.Mono;
+
+@RestController
+@RequestMapping("/cors-on-global-config-and-more")
+public class FurtherCorsConfigsController {
+
+ @DeleteMapping("/further-mixed-config-endpoint")
+ @CrossOrigin(methods = { RequestMethod.DELETE },
+ allowedHeaders = { "Baeldung-Other-Allowed" },
+ exposedHeaders = { "Baeldung-Other-Exposed" }
+ )
+ public Mono corsEnabledHeaderExposedEndpoint() {
+ return Mono.just("CORS Global Configured + Request Configs.");
+ }
+
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/controllers/RegularRestController.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/controllers/RegularRestController.java
new file mode 100644
index 0000000000..5945cfc9f2
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/controllers/RegularRestController.java
@@ -0,0 +1,23 @@
+package com.baeldung.reactive.cors.global.controllers;
+
+import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.PutMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import reactor.core.publisher.Mono;
+
+@RestController
+@RequestMapping("/cors-on-global-config")
+public class RegularRestController {
+
+ @PutMapping("/regular-put-endpoint")
+ public Mono regularPutEndpoint() {
+ return Mono.just("Regular PUT endpoint");
+ }
+
+ @DeleteMapping("/regular-delete-endpoint")
+ public Mono regularDeleteEndpoint() {
+ return Mono.just("Regular DELETE endpoint");
+ }
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/functional/handlers/FunctionalHandler.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/functional/handlers/FunctionalHandler.java
new file mode 100644
index 0000000000..e6e32d7cc8
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/functional/handlers/FunctionalHandler.java
@@ -0,0 +1,18 @@
+package com.baeldung.reactive.cors.global.functional.handlers;
+
+import org.springframework.stereotype.Component;
+import org.springframework.web.reactive.function.server.ServerRequest;
+import org.springframework.web.reactive.function.server.ServerResponse;
+
+import reactor.core.publisher.Mono;
+
+@Component
+public class FunctionalHandler {
+
+ public Mono useHandler(final ServerRequest request) {
+ final String responseMessage = "CORS GLOBAL CONFIG IS NOT EFFECTIVE ON FUNCTIONAL ENDPOINTS!!!";
+
+ return ServerResponse.ok()
+ .body(Mono.just(responseMessage), String.class);
+ }
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/functional/routers/CorsRouterFunctions.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/functional/routers/CorsRouterFunctions.java
new file mode 100644
index 0000000000..19621a9e97
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/global/functional/routers/CorsRouterFunctions.java
@@ -0,0 +1,20 @@
+package com.baeldung.reactive.cors.global.functional.routers;
+
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.web.reactive.function.server.RequestPredicates;
+import org.springframework.web.reactive.function.server.RouterFunction;
+import org.springframework.web.reactive.function.server.RouterFunctions;
+import org.springframework.web.reactive.function.server.ServerResponse;
+
+import com.baeldung.reactive.cors.global.functional.handlers.FunctionalHandler;
+
+@Configuration
+public class CorsRouterFunctions {
+
+ @Bean
+ public RouterFunction responseHeaderRoute(@Autowired FunctionalHandler handler) {
+ return RouterFunctions.route(RequestPredicates.PUT("/global-config-on-functional/cors-disabled-functional-endpoint"), handler::useHandler);
+ }
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/CorsWebFilterApplication.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/CorsWebFilterApplication.java
new file mode 100644
index 0000000000..38140c0d71
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/CorsWebFilterApplication.java
@@ -0,0 +1,25 @@
+package com.baeldung.reactive.cors.webfilter;
+
+import java.util.Collections;
+
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+import org.springframework.boot.autoconfigure.data.mongo.MongoDataAutoConfiguration;
+import org.springframework.boot.autoconfigure.data.mongo.MongoReactiveDataAutoConfiguration;
+import org.springframework.boot.autoconfigure.mongo.MongoAutoConfiguration;
+import org.springframework.boot.autoconfigure.mongo.MongoReactiveAutoConfiguration;
+
+@SpringBootApplication(exclude = { MongoAutoConfiguration.class,
+ MongoDataAutoConfiguration.class,
+ MongoReactiveDataAutoConfiguration.class,
+ MongoReactiveAutoConfiguration.class }
+)
+public class CorsWebFilterApplication {
+
+ public static void main(String[] args) {
+ SpringApplication app = new SpringApplication(CorsWebFilterApplication.class);
+ app.setDefaultProperties(Collections.singletonMap("server.port", "8083"));
+ app.run(args);
+ }
+
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/config/CorsWebFilterConfig.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/config/CorsWebFilterConfig.java
new file mode 100644
index 0000000000..55fbcc2903
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/config/CorsWebFilterConfig.java
@@ -0,0 +1,29 @@
+package com.baeldung.reactive.cors.webfilter.config;
+
+import java.util.Arrays;
+
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.web.cors.CorsConfiguration;
+import org.springframework.web.cors.reactive.CorsWebFilter;
+import org.springframework.web.cors.reactive.UrlBasedCorsConfigurationSource;
+import org.springframework.web.util.pattern.PathPatternParser;
+
+@Configuration
+public class CorsWebFilterConfig {
+
+ @Bean
+ CorsWebFilter corsWebFilter() {
+ CorsConfiguration corsConfig = new CorsConfiguration();
+ corsConfig.setAllowedOrigins(Arrays.asList("http://allowed-origin.com"));
+ corsConfig.setMaxAge(8000L);
+ corsConfig.addAllowedMethod("PUT");
+ corsConfig.addAllowedHeader("Baeldung-Allowed");
+
+ UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(new PathPatternParser());
+ source.registerCorsConfiguration("/**", corsConfig);
+
+ return new CorsWebFilter(source);
+ }
+
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/controllers/FurtherCorsConfigsController.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/controllers/FurtherCorsConfigsController.java
new file mode 100644
index 0000000000..4f9b9bd037
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/controllers/FurtherCorsConfigsController.java
@@ -0,0 +1,26 @@
+package com.baeldung.reactive.cors.webfilter.controllers;
+
+import org.springframework.web.bind.annotation.CrossOrigin;
+import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.RestController;
+
+import reactor.core.publisher.Mono;
+
+@RestController
+@RequestMapping("/web-filter-and-more-on-annotated")
+public class FurtherCorsConfigsController {
+
+ @DeleteMapping("/further-mixed-config-endpoint")
+ @CrossOrigin(methods = { RequestMethod.DELETE },
+ allowedHeaders = { "Baeldung-Other-Allowed" },
+ exposedHeaders = { "Baeldung-Other-Exposed" }
+ )
+ public Mono corsEnabledHeaderExposedEndpoint() {
+ final String responseMessage = "CORS @CrossOrigin IS NOT EFFECTIVE with WebFilter!!!";
+
+ return Mono.just(responseMessage);
+ }
+
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/controllers/RegularRestController.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/controllers/RegularRestController.java
new file mode 100644
index 0000000000..6985810aa5
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/controllers/RegularRestController.java
@@ -0,0 +1,23 @@
+package com.baeldung.reactive.cors.webfilter.controllers;
+
+import org.springframework.web.bind.annotation.DeleteMapping;
+import org.springframework.web.bind.annotation.PutMapping;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+import reactor.core.publisher.Mono;
+
+@RestController
+@RequestMapping("/web-filter-on-annotated")
+public class RegularRestController {
+
+ @PutMapping("/regular-put-endpoint")
+ public Mono regularPutEndpoint() {
+ return Mono.just("Regular PUT endpoint");
+ }
+
+ @DeleteMapping("/regular-delete-endpoint")
+ public Mono regularDeleteEndpoint() {
+ return Mono.just("Regular DELETE endpoint");
+ }
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/functional/handlers/CorsWithWebFilterHandler.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/functional/handlers/CorsWithWebFilterHandler.java
new file mode 100644
index 0000000000..04e4602049
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/functional/handlers/CorsWithWebFilterHandler.java
@@ -0,0 +1,16 @@
+package com.baeldung.reactive.cors.webfilter.functional.handlers;
+
+import org.springframework.stereotype.Component;
+import org.springframework.web.reactive.function.server.ServerRequest;
+import org.springframework.web.reactive.function.server.ServerResponse;
+
+import reactor.core.publisher.Mono;
+
+@Component
+public class CorsWithWebFilterHandler {
+
+ public Mono useHandler(final ServerRequest request) {
+ return ServerResponse.ok()
+ .body(Mono.just("Functional Endpoint"), String.class);
+ }
+}
diff --git a/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/functional/routers/CorsWithWebFilterRouterFunctions.java b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/functional/routers/CorsWithWebFilterRouterFunctions.java
new file mode 100644
index 0000000000..a3905bb79f
--- /dev/null
+++ b/spring-5-reactive/src/main/java/com/baeldung/reactive/cors/webfilter/functional/routers/CorsWithWebFilterRouterFunctions.java
@@ -0,0 +1,20 @@
+package com.baeldung.reactive.cors.webfilter.functional.routers;
+
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.web.reactive.function.server.RequestPredicates;
+import org.springframework.web.reactive.function.server.RouterFunction;
+import org.springframework.web.reactive.function.server.RouterFunctions;
+import org.springframework.web.reactive.function.server.ServerResponse;
+
+import com.baeldung.reactive.cors.webfilter.functional.handlers.CorsWithWebFilterHandler;
+
+@Configuration
+public class CorsWithWebFilterRouterFunctions {
+
+ @Bean
+ public RouterFunction responseHeaderRoute(@Autowired CorsWithWebFilterHandler handler) {
+ return RouterFunctions.route(RequestPredicates.PUT("/web-filter-on-functional/functional-endpoint"), handler::useHandler);
+ }
+}
diff --git a/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnAnnotatedElementsLiveTest.java b/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnAnnotatedElementsLiveTest.java
new file mode 100644
index 0000000000..0043d62e5a
--- /dev/null
+++ b/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnAnnotatedElementsLiveTest.java
@@ -0,0 +1,147 @@
+package com.baeldung.reactive.cors;
+
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Test;
+import org.junit.runner.RunWith;
+import org.springframework.boot.test.context.SpringBootTest;
+import org.springframework.test.context.junit4.SpringRunner;
+import org.springframework.test.web.reactive.server.WebTestClient;
+import org.springframework.test.web.reactive.server.WebTestClient.ResponseSpec;
+
+@RunWith(SpringRunner.class)
+@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
+public class CorsOnAnnotatedElementsLiveTest {
+
+ private static final String BASE_URL = "http://localhost:8081";
+ private static final String BASE_CORS_ON_METHODS_URL = "/cors-on-methods";
+ private static final String BASE_CORS_ON_CONTROLLER_URL = "/cors-on-controller";
+ private static final String CONTROLLER_CORS_ALLOWED_ORIGIN = "http://allowed-origin.com";
+ private static final String CORS_DEFAULT_ORIGIN = "http://default-origin.com";
+
+ private static WebTestClient client;
+
+ @BeforeAll
+ public static void setup() {
+ client = WebTestClient.bindToServer()
+ .baseUrl(BASE_URL)
+ .defaultHeader("Origin", CORS_DEFAULT_ORIGIN)
+ .build();
+ }
+
+ @Test
+ public void whenRequestingMethodCorsEnabledEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.put()
+ .uri(BASE_CORS_ON_METHODS_URL + "/cors-enabled-endpoint")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", "*");
+ }
+
+ @Test
+ public void whenPreflightMethodCorsEnabled_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.options()
+ .uri(BASE_CORS_ON_METHODS_URL + "/cors-enabled-endpoint")
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", "*");
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Methods", "PUT");
+ response.expectHeader()
+ .exists("Access-Control-Max-Age");
+ }
+
+ @Test
+ public void whenRequestingMethodCorsDisabledEndpoint_thenObtainResponseWithoutCorsHeaders() {
+ ResponseSpec response = client.put()
+ .uri(BASE_CORS_ON_METHODS_URL + "/cors-disabled-put-endpoint")
+ .exchange();
+
+ response.expectHeader()
+ .doesNotExist("Access-Control-Allow-Origin");
+ }
+
+ @Test
+ public void whenRequestingMethodCorsRestrictiveOrigin_thenObtainForbiddenResponse() {
+ ResponseSpec response = client.put()
+ .uri(BASE_CORS_ON_METHODS_URL + "/cors-enabled-origin-restrictive-endpoint")
+ .exchange();
+
+ response.expectStatus()
+ .isForbidden();
+ }
+
+ @Test
+ public void whenPreflightMethodCorsRestrictiveOrigin_thenObtainForbiddenResponse() {
+ ResponseSpec response = client.options()
+ .uri(BASE_CORS_ON_METHODS_URL + "/cors-enabled-origin-restrictive-endpoint")
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectStatus()
+ .isForbidden();
+ }
+
+ @Test
+ public void whenPreflightMethodCorsRestrictiveHeader_thenObtainResponseWithAllowedHeaders() {
+ ResponseSpec response = client.options()
+ .uri(BASE_CORS_ON_METHODS_URL + "/cors-enabled-header-restrictive-endpoint")
+ .header("Access-Control-Request-Method", "PUT")
+ .header("Access-Control-Request-Headers", "Baeldung-Not-Allowed, Baeldung-Allowed")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Headers", "Baeldung-Allowed");
+ }
+
+ @Test
+ public void whenPreflightControllerCorsRegularEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.options()
+ .uri(BASE_CORS_ON_CONTROLLER_URL + "/regular-endpoint")
+ .header("Origin", CONTROLLER_CORS_ALLOWED_ORIGIN)
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CONTROLLER_CORS_ALLOWED_ORIGIN);
+ }
+
+ @Test
+ public void whenPreflightControllerCorsRestrictiveOrigin_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.options()
+ .uri(BASE_CORS_ON_CONTROLLER_URL + "/cors-enabled-origin-restrictive-endpoint")
+ .header("Origin", CONTROLLER_CORS_ALLOWED_ORIGIN)
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CONTROLLER_CORS_ALLOWED_ORIGIN);
+ }
+
+ @Test
+ public void whenPreflightControllerCorsRestrictiveOriginWithAnotherAllowedOrigin_thenObtainResponseWithCorsHeaders() {
+ final String anotherAllowedOrigin = "http://another-allowed-origin.com";
+ ResponseSpec response = client.options()
+ .uri(BASE_CORS_ON_CONTROLLER_URL + "/cors-enabled-origin-restrictive-endpoint")
+ .header("Origin", anotherAllowedOrigin)
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", anotherAllowedOrigin);
+ }
+
+ @Test
+ public void whenPreflightControllerCorsExposingHeaders_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.options()
+ .uri(BASE_CORS_ON_CONTROLLER_URL + "/cors-enabled-exposed-header-endpoint")
+ .header("Origin", CONTROLLER_CORS_ALLOWED_ORIGIN)
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Expose-Headers", "Baeldung-Exposed");
+ }
+}
diff --git a/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnGlobalConfigLiveTest.java b/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnGlobalConfigLiveTest.java
new file mode 100644
index 0000000000..39927af4c3
--- /dev/null
+++ b/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnGlobalConfigLiveTest.java
@@ -0,0 +1,99 @@
+package com.baeldung.reactive.cors;
+
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Test;
+import org.junit.runner.RunWith;
+import org.springframework.boot.test.context.SpringBootTest;
+import org.springframework.test.context.junit4.SpringRunner;
+import org.springframework.test.web.reactive.server.WebTestClient;
+import org.springframework.test.web.reactive.server.WebTestClient.ResponseSpec;
+
+@RunWith(SpringRunner.class)
+@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
+public class CorsOnGlobalConfigLiveTest {
+
+ private static final String BASE_URL = "http://localhost:8082";
+ private static final String BASE_REGULAR_URL = "/cors-on-global-config";
+ private static final String BASE_EXTRA_CORS_CONFIG_URL = "/cors-on-global-config-and-more";
+ private static final String BASE_FUNCTIONALS_URL = "/global-config-on-functional";
+ private static final String CORS_DEFAULT_ORIGIN = "http://allowed-origin.com";
+
+ private static WebTestClient client;
+
+ @BeforeAll
+ public static void setup() {
+ client = WebTestClient.bindToServer()
+ .baseUrl(BASE_URL)
+ .defaultHeader("Origin", CORS_DEFAULT_ORIGIN)
+ .build();
+ }
+
+ @Test
+ public void whenRequestingRegularEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.put()
+ .uri(BASE_REGULAR_URL + "/regular-put-endpoint")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CORS_DEFAULT_ORIGIN);
+ }
+
+ @Test
+ public void whenRequestingRegularDeleteEndpoint_thenObtainForbiddenResponse() {
+ ResponseSpec response = client.delete()
+ .uri(BASE_REGULAR_URL + "/regular-delete-endpoint")
+ .exchange();
+
+ response.expectStatus()
+ .isForbidden();
+ }
+
+ @Test
+ public void whenPreflightAllowedDeleteEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.options()
+ .uri(BASE_EXTRA_CORS_CONFIG_URL + "/further-mixed-config-endpoint")
+ .header("Access-Control-Request-Method", "DELETE")
+ .header("Access-Control-Request-Headers", "Baeldung-Not-Allowed, Baeldung-Allowed, Baeldung-Other-Allowed")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CORS_DEFAULT_ORIGIN);
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Methods", "PUT,DELETE");
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Headers", "Baeldung-Allowed, Baeldung-Other-Allowed");
+ response.expectHeader()
+ .exists("Access-Control-Max-Age");
+ }
+
+ @Test
+ public void whenRequestAllowedDeleteEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.delete()
+ .uri(BASE_EXTRA_CORS_CONFIG_URL + "/further-mixed-config-endpoint")
+ .exchange();
+
+ response.expectStatus()
+ .isOk();
+ }
+
+ @Test
+ public void whenPreflightFunctionalEndpoint_thenObtain404Response() {
+ ResponseSpec response = client.options()
+ .uri(BASE_FUNCTIONALS_URL + "/cors-disabled-functional-endpoint")
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectStatus()
+ .isNotFound();
+ }
+
+ @Test
+ public void whenRequestFunctionalEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.put()
+ .uri(BASE_FUNCTIONALS_URL + "/cors-disabled-functional-endpoint")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CORS_DEFAULT_ORIGIN);
+ }
+}
diff --git a/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnWebFilterLiveTest.java b/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnWebFilterLiveTest.java
new file mode 100644
index 0000000000..e5a3c8a99a
--- /dev/null
+++ b/spring-5-reactive/src/test/java/com/baeldung/reactive/cors/CorsOnWebFilterLiveTest.java
@@ -0,0 +1,96 @@
+package com.baeldung.reactive.cors;
+
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Test;
+import org.junit.runner.RunWith;
+import org.springframework.boot.test.context.SpringBootTest;
+import org.springframework.test.context.junit4.SpringRunner;
+import org.springframework.test.web.reactive.server.WebTestClient;
+import org.springframework.test.web.reactive.server.WebTestClient.ResponseSpec;
+
+@RunWith(SpringRunner.class)
+@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
+public class CorsOnWebFilterLiveTest {
+
+ private static final String BASE_URL = "http://localhost:8083";
+ private static final String BASE_REGULAR_URL = "/web-filter-on-annotated";
+ private static final String BASE_EXTRA_CORS_CONFIG_URL = "/web-filter-and-more-on-annotated";
+ private static final String BASE_FUNCTIONALS_URL = "/web-filter-on-functional";
+ private static final String CORS_DEFAULT_ORIGIN = "http://allowed-origin.com";
+
+ private static WebTestClient client;
+
+ @BeforeAll
+ public static void setup() {
+ client = WebTestClient.bindToServer()
+ .baseUrl(BASE_URL)
+ .defaultHeader("Origin", CORS_DEFAULT_ORIGIN)
+ .build();
+ }
+
+ @Test
+ public void whenRequestingRegularEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.put()
+ .uri(BASE_REGULAR_URL + "/regular-put-endpoint")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CORS_DEFAULT_ORIGIN);
+ }
+
+ @Test
+ public void whenRequestingRegularDeleteEndpoint_thenObtainForbiddenResponse() {
+ ResponseSpec response = client.delete()
+ .uri(BASE_REGULAR_URL + "/regular-delete-endpoint")
+ .exchange();
+
+ response.expectStatus()
+ .isForbidden();
+ }
+
+ @Test
+ public void whenPreflightDeleteEndpointWithExtraConfigs_thenObtainForbiddenResponse() {
+ ResponseSpec response = client.options()
+ .uri(BASE_EXTRA_CORS_CONFIG_URL + "/further-mixed-config-endpoint")
+ .header("Access-Control-Request-Method", "DELETE")
+ .exchange();
+
+ response.expectStatus()
+ .isForbidden();
+ }
+
+ @Test
+ public void whenRequestDeleteEndpointWithExtraConfigs_thenObtainForbiddenResponse() {
+ ResponseSpec response = client.delete()
+ .uri(BASE_EXTRA_CORS_CONFIG_URL + "/further-mixed-config-endpoint")
+ .exchange();
+
+ response.expectStatus()
+ .isForbidden();
+ }
+
+ @Test
+ public void whenPreflightFunctionalEndpoint_thenObtain404Response() {
+ ResponseSpec response = client.options()
+ .uri(BASE_FUNCTIONALS_URL + "/functional-endpoint")
+ .header("Access-Control-Request-Method", "PUT")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CORS_DEFAULT_ORIGIN);
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Methods", "PUT");
+ response.expectHeader()
+ .valueEquals("Access-Control-Max-Age", "8000");
+ }
+
+ @Test
+ public void whenRequestFunctionalEndpoint_thenObtainResponseWithCorsHeaders() {
+ ResponseSpec response = client.put()
+ .uri(BASE_FUNCTIONALS_URL + "/functional-endpoint")
+ .exchange();
+
+ response.expectHeader()
+ .valueEquals("Access-Control-Allow-Origin", CORS_DEFAULT_ORIGIN);
+ }
+}
diff --git a/spring-amqp-simple/src/test/java/broadcast/BroadcastMessageControllerIntegrationTest.java b/spring-amqp-simple/src/test/java/broadcast/BroadcastMessageControllerIntegrationTest.java
deleted file mode 100644
index c3be7f1ede..0000000000
--- a/spring-amqp-simple/src/test/java/broadcast/BroadcastMessageControllerIntegrationTest.java
+++ /dev/null
@@ -1,48 +0,0 @@
-package broadcast;
-
-import com.baeldung.springamqpsimple.broadcast.BroadcastConfig;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.springframework.amqp.rabbit.core.RabbitTemplate;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.context.SpringBootTest;
-import org.springframework.boot.test.mock.mockito.MockBean;
-import org.springframework.boot.test.web.client.TestRestTemplate;
-import org.springframework.http.HttpStatus;
-import org.springframework.http.ResponseEntity;
-import org.springframework.test.context.ActiveProfiles;
-import org.springframework.test.context.junit4.SpringRunner;
-
-import static org.junit.Assert.*;
-import static org.mockito.Mockito.*;
-import static org.springframework.boot.test.context.SpringBootTest.WebEnvironment.RANDOM_PORT;
-
-@RunWith(SpringRunner.class)
-@ActiveProfiles("test")
-@SpringBootTest(webEnvironment = RANDOM_PORT)
-public class BroadcastMessageControllerIntegrationTest {
-
- @Autowired
- private TestRestTemplate restTemplate;
-
- @MockBean
- private RabbitTemplate rabbitTemplate;
-
- @Test
- public void whenPostingMessage_thenMessageIsCreated() {
- final String message = "Hello World!";
- ResponseEntity responseEntity = restTemplate.postForEntity("/broadcast", message, Void.class);
-
- assertEquals(HttpStatus.CREATED, responseEntity.getStatusCode());
- }
-
- @Test
- public void whenPostingMessage_thenMessageIsSentToBroker() {
- final String message = "Hello World!";
- restTemplate.postForEntity("/broadcast", message, Void.class);
-
- verify(rabbitTemplate).convertAndSend(BroadcastConfig.fanoutExchangeName, "", message);
- verify(rabbitTemplate).convertAndSend(BroadcastConfig.topicExchangeName, "user.not-important.info", message);
- verify(rabbitTemplate).convertAndSend(BroadcastConfig.topicExchangeName, "user.important.error", message);
- }
-}
\ No newline at end of file
diff --git a/spring-amqp-simple/src/test/java/com/baeldung/springamqpsimple/MessageControllerIntegrationTest.java b/spring-amqp-simple/src/test/java/com/baeldung/springamqpsimple/MessageControllerIntegrationTest.java
deleted file mode 100644
index a053edaa0e..0000000000
--- a/spring-amqp-simple/src/test/java/com/baeldung/springamqpsimple/MessageControllerIntegrationTest.java
+++ /dev/null
@@ -1,46 +0,0 @@
-package com.baeldung.springamqpsimple;
-
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.springframework.amqp.rabbit.core.RabbitTemplate;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.context.SpringBootTest;
-import org.springframework.boot.test.mock.mockito.MockBean;
-import org.springframework.boot.test.web.client.TestRestTemplate;
-import org.springframework.http.HttpStatus;
-import org.springframework.http.ResponseEntity;
-import org.springframework.test.context.ActiveProfiles;
-import org.springframework.test.context.junit4.SpringRunner;
-
-import static org.junit.Assert.assertEquals;
-import static org.mockito.Mockito.verify;
-import static org.springframework.boot.test.context.SpringBootTest.WebEnvironment.RANDOM_PORT;
-
-@RunWith(SpringRunner.class)
-@ActiveProfiles("test")
-@SpringBootTest(webEnvironment = RANDOM_PORT)
-public class MessageControllerIntegrationTest {
-
- @Autowired
- private TestRestTemplate restTemplate;
-
- @MockBean
- private RabbitTemplate rabbitTemplate;
-
- @Test
- public void whenPostingMessage_thenMessageIsCreated() {
- final String message = "Hello World!";
- ResponseEntity responseEntity = restTemplate.postForEntity("/messages", message, Void.class);
-
- assertEquals(HttpStatus.CREATED, responseEntity.getStatusCode());
- }
-
- @Test
- public void whenPostingMessage_thenMessageIsSentToBroker() {
- final String message = "Hello World!";
- restTemplate.postForEntity("/messages", message, Void.class);
-
- verify(rabbitTemplate).convertAndSend(SpringAmqpConfig.queueName, message);
- }
-}
\ No newline at end of file
diff --git a/spring-boot-security/src/main/java/com/baeldung/springbootsecurity/form_login/SpringBootSecurityApplication.java b/spring-boot-security/src/main/java/com/baeldung/springbootsecurity/form_login/SpringBootSecurityApplication.java
deleted file mode 100644
index 9f4796e1f9..0000000000
--- a/spring-boot-security/src/main/java/com/baeldung/springbootsecurity/form_login/SpringBootSecurityApplication.java
+++ /dev/null
@@ -1,12 +0,0 @@
-package com.baeldung.springbootsecurity.form_login;
-
-import org.springframework.boot.SpringApplication;
-import org.springframework.boot.autoconfigure.SpringBootApplication;
-
-@SpringBootApplication(scanBasePackages = "com.baeldung.springbootsecurity.form_login")
-public class SpringBootSecurityApplication {
-
- public static void main(String[] args) {
- SpringApplication.run(SpringBootSecurityApplication.class, args);
- }
-}
diff --git a/spring-boot-security/src/main/java/com/baeldung/springbootsecurity/form_login/configuration/SecurityConfiguration.java b/spring-boot-security/src/main/java/com/baeldung/springbootsecurity/form_login/configuration/SecurityConfiguration.java
deleted file mode 100644
index 6ab522ef00..0000000000
--- a/spring-boot-security/src/main/java/com/baeldung/springbootsecurity/form_login/configuration/SecurityConfiguration.java
+++ /dev/null
@@ -1,67 +0,0 @@
-package com.baeldung.springbootsecurity.form_login.configuration;
-
-import com.fasterxml.jackson.databind.ObjectMapper;
-import org.springframework.context.annotation.Bean;
-import org.springframework.context.annotation.Configuration;
-import org.springframework.http.HttpStatus;
-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.core.AuthenticationException;
-import org.springframework.security.web.authentication.AuthenticationFailureHandler;
-
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-import java.io.IOException;
-import java.util.Calendar;
-import java.util.HashMap;
-import java.util.Map;
-
-@Configuration
-@EnableWebSecurity
-public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
-
- @Override
- protected void configure(AuthenticationManagerBuilder auth) throws Exception {
- auth
- .inMemoryAuthentication()
- .withUser("baeldung")
- .password("baeldung")
- .roles("USER");
- }
-
- @Override
- protected void configure(HttpSecurity http) throws Exception {
- http
- .authorizeRequests()
- .anyRequest()
- .authenticated()
- .and()
- .formLogin()
- .failureHandler(customAuthenticationFailureHandler());
- }
-
- @Bean
- public AuthenticationFailureHandler customAuthenticationFailureHandler() {
- return new CustomAuthenticationFailureHandler();
- }
-
- /**
- * Custom AuthenticationFailureHandler
- */
- public class CustomAuthenticationFailureHandler implements AuthenticationFailureHandler {
- private final ObjectMapper objectMapper = new ObjectMapper();
-
- @Override
- public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) throws IOException, ServletException {
- response.setStatus(HttpStatus.UNAUTHORIZED.value());
- Map data = new HashMap<>();
- data.put("timestamp", Calendar.getInstance().getTime());
- data.put("exception", exception.getMessage());
-
- response.getOutputStream().println(objectMapper.writeValueAsString(data));
- }
- }
-}
diff --git a/spring-boot-security/src/test/java/com/baeldung/springbootsecurity/form_login/FormLoginIntegrationTest.java b/spring-boot-security/src/test/java/com/baeldung/springbootsecurity/form_login/FormLoginIntegrationTest.java
deleted file mode 100644
index d5b5d8637b..0000000000
--- a/spring-boot-security/src/test/java/com/baeldung/springbootsecurity/form_login/FormLoginIntegrationTest.java
+++ /dev/null
@@ -1,87 +0,0 @@
-package com.baeldung.springbootsecurity.form_login;
-
-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.test.context.junit4.SpringRunner;
-import org.springframework.test.web.servlet.MockMvc;
-import org.springframework.test.web.servlet.MvcResult;
-import org.springframework.test.web.servlet.setup.MockMvcBuilders;
-import org.springframework.web.context.WebApplicationContext;
-
-import javax.servlet.Filter;
-
-import static org.junit.Assert.assertTrue;
-import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.formLogin;
-import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.csrf;
-import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.authenticated;
-import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.unauthenticated;
-import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
-import static org.springframework.test.web.servlet.result.MockMvcResultHandlers.print;
-import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.redirectedUrl;
-import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
-
-@RunWith(SpringRunner.class)
-@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT, classes = com.baeldung.springbootsecurity.form_login.SpringBootSecurityApplication.class)
-public class FormLoginIntegrationTest {
-
- @Autowired
- private WebApplicationContext context;
-
- @Autowired
- private Filter springSecurityFilterChain;
-
- private MockMvc mvc;
-
- @Before
- public void setup() {
- mvc = MockMvcBuilders
- .webAppContextSetup(context)
- .addFilters(springSecurityFilterChain)
- .build();
- }
-
- @Test
- public void givenRequestWithoutSessionOrCsrfToken_shouldFailWith403() throws Exception {
- mvc
- .perform(post("/"))
- .andExpect(status().isForbidden());
- }
-
- @Test
- public void givenRequestWithInvalidCsrfToken_shouldFailWith403() throws Exception {
- mvc
- .perform(post("/").with(csrf().useInvalidToken()))
- .andExpect(status().isForbidden());
- }
-
- @Test
- public void givenRequestWithValidCsrfTokenAndWithoutSessionToken_shouldReceive302WithLocationHeaderToLoginPage() throws Exception {
- MvcResult mvcResult = mvc.perform(post("/").with(csrf())).andReturn();
- assertTrue(mvcResult.getResponse().getStatus() == 302);
- assertTrue(mvcResult.getResponse().getHeader("Location").contains("login"));
- }
-
- @Test
- public void givenValidRequestWithValidCredentials_shouldLoginSuccessfully() throws Exception {
- mvc
- .perform(formLogin().user("baeldung").password("baeldung"))
- .andExpect(status().isFound())
- .andExpect(redirectedUrl("/"))
- .andExpect(authenticated().withUsername("baeldung"));
- }
-
- @Test
- public void givenValidRequestWithInvalidCredentials_shouldFailWith401() throws Exception {
- MvcResult result = mvc
- .perform(formLogin().user("random").password("random"))
- .andExpect(status().isUnauthorized())
- .andDo(print())
- .andExpect(unauthenticated())
- .andReturn();
-
- assertTrue(result.getResponse().getContentAsString().contains("Bad credentials"));
- }
-}
diff --git a/spring-boot-security/src/test/java/com/baeldung/springbootsecurity/form_login/FormLoginUnitTest.java b/spring-boot-security/src/test/java/com/baeldung/springbootsecurity/form_login/FormLoginUnitTest.java
deleted file mode 100644
index d518f3b0c2..0000000000
--- a/spring-boot-security/src/test/java/com/baeldung/springbootsecurity/form_login/FormLoginUnitTest.java
+++ /dev/null
@@ -1,87 +0,0 @@
-package com.baeldung.springbootsecurity.form_login;
-
-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.test.context.junit4.SpringRunner;
-import org.springframework.test.web.servlet.MockMvc;
-import org.springframework.test.web.servlet.MvcResult;
-import org.springframework.test.web.servlet.setup.MockMvcBuilders;
-import org.springframework.web.context.WebApplicationContext;
-
-import javax.servlet.Filter;
-
-import static org.junit.Assert.assertTrue;
-import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.formLogin;
-import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestPostProcessors.csrf;
-import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.authenticated;
-import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.unauthenticated;
-import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
-import static org.springframework.test.web.servlet.result.MockMvcResultHandlers.print;
-import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.redirectedUrl;
-import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
-
-@RunWith(SpringRunner.class)
-@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT, classes = com.baeldung.springbootsecurity.form_login.SpringBootSecurityApplication.class)
-public class FormLoginUnitTest {
-
- @Autowired
- private WebApplicationContext context;
-
- @Autowired
- private Filter springSecurityFilterChain;
-
- private MockMvc mvc;
-
- @Before
- public void setup() {
- mvc = MockMvcBuilders
- .webAppContextSetup(context)
- .addFilters(springSecurityFilterChain)
- .build();
- }
-
- @Test
- public void givenRequestWithoutSessionOrCsrfToken_shouldFailWith403() throws Exception {
- mvc
- .perform(post("/"))
- .andExpect(status().isForbidden());
- }
-
- @Test
- public void givenRequestWithInvalidCsrfToken_shouldFailWith403() throws Exception {
- mvc
- .perform(post("/").with(csrf().useInvalidToken()))
- .andExpect(status().isForbidden());
- }
-
- @Test
- public void givenRequestWithValidCsrfTokenAndWithoutSessionToken_shouldReceive302WithLocationHeaderToLoginPage() throws Exception {
- MvcResult mvcResult = mvc.perform(post("/").with(csrf())).andReturn();
- assertTrue(mvcResult.getResponse().getStatus() == 302);
- assertTrue(mvcResult.getResponse().getHeader("Location").contains("login"));
- }
-
- @Test
- public void givenValidRequestWithValidCredentials_shouldLoginSuccessfully() throws Exception {
- mvc
- .perform(formLogin().user("baeldung").password("baeldung"))
- .andExpect(status().isFound())
- .andExpect(redirectedUrl("/"))
- .andExpect(authenticated().withUsername("baeldung"));
- }
-
- @Test
- public void givenValidRequestWithInvalidCredentials_shouldFailWith401() throws Exception {
- MvcResult result = mvc
- .perform(formLogin().user("random").password("random"))
- .andExpect(status().isUnauthorized())
- .andDo(print())
- .andExpect(unauthenticated())
- .andReturn();
-
- assertTrue(result.getResponse().getContentAsString().contains("Bad credentials"));
- }
-}
diff --git a/spring-data-5-reactive/pom.xml b/spring-data-5-reactive/pom.xml
index b2a317878f..bcf37f1da4 100644
--- a/spring-data-5-reactive/pom.xml
+++ b/spring-data-5-reactive/pom.xml
@@ -6,8 +6,6 @@
spring-5-data-reactive
0.0.1-SNAPSHOT
jar
- Spring-5-data-reactive
- Spring-5-data-reactive with Springboot 2.0.1
org.springframework.boot
diff --git a/spring-data-rest/src/test/java/com/baeldung/relationships/SpringDataRelationshipsIntegrationTest.java b/spring-data-rest/src/test/java/com/baeldung/relationships/SpringDataRelationshipsIntegrationTest.java
deleted file mode 100644
index 196dc18d9e..0000000000
--- a/spring-data-rest/src/test/java/com/baeldung/relationships/SpringDataRelationshipsIntegrationTest.java
+++ /dev/null
@@ -1,107 +0,0 @@
-package com.baeldung.relationships;
-
-import static org.junit.Assert.assertEquals;
-
-import org.json.JSONArray;
-import org.json.JSONException;
-import org.json.JSONObject;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.beans.factory.annotation.Value;
-import org.springframework.boot.test.context.SpringBootTest;
-import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;
-import org.springframework.boot.test.web.client.TestRestTemplate;
-import org.springframework.http.HttpEntity;
-import org.springframework.http.HttpHeaders;
-import org.springframework.http.HttpMethod;
-import org.springframework.http.ResponseEntity;
-import org.springframework.test.context.junit4.SpringRunner;
-
-import com.baeldung.SpringDataRestApplication;
-import com.baeldung.models.Address;
-import com.baeldung.models.Author;
-import com.baeldung.models.Book;
-import com.baeldung.models.Library;
-
-@RunWith(SpringRunner.class)
-@SpringBootTest(classes = SpringDataRestApplication.class, webEnvironment = WebEnvironment.RANDOM_PORT)
-public class SpringDataRelationshipsIntegrationTest {
-
- @Autowired
- private TestRestTemplate template;
-
- @Value("${local.server.port}")
- private int port;
-
- private static final String BOOK_ENDPOINT = "http://localhost:%s/books/";
- private static final String AUTHOR_ENDPOINT = "http://localhost:%s/authors/";
- private static final String ADDRESS_ENDPOINT = "http://localhost:%s/addresses/";
- private static final String LIBRARY_ENDPOINT = "http://localhost:%s/libraries/";
-
- private static final String LIBRARY_NAME = "My Library";
- private static final String AUTHOR_NAME = "George Orwell";
-
- @Test
- public void whenSaveOneToOneRelationship_thenCorrect() throws JSONException {
- Library library = new Library(LIBRARY_NAME);
- template.postForEntity(String.format(LIBRARY_ENDPOINT, port), library, Library.class);
-
- Address address = new Address("Main street, nr 1");
- template.postForEntity(String.format(ADDRESS_ENDPOINT, port), address, Address.class);
-
- HttpHeaders requestHeaders = new HttpHeaders();
- requestHeaders.add("Content-type", "text/uri-list");
- HttpEntity httpEntity = new HttpEntity<>(String.format(ADDRESS_ENDPOINT, port) + "/1", requestHeaders);
- template.exchange(String.format(LIBRARY_ENDPOINT, port) + "/1/libraryAddress", HttpMethod.PUT, httpEntity, String.class);
-
- ResponseEntity libraryGetResponse = template.getForEntity(String.format(ADDRESS_ENDPOINT, port) + "/1/library", Library.class);
- assertEquals("library is incorrect", libraryGetResponse.getBody()
- .getName(), LIBRARY_NAME);
- }
-
- @Test
- public void whenSaveOneToManyRelationship_thenCorrect() throws JSONException{
- Library library = new Library(LIBRARY_NAME);
- template.postForEntity(String.format(LIBRARY_ENDPOINT, port), library, Library.class);
-
- Book book1 = new Book("Dune");
- template.postForEntity(String.format(BOOK_ENDPOINT, port), book1, Book.class);
-
- Book book2 = new Book("1984");
- template.postForEntity(String.format(BOOK_ENDPOINT, port), book2, Book.class);
-
- HttpHeaders requestHeaders = new HttpHeaders();
- requestHeaders.add("Content-type", "text/uri-list");
- HttpEntity bookHttpEntity = new HttpEntity<>(String.format(LIBRARY_ENDPOINT, port) + "/1", requestHeaders);
- template.exchange(String.format(BOOK_ENDPOINT, port) + "/1/library", HttpMethod.PUT, bookHttpEntity, String.class);
- template.exchange(String.format(BOOK_ENDPOINT, port) + "/2/library", HttpMethod.PUT, bookHttpEntity, String.class);
-
- ResponseEntity libraryGetResponse = template.getForEntity(String.format(BOOK_ENDPOINT, port) + "/1/library", Library.class);
- assertEquals("library is incorrect", libraryGetResponse.getBody()
- .getName(), LIBRARY_NAME);
- }
-
- @Test
- public void whenSaveManyToManyRelationship_thenCorrect() throws JSONException{
- Author author1 = new Author(AUTHOR_NAME);
- template.postForEntity(String.format(AUTHOR_ENDPOINT, port), author1, Author.class);
-
- Book book1 = new Book("Animal Farm");
- template.postForEntity(String.format(BOOK_ENDPOINT, port), book1, Book.class);
-
- Book book2 = new Book("1984");
- template.postForEntity(String.format(BOOK_ENDPOINT, port), book2, Book.class);
-
- HttpHeaders requestHeaders = new HttpHeaders();
- requestHeaders.add("Content-type", "text/uri-list");
- HttpEntity httpEntity = new HttpEntity<>(String.format(BOOK_ENDPOINT, port) + "/1\n" + String.format(BOOK_ENDPOINT, port) + "/2", requestHeaders);
- template.exchange(String.format(AUTHOR_ENDPOINT, port) + "/1/books", HttpMethod.PUT, httpEntity, String.class);
-
- String jsonResponse = template.getForObject(String.format(BOOK_ENDPOINT, port) + "/1/authors", String.class);
- JSONObject jsonObj = new JSONObject(jsonResponse).getJSONObject("_embedded");
- JSONArray jsonArray = jsonObj.getJSONArray("authors");
- assertEquals("author is incorrect", jsonArray.getJSONObject(0)
- .getString("name"), AUTHOR_NAME);
- }
-}
diff --git a/spring-security-anguar/server/src/test/java/com/baeldung/springbootsecurityrest/BasicAuthConfigurationIntegrationTest.java b/spring-security-anguar/server/src/test/java/com/baeldung/springbootsecurityrest/BasicAuthConfigurationIntegrationTest.java
deleted file mode 100644
index 952a0806a1..0000000000
--- a/spring-security-anguar/server/src/test/java/com/baeldung/springbootsecurityrest/BasicAuthConfigurationIntegrationTest.java
+++ /dev/null
@@ -1,87 +0,0 @@
-package com.baeldung.springbootsecurityrest;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-import static org.springframework.boot.test.context.SpringBootTest.WebEnvironment.RANDOM_PORT;
-
-import java.io.IOException;
-import java.net.MalformedURLException;
-import java.net.URL;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.springframework.boot.context.embedded.LocalServerPort;
-import org.springframework.boot.test.context.SpringBootTest;
-import org.springframework.boot.test.web.client.TestRestTemplate;
-import org.springframework.http.HttpStatus;
-import org.springframework.http.ResponseEntity;
-import org.springframework.test.context.junit4.SpringRunner;
-
-import com.baeldung.springbootsecurityrest.basicauth.SpringBootSecurityApplication;
-import com.baeldung.springbootsecurityrest.vo.User;
-
-@RunWith(SpringRunner.class)
-@SpringBootTest(webEnvironment = RANDOM_PORT, classes = SpringBootSecurityApplication.class)
-public class BasicAuthConfigurationIntegrationTest {
-
- TestRestTemplate restTemplate;
- URL base;
-
- @LocalServerPort int port;
-
- @Before
- public void setUp() throws MalformedURLException {
- restTemplate = new TestRestTemplate("user", "password");
- base = new URL("http://localhost:" + port);
- }
-
- @Test
- public void givenCorrectCredentials_whenLogin_ThenSuccess() throws IllegalStateException, IOException {
- restTemplate = new TestRestTemplate();
- User user = new User();
- user.setUserName("user");
- user.setPassword("password");
- ResponseEntity response = restTemplate.postForEntity(base.toString()+"/login",user, String.class);
-
- assertEquals(HttpStatus.OK, response.getStatusCode());
- assertTrue(response
- .getBody()
- .contains("true"));
- }
-
- @Test
- public void givenWrongCredentials_whenLogin_ThenReturnFalse() throws IllegalStateException, IOException {
- restTemplate = new TestRestTemplate();
- User user = new User();
- user.setUserName("user");
- user.setPassword("wrongpassword");
- ResponseEntity response = restTemplate.postForEntity(base.toString()+"/login",user, String.class);
-
- assertEquals(HttpStatus.OK, response.getStatusCode());
- assertTrue(response
- .getBody()
- .contains("false"));
- }
-
- @Test
- public void givenLoggedInUser_whenRequestsHomePage_ThenSuccess() throws IllegalStateException, IOException {
- ResponseEntity response = restTemplate.getForEntity(base.toString()+"/user", String.class);
-
- assertEquals(HttpStatus.OK, response.getStatusCode());
- assertTrue(response
- .getBody()
- .contains("user"));
- }
-
- @Test
- public void givenWrongCredentials_whenRequestsHomePage_ThenUnauthorized() throws IllegalStateException, IOException {
- restTemplate = new TestRestTemplate("user", "wrongpassword");
- ResponseEntity response = restTemplate.getForEntity(base.toString()+"/user", String.class);
-
- assertEquals(HttpStatus.UNAUTHORIZED, response.getStatusCode());
- assertTrue(response
- .getBody()
- .contains("Unauthorized"));
- }
-}
diff --git a/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/ManualSecurityConfig.java b/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/ManualSecurityConfig.java
index 874856095c..23d13a0ff1 100644
--- a/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/ManualSecurityConfig.java
+++ b/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/ManualSecurityConfig.java
@@ -3,7 +3,6 @@ package org.baeldung.security.spring;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
-import org.springframework.security.config.BeanIds;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
@@ -24,7 +23,7 @@ public class ManualSecurityConfig extends WebSecurityConfigurerAdapter {
@Override
protected void configure(final AuthenticationManagerBuilder auth) throws Exception {
- auth.inMemoryAuthentication().withUser("user1").password("user1Pass").authorities("ROLE_USER").and().withUser("admin").password("adminPass").authorities("ROLE_ADMIN");
+ auth.inMemoryAuthentication().withUser("user1").password("{noop}user1Pass").authorities("ROLE_USER").and().withUser("admin").password("adminPass").authorities("ROLE_ADMIN");
}
@Override
@@ -32,7 +31,7 @@ public class ManualSecurityConfig extends WebSecurityConfigurerAdapter {
web.ignoring().antMatchers("/resources/**");
}
- @Bean(name = BeanIds.AUTHENTICATION_MANAGER)
+ @Bean("authenticationManager")
@Override
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
diff --git a/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithCsrfConfig.java b/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithCsrfConfig.java
index 9600977e37..ca401622c0 100644
--- a/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithCsrfConfig.java
+++ b/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithCsrfConfig.java
@@ -1,6 +1,8 @@
package org.baeldung.security.spring;
+import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
+import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
@@ -17,7 +19,11 @@ public class SecurityWithCsrfConfig extends WebSecurityConfigurerAdapter {
super();
}
- // java config
+ @Bean("authenticationManager")
+ @Override
+ public AuthenticationManager authenticationManagerBean() throws Exception {
+ return super.authenticationManagerBean();
+ }
@Override
protected void configure(final AuthenticationManagerBuilder auth) throws Exception {
diff --git a/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithoutCsrfConfig.java b/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithoutCsrfConfig.java
index f7dbd5b42c..1067c70fea 100644
--- a/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithoutCsrfConfig.java
+++ b/spring-security-mvc-custom/src/test/java/org/baeldung/security/spring/SecurityWithoutCsrfConfig.java
@@ -1,6 +1,8 @@
package org.baeldung.security.spring;
+import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
+import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
@@ -17,7 +19,11 @@ public class SecurityWithoutCsrfConfig extends WebSecurityConfigurerAdapter {
super();
}
- // java config
+ @Bean("authenticationManager")
+ @Override
+ public AuthenticationManager authenticationManagerBean() throws Exception {
+ return super.authenticationManagerBean();
+ }
@Override
protected void configure(final AuthenticationManagerBuilder auth) throws Exception {
diff --git a/spring-security-mvc-login/src/main/java/org/baeldung/security/CustomAuthenticationFailureHandler.java b/spring-security-mvc-login/src/main/java/org/baeldung/security/CustomAuthenticationFailureHandler.java
new file mode 100644
index 0000000000..5eddf3883e
--- /dev/null
+++ b/spring-security-mvc-login/src/main/java/org/baeldung/security/CustomAuthenticationFailureHandler.java
@@ -0,0 +1,22 @@
+package org.baeldung.security;
+
+import org.springframework.http.HttpStatus;
+import org.springframework.security.core.AuthenticationException;
+import org.springframework.security.web.authentication.AuthenticationFailureHandler;
+
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import java.io.IOException;
+import java.util.Calendar;
+
+public class CustomAuthenticationFailureHandler implements AuthenticationFailureHandler {
+
+ @Override
+ public void onAuthenticationFailure(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, AuthenticationException e) throws IOException, ServletException {
+ httpServletResponse.setStatus(HttpStatus.UNAUTHORIZED.value());
+
+ String jsonPayload = "{\"message\" : \"%s\", \"timestamp\" : \"%s\" }";
+ httpServletResponse.getOutputStream().println(String.format(jsonPayload, e.getMessage(), Calendar.getInstance().getTime()));
+ }
+}
diff --git a/spring-security-mvc-login/src/main/java/org/baeldung/spring/SecSecurityConfig.java b/spring-security-mvc-login/src/main/java/org/baeldung/spring/SecSecurityConfig.java
index d9a43d48d0..accc7c9afd 100644
--- a/spring-security-mvc-login/src/main/java/org/baeldung/spring/SecSecurityConfig.java
+++ b/spring-security-mvc-login/src/main/java/org/baeldung/spring/SecSecurityConfig.java
@@ -1,6 +1,7 @@
package org.baeldung.spring;
import org.baeldung.security.CustomAccessDeniedHandler;
+import org.baeldung.security.CustomAuthenticationFailureHandler;
import org.baeldung.security.CustomLogoutSuccessHandler;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@@ -10,6 +11,7 @@ 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.web.access.AccessDeniedHandler;
+import org.springframework.security.web.authentication.AuthenticationFailureHandler;
import org.springframework.security.web.authentication.logout.LogoutSuccessHandler;
@Configuration
@@ -26,11 +28,11 @@ public class SecSecurityConfig extends WebSecurityConfigurerAdapter {
protected void configure(final AuthenticationManagerBuilder auth) throws Exception {
// @formatter:off
auth.inMemoryAuthentication()
- .withUser("user1").password("user1Pass").roles("USER")
- .and()
- .withUser("user2").password("user2Pass").roles("USER")
- .and()
- .withUser("admin").password("adminPass").roles("ADMIN");
+ .withUser("user1").password("user1Pass").roles("USER")
+ .and()
+ .withUser("user2").password("user2Pass").roles("USER")
+ .and()
+ .withUser("admin").password("adminPass").roles("ADMIN");
// @formatter:on
}
@@ -38,23 +40,24 @@ public class SecSecurityConfig extends WebSecurityConfigurerAdapter {
protected void configure(final HttpSecurity http) throws Exception {
// @formatter:off
http
- .csrf().disable()
- .authorizeRequests()
- .antMatchers("/admin/**").hasRole("ADMIN")
- .antMatchers("/anonymous*").anonymous()
- .antMatchers("/login*").permitAll()
- .anyRequest().authenticated()
- .and()
- .formLogin()
- .loginPage("/login.html")
- .loginProcessingUrl("/perform_login")
- .defaultSuccessUrl("/homepage.html",true)
- .failureUrl("/login.html?error=true")
- .and()
- .logout()
- .logoutUrl("/perform_logout")
- .deleteCookies("JSESSIONID")
- .logoutSuccessHandler(logoutSuccessHandler());
+ .csrf().disable()
+ .authorizeRequests()
+ .antMatchers("/admin/**").hasRole("ADMIN")
+ .antMatchers("/anonymous*").anonymous()
+ .antMatchers("/login*").permitAll()
+ .anyRequest().authenticated()
+ .and()
+ .formLogin()
+ .loginPage("/login.html")
+ .loginProcessingUrl("/perform_login")
+ .defaultSuccessUrl("/homepage.html", true)
+ //.failureUrl("/login.html?error=true")
+ .failureHandler(authenticationFailureHandler())
+ .and()
+ .logout()
+ .logoutUrl("/perform_logout")
+ .deleteCookies("JSESSIONID")
+ .logoutSuccessHandler(logoutSuccessHandler());
//.and()
//.exceptionHandling().accessDeniedPage("/accessDenied");
//.exceptionHandling().accessDeniedHandler(accessDeniedHandler());
@@ -71,4 +74,8 @@ public class SecSecurityConfig extends WebSecurityConfigurerAdapter {
return new CustomAccessDeniedHandler();
}
+ @Bean
+ public AuthenticationFailureHandler authenticationFailureHandler() {
+ return new CustomAuthenticationFailureHandler();
+ }
}
diff --git a/spring-security-mvc-login/src/main/resources/webSecurityConfig.xml b/spring-security-mvc-login/src/main/resources/webSecurityConfig.xml
index f0fa956934..189522889f 100644
--- a/spring-security-mvc-login/src/main/resources/webSecurityConfig.xml
+++ b/spring-security-mvc-login/src/main/resources/webSecurityConfig.xml
@@ -15,20 +15,22 @@
-
+
-
+
+
+
diff --git a/spring-security-mvc-login/src/test/java/org/baeldung/security/FormLoginUnitTest.java b/spring-security-mvc-login/src/test/java/org/baeldung/security/FormLoginUnitTest.java
new file mode 100644
index 0000000000..4b3a091e6c
--- /dev/null
+++ b/spring-security-mvc-login/src/test/java/org/baeldung/security/FormLoginUnitTest.java
@@ -0,0 +1,63 @@
+package org.baeldung.security;
+
+import org.baeldung.spring.SecSecurityConfig;
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.test.context.ContextConfiguration;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+import org.springframework.test.context.web.WebAppConfiguration;
+import org.springframework.test.web.servlet.MockMvc;
+import org.springframework.test.web.servlet.MvcResult;
+import org.springframework.test.web.servlet.setup.MockMvcBuilders;
+import org.springframework.web.context.WebApplicationContext;
+
+import javax.servlet.Filter;
+
+import static org.junit.Assert.assertTrue;
+import static org.springframework.security.test.web.servlet.request.SecurityMockMvcRequestBuilders.formLogin;
+import static org.springframework.security.test.web.servlet.response.SecurityMockMvcResultMatchers.authenticated;
+import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
+
+@RunWith(SpringJUnit4ClassRunner.class)
+@ContextConfiguration(classes = {SecSecurityConfig.class})
+@WebAppConfiguration
+public class FormLoginUnitTest {
+
+ @Autowired
+ private WebApplicationContext context;
+
+ @Autowired
+ private Filter springSecurityFilterChain;
+
+ private MockMvc mvc;
+
+ @Before
+ public void setup() {
+ mvc = MockMvcBuilders
+ .webAppContextSetup(context)
+ .addFilters(springSecurityFilterChain)
+ .build();
+ }
+
+ @Test
+ public void givenValidRequestWithValidCredentials_shouldLoginSuccessfully() throws Exception {
+ mvc
+ .perform(formLogin("/perform_login").user("user1").password("user1Pass"))
+ .andExpect(status().isFound())
+ .andExpect(authenticated().withUsername("user1"));
+ }
+
+ @Test
+ public void givenValidRequestWithInvalidCredentials_shouldFailWith401() throws Exception {
+ MvcResult result = mvc
+ .perform(formLogin("/perform_login").user("random").password("random")).andReturn();
+ /*.andExpect(status().isUnauthorized())
+ .andDo(print())
+ .andExpect(unauthenticated())
+ .andReturn();*/
+
+ assertTrue(result.getResponse().getContentAsString().contains("Bad credentials"));
+ }
+}
diff --git a/spring-security-x509/keystore/Makefile b/spring-security-x509/keystore/Makefile
index 5321be9de3..63498fea76 100644
--- a/spring-security-x509/keystore/Makefile
+++ b/spring-security-x509/keystore/Makefile
@@ -85,4 +85,4 @@ add-client:
clean:
# Remove generated artifacts
- find . ! -name Makefile -type f -exec rm -f {} \;
+ find . \( -name "$(CLIENTNAME)*" -o -name "$(HOSTNAME)*" -o -name "$(KEYSTORE)" -o -name "$(TRUSTSTORE)" -o -name ca.crt \) -type f -exec rm -f {} \;
diff --git a/testing-modules/groovy-spock/pom.xml b/testing-modules/groovy-spock/pom.xml
index f1f0883277..e0da345eb4 100644
--- a/testing-modules/groovy-spock/pom.xml
+++ b/testing-modules/groovy-spock/pom.xml
@@ -6,7 +6,6 @@
groovy-spock
1.0-SNAPSHOT
jar
- Spock Framework - Example Project
com.baeldung
diff --git a/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockAnnotationUnitTest.java b/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockAnnotationUnitTest.java
index 5d565fea88..fcc646e8ea 100644
--- a/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockAnnotationUnitTest.java
+++ b/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockAnnotationUnitTest.java
@@ -15,18 +15,22 @@ public class MockAnnotationUnitTest {
UserRepository mockRepository;
@Test
- public void testMockAnnotation() {
+ public void givenCountMethodMocked_WhenCountInvoked_ThenMockValueReturned() {
Mockito.when(mockRepository.count()).thenReturn(123L);
+
long userCount = mockRepository.count();
+
Assert.assertEquals(123L, userCount);
Mockito.verify(mockRepository).count();
}
@Test
- public void testMockitoMockMethod() {
+ public void givenCountMethodOfLocalMockVariableMocked_WhenCountInvoked_ThenMockedValueReturned() {
UserRepository localMockRepository = Mockito.mock(UserRepository.class);
Mockito.when(localMockRepository.count()).thenReturn(111L);
+
long userCount = localMockRepository.count();
+
Assert.assertEquals(111L, userCount);
Mockito.verify(localMockRepository).count();
}
diff --git a/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockBeanAnnotationIntegrationTest.java b/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockBeanAnnotationIntegrationTest.java
index 008e674696..fd9236fe13 100644
--- a/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockBeanAnnotationIntegrationTest.java
+++ b/testing-modules/mockito/src/test/java/org/baeldung/mockito/MockBeanAnnotationIntegrationTest.java
@@ -20,10 +20,12 @@ public class MockBeanAnnotationIntegrationTest {
ApplicationContext context;
@Test
- public void testMockBean() {
+ public void givenCountMethodMocked_WhenCountInvokedOnBeanFromContext_ThenMockValueReturned() {
Mockito.when(mockRepository.count()).thenReturn(123L);
+
UserRepository userRepoFromContext = context.getBean(UserRepository.class);
long userCount = userRepoFromContext.count();
+
Assert.assertEquals(123L, userCount);
Mockito.verify(mockRepository).count();
}