implements Bookshelf {
+ private static Bookshelf INSTANCE;
+
+ @Override
+ public Bookshelf getInstance() {
+ if (INSTANCE == null) {
+ INSTANCE = new BookshelfImpl();
+ INSTANCE.init();
+ }
+ return INSTANCE;
+ }
+
+ @Override
+ public Book findByTitle(String title) {
+ return this.stream()
+ .filter(book -> book.getTitle().toLowerCase().contains(title.toLowerCase()))
+ .findFirst()
+ .orElse(null);
+ }
+}
diff --git a/patterns/src/main/resources/front controller.png b/patterns/src/main/resources/front controller.png
new file mode 100644
index 0000000000..af22a38e37
Binary files /dev/null and b/patterns/src/main/resources/front controller.png differ
diff --git a/patterns/src/main/resources/front controller.puml b/patterns/src/main/resources/front controller.puml
new file mode 100644
index 0000000000..cbc2dc8bd9
--- /dev/null
+++ b/patterns/src/main/resources/front controller.puml
@@ -0,0 +1,22 @@
+@startuml
+scale 1.5
+class Handler {
+doGet
+doPost
+}
+
+abstract class AbstractCommand {
+process
+}
+class ConcreteCommand1 {
+process
+}
+class ConcreteCommand2 {
+process
+}
+
+Handler .right.> AbstractCommand
+AbstractCommand <|-- ConcreteCommand1
+AbstractCommand <|-- ConcreteCommand2
+
+@enduml
\ No newline at end of file
diff --git a/patterns/src/main/webapp/WEB-INF/jsp/book-found.jsp b/patterns/src/main/webapp/WEB-INF/jsp/book-found.jsp
new file mode 100644
index 0000000000..42e08b4a46
--- /dev/null
+++ b/patterns/src/main/webapp/WEB-INF/jsp/book-found.jsp
@@ -0,0 +1,12 @@
+
+
+
+ Bookshelf: Title found
+
+
+ Our Bookshelf contains this title:
+ ${book.getTitle()}
+ Author: ${book.getAuthor()}
+
+
+
diff --git a/patterns/src/main/webapp/WEB-INF/jsp/book-notfound.jsp b/patterns/src/main/webapp/WEB-INF/jsp/book-notfound.jsp
new file mode 100644
index 0000000000..2f8ac01755
--- /dev/null
+++ b/patterns/src/main/webapp/WEB-INF/jsp/book-notfound.jsp
@@ -0,0 +1,10 @@
+
+
+
+ Bookshelf: Title not found
+
+
+ Our Bookshelf doesn't contains this title:
+ ${param.get("title")}
+
+
diff --git a/patterns/src/main/webapp/WEB-INF/jsp/unknown.jsp b/patterns/src/main/webapp/WEB-INF/jsp/unknown.jsp
new file mode 100644
index 0000000000..b52b2de8d5
--- /dev/null
+++ b/patterns/src/main/webapp/WEB-INF/jsp/unknown.jsp
@@ -0,0 +1,9 @@
+
+
+
+ Bookshelf: Command unknown
+
+
+ Sorry, this command is not known!
+
+
diff --git a/patterns/src/main/webapp/WEB-INF/web.xml b/patterns/src/main/webapp/WEB-INF/web.xml
new file mode 100644
index 0000000000..77113db09b
--- /dev/null
+++ b/patterns/src/main/webapp/WEB-INF/web.xml
@@ -0,0 +1,15 @@
+
+
+
+ front-controller
+ com.baeldung.enterprise.patterns.front.controller.FrontControllerServlet
+
+
+ front-controller
+ /
+
+
diff --git a/play-framework/student-api/.gitignore b/play-framework/student-api/.gitignore
new file mode 100644
index 0000000000..eb372fc719
--- /dev/null
+++ b/play-framework/student-api/.gitignore
@@ -0,0 +1,8 @@
+logs
+target
+/.idea
+/.idea_modules
+/.classpath
+/.project
+/.settings
+/RUNNING_PID
diff --git a/play-framework/student-api/LICENSE b/play-framework/student-api/LICENSE
new file mode 100644
index 0000000000..4baedcb95f
--- /dev/null
+++ b/play-framework/student-api/LICENSE
@@ -0,0 +1,8 @@
+This software is licensed under the Apache 2 license, quoted below.
+
+Licensed under the Apache License, Version 2.0 (the "License"); you may not use this project except in compliance with
+the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0.
+
+Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific
+language governing permissions and limitations under the License.
\ No newline at end of file
diff --git a/play-framework/student-api/README b/play-framework/student-api/README
new file mode 100644
index 0000000000..f21d092edf
--- /dev/null
+++ b/play-framework/student-api/README
@@ -0,0 +1,49 @@
+This is your new Play application
+=================================
+
+This file will be packaged with your application when using `activator dist`.
+
+There are several demonstration files available in this template.
+
+Controllers
+===========
+
+- HomeController.java:
+
+ Shows how to handle simple HTTP requests.
+
+- AsyncController.java:
+
+ Shows how to do asynchronous programming when handling a request.
+
+- CountController.java:
+
+ Shows how to inject a component into a controller and use the component when
+ handling requests.
+
+Components
+==========
+
+- Module.java:
+
+ Shows how to use Guice to bind all the components needed by your application.
+
+- Counter.java:
+
+ An example of a component that contains state, in this case a simple counter.
+
+- ApplicationTimer.java:
+
+ An example of a component that starts when the application starts and stops
+ when the application stops.
+
+Filters
+=======
+
+- Filters.java:
+
+ Creates the list of HTTP filters used by your application.
+
+- ExampleFilter.java
+
+ A simple filter that adds a header to every response.
\ No newline at end of file
diff --git a/play-framework/student-api/app/Filters.java b/play-framework/student-api/app/Filters.java
new file mode 100644
index 0000000000..255de8ca93
--- /dev/null
+++ b/play-framework/student-api/app/Filters.java
@@ -0,0 +1,46 @@
+import javax.inject.*;
+import play.*;
+import play.mvc.EssentialFilter;
+import play.http.HttpFilters;
+import play.mvc.*;
+
+import filters.ExampleFilter;
+
+/**
+ * This class configures filters that run on every request. This
+ * class is queried by Play to get a list of filters.
+ *
+ * Play will automatically use filters from any class called
+ * Filters that is placed the root package. You can load filters
+ * from a different class by adding a `play.http.filters` setting to
+ * the application.conf configuration file.
+ */
+@Singleton
+public class Filters implements HttpFilters {
+
+ private final Environment env;
+ private final EssentialFilter exampleFilter;
+
+ /**
+ * @param env Basic environment settings for the current application.
+ * @param exampleFilter A demonstration filter that adds a header to
+ */
+ @Inject
+ public Filters(Environment env, ExampleFilter exampleFilter) {
+ this.env = env;
+ this.exampleFilter = exampleFilter;
+ }
+
+ @Override
+ public EssentialFilter[] filters() {
+ // Use the example filter if we're running development mode. If
+ // we're running in production or test mode then don't use any
+ // filters at all.
+ if (env.mode().equals(Mode.DEV)) {
+ return new EssentialFilter[] { exampleFilter };
+ } else {
+ return new EssentialFilter[] {};
+ }
+ }
+
+}
diff --git a/play-framework/student-api/app/Module.java b/play-framework/student-api/app/Module.java
new file mode 100644
index 0000000000..6e7d1766ef
--- /dev/null
+++ b/play-framework/student-api/app/Module.java
@@ -0,0 +1,31 @@
+import com.google.inject.AbstractModule;
+import java.time.Clock;
+
+import services.ApplicationTimer;
+import services.AtomicCounter;
+import services.Counter;
+
+/**
+ * This class is a Guice module that tells Guice how to bind several
+ * different types. This Guice module is created when the Play
+ * application starts.
+ *
+ * Play will automatically use any class called `Module` that is in
+ * the root package. You can create modules in other locations by
+ * adding `play.modules.enabled` settings to the `application.conf`
+ * configuration file.
+ */
+public class Module extends AbstractModule {
+
+ @Override
+ public void configure() {
+ // Use the system clock as the default implementation of Clock
+ bind(Clock.class).toInstance(Clock.systemDefaultZone());
+ // Ask Guice to create an instance of ApplicationTimer when the
+ // application starts.
+ bind(ApplicationTimer.class).asEagerSingleton();
+ // Set AtomicCounter as the implementation for Counter.
+ bind(Counter.class).to(AtomicCounter.class);
+ }
+
+}
diff --git a/play-framework/student-api/app/controllers/AsyncController.java b/play-framework/student-api/app/controllers/AsyncController.java
new file mode 100644
index 0000000000..92c84bb755
--- /dev/null
+++ b/play-framework/student-api/app/controllers/AsyncController.java
@@ -0,0 +1,64 @@
+package controllers;
+
+import akka.actor.ActorSystem;
+
+import javax.inject.*;
+
+import play.*;
+import play.mvc.*;
+
+import java.util.concurrent.Executor;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.CompletionStage;
+import java.util.concurrent.TimeUnit;
+
+import scala.concurrent.duration.Duration;
+import scala.concurrent.ExecutionContextExecutor;
+
+/**
+ * This controller contains an action that demonstrates how to write
+ * simple asynchronous code in a controller. It uses a timer to
+ * asynchronously delay sending a response for 1 second.
+ *
+ * @param actorSystem We need the {@link ActorSystem}'s
+ * {@link Scheduler} to run code after a delay.
+ * @param exec We need a Java {@link Executor} to apply the result
+ * of the {@link CompletableFuture} and a Scala
+ * {@link ExecutionContext} so we can use the Akka {@link Scheduler}.
+ * An {@link ExecutionContextExecutor} implements both interfaces.
+ */
+@Singleton
+public class AsyncController extends Controller {
+
+ private final ActorSystem actorSystem;
+ private final ExecutionContextExecutor exec;
+
+ @Inject
+ public AsyncController(ActorSystem actorSystem, ExecutionContextExecutor exec) {
+ this.actorSystem = actorSystem;
+ this.exec = exec;
+ }
+
+ /**
+ * An action that returns a plain text message after a delay
+ * of 1 second.
+ *
+ * The configuration in the routes file means that this method
+ * will be called when the application receives a GET request with
+ * a path of /message.
+ */
+ public CompletionStage message() {
+ return getFutureMessage(1, TimeUnit.SECONDS).thenApplyAsync(Results::ok, exec);
+ }
+
+ private CompletionStage getFutureMessage(long time, TimeUnit timeUnit) {
+ CompletableFuture future = new CompletableFuture<>();
+ actorSystem.scheduler().scheduleOnce(
+ Duration.create(time, timeUnit),
+ () -> future.complete("Hi!"),
+ exec
+ );
+ return future;
+ }
+
+}
diff --git a/play-framework/student-api/app/controllers/CountController.java b/play-framework/student-api/app/controllers/CountController.java
new file mode 100644
index 0000000000..02fcb15f8e
--- /dev/null
+++ b/play-framework/student-api/app/controllers/CountController.java
@@ -0,0 +1,35 @@
+package controllers;
+
+import javax.inject.*;
+import play.*;
+import play.mvc.*;
+
+import services.Counter;
+
+/**
+ * This controller demonstrates how to use dependency injection to
+ * bind a component into a controller class. The class contains an
+ * action that shows an incrementing count to users. The {@link Counter}
+ * object is injected by the Guice dependency injection system.
+ */
+@Singleton
+public class CountController extends Controller {
+
+ private final Counter counter;
+
+ @Inject
+ public CountController(Counter counter) {
+ this.counter = counter;
+ }
+
+ /**
+ * An action that responds with the {@link Counter}'s current
+ * count. The result is plain text. This action is mapped to
+ * GET requests with a path of /count
+ * requests by an entry in the routes config file.
+ */
+ public Result count() {
+ return ok(Integer.toString(counter.nextCount()));
+ }
+
+}
diff --git a/play-framework/student-api/app/controllers/HomeController.java b/play-framework/student-api/app/controllers/HomeController.java
new file mode 100644
index 0000000000..6a79856eb4
--- /dev/null
+++ b/play-framework/student-api/app/controllers/HomeController.java
@@ -0,0 +1,23 @@
+package controllers;
+
+import play.mvc.*;
+
+import views.html.*;
+
+/**
+ * This controller contains an action to handle HTTP requests
+ * to the application's home page.
+ */
+public class HomeController extends Controller {
+
+ /**
+ * An action that renders an HTML page with a welcome message.
+ * The configuration in the routes file means that
+ * this method will be called when the application receives a
+ * GET request with a path of /.
+ */
+ public Result index() {
+ return ok(index.render("Your new application is ready."));
+ }
+
+}
diff --git a/play-framework/student-api/app/controllers/StudentController.java b/play-framework/student-api/app/controllers/StudentController.java
new file mode 100644
index 0000000000..8b759b9598
--- /dev/null
+++ b/play-framework/student-api/app/controllers/StudentController.java
@@ -0,0 +1,63 @@
+package controllers;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import models.Student;
+import models.StudentStore;
+import play.libs.Json;
+import play.mvc.Controller;
+import play.mvc.Result;
+import util.Util;
+
+import java.util.Set;
+
+public class StudentController extends Controller {
+ public Result create() {
+ JsonNode json = request().body().asJson();
+ if (json == null) {
+ return badRequest(Util.createResponse("Expecting Json data", false));
+ }
+ Student student = StudentStore.getInstance().addStudent(Json.fromJson(json, Student.class));
+ JsonNode jsonObject = Json.toJson(student);
+ return created(Util.createResponse(jsonObject, true));
+ }
+
+ public Result update() {
+ JsonNode json = request().body().asJson();
+ if (json == null) {
+ return badRequest(Util.createResponse("Expecting Json data", false));
+ }
+ Student student = StudentStore.getInstance().updateStudent(Json.fromJson(json, Student.class));
+ if (student == null) {
+ return notFound(Util.createResponse("Student not found", false));
+ }
+
+ JsonNode jsonObject = Json.toJson(student);
+ return ok(Util.createResponse(jsonObject, true));
+ }
+
+ public Result retrieve(int id) {
+ if (StudentStore.getInstance().getStudent(id) == null) {
+ return notFound(Util.createResponse("Student with id:" + id + " not found", false));
+ }
+ JsonNode jsonObjects = Json.toJson(StudentStore.getInstance().getStudent(id));
+ return ok(Util.createResponse(jsonObjects, true));
+ }
+
+ public Result listStudents() {
+ Set result = StudentStore.getInstance().getAllStudents();
+ ObjectMapper mapper = new ObjectMapper();
+
+ JsonNode jsonData = mapper.convertValue(result, JsonNode.class);
+ return ok(Util.createResponse(jsonData, true));
+
+ }
+
+ public Result delete(int id) {
+ if (!StudentStore.getInstance().deleteStudent(id)) {
+ return notFound(Util.createResponse("Student with id:" + id + " not found", false));
+ }
+ return ok(Util.createResponse("Student with id:" + id + " deleted", true));
+ }
+
+}
diff --git a/play-framework/student-api/app/filters/ExampleFilter.java b/play-framework/student-api/app/filters/ExampleFilter.java
new file mode 100644
index 0000000000..67a6a36cc3
--- /dev/null
+++ b/play-framework/student-api/app/filters/ExampleFilter.java
@@ -0,0 +1,45 @@
+package filters;
+
+import akka.stream.Materializer;
+import java.util.concurrent.CompletionStage;
+import java.util.concurrent.Executor;
+import java.util.function.Function;
+import javax.inject.*;
+import play.mvc.*;
+import play.mvc.Http.RequestHeader;
+
+
+/**
+ * This is a simple filter that adds a header to all requests. It's
+ * added to the application's list of filters by the
+ * {@link Filters} class.
+ */
+@Singleton
+public class ExampleFilter extends Filter {
+
+ private final Executor exec;
+
+ /**
+ * @param mat This object is needed to handle streaming of requests
+ * and responses.
+ * @param exec This class is needed to execute code asynchronously.
+ * It is used below by the thenAsyncApply method.
+ */
+ @Inject
+ public ExampleFilter(Materializer mat, Executor exec) {
+ super(mat);
+ this.exec = exec;
+ }
+
+ @Override
+ public CompletionStage apply(
+ Function> next,
+ RequestHeader requestHeader) {
+
+ return next.apply(requestHeader).thenApplyAsync(
+ result -> result.withHeader("X-ExampleFilter", "foo"),
+ exec
+ );
+ }
+
+}
diff --git a/play-framework/student-api/app/models/Student.java b/play-framework/student-api/app/models/Student.java
new file mode 100644
index 0000000000..dc539767bd
--- /dev/null
+++ b/play-framework/student-api/app/models/Student.java
@@ -0,0 +1,47 @@
+package models;
+public class Student {
+ private String firstName;
+ private String lastName;
+ private int age;
+ private int id;
+ public Student(){}
+ public Student(String firstName, String lastName, int age) {
+ super();
+ this.firstName = firstName;
+ this.lastName = lastName;
+ this.age = age;
+ }
+
+ public String getFirstName() {
+ return firstName;
+ }
+
+ public void setFirstName(String firstName) {
+ this.firstName = firstName;
+ }
+
+ public String getLastName() {
+ return lastName;
+ }
+
+ public void setLastName(String lastName) {
+ this.lastName = lastName;
+ }
+
+ public int getAge() {
+ return age;
+ }
+
+ public void setAge(int age) {
+ this.age = age;
+ }
+
+ public int getId() {
+ return id;
+ }
+
+ public void setId(int id) {
+ this.id = id;
+ }
+
+}
diff --git a/play-framework/student-api/app/models/StudentStore.java b/play-framework/student-api/app/models/StudentStore.java
new file mode 100644
index 0000000000..add6a5dbd6
--- /dev/null
+++ b/play-framework/student-api/app/models/StudentStore.java
@@ -0,0 +1,46 @@
+package models;
+
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+public class StudentStore {
+ private static StudentStore instance;
+ private Map students = new HashMap<>();
+
+ public static StudentStore getInstance() {
+ if (instance == null) {
+ instance = new StudentStore();
+ }
+ return instance;
+ }
+
+ public Student addStudent(Student student) {
+ int id = students.size();
+ student.setId(id);
+ students.put(id, student);
+ return student;
+ }
+
+ public Student getStudent(int id) {
+ return students.get(id);
+ }
+
+ public Set getAllStudents() {
+ return new HashSet<>(students.values());
+ }
+
+ public Student updateStudent(Student student) {
+ int id = student.getId();
+ if (students.containsKey(id)) {
+ students.put(id, student);
+ return student;
+ }
+ return null;
+ }
+
+ public boolean deleteStudent(int id) {
+ return students.remove(id) != null;
+ }
+}
\ No newline at end of file
diff --git a/play-framework/student-api/app/services/ApplicationTimer.java b/play-framework/student-api/app/services/ApplicationTimer.java
new file mode 100644
index 0000000000..a951562b1d
--- /dev/null
+++ b/play-framework/student-api/app/services/ApplicationTimer.java
@@ -0,0 +1,50 @@
+package services;
+
+import java.time.Clock;
+import java.time.Instant;
+import java.util.concurrent.CompletableFuture;
+import javax.inject.*;
+import play.Logger;
+import play.inject.ApplicationLifecycle;
+
+/**
+ * This class demonstrates how to run code when the
+ * application starts and stops. It starts a timer when the
+ * application starts. When the application stops it prints out how
+ * long the application was running for.
+ *
+ * This class is registered for Guice dependency injection in the
+ * {@link Module} class. We want the class to start when the application
+ * starts, so it is registered as an "eager singleton". See the code
+ * in the {@link Module} class to see how this happens.
+ *
+ * This class needs to run code when the server stops. It uses the
+ * application's {@link ApplicationLifecycle} to register a stop hook.
+ */
+@Singleton
+public class ApplicationTimer {
+
+ private final Clock clock;
+ private final ApplicationLifecycle appLifecycle;
+ private final Instant start;
+
+ @Inject
+ public ApplicationTimer(Clock clock, ApplicationLifecycle appLifecycle) {
+ this.clock = clock;
+ this.appLifecycle = appLifecycle;
+ // This code is called when the application starts.
+ start = clock.instant();
+ Logger.info("ApplicationTimer demo: Starting application at " + start);
+
+ // When the application starts, register a stop hook with the
+ // ApplicationLifecycle object. The code inside the stop hook will
+ // be run when the application stops.
+ appLifecycle.addStopHook(() -> {
+ Instant stop = clock.instant();
+ Long runningTime = stop.getEpochSecond() - start.getEpochSecond();
+ Logger.info("ApplicationTimer demo: Stopping application at " + clock.instant() + " after " + runningTime + "s.");
+ return CompletableFuture.completedFuture(null);
+ });
+ }
+
+}
diff --git a/play-framework/student-api/app/services/AtomicCounter.java b/play-framework/student-api/app/services/AtomicCounter.java
new file mode 100644
index 0000000000..41f741cbf7
--- /dev/null
+++ b/play-framework/student-api/app/services/AtomicCounter.java
@@ -0,0 +1,26 @@
+package services;
+
+import java.util.concurrent.atomic.AtomicInteger;
+import javax.inject.*;
+
+/**
+ * This class is a concrete implementation of the {@link Counter} trait.
+ * It is configured for Guice dependency injection in the {@link Module}
+ * class.
+ *
+ * This class has a {@link Singleton} annotation because we need to make
+ * sure we only use one counter per application. Without this
+ * annotation we would get a new instance every time a {@link Counter} is
+ * injected.
+ */
+@Singleton
+public class AtomicCounter implements Counter {
+
+ private final AtomicInteger atomicCounter = new AtomicInteger();
+
+ @Override
+ public int nextCount() {
+ return atomicCounter.getAndIncrement();
+ }
+
+}
diff --git a/play-framework/student-api/app/services/Counter.java b/play-framework/student-api/app/services/Counter.java
new file mode 100644
index 0000000000..dadad8b09d
--- /dev/null
+++ b/play-framework/student-api/app/services/Counter.java
@@ -0,0 +1,13 @@
+package services;
+
+/**
+ * This interface demonstrates how to create a component that is injected
+ * into a controller. The interface represents a counter that returns a
+ * incremented number each time it is called.
+ *
+ * The {@link Modules} class binds this interface to the
+ * {@link AtomicCounter} implementation.
+ */
+public interface Counter {
+ int nextCount();
+}
diff --git a/play-framework/student-api/app/util/Util.java b/play-framework/student-api/app/util/Util.java
new file mode 100644
index 0000000000..a853a4cb43
--- /dev/null
+++ b/play-framework/student-api/app/util/Util.java
@@ -0,0 +1,17 @@
+package util;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.node.ObjectNode;
+import play.libs.Json;
+
+public class Util {
+ public static ObjectNode createResponse(Object response, boolean ok) {
+ ObjectNode result = Json.newObject();
+ result.put("isSuccessfull", ok);
+ if (response instanceof String)
+ result.put("body", (String) response);
+ else result.put("body", (JsonNode) response);
+
+ return result;
+ }
+}
\ No newline at end of file
diff --git a/play-framework/student-api/app/views/index.scala.html b/play-framework/student-api/app/views/index.scala.html
new file mode 100644
index 0000000000..4539f5a10b
--- /dev/null
+++ b/play-framework/student-api/app/views/index.scala.html
@@ -0,0 +1,20 @@
+@*
+ * This template takes a single argument, a String containing a
+ * message to display.
+ *@
+@(message: String)
+
+@*
+ * Call the `main` template with two arguments. The first
+ * argument is a `String` with the title of the page, the second
+ * argument is an `Html` object containing the body of the page.
+ *@
+@main("Welcome to Play") {
+
+ @*
+ * Get an `Html` object by calling the built-in Play welcome
+ * template and passing a `String` message.
+ *@
+ @play20.welcome(message, style = "Java")
+
+}
diff --git a/play-framework/student-api/app/views/main.scala.html b/play-framework/student-api/app/views/main.scala.html
new file mode 100644
index 0000000000..9414f4be6e
--- /dev/null
+++ b/play-framework/student-api/app/views/main.scala.html
@@ -0,0 +1,23 @@
+@*
+ * This template is called from the `index` template. This template
+ * handles the rendering of the page header and body tags. It takes
+ * two arguments, a `String` for the title of the page and an `Html`
+ * object to insert into the body of the page.
+ *@
+@(title: String)(content: Html)
+
+
+
+
+ @* Here's where we render the page title `String`. *@
+ @title
+
+
+
+
+
+ @* And here's where we render the `Html` object containing
+ * the page content. *@
+ @content
+
+
diff --git a/play-framework/student-api/bin/activator b/play-framework/student-api/bin/activator
new file mode 100644
index 0000000000..a8b11d482f
--- /dev/null
+++ b/play-framework/student-api/bin/activator
@@ -0,0 +1,397 @@
+#!/usr/bin/env bash
+
+### ------------------------------- ###
+### Helper methods for BASH scripts ###
+### ------------------------------- ###
+
+realpath () {
+(
+ TARGET_FILE="$1"
+ FIX_CYGPATH="$2"
+
+ cd "$(dirname "$TARGET_FILE")"
+ TARGET_FILE=$(basename "$TARGET_FILE")
+
+ COUNT=0
+ while [ -L "$TARGET_FILE" -a $COUNT -lt 100 ]
+ do
+ TARGET_FILE=$(readlink "$TARGET_FILE")
+ cd "$(dirname "$TARGET_FILE")"
+ TARGET_FILE=$(basename "$TARGET_FILE")
+ COUNT=$(($COUNT + 1))
+ done
+
+ # make sure we grab the actual windows path, instead of cygwin's path.
+ if [[ "x$FIX_CYGPATH" != "x" ]]; then
+ echo "$(cygwinpath "$(pwd -P)/$TARGET_FILE")"
+ else
+ echo "$(pwd -P)/$TARGET_FILE"
+ fi
+)
+}
+
+
+# Uses uname to detect if we're in the odd cygwin environment.
+is_cygwin() {
+ local os=$(uname -s)
+ case "$os" in
+ CYGWIN*) return 0 ;;
+ *) return 1 ;;
+ esac
+}
+
+# TODO - Use nicer bash-isms here.
+CYGWIN_FLAG=$(if is_cygwin; then echo true; else echo false; fi)
+
+
+# This can fix cygwin style /cygdrive paths so we get the
+# windows style paths.
+cygwinpath() {
+ local file="$1"
+ if [[ "$CYGWIN_FLAG" == "true" ]]; then
+ echo $(cygpath -w $file)
+ else
+ echo $file
+ fi
+}
+
+# Make something URI friendly
+make_url() {
+ url="$1"
+ local nospaces=${url// /%20}
+ if is_cygwin; then
+ echo "/${nospaces//\\//}"
+ else
+ echo "$nospaces"
+ fi
+}
+
+declare -a residual_args
+declare -a java_args
+declare -a scalac_args
+declare -a sbt_commands
+declare java_cmd=java
+declare java_version
+declare -r real_script_path="$(realpath "$0")"
+declare -r sbt_home="$(realpath "$(dirname "$(dirname "$real_script_path")")")"
+declare -r sbt_bin_dir="$(dirname "$real_script_path")"
+declare -r app_version="1.3.10"
+
+declare -r script_name=activator
+declare -r java_opts=( "${ACTIVATOR_OPTS[@]}" "${SBT_OPTS[@]}" "${JAVA_OPTS[@]}" "${java_opts[@]}" )
+userhome="$HOME"
+if is_cygwin; then
+ # cygwin sets home to something f-d up, set to real windows homedir
+ userhome="$USERPROFILE"
+fi
+declare -r activator_user_home_dir="${userhome}/.activator"
+declare -r java_opts_config_home="${activator_user_home_dir}/activatorconfig.txt"
+declare -r java_opts_config_version="${activator_user_home_dir}/${app_version}/activatorconfig.txt"
+
+echoerr () {
+ echo 1>&2 "$@"
+}
+vlog () {
+ [[ $verbose || $debug ]] && echoerr "$@"
+}
+dlog () {
+ [[ $debug ]] && echoerr "$@"
+}
+
+jar_file () {
+ echo "$(cygwinpath "${sbt_home}/libexec/activator-launch-${app_version}.jar")"
+}
+
+acquire_sbt_jar () {
+ sbt_jar="$(jar_file)"
+
+ if [[ ! -f "$sbt_jar" ]]; then
+ echoerr "Could not find launcher jar: $sbt_jar"
+ exit 2
+ fi
+}
+
+execRunner () {
+ # print the arguments one to a line, quoting any containing spaces
+ [[ $verbose || $debug ]] && echo "# Executing command line:" && {
+ for arg; do
+ if printf "%s\n" "$arg" | grep -q ' '; then
+ printf "\"%s\"\n" "$arg"
+ else
+ printf "%s\n" "$arg"
+ fi
+ done
+ echo ""
+ }
+
+ # THis used to be exec, but we loose the ability to re-hook stty then
+ # for cygwin... Maybe we should flag the feature here...
+ "$@"
+}
+
+addJava () {
+ dlog "[addJava] arg = '$1'"
+ java_args=( "${java_args[@]}" "$1" )
+}
+addSbt () {
+ dlog "[addSbt] arg = '$1'"
+ sbt_commands=( "${sbt_commands[@]}" "$1" )
+}
+addResidual () {
+ dlog "[residual] arg = '$1'"
+ residual_args=( "${residual_args[@]}" "$1" )
+}
+addDebugger () {
+ addJava "-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=$1"
+}
+
+get_mem_opts () {
+ # if we detect any of these settings in ${JAVA_OPTS} we need to NOT output our settings.
+ # The reason is the Xms/Xmx, if they don't line up, cause errors.
+ if [[ "${JAVA_OPTS}" == *-Xmx* ]] || [[ "${JAVA_OPTS}" == *-Xms* ]] || [[ "${JAVA_OPTS}" == *-XX:MaxPermSize* ]] || [[ "${JAVA_OPTS}" == *-XX:MaxMetaspaceSize* ]] || [[ "${JAVA_OPTS}" == *-XX:ReservedCodeCacheSize* ]]; then
+ echo ""
+ else
+ # a ham-fisted attempt to move some memory settings in concert
+ # so they need not be messed around with individually.
+ local mem=${1:-1024}
+ local codecache=$(( $mem / 8 ))
+ (( $codecache > 128 )) || codecache=128
+ (( $codecache < 512 )) || codecache=512
+ local class_metadata_size=$(( $codecache * 2 ))
+ local class_metadata_opt=$([[ "$java_version" < "1.8" ]] && echo "MaxPermSize" || echo "MaxMetaspaceSize")
+
+ echo "-Xms${mem}m -Xmx${mem}m -XX:ReservedCodeCacheSize=${codecache}m -XX:${class_metadata_opt}=${class_metadata_size}m"
+ fi
+}
+
+require_arg () {
+ local type="$1"
+ local opt="$2"
+ local arg="$3"
+ if [[ -z "$arg" ]] || [[ "${arg:0:1}" == "-" ]]; then
+ echo "$opt requires <$type> argument"
+ exit 1
+ fi
+}
+
+is_function_defined() {
+ declare -f "$1" > /dev/null
+}
+
+# If we're *not* running in a terminal, and we don't have any arguments, then we need to add the 'ui' parameter
+detect_terminal_for_ui() {
+ [[ ! -t 0 ]] && [[ "${#residual_args}" == "0" ]] && {
+ addResidual "ui"
+ }
+ # SPECIAL TEST FOR MAC
+ [[ "$(uname)" == "Darwin" ]] && [[ "$HOME" == "$PWD" ]] && [[ "${#residual_args}" == "0" ]] && {
+ echo "Detected MAC OSX launched script...."
+ echo "Swapping to UI"
+ addResidual "ui"
+ }
+}
+
+process_args () {
+ while [[ $# -gt 0 ]]; do
+ case "$1" in
+ -h|-help) usage; exit 1 ;;
+ -v|-verbose) verbose=1 && shift ;;
+ -d|-debug) debug=1 && shift ;;
+
+ -ivy) require_arg path "$1" "$2" && addJava "-Dsbt.ivy.home=$2" && shift 2 ;;
+ -mem) require_arg integer "$1" "$2" && sbt_mem="$2" && shift 2 ;;
+ -jvm-debug) require_arg port "$1" "$2" && addDebugger $2 && shift 2 ;;
+ -batch) exec &1 | awk -F '"' '/version/ {print $2}')
+ vlog "[process_args] java_version = '$java_version'"
+}
+
+# Detect that we have java installed.
+checkJava() {
+ local required_version="$1"
+ # Now check to see if it's a good enough version
+ if [[ "$java_version" == "" ]]; then
+ echo
+ echo No java installations was detected.
+ echo Please go to http://www.java.com/getjava/ and download
+ echo
+ exit 1
+ elif [[ ! "$java_version" > "$required_version" ]]; then
+ echo
+ echo The java installation you have is not up to date
+ echo $script_name requires at least version $required_version+, you have
+ echo version $java_version
+ echo
+ echo Please go to http://www.java.com/getjava/ and download
+ echo a valid Java Runtime and install before running $script_name.
+ echo
+ exit 1
+ fi
+}
+
+
+run() {
+ # no jar? download it.
+ [[ -f "$sbt_jar" ]] || acquire_sbt_jar "$sbt_version" || {
+ # still no jar? uh-oh.
+ echo "Download failed. Obtain the sbt-launch.jar manually and place it at $sbt_jar"
+ exit 1
+ }
+
+ # process the combined args, then reset "$@" to the residuals
+ process_args "$@"
+ detect_terminal_for_ui
+ set -- "${residual_args[@]}"
+ argumentCount=$#
+
+ # TODO - java check should be configurable...
+ checkJava "1.6"
+
+ #If we're in cygwin, we should use the windows config, and terminal hacks
+ if [[ "$CYGWIN_FLAG" == "true" ]]; then
+ stty -icanon min 1 -echo > /dev/null 2>&1
+ addJava "-Djline.terminal=jline.UnixTerminal"
+ addJava "-Dsbt.cygwin=true"
+ fi
+
+ # run sbt
+ execRunner "$java_cmd" \
+ "-Dactivator.home=$(make_url "$sbt_home")" \
+ ${SBT_OPTS:-$default_sbt_opts} \
+ $(get_mem_opts $sbt_mem) \
+ ${JAVA_OPTS} \
+ ${java_args[@]} \
+ -jar "$sbt_jar" \
+ "${sbt_commands[@]}" \
+ "${residual_args[@]}"
+
+ exit_code=$?
+
+ # Clean up the terminal from cygwin hacks.
+ if [[ "$CYGWIN_FLAG" == "true" ]]; then
+ stty icanon echo > /dev/null 2>&1
+ fi
+ exit $exit_code
+}
+
+
+declare -r noshare_opts="-Dsbt.global.base=project/.sbtboot -Dsbt.boot.directory=project/.boot -Dsbt.ivy.home=project/.ivy"
+declare -r sbt_opts_file=".sbtopts"
+declare -r etc_sbt_opts_file="${sbt_home}/conf/sbtopts"
+declare -r win_sbt_opts_file="${sbt_home}/conf/sbtconfig.txt"
+
+usage() {
+ cat < path to global settings/plugins directory (default: ~/.sbt)
+ -sbt-boot path to shared boot directory (default: ~/.sbt/boot in 0.11 series)
+ -ivy path to local Ivy repository (default: ~/.ivy2)
+ -mem set memory options (default: $sbt_mem, which is $(get_mem_opts $sbt_mem))
+ -no-share use all local caches; no sharing
+ -no-global uses global caches, but does not use global ~/.sbt directory.
+ -jvm-debug Turn on JVM debugging, open at the given port.
+ -batch Disable interactive mode
+
+ # sbt version (default: from project/build.properties if present, else latest release)
+ -sbt-version use the specified version of sbt
+ -sbt-jar use the specified jar as the sbt launcher
+ -sbt-rc use an RC version of sbt
+ -sbt-snapshot use a snapshot version of sbt
+
+ # java version (default: java from PATH, currently $(java -version 2>&1 | grep version))
+ -java-home alternate JAVA_HOME
+
+ # jvm options and output control
+ JAVA_OPTS environment variable, if unset uses "$java_opts"
+ SBT_OPTS environment variable, if unset uses "$default_sbt_opts"
+ ACTIVATOR_OPTS Environment variable, if unset uses ""
+ .sbtopts if this file exists in the current directory, it is
+ prepended to the runner args
+ /etc/sbt/sbtopts if this file exists, it is prepended to the runner args
+ -Dkey=val pass -Dkey=val directly to the java runtime
+ -J-X pass option -X directly to the java runtime
+ (-J is stripped)
+ -S-X add -X to sbt's scalacOptions (-S is stripped)
+
+In the case of duplicated or conflicting options, the order above
+shows precedence: JAVA_OPTS lowest, command line options highest.
+EOM
+}
+
+
+
+process_my_args () {
+ while [[ $# -gt 0 ]]; do
+ case "$1" in
+ -no-colors) addJava "-Dsbt.log.noformat=true" && shift ;;
+ -no-share) addJava "$noshare_opts" && shift ;;
+ -no-global) addJava "-Dsbt.global.base=$(pwd)/project/.sbtboot" && shift ;;
+ -sbt-boot) require_arg path "$1" "$2" && addJava "-Dsbt.boot.directory=$2" && shift 2 ;;
+ -sbt-dir) require_arg path "$1" "$2" && addJava "-Dsbt.global.base=$2" && shift 2 ;;
+ -debug-inc) addJava "-Dxsbt.inc.debug=true" && shift ;;
+ -batch) exec ^&1') do (
+ if %%~j==java set JAVAINSTALLED=1
+ if %%~j==openjdk set JAVAINSTALLED=1
+)
+
+rem Detect the same thing about javac
+if "%_JAVACCMD%"=="" (
+ if not "%JAVA_HOME%"=="" (
+ if exist "%JAVA_HOME%\bin\javac.exe" set "_JAVACCMD=%JAVA_HOME%\bin\javac.exe"
+ )
+)
+if "%_JAVACCMD%"=="" set _JAVACCMD=javac
+for /F %%j in ('"%_JAVACCMD%" -version 2^>^&1') do (
+ if %%~j==javac set JAVACINSTALLED=1
+)
+
+rem BAT has no logical or, so we do it OLD SCHOOL! Oppan Redmond Style
+set JAVAOK=true
+if not defined JAVAINSTALLED set JAVAOK=false
+if not defined JAVACINSTALLED set JAVAOK=false
+
+if "%JAVAOK%"=="false" (
+ echo.
+ echo A Java JDK is not installed or can't be found.
+ if not "%JAVA_HOME%"=="" (
+ echo JAVA_HOME = "%JAVA_HOME%"
+ )
+ echo.
+ echo Please go to
+ echo http://www.oracle.com/technetwork/java/javase/downloads/index.html
+ echo and download a valid Java JDK and install before running Activator.
+ echo.
+ echo If you think this message is in error, please check
+ echo your environment variables to see if "java.exe" and "javac.exe" are
+ echo available via JAVA_HOME or PATH.
+ echo.
+ if defined DOUBLECLICKED pause
+ exit /B 1
+)
+
+rem Check what Java version is being used to determine what memory options to use
+for /f "tokens=3" %%g in ('java -version 2^>^&1 ^| findstr /i "version"') do (
+ set JAVA_VERSION=%%g
+)
+
+rem Strips away the " characters
+set JAVA_VERSION=%JAVA_VERSION:"=%
+
+rem TODO Check if there are existing mem settings in JAVA_OPTS/CFG_OPTS and use those instead of the below
+for /f "delims=. tokens=1-3" %%v in ("%JAVA_VERSION%") do (
+ set MAJOR=%%v
+ set MINOR=%%w
+ set BUILD=%%x
+
+ set META_SIZE=-XX:MetaspaceSize=64M -XX:MaxMetaspaceSize=256M
+ if "!MINOR!" LSS "8" (
+ set META_SIZE=-XX:PermSize=64M -XX:MaxPermSize=256M
+ )
+
+ set MEM_OPTS=!META_SIZE!
+ )
+
+rem We use the value of the JAVA_OPTS environment variable if defined, rather than the config.
+set _JAVA_OPTS=%JAVA_OPTS%
+if "%_JAVA_OPTS%"=="" set _JAVA_OPTS=%CFG_OPTS%
+
+set DEBUG_OPTS=
+
+rem Loop through the arguments, building remaining args in args variable
+set args=
+:argsloop
+if not "%~1"=="" (
+ rem Checks if the argument contains "-D" and if true, adds argument 1 with 2 and puts an equal sign between them.
+ rem This is done since batch considers "=" to be a delimiter so we need to circumvent this behavior with a small hack.
+ set arg1=%~1
+ if "!arg1:~0,2!"=="-D" (
+ set "args=%args% "%~1"="%~2""
+ shift
+ shift
+ goto argsloop
+ )
+
+ if "%~1"=="-jvm-debug" (
+ if not "%~2"=="" (
+ rem This piece of magic somehow checks that an argument is a number
+ for /F "delims=0123456789" %%i in ("%~2") do (
+ set var="%%i"
+ )
+ if defined var (
+ rem Not a number, assume no argument given and default to 9999
+ set JPDA_PORT=9999
+ ) else (
+ rem Port was given, shift arguments
+ set JPDA_PORT=%~2
+ shift
+ )
+ ) else (
+ set JPDA_PORT=9999
+ )
+ shift
+
+ set DEBUG_OPTS=-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=!JPDA_PORT!
+ goto argsloop
+ )
+ rem else
+ set "args=%args% "%~1""
+ shift
+ goto argsloop
+)
+
+:run
+
+if "!args!"=="" (
+ if defined DOUBLECLICKED (
+ set CMDS="ui"
+ ) else set CMDS=!args!
+) else set CMDS=!args!
+
+rem We add a / in front, so we get file:///C: instead of file://C:
+rem Java considers the later a UNC path.
+rem We also attempt a solid effort at making it URI friendly.
+rem We don't even bother with UNC paths.
+set JAVA_FRIENDLY_HOME_1=/!ACTIVATOR_HOME:\=/!
+set JAVA_FRIENDLY_HOME=/!JAVA_FRIENDLY_HOME_1: =%%20!
+
+rem Checks if the command contains spaces to know if it should be wrapped in quotes or not
+set NON_SPACED_CMD=%_JAVACMD: =%
+if "%_JAVACMD%"=="%NON_SPACED_CMD%" %_JAVACMD% %DEBUG_OPTS% %MEM_OPTS% %ACTIVATOR_OPTS% %SBT_OPTS% %_JAVA_OPTS% "-Dactivator.home=%JAVA_FRIENDLY_HOME%" -jar "%ACTIVATOR_HOME%\libexec\%ACTIVATOR_LAUNCH_JAR%" %CMDS%
+if NOT "%_JAVACMD%"=="%NON_SPACED_CMD%" "%_JAVACMD%" %DEBUG_OPTS% %MEM_OPTS% %ACTIVATOR_OPTS% %SBT_OPTS% %_JAVA_OPTS% "-Dactivator.home=%JAVA_FRIENDLY_HOME%" -jar "%ACTIVATOR_HOME%\libexec\%ACTIVATOR_LAUNCH_JAR%" %CMDS%
+
+if ERRORLEVEL 1 goto error
+goto end
+
+:error
+set ERROR_CODE=1
+
+:end
+
+@endlocal
+
+exit /B %ERROR_CODE%
diff --git a/play-framework/student-api/build.sbt b/play-framework/student-api/build.sbt
new file mode 100644
index 0000000000..0f5ea736f6
--- /dev/null
+++ b/play-framework/student-api/build.sbt
@@ -0,0 +1,13 @@
+name := """student-api"""
+
+version := "1.0-SNAPSHOT"
+
+lazy val root = (project in file(".")).enablePlugins(PlayJava)
+
+scalaVersion := "2.11.7"
+
+libraryDependencies ++= Seq(
+ javaJdbc,
+ cache,
+ javaWs
+)
diff --git a/play-framework/student-api/conf/application.conf b/play-framework/student-api/conf/application.conf
new file mode 100644
index 0000000000..489d3f9b3e
--- /dev/null
+++ b/play-framework/student-api/conf/application.conf
@@ -0,0 +1,353 @@
+# This is the main configuration file for the application.
+# https://www.playframework.com/documentation/latest/ConfigFile
+# ~~~~~
+# Play uses HOCON as its configuration file format. HOCON has a number
+# of advantages over other config formats, but there are two things that
+# can be used when modifying settings.
+#
+# You can include other configuration files in this main application.conf file:
+#include "extra-config.conf"
+#
+# You can declare variables and substitute for them:
+#mykey = ${some.value}
+#
+# And if an environment variable exists when there is no other subsitution, then
+# HOCON will fall back to substituting environment variable:
+#mykey = ${JAVA_HOME}
+
+## Akka
+# https://www.playframework.com/documentation/latest/ScalaAkka#Configuration
+# https://www.playframework.com/documentation/latest/JavaAkka#Configuration
+# ~~~~~
+# Play uses Akka internally and exposes Akka Streams and actors in Websockets and
+# other streaming HTTP responses.
+akka {
+ # "akka.log-config-on-start" is extraordinarly useful because it log the complete
+ # configuration at INFO level, including defaults and overrides, so it s worth
+ # putting at the very top.
+ #
+ # Put the following in your conf/logback.xml file:
+ #
+ #
+ #
+ # And then uncomment this line to debug the configuration.
+ #
+ #log-config-on-start = true
+}
+
+## Secret key
+# http://www.playframework.com/documentation/latest/ApplicationSecret
+# ~~~~~
+# The secret key is used to sign Play's session cookie.
+# This must be changed for production, but we don't recommend you change it in this file.
+play.crypto.secret = "changeme"
+
+## Modules
+# https://www.playframework.com/documentation/latest/Modules
+# ~~~~~
+# Control which modules are loaded when Play starts. Note that modules are
+# the replacement for "GlobalSettings", which are deprecated in 2.5.x.
+# Please see https://www.playframework.com/documentation/latest/GlobalSettings
+# for more information.
+#
+# You can also extend Play functionality by using one of the publically available
+# Play modules: https://playframework.com/documentation/latest/ModuleDirectory
+play.modules {
+ # By default, Play will load any class called Module that is defined
+ # in the root package (the "app" directory), or you can define them
+ # explicitly below.
+ # If there are any built-in modules that you want to disable, you can list them here.
+ #enabled += my.application.Module
+
+ # If there are any built-in modules that you want to disable, you can list them here.
+ #disabled += ""
+}
+
+## IDE
+# https://www.playframework.com/documentation/latest/IDE
+# ~~~~~
+# Depending on your IDE, you can add a hyperlink for errors that will jump you
+# directly to the code location in the IDE in dev mode. The following line makes
+# use of the IntelliJ IDEA REST interface:
+#play.editor="http://localhost:63342/api/file/?file=%s&line=%s"
+
+## Internationalisation
+# https://www.playframework.com/documentation/latest/JavaI18N
+# https://www.playframework.com/documentation/latest/ScalaI18N
+# ~~~~~
+# Play comes with its own i18n settings, which allow the user's preferred language
+# to map through to internal messages, or allow the language to be stored in a cookie.
+play.i18n {
+ # The application languages
+ langs = [ "en" ]
+
+ # Whether the language cookie should be secure or not
+ #langCookieSecure = true
+
+ # Whether the HTTP only attribute of the cookie should be set to true
+ #langCookieHttpOnly = true
+}
+
+## Play HTTP settings
+# ~~~~~
+play.http {
+ ## Router
+ # https://www.playframework.com/documentation/latest/JavaRouting
+ # https://www.playframework.com/documentation/latest/ScalaRouting
+ # ~~~~~
+ # Define the Router object to use for this application.
+ # This router will be looked up first when the application is starting up,
+ # so make sure this is the entry point.
+ # Furthermore, it's assumed your route file is named properly.
+ # So for an application router like `my.application.Router`,
+ # you may need to define a router file `conf/my.application.routes`.
+ # Default to Routes in the root package (aka "apps" folder) (and conf/routes)
+ #router = my.application.Router
+
+ ## Action Creator
+ # https://www.playframework.com/documentation/latest/JavaActionCreator
+ # ~~~~~
+ #actionCreator = null
+
+ ## ErrorHandler
+ # https://www.playframework.com/documentation/latest/JavaRouting
+ # https://www.playframework.com/documentation/latest/ScalaRouting
+ # ~~~~~
+ # If null, will attempt to load a class called ErrorHandler in the root package,
+ #errorHandler = null
+
+ ## Filters
+ # https://www.playframework.com/documentation/latest/ScalaHttpFilters
+ # https://www.playframework.com/documentation/latest/JavaHttpFilters
+ # ~~~~~
+ # Filters run code on every request. They can be used to perform
+ # common logic for all your actions, e.g. adding common headers.
+ # Defaults to "Filters" in the root package (aka "apps" folder)
+ # Alternatively you can explicitly register a class here.
+ #filters = my.application.Filters
+
+ ## Session & Flash
+ # https://www.playframework.com/documentation/latest/JavaSessionFlash
+ # https://www.playframework.com/documentation/latest/ScalaSessionFlash
+ # ~~~~~
+ session {
+ # Sets the cookie to be sent only over HTTPS.
+ #secure = true
+
+ # Sets the cookie to be accessed only by the server.
+ #httpOnly = true
+
+ # Sets the max-age field of the cookie to 5 minutes.
+ # NOTE: this only sets when the browser will discard the cookie. Play will consider any
+ # cookie value with a valid signature to be a valid session forever. To implement a server side session timeout,
+ # you need to put a timestamp in the session and check it at regular intervals to possibly expire it.
+ #maxAge = 300
+
+ # Sets the domain on the session cookie.
+ #domain = "example.com"
+ }
+
+ flash {
+ # Sets the cookie to be sent only over HTTPS.
+ #secure = true
+
+ # Sets the cookie to be accessed only by the server.
+ #httpOnly = true
+ }
+}
+
+## Netty Provider
+# https://www.playframework.com/documentation/latest/SettingsNetty
+# ~~~~~
+play.server.netty {
+ # Whether the Netty wire should be logged
+ #log.wire = true
+
+ # If you run Play on Linux, you can use Netty's native socket transport
+ # for higher performance with less garbage.
+ #transport = "native"
+}
+
+## WS (HTTP Client)
+# https://www.playframework.com/documentation/latest/ScalaWS#Configuring-WS
+# ~~~~~
+# The HTTP client primarily used for REST APIs. The default client can be
+# configured directly, but you can also create different client instances
+# with customized settings. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += ws // or javaWs if using java
+#
+play.ws {
+ # Sets HTTP requests not to follow 302 requests
+ #followRedirects = false
+
+ # Sets the maximum number of open HTTP connections for the client.
+ #ahc.maxConnectionsTotal = 50
+
+ ## WS SSL
+ # https://www.playframework.com/documentation/latest/WsSSL
+ # ~~~~~
+ ssl {
+ # Configuring HTTPS with Play WS does not require programming. You can
+ # set up both trustManager and keyManager for mutual authentication, and
+ # turn on JSSE debugging in development with a reload.
+ #debug.handshake = true
+ #trustManager = {
+ # stores = [
+ # { type = "JKS", path = "exampletrust.jks" }
+ # ]
+ #}
+ }
+}
+
+## Cache
+# https://www.playframework.com/documentation/latest/JavaCache
+# https://www.playframework.com/documentation/latest/ScalaCache
+# ~~~~~
+# Play comes with an integrated cache API that can reduce the operational
+# overhead of repeated requests. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += cache
+#
+play.cache {
+ # If you want to bind several caches, you can bind the individually
+ #bindCaches = ["db-cache", "user-cache", "session-cache"]
+}
+
+## Filters
+# https://www.playframework.com/documentation/latest/Filters
+# ~~~~~
+# There are a number of built-in filters that can be enabled and configured
+# to give Play greater security. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += filters
+#
+play.filters {
+ ## CORS filter configuration
+ # https://www.playframework.com/documentation/latest/CorsFilter
+ # ~~~~~
+ # CORS is a protocol that allows web applications to make requests from the browser
+ # across different domains.
+ # NOTE: You MUST apply the CORS configuration before the CSRF filter, as CSRF has
+ # dependencies on CORS settings.
+ cors {
+ # Filter paths by a whitelist of path prefixes
+ #pathPrefixes = ["/some/path", ...]
+
+ # The allowed origins. If null, all origins are allowed.
+ #allowedOrigins = ["http://www.example.com"]
+
+ # The allowed HTTP methods. If null, all methods are allowed
+ #allowedHttpMethods = ["GET", "POST"]
+ }
+
+ ## CSRF Filter
+ # https://www.playframework.com/documentation/latest/ScalaCsrf#Applying-a-global-CSRF-filter
+ # https://www.playframework.com/documentation/latest/JavaCsrf#Applying-a-global-CSRF-filter
+ # ~~~~~
+ # Play supports multiple methods for verifying that a request is not a CSRF request.
+ # The primary mechanism is a CSRF token. This token gets placed either in the query string
+ # or body of every form submitted, and also gets placed in the users session.
+ # Play then verifies that both tokens are present and match.
+ csrf {
+ # Sets the cookie to be sent only over HTTPS
+ #cookie.secure = true
+
+ # Defaults to CSRFErrorHandler in the root package.
+ #errorHandler = MyCSRFErrorHandler
+ }
+
+ ## Security headers filter configuration
+ # https://www.playframework.com/documentation/latest/SecurityHeaders
+ # ~~~~~
+ # Defines security headers that prevent XSS attacks.
+ # If enabled, then all options are set to the below configuration by default:
+ headers {
+ # The X-Frame-Options header. If null, the header is not set.
+ #frameOptions = "DENY"
+
+ # The X-XSS-Protection header. If null, the header is not set.
+ #xssProtection = "1; mode=block"
+
+ # The X-Content-Type-Options header. If null, the header is not set.
+ #contentTypeOptions = "nosniff"
+
+ # The X-Permitted-Cross-Domain-Policies header. If null, the header is not set.
+ #permittedCrossDomainPolicies = "master-only"
+
+ # The Content-Security-Policy header. If null, the header is not set.
+ #contentSecurityPolicy = "default-src 'self'"
+ }
+
+ ## Allowed hosts filter configuration
+ # https://www.playframework.com/documentation/latest/AllowedHostsFilter
+ # ~~~~~
+ # Play provides a filter that lets you configure which hosts can access your application.
+ # This is useful to prevent cache poisoning attacks.
+ hosts {
+ # Allow requests to example.com, its subdomains, and localhost:9000.
+ #allowed = [".example.com", "localhost:9000"]
+ }
+}
+
+## Evolutions
+# https://www.playframework.com/documentation/latest/Evolutions
+# ~~~~~
+# Evolutions allows database scripts to be automatically run on startup in dev mode
+# for database migrations. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += evolutions
+#
+play.evolutions {
+ # You can disable evolutions for a specific datasource if necessary
+ #db.default.enabled = false
+}
+
+## Database Connection Pool
+# https://www.playframework.com/documentation/latest/SettingsJDBC
+# ~~~~~
+# Play doesn't require a JDBC database to run, but you can easily enable one.
+#
+# libraryDependencies += jdbc
+#
+play.db {
+ # The combination of these two settings results in "db.default" as the
+ # default JDBC pool:
+ #config = "db"
+ #default = "default"
+
+ # Play uses HikariCP as the default connection pool. You can override
+ # settings by changing the prototype:
+ prototype {
+ # Sets a fixed JDBC connection pool size of 50
+ #hikaricp.minimumIdle = 50
+ #hikaricp.maximumPoolSize = 50
+ }
+}
+
+## JDBC Datasource
+# https://www.playframework.com/documentation/latest/JavaDatabase
+# https://www.playframework.com/documentation/latest/ScalaDatabase
+# ~~~~~
+# Once JDBC datasource is set up, you can work with several different
+# database options:
+#
+# Slick (Scala preferred option): https://www.playframework.com/documentation/latest/PlaySlick
+# JPA (Java preferred option): https://playframework.com/documentation/latest/JavaJPA
+# EBean: https://playframework.com/documentation/latest/JavaEbean
+# Anorm: https://www.playframework.com/documentation/latest/ScalaAnorm
+#
+db {
+ # You can declare as many datasources as you want.
+ # By convention, the default datasource is named `default`
+
+ # https://www.playframework.com/documentation/latest/Developing-with-the-H2-Database
+ #default.driver = org.h2.Driver
+ #default.url = "jdbc:h2:mem:play"
+ #default.username = sa
+ #default.password = ""
+
+ # You can turn on SQL logging for any datasource
+ # https://www.playframework.com/documentation/latest/Highlights25#Logging-SQL-statements
+ #default.logSql=true
+}
diff --git a/play-framework/student-api/conf/logback.xml b/play-framework/student-api/conf/logback.xml
new file mode 100644
index 0000000000..86ec12c0af
--- /dev/null
+++ b/play-framework/student-api/conf/logback.xml
@@ -0,0 +1,41 @@
+
+
+
+
+
+
+ ${application.home:-.}/logs/application.log
+
+ %date [%level] from %logger in %thread - %message%n%xException
+
+
+
+
+
+ %coloredLevel %logger{15} - %message%n%xException{10}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/play-framework/student-api/conf/routes b/play-framework/student-api/conf/routes
new file mode 100644
index 0000000000..ab55792683
--- /dev/null
+++ b/play-framework/student-api/conf/routes
@@ -0,0 +1,12 @@
+# Routes
+# This file defines all application routes (Higher priority routes first)
+# ~~~~
+
+GET / controllers.StudentController.listStudents()
+POST /:id controllers.StudentController.retrieve(id:Int)
+POST / controllers.StudentController.create()
+PUT / controllers.StudentController.update()
+DELETE /:id controllers.StudentController.delete(id:Int)
+
+# Map static resources from the /public folder to the /assets URL path
+GET /assets/*file controllers.Assets.versioned(path="/public", file: Asset)
diff --git a/play-framework/student-api/libexec/activator-launch-1.3.10.jar b/play-framework/student-api/libexec/activator-launch-1.3.10.jar
new file mode 100644
index 0000000000..69050e7dec
Binary files /dev/null and b/play-framework/student-api/libexec/activator-launch-1.3.10.jar differ
diff --git a/play-framework/student-api/project/build.properties b/play-framework/student-api/project/build.properties
new file mode 100644
index 0000000000..6d9fa6badb
--- /dev/null
+++ b/play-framework/student-api/project/build.properties
@@ -0,0 +1,4 @@
+#Activator-generated Properties
+#Wed Sep 07 12:29:40 EAT 2016
+template.uuid=c373963b-f5ad-433b-8e74-178e7ae25b1c
+sbt.version=0.13.11
diff --git a/play-framework/student-api/project/plugins.sbt b/play-framework/student-api/project/plugins.sbt
new file mode 100644
index 0000000000..51c5b2a35a
--- /dev/null
+++ b/play-framework/student-api/project/plugins.sbt
@@ -0,0 +1,21 @@
+// The Play plugin
+addSbtPlugin("com.typesafe.play" % "sbt-plugin" % "2.5.6")
+
+// Web plugins
+addSbtPlugin("com.typesafe.sbt" % "sbt-coffeescript" % "1.0.0")
+addSbtPlugin("com.typesafe.sbt" % "sbt-less" % "1.1.0")
+addSbtPlugin("com.typesafe.sbt" % "sbt-jshint" % "1.0.3")
+addSbtPlugin("com.typesafe.sbt" % "sbt-rjs" % "1.0.7")
+addSbtPlugin("com.typesafe.sbt" % "sbt-digest" % "1.1.0")
+addSbtPlugin("com.typesafe.sbt" % "sbt-mocha" % "1.1.0")
+addSbtPlugin("org.irundaia.sbt" % "sbt-sassify" % "1.4.2")
+
+// Play enhancer - this automatically generates getters/setters for public fields
+// and rewrites accessors of these fields to use the getters/setters. Remove this
+// plugin if you prefer not to have this feature, or disable on a per project
+// basis using disablePlugins(PlayEnhancer) in your build.sbt
+addSbtPlugin("com.typesafe.sbt" % "sbt-play-enhancer" % "1.1.0")
+
+// Play Ebean support, to enable, uncomment this line, and enable in your build.sbt using
+// enablePlugins(PlayEbean).
+// addSbtPlugin("com.typesafe.sbt" % "sbt-play-ebean" % "1.0.0")
diff --git a/play-framework/student-api/public/images/favicon.png b/play-framework/student-api/public/images/favicon.png
new file mode 100644
index 0000000000..c7d92d2ae4
Binary files /dev/null and b/play-framework/student-api/public/images/favicon.png differ
diff --git a/play-framework/student-api/public/javascripts/hello.js b/play-framework/student-api/public/javascripts/hello.js
new file mode 100644
index 0000000000..02ee13c7ca
--- /dev/null
+++ b/play-framework/student-api/public/javascripts/hello.js
@@ -0,0 +1,3 @@
+if (window.console) {
+ console.log("Welcome to your Play application's JavaScript!");
+}
diff --git a/couchbase-sdk-spring-service/src/main/resources/application.properties b/play-framework/student-api/public/stylesheets/main.css
similarity index 100%
rename from couchbase-sdk-spring-service/src/main/resources/application.properties
rename to play-framework/student-api/public/stylesheets/main.css
diff --git a/play-framework/student-api/test/ApplicationTest.java b/play-framework/student-api/test/ApplicationTest.java
new file mode 100644
index 0000000000..1133978e9a
--- /dev/null
+++ b/play-framework/student-api/test/ApplicationTest.java
@@ -0,0 +1,172 @@
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+
+import java.io.BufferedReader;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.net.HttpURLConnection;
+import java.net.MalformedURLException;
+import java.net.URL;
+import java.util.Arrays;
+
+import org.json.JSONArray;
+import org.json.JSONObject;
+import org.junit.Before;
+import org.junit.Test;
+import model.Student;
+import play.test.*;
+import static play.test.Helpers.*;
+
+public class ApplicationTest{
+ private static final String BASE_URL = "http://localhost:9000";
+
+ @Test
+public void testInServer() throws Exception {
+ TestServer server = testServer(3333);
+ running(server, () -> {
+ try {
+ WSClient ws = play.libs.ws.WS.newClient(3333);
+ CompletionStage completionStage = ws.url("/").get();
+ WSResponse response = completionStage.toCompletableFuture().get();
+ ws.close();
+ assertEquals(OK, response.getStatus());
+ } catch (Exception e) {
+ logger.error(e.getMessage(), e);
+ }
+ });
+}
+ @Test
+ public void whenCreatesRecord_thenCorrect() {
+ Student student = new Student("jody", "west", 50);
+ JSONObject obj = new JSONObject(makeRequest(BASE_URL, "POST", new JSONObject(student)));
+ assertTrue(obj.getBoolean("isSuccessfull"));
+ JSONObject body = obj.getJSONObject("body");
+ assertEquals(student.getAge(), body.getInt("age"));
+ assertEquals(student.getFirstName(), body.getString("firstName"));
+ assertEquals(student.getLastName(), body.getString("lastName"));
+ }
+
+ @Test
+ public void whenDeletesCreatedRecord_thenCorrect() {
+ Student student = new Student("Usain", "Bolt", 25);
+ JSONObject ob1 = new JSONObject(makeRequest(BASE_URL, "POST", new JSONObject(student))).getJSONObject("body");
+ int id = ob1.getInt("id");
+ JSONObject obj1 = new JSONObject(makeRequest(BASE_URL + "/" + id, "POST", new JSONObject()));
+ assertTrue(obj1.getBoolean("isSuccessfull"));
+ makeRequest(BASE_URL + "/" + id, "DELETE", null);
+ JSONObject obj2 = new JSONObject(makeRequest(BASE_URL + "/" + id, "POST", new JSONObject()));
+ assertFalse(obj2.getBoolean("isSuccessfull"));
+ }
+
+ @Test
+ public void whenUpdatesCreatedRecord_thenCorrect() {
+ Student student = new Student("john", "doe", 50);
+ JSONObject body1 = new JSONObject(makeRequest(BASE_URL, "POST", new JSONObject(student))).getJSONObject("body");
+ assertEquals(student.getAge(), body1.getInt("age"));
+ int newAge = 60;
+ body1.put("age", newAge);
+ JSONObject body2 = new JSONObject(makeRequest(BASE_URL, "PUT", body1)).getJSONObject("body");
+ assertFalse(student.getAge() == body2.getInt("age"));
+ assertTrue(newAge == body2.getInt("age"));
+ }
+
+ @Test
+ public void whenGetsAllRecords_thenCorrect() {
+ Student student1 = new Student("jane", "daisy", 50);
+ Student student2 = new Student("john", "daniel", 60);
+ Student student3 = new Student("don", "mason", 55);
+ Student student4 = new Student("scarlet", "ohara", 90);
+
+ makeRequest(BASE_URL, "POST", new JSONObject(student1));
+ makeRequest(BASE_URL, "POST", new JSONObject(student2));
+ makeRequest(BASE_URL, "POST", new JSONObject(student3));
+ makeRequest(BASE_URL, "POST", new JSONObject(student4));
+
+ JSONObject objects = new JSONObject(makeRequest(BASE_URL, "GET", null));
+ assertTrue(objects.getBoolean("isSuccessfull"));
+ JSONArray array = objects.getJSONArray("body");
+ assertTrue(array.length() >= 4);
+ }
+
+ public static String makeRequest(String myUrl, String httpMethod, JSONObject parameters) {
+
+ URL url = null;
+ try {
+ url = new URL(myUrl);
+ } catch (MalformedURLException e) {
+ e.printStackTrace();
+ }
+ HttpURLConnection conn = null;
+ try {
+
+ conn = (HttpURLConnection) url.openConnection();
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ conn.setDoInput(true);
+
+ conn.setReadTimeout(10000);
+
+ conn.setRequestProperty("Content-Type", "application/json");
+ DataOutputStream dos = null;
+ int respCode = 0;
+ String inputString = null;
+ try {
+ conn.setRequestMethod(httpMethod);
+
+ if (Arrays.asList("POST", "PUT").contains(httpMethod)) {
+ String params = parameters.toString();
+
+ conn.setDoOutput(true);
+
+ dos = new DataOutputStream(conn.getOutputStream());
+ dos.writeBytes(params);
+ dos.flush();
+ dos.close();
+ }
+ respCode = conn.getResponseCode();
+ if (respCode != 200 && respCode != 201) {
+ String error = inputStreamToString(conn.getErrorStream());
+ return error;
+ }
+ inputString = inputStreamToString(conn.getInputStream());
+
+ } catch (IOException e) {
+
+ e.printStackTrace();
+ }
+ return inputString;
+ }
+
+ public static String inputStreamToString(InputStream is) {
+ BufferedReader br = null;
+ StringBuilder sb = new StringBuilder();
+
+ String line;
+ try {
+
+ br = new BufferedReader(new InputStreamReader(is));
+ while ((line = br.readLine()) != null) {
+ sb.append(line);
+ }
+
+ } catch (IOException e) {
+ e.printStackTrace();
+ } finally {
+ if (br != null) {
+ try {
+ br.close();
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ }
+ }
+
+ return sb.toString();
+
+ }
+}
diff --git a/pom.xml b/pom.xml
index daa92744ae..709c3e4e00 100644
--- a/pom.xml
+++ b/pom.xml
@@ -1,4 +1,5 @@
-
+
4.0.0
com.baeldung
parent-modules
@@ -8,33 +9,40 @@
pom
-
+
UTF-8
-
+
assertj
apache-cxf
- apache-fop
+
autovalue-tutorial
+
cdi
core-java
core-java-8
- couchbase-sdk-intro
- couchbase-sdk-spring-service
+ couchbase-sdk
+
+ dozer
dependency-injection
deltaspike
+
+ patterns
+ feign-client
gson
- gson-jackson-performance
guava
guava18
guava19
+
handling-spring-static-resources
httpclient
+
immutables
+
jackson
javaxval
jjwt
@@ -43,16 +51,24 @@
json
json-path
junit5
- mockito
- mocks
jee7schedule
+
+ log4j
+
+ mockito
+ mocks
+ mutation-testing
+
+ orika
+
querydsl
+
rest-assured
rest-testing
resteasy
- log4j
+ okhttp
spring-all
spring-akka
@@ -63,7 +79,6 @@
spring-cucumber
spring-data-cassandra
spring-data-couchbase-2
- spring-data-couchbase-2b
spring-data-elasticsearch
spring-data-neo4j
spring-data-mongodb
@@ -74,12 +89,13 @@
spring-hibernate3
spring-hibernate4
spring-jpa
- spring-jpa-jndi
+ spring-jms
spring-katharsis
spring-mockito
spring-mvc-java
spring-mvc-no-xml
spring-mvc-xml
+ spring-mvc-tiles
spring-openid
spring-protobuf
spring-quartz
@@ -87,8 +103,8 @@
spring-rest
spring-rest-angular
spring-rest-docs
- spring-cloud-config
- spring-cloud-hystrix
+ spring-cloud
+ spring-cloud-data-flow
spring-security-basic-auth
spring-security-custom-permission
@@ -106,17 +122,17 @@
spring-security-x509
spring-thymeleaf
spring-zuul
+ spring-mvc-velocity
+
jsf
xml
lombok
redis
- webjars
- mutation-testing
- spring-mvc-velocity
+ wicket
xstream
- dozer
- orika
+ java-cassandra
+ annotations
diff --git a/rest-assured/pom.xml b/rest-assured/pom.xml
index 47241b18bd..e2a2af9cd9 100644
--- a/rest-assured/pom.xml
+++ b/rest-assured/pom.xml
@@ -1,257 +1,226 @@
- 4.0.0
- com.baeldung
- rest-assured
- 1.0
- rest-assured
-
-
-
- org.apache.maven.plugins
- maven-compiler-plugin
- 3.3
-
- 8
- 8
-
-
-
-
-
-
-
- javax.servlet
- javax.servlet-api
- 3.1-b06
-
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ 4.0.0
+ com.baeldung
+ rest-assured
+ 1.0
+ rest-assured
-
-
- javax.servlet
- servlet-api
- 2.5
-
+
+
+ javax.servlet
+ javax.servlet-api
+ 3.1-b06
+
+
+ javax.servlet
+ servlet-api
+ 2.5
+
+
+ org.eclipse.jetty
+ jetty-security
+ 9.2.0.M1
+
+
+ org.eclipse.jetty
+ jetty-servlet
+ 9.2.0.M1
+
+
+ org.eclipse.jetty
+ jetty-servlets
+ 9.2.0.M1
+
+
+ org.eclipse.jetty
+ jetty-io
+ 9.2.0.M1
+
+
+ org.eclipse.jetty
+ jetty-http
+ 9.2.0.M1
+
+
+ org.eclipse.jetty
+ jetty-server
+ 9.2.0.M1
+
+
+ org.eclipse.jetty
+ jetty-util
+ 9.2.0.M1
+
-
-
- org.eclipse.jetty
- jetty-security
- 9.2.0.M1
-
+
+ org.slf4j
+ slf4j-api
+ 1.7.21
+
-
-
- org.eclipse.jetty
- jetty-servlet
- 9.2.0.M1
-
+
+ log4j
+ log4j
+ 1.2.17
+
+
+ org.slf4j
+ slf4j-log4j12
+ 1.7.21
+
-
-
- org.eclipse.jetty
- jetty-servlets
- 9.2.0.M1
-
+
+ commons-logging
+ commons-logging
+ 1.2
+
-
-
- org.eclipse.jetty
- jetty-io
- 9.2.0.M1
-
+
+ org.apache.httpcomponents
+ httpcore
+ 4.4.5
+
-
-
- org.eclipse.jetty
- jetty-http
- 9.2.0.M1
-
+
+ org.apache.commons
+ commons-lang3
+ 3.4
+
+
+ com.github.fge
+ uri-template
+ 0.9
+
+
+ com.googlecode.libphonenumber
+ libphonenumber
+ 7.4.5
+
-
-
- org.eclipse.jetty
- jetty-server
- 9.2.0.M1
-
+
+ javax.mail
+ mail
+ 1.4.7
+
-
-
- org.eclipse.jetty
- jetty-util
- 9.2.0.M1
-
+
+ joda-time
+ joda-time
+ 2.9.4
+
+
+ com.fasterxml.jackson.core
+ jackson-annotations
+ ${jackson.version}
+
+
+ com.fasterxml.jackson.core
+ jackson-databind
+ ${jackson.version}
+
-
-
- org.slf4j
- slf4j-api
- 1.7.21
-
+
+ com.github.fge
+ msg-simple
+ 1.1
+
-
-
- log4j
- log4j
- 1.2.17
-
-
-
- org.slf4j
- slf4j-log4j12
- 1.7.21
-
+
+ com.github.fge
+ jackson-coreutils
+ 1.8
+
-
-
-
- commons-logging
- commons-logging
- 1.2
-
+
+ com.google.guava
+ guava
+ ${guava.version}
+
+
+ com.github.fge
+ btf
+ 1.2
+
-
- org.apache.httpcomponents
- httpcore
- 4.4.5
-
+
+ org.apache.httpcomponents
+ httpclient
+ 4.5.2
+
-
-
- org.apache.commons
- commons-lang3
- 3.4
-
+
+ org.codehaus.groovy
+ groovy-all
+ 2.4.7
+
-
-
-
- com.github.fge
- uri-template
- 0.9
-
+
+ com.github.tomakehurst
+ wiremock
+ 2.1.7
+
+
+ io.rest-assured
+ rest-assured
+ 3.0.0
+ test
+
+
+ io.rest-assured
+ json-schema-validator
+ 3.0.0
+
+
+ com.github.fge
+ json-schema-validator
+ 2.2.6
+
+
+ com.github.fge
+ json-schema-core
+ 1.2.5
+
+
+ junit
+ junit
+ 4.3
+ test
+
-
-
- com.googlecode.libphonenumber
- libphonenumber
- 7.4.5
-
+
+ org.hamcrest
+ hamcrest-all
+ 1.3
+
+
+ commons-collections
+ commons-collections
+ 3.2.2
+
-
- javax.mail
- mail
- 1.4.7
-
+
-
- joda-time
- joda-time
- 2.9.4
-
+
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ 3.3
+
+ 8
+ 8
+
+
+
+
-
- com.fasterxml.jackson.core
- jackson-annotations
- 2.8.0
-
+
+ 2.8.3
+ 19.0
+
-
- com.fasterxml.jackson.core
- jackson-databind
- 2.8.0
-
-
-
- com.fasterxml.jackson.core
- jackson-core
- 2.8.0
-
-
-
- com.github.fge
- msg-simple
- 1.1
-
-
-
- com.github.fge
- jackson-coreutils
- 1.8
-
-
-
-
-
- com.google.guava
- guava
- 18.0
-
-
- com.github.fge
- btf
- 1.2
-
-
-
- org.apache.httpcomponents
- httpclient
- 4.5.2
-
-
-
- org.codehaus.groovy
- groovy-all
- 2.4.7
-
-
-
- com.github.tomakehurst
- wiremock
- 2.1.7
-
-
- io.rest-assured
- rest-assured
- 3.0.0
- test
-
-
- io.rest-assured
- json-schema-validator
- 3.0.0
-
-
- com.github.fge
- json-schema-validator
- 2.2.6
-
-
- com.github.fge
- json-schema-core
- 1.2.5
-
-
- junit
- junit
- 4.3
- test
-
-
-
- org.hamcrest
- hamcrest-all
- 1.3
-
-
-
- commons-collections
- commons-collections
- 3.2.2
-
-
-
diff --git a/rest-testing/pom.xml b/rest-testing/pom.xml
index 652f2ab601..819e8de8a5 100644
--- a/rest-testing/pom.xml
+++ b/rest-testing/pom.xml
@@ -156,7 +156,7 @@
- 2.7.2
+ 2.7.8
1.7.13
diff --git a/routing-in-play/.gitignore b/routing-in-play/.gitignore
new file mode 100644
index 0000000000..eb372fc719
--- /dev/null
+++ b/routing-in-play/.gitignore
@@ -0,0 +1,8 @@
+logs
+target
+/.idea
+/.idea_modules
+/.classpath
+/.project
+/.settings
+/RUNNING_PID
diff --git a/routing-in-play/LICENSE b/routing-in-play/LICENSE
new file mode 100644
index 0000000000..4baedcb95f
--- /dev/null
+++ b/routing-in-play/LICENSE
@@ -0,0 +1,8 @@
+This software is licensed under the Apache 2 license, quoted below.
+
+Licensed under the Apache License, Version 2.0 (the "License"); you may not use this project except in compliance with
+the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0.
+
+Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific
+language governing permissions and limitations under the License.
\ No newline at end of file
diff --git a/routing-in-play/README b/routing-in-play/README
new file mode 100644
index 0000000000..f21d092edf
--- /dev/null
+++ b/routing-in-play/README
@@ -0,0 +1,49 @@
+This is your new Play application
+=================================
+
+This file will be packaged with your application when using `activator dist`.
+
+There are several demonstration files available in this template.
+
+Controllers
+===========
+
+- HomeController.java:
+
+ Shows how to handle simple HTTP requests.
+
+- AsyncController.java:
+
+ Shows how to do asynchronous programming when handling a request.
+
+- CountController.java:
+
+ Shows how to inject a component into a controller and use the component when
+ handling requests.
+
+Components
+==========
+
+- Module.java:
+
+ Shows how to use Guice to bind all the components needed by your application.
+
+- Counter.java:
+
+ An example of a component that contains state, in this case a simple counter.
+
+- ApplicationTimer.java:
+
+ An example of a component that starts when the application starts and stops
+ when the application stops.
+
+Filters
+=======
+
+- Filters.java:
+
+ Creates the list of HTTP filters used by your application.
+
+- ExampleFilter.java
+
+ A simple filter that adds a header to every response.
\ No newline at end of file
diff --git a/routing-in-play/app/Filters.java b/routing-in-play/app/Filters.java
new file mode 100644
index 0000000000..255de8ca93
--- /dev/null
+++ b/routing-in-play/app/Filters.java
@@ -0,0 +1,46 @@
+import javax.inject.*;
+import play.*;
+import play.mvc.EssentialFilter;
+import play.http.HttpFilters;
+import play.mvc.*;
+
+import filters.ExampleFilter;
+
+/**
+ * This class configures filters that run on every request. This
+ * class is queried by Play to get a list of filters.
+ *
+ * Play will automatically use filters from any class called
+ * Filters that is placed the root package. You can load filters
+ * from a different class by adding a `play.http.filters` setting to
+ * the application.conf configuration file.
+ */
+@Singleton
+public class Filters implements HttpFilters {
+
+ private final Environment env;
+ private final EssentialFilter exampleFilter;
+
+ /**
+ * @param env Basic environment settings for the current application.
+ * @param exampleFilter A demonstration filter that adds a header to
+ */
+ @Inject
+ public Filters(Environment env, ExampleFilter exampleFilter) {
+ this.env = env;
+ this.exampleFilter = exampleFilter;
+ }
+
+ @Override
+ public EssentialFilter[] filters() {
+ // Use the example filter if we're running development mode. If
+ // we're running in production or test mode then don't use any
+ // filters at all.
+ if (env.mode().equals(Mode.DEV)) {
+ return new EssentialFilter[] { exampleFilter };
+ } else {
+ return new EssentialFilter[] {};
+ }
+ }
+
+}
diff --git a/routing-in-play/app/Module.java b/routing-in-play/app/Module.java
new file mode 100644
index 0000000000..6e7d1766ef
--- /dev/null
+++ b/routing-in-play/app/Module.java
@@ -0,0 +1,31 @@
+import com.google.inject.AbstractModule;
+import java.time.Clock;
+
+import services.ApplicationTimer;
+import services.AtomicCounter;
+import services.Counter;
+
+/**
+ * This class is a Guice module that tells Guice how to bind several
+ * different types. This Guice module is created when the Play
+ * application starts.
+ *
+ * Play will automatically use any class called `Module` that is in
+ * the root package. You can create modules in other locations by
+ * adding `play.modules.enabled` settings to the `application.conf`
+ * configuration file.
+ */
+public class Module extends AbstractModule {
+
+ @Override
+ public void configure() {
+ // Use the system clock as the default implementation of Clock
+ bind(Clock.class).toInstance(Clock.systemDefaultZone());
+ // Ask Guice to create an instance of ApplicationTimer when the
+ // application starts.
+ bind(ApplicationTimer.class).asEagerSingleton();
+ // Set AtomicCounter as the implementation for Counter.
+ bind(Counter.class).to(AtomicCounter.class);
+ }
+
+}
diff --git a/routing-in-play/app/controllers/HomeController.java b/routing-in-play/app/controllers/HomeController.java
new file mode 100644
index 0000000000..6e340d594f
--- /dev/null
+++ b/routing-in-play/app/controllers/HomeController.java
@@ -0,0 +1,33 @@
+package controllers;
+
+import play.mvc.*;
+
+import views.html.*;
+
+/**
+ * This controller contains an action to handle HTTP requests
+ * to the application's home page.
+ */
+public class HomeController extends Controller {
+
+ /**
+ * An action that renders an HTML page with a welcome message.
+ * The configuration in the routes file means that
+ * this method will be called when the application receives a
+ * GET request with a path of /.
+ */
+ public Result index(String author,int id) {
+ return ok("Routing in Play by:"+author+" ID:"+id);
+ }
+ public Result greet(String name,int age) {
+ return ok("Hello "+name+", you are "+age+" years old");
+ }
+ public Result introduceMe(String data) {
+ String[] clientData=data.split(",");
+ return ok("Your name is "+clientData[0]+", you are "+clientData[1]+" years old");
+ }
+ public Result squareMe(Long num) {
+ return ok(num+" Squared is "+(num*num));
+ }
+
+}
diff --git a/routing-in-play/app/filters/ExampleFilter.java b/routing-in-play/app/filters/ExampleFilter.java
new file mode 100644
index 0000000000..67a6a36cc3
--- /dev/null
+++ b/routing-in-play/app/filters/ExampleFilter.java
@@ -0,0 +1,45 @@
+package filters;
+
+import akka.stream.Materializer;
+import java.util.concurrent.CompletionStage;
+import java.util.concurrent.Executor;
+import java.util.function.Function;
+import javax.inject.*;
+import play.mvc.*;
+import play.mvc.Http.RequestHeader;
+
+
+/**
+ * This is a simple filter that adds a header to all requests. It's
+ * added to the application's list of filters by the
+ * {@link Filters} class.
+ */
+@Singleton
+public class ExampleFilter extends Filter {
+
+ private final Executor exec;
+
+ /**
+ * @param mat This object is needed to handle streaming of requests
+ * and responses.
+ * @param exec This class is needed to execute code asynchronously.
+ * It is used below by the thenAsyncApply method.
+ */
+ @Inject
+ public ExampleFilter(Materializer mat, Executor exec) {
+ super(mat);
+ this.exec = exec;
+ }
+
+ @Override
+ public CompletionStage apply(
+ Function> next,
+ RequestHeader requestHeader) {
+
+ return next.apply(requestHeader).thenApplyAsync(
+ result -> result.withHeader("X-ExampleFilter", "foo"),
+ exec
+ );
+ }
+
+}
diff --git a/routing-in-play/app/services/ApplicationTimer.java b/routing-in-play/app/services/ApplicationTimer.java
new file mode 100644
index 0000000000..a951562b1d
--- /dev/null
+++ b/routing-in-play/app/services/ApplicationTimer.java
@@ -0,0 +1,50 @@
+package services;
+
+import java.time.Clock;
+import java.time.Instant;
+import java.util.concurrent.CompletableFuture;
+import javax.inject.*;
+import play.Logger;
+import play.inject.ApplicationLifecycle;
+
+/**
+ * This class demonstrates how to run code when the
+ * application starts and stops. It starts a timer when the
+ * application starts. When the application stops it prints out how
+ * long the application was running for.
+ *
+ * This class is registered for Guice dependency injection in the
+ * {@link Module} class. We want the class to start when the application
+ * starts, so it is registered as an "eager singleton". See the code
+ * in the {@link Module} class to see how this happens.
+ *
+ * This class needs to run code when the server stops. It uses the
+ * application's {@link ApplicationLifecycle} to register a stop hook.
+ */
+@Singleton
+public class ApplicationTimer {
+
+ private final Clock clock;
+ private final ApplicationLifecycle appLifecycle;
+ private final Instant start;
+
+ @Inject
+ public ApplicationTimer(Clock clock, ApplicationLifecycle appLifecycle) {
+ this.clock = clock;
+ this.appLifecycle = appLifecycle;
+ // This code is called when the application starts.
+ start = clock.instant();
+ Logger.info("ApplicationTimer demo: Starting application at " + start);
+
+ // When the application starts, register a stop hook with the
+ // ApplicationLifecycle object. The code inside the stop hook will
+ // be run when the application stops.
+ appLifecycle.addStopHook(() -> {
+ Instant stop = clock.instant();
+ Long runningTime = stop.getEpochSecond() - start.getEpochSecond();
+ Logger.info("ApplicationTimer demo: Stopping application at " + clock.instant() + " after " + runningTime + "s.");
+ return CompletableFuture.completedFuture(null);
+ });
+ }
+
+}
diff --git a/routing-in-play/app/services/AtomicCounter.java b/routing-in-play/app/services/AtomicCounter.java
new file mode 100644
index 0000000000..41f741cbf7
--- /dev/null
+++ b/routing-in-play/app/services/AtomicCounter.java
@@ -0,0 +1,26 @@
+package services;
+
+import java.util.concurrent.atomic.AtomicInteger;
+import javax.inject.*;
+
+/**
+ * This class is a concrete implementation of the {@link Counter} trait.
+ * It is configured for Guice dependency injection in the {@link Module}
+ * class.
+ *
+ * This class has a {@link Singleton} annotation because we need to make
+ * sure we only use one counter per application. Without this
+ * annotation we would get a new instance every time a {@link Counter} is
+ * injected.
+ */
+@Singleton
+public class AtomicCounter implements Counter {
+
+ private final AtomicInteger atomicCounter = new AtomicInteger();
+
+ @Override
+ public int nextCount() {
+ return atomicCounter.getAndIncrement();
+ }
+
+}
diff --git a/routing-in-play/app/services/Counter.java b/routing-in-play/app/services/Counter.java
new file mode 100644
index 0000000000..dadad8b09d
--- /dev/null
+++ b/routing-in-play/app/services/Counter.java
@@ -0,0 +1,13 @@
+package services;
+
+/**
+ * This interface demonstrates how to create a component that is injected
+ * into a controller. The interface represents a counter that returns a
+ * incremented number each time it is called.
+ *
+ * The {@link Modules} class binds this interface to the
+ * {@link AtomicCounter} implementation.
+ */
+public interface Counter {
+ int nextCount();
+}
diff --git a/routing-in-play/app/views/index.scala.html b/routing-in-play/app/views/index.scala.html
new file mode 100644
index 0000000000..4539f5a10b
--- /dev/null
+++ b/routing-in-play/app/views/index.scala.html
@@ -0,0 +1,20 @@
+@*
+ * This template takes a single argument, a String containing a
+ * message to display.
+ *@
+@(message: String)
+
+@*
+ * Call the `main` template with two arguments. The first
+ * argument is a `String` with the title of the page, the second
+ * argument is an `Html` object containing the body of the page.
+ *@
+@main("Welcome to Play") {
+
+ @*
+ * Get an `Html` object by calling the built-in Play welcome
+ * template and passing a `String` message.
+ *@
+ @play20.welcome(message, style = "Java")
+
+}
diff --git a/routing-in-play/app/views/main.scala.html b/routing-in-play/app/views/main.scala.html
new file mode 100644
index 0000000000..9414f4be6e
--- /dev/null
+++ b/routing-in-play/app/views/main.scala.html
@@ -0,0 +1,23 @@
+@*
+ * This template is called from the `index` template. This template
+ * handles the rendering of the page header and body tags. It takes
+ * two arguments, a `String` for the title of the page and an `Html`
+ * object to insert into the body of the page.
+ *@
+@(title: String)(content: Html)
+
+
+
+
+ @* Here's where we render the page title `String`. *@
+ @title
+
+
+
+
+
+ @* And here's where we render the `Html` object containing
+ * the page content. *@
+ @content
+
+
diff --git a/routing-in-play/bin/activator b/routing-in-play/bin/activator
new file mode 100644
index 0000000000..a8b11d482f
--- /dev/null
+++ b/routing-in-play/bin/activator
@@ -0,0 +1,397 @@
+#!/usr/bin/env bash
+
+### ------------------------------- ###
+### Helper methods for BASH scripts ###
+### ------------------------------- ###
+
+realpath () {
+(
+ TARGET_FILE="$1"
+ FIX_CYGPATH="$2"
+
+ cd "$(dirname "$TARGET_FILE")"
+ TARGET_FILE=$(basename "$TARGET_FILE")
+
+ COUNT=0
+ while [ -L "$TARGET_FILE" -a $COUNT -lt 100 ]
+ do
+ TARGET_FILE=$(readlink "$TARGET_FILE")
+ cd "$(dirname "$TARGET_FILE")"
+ TARGET_FILE=$(basename "$TARGET_FILE")
+ COUNT=$(($COUNT + 1))
+ done
+
+ # make sure we grab the actual windows path, instead of cygwin's path.
+ if [[ "x$FIX_CYGPATH" != "x" ]]; then
+ echo "$(cygwinpath "$(pwd -P)/$TARGET_FILE")"
+ else
+ echo "$(pwd -P)/$TARGET_FILE"
+ fi
+)
+}
+
+
+# Uses uname to detect if we're in the odd cygwin environment.
+is_cygwin() {
+ local os=$(uname -s)
+ case "$os" in
+ CYGWIN*) return 0 ;;
+ *) return 1 ;;
+ esac
+}
+
+# TODO - Use nicer bash-isms here.
+CYGWIN_FLAG=$(if is_cygwin; then echo true; else echo false; fi)
+
+
+# This can fix cygwin style /cygdrive paths so we get the
+# windows style paths.
+cygwinpath() {
+ local file="$1"
+ if [[ "$CYGWIN_FLAG" == "true" ]]; then
+ echo $(cygpath -w $file)
+ else
+ echo $file
+ fi
+}
+
+# Make something URI friendly
+make_url() {
+ url="$1"
+ local nospaces=${url// /%20}
+ if is_cygwin; then
+ echo "/${nospaces//\\//}"
+ else
+ echo "$nospaces"
+ fi
+}
+
+declare -a residual_args
+declare -a java_args
+declare -a scalac_args
+declare -a sbt_commands
+declare java_cmd=java
+declare java_version
+declare -r real_script_path="$(realpath "$0")"
+declare -r sbt_home="$(realpath "$(dirname "$(dirname "$real_script_path")")")"
+declare -r sbt_bin_dir="$(dirname "$real_script_path")"
+declare -r app_version="1.3.10"
+
+declare -r script_name=activator
+declare -r java_opts=( "${ACTIVATOR_OPTS[@]}" "${SBT_OPTS[@]}" "${JAVA_OPTS[@]}" "${java_opts[@]}" )
+userhome="$HOME"
+if is_cygwin; then
+ # cygwin sets home to something f-d up, set to real windows homedir
+ userhome="$USERPROFILE"
+fi
+declare -r activator_user_home_dir="${userhome}/.activator"
+declare -r java_opts_config_home="${activator_user_home_dir}/activatorconfig.txt"
+declare -r java_opts_config_version="${activator_user_home_dir}/${app_version}/activatorconfig.txt"
+
+echoerr () {
+ echo 1>&2 "$@"
+}
+vlog () {
+ [[ $verbose || $debug ]] && echoerr "$@"
+}
+dlog () {
+ [[ $debug ]] && echoerr "$@"
+}
+
+jar_file () {
+ echo "$(cygwinpath "${sbt_home}/libexec/activator-launch-${app_version}.jar")"
+}
+
+acquire_sbt_jar () {
+ sbt_jar="$(jar_file)"
+
+ if [[ ! -f "$sbt_jar" ]]; then
+ echoerr "Could not find launcher jar: $sbt_jar"
+ exit 2
+ fi
+}
+
+execRunner () {
+ # print the arguments one to a line, quoting any containing spaces
+ [[ $verbose || $debug ]] && echo "# Executing command line:" && {
+ for arg; do
+ if printf "%s\n" "$arg" | grep -q ' '; then
+ printf "\"%s\"\n" "$arg"
+ else
+ printf "%s\n" "$arg"
+ fi
+ done
+ echo ""
+ }
+
+ # THis used to be exec, but we loose the ability to re-hook stty then
+ # for cygwin... Maybe we should flag the feature here...
+ "$@"
+}
+
+addJava () {
+ dlog "[addJava] arg = '$1'"
+ java_args=( "${java_args[@]}" "$1" )
+}
+addSbt () {
+ dlog "[addSbt] arg = '$1'"
+ sbt_commands=( "${sbt_commands[@]}" "$1" )
+}
+addResidual () {
+ dlog "[residual] arg = '$1'"
+ residual_args=( "${residual_args[@]}" "$1" )
+}
+addDebugger () {
+ addJava "-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=$1"
+}
+
+get_mem_opts () {
+ # if we detect any of these settings in ${JAVA_OPTS} we need to NOT output our settings.
+ # The reason is the Xms/Xmx, if they don't line up, cause errors.
+ if [[ "${JAVA_OPTS}" == *-Xmx* ]] || [[ "${JAVA_OPTS}" == *-Xms* ]] || [[ "${JAVA_OPTS}" == *-XX:MaxPermSize* ]] || [[ "${JAVA_OPTS}" == *-XX:MaxMetaspaceSize* ]] || [[ "${JAVA_OPTS}" == *-XX:ReservedCodeCacheSize* ]]; then
+ echo ""
+ else
+ # a ham-fisted attempt to move some memory settings in concert
+ # so they need not be messed around with individually.
+ local mem=${1:-1024}
+ local codecache=$(( $mem / 8 ))
+ (( $codecache > 128 )) || codecache=128
+ (( $codecache < 512 )) || codecache=512
+ local class_metadata_size=$(( $codecache * 2 ))
+ local class_metadata_opt=$([[ "$java_version" < "1.8" ]] && echo "MaxPermSize" || echo "MaxMetaspaceSize")
+
+ echo "-Xms${mem}m -Xmx${mem}m -XX:ReservedCodeCacheSize=${codecache}m -XX:${class_metadata_opt}=${class_metadata_size}m"
+ fi
+}
+
+require_arg () {
+ local type="$1"
+ local opt="$2"
+ local arg="$3"
+ if [[ -z "$arg" ]] || [[ "${arg:0:1}" == "-" ]]; then
+ echo "$opt requires <$type> argument"
+ exit 1
+ fi
+}
+
+is_function_defined() {
+ declare -f "$1" > /dev/null
+}
+
+# If we're *not* running in a terminal, and we don't have any arguments, then we need to add the 'ui' parameter
+detect_terminal_for_ui() {
+ [[ ! -t 0 ]] && [[ "${#residual_args}" == "0" ]] && {
+ addResidual "ui"
+ }
+ # SPECIAL TEST FOR MAC
+ [[ "$(uname)" == "Darwin" ]] && [[ "$HOME" == "$PWD" ]] && [[ "${#residual_args}" == "0" ]] && {
+ echo "Detected MAC OSX launched script...."
+ echo "Swapping to UI"
+ addResidual "ui"
+ }
+}
+
+process_args () {
+ while [[ $# -gt 0 ]]; do
+ case "$1" in
+ -h|-help) usage; exit 1 ;;
+ -v|-verbose) verbose=1 && shift ;;
+ -d|-debug) debug=1 && shift ;;
+
+ -ivy) require_arg path "$1" "$2" && addJava "-Dsbt.ivy.home=$2" && shift 2 ;;
+ -mem) require_arg integer "$1" "$2" && sbt_mem="$2" && shift 2 ;;
+ -jvm-debug) require_arg port "$1" "$2" && addDebugger $2 && shift 2 ;;
+ -batch) exec &1 | awk -F '"' '/version/ {print $2}')
+ vlog "[process_args] java_version = '$java_version'"
+}
+
+# Detect that we have java installed.
+checkJava() {
+ local required_version="$1"
+ # Now check to see if it's a good enough version
+ if [[ "$java_version" == "" ]]; then
+ echo
+ echo No java installations was detected.
+ echo Please go to http://www.java.com/getjava/ and download
+ echo
+ exit 1
+ elif [[ ! "$java_version" > "$required_version" ]]; then
+ echo
+ echo The java installation you have is not up to date
+ echo $script_name requires at least version $required_version+, you have
+ echo version $java_version
+ echo
+ echo Please go to http://www.java.com/getjava/ and download
+ echo a valid Java Runtime and install before running $script_name.
+ echo
+ exit 1
+ fi
+}
+
+
+run() {
+ # no jar? download it.
+ [[ -f "$sbt_jar" ]] || acquire_sbt_jar "$sbt_version" || {
+ # still no jar? uh-oh.
+ echo "Download failed. Obtain the sbt-launch.jar manually and place it at $sbt_jar"
+ exit 1
+ }
+
+ # process the combined args, then reset "$@" to the residuals
+ process_args "$@"
+ detect_terminal_for_ui
+ set -- "${residual_args[@]}"
+ argumentCount=$#
+
+ # TODO - java check should be configurable...
+ checkJava "1.6"
+
+ #If we're in cygwin, we should use the windows config, and terminal hacks
+ if [[ "$CYGWIN_FLAG" == "true" ]]; then
+ stty -icanon min 1 -echo > /dev/null 2>&1
+ addJava "-Djline.terminal=jline.UnixTerminal"
+ addJava "-Dsbt.cygwin=true"
+ fi
+
+ # run sbt
+ execRunner "$java_cmd" \
+ "-Dactivator.home=$(make_url "$sbt_home")" \
+ ${SBT_OPTS:-$default_sbt_opts} \
+ $(get_mem_opts $sbt_mem) \
+ ${JAVA_OPTS} \
+ ${java_args[@]} \
+ -jar "$sbt_jar" \
+ "${sbt_commands[@]}" \
+ "${residual_args[@]}"
+
+ exit_code=$?
+
+ # Clean up the terminal from cygwin hacks.
+ if [[ "$CYGWIN_FLAG" == "true" ]]; then
+ stty icanon echo > /dev/null 2>&1
+ fi
+ exit $exit_code
+}
+
+
+declare -r noshare_opts="-Dsbt.global.base=project/.sbtboot -Dsbt.boot.directory=project/.boot -Dsbt.ivy.home=project/.ivy"
+declare -r sbt_opts_file=".sbtopts"
+declare -r etc_sbt_opts_file="${sbt_home}/conf/sbtopts"
+declare -r win_sbt_opts_file="${sbt_home}/conf/sbtconfig.txt"
+
+usage() {
+ cat < path to global settings/plugins directory (default: ~/.sbt)
+ -sbt-boot path to shared boot directory (default: ~/.sbt/boot in 0.11 series)
+ -ivy path to local Ivy repository (default: ~/.ivy2)
+ -mem set memory options (default: $sbt_mem, which is $(get_mem_opts $sbt_mem))
+ -no-share use all local caches; no sharing
+ -no-global uses global caches, but does not use global ~/.sbt directory.
+ -jvm-debug Turn on JVM debugging, open at the given port.
+ -batch Disable interactive mode
+
+ # sbt version (default: from project/build.properties if present, else latest release)
+ -sbt-version use the specified version of sbt
+ -sbt-jar use the specified jar as the sbt launcher
+ -sbt-rc use an RC version of sbt
+ -sbt-snapshot use a snapshot version of sbt
+
+ # java version (default: java from PATH, currently $(java -version 2>&1 | grep version))
+ -java-home alternate JAVA_HOME
+
+ # jvm options and output control
+ JAVA_OPTS environment variable, if unset uses "$java_opts"
+ SBT_OPTS environment variable, if unset uses "$default_sbt_opts"
+ ACTIVATOR_OPTS Environment variable, if unset uses ""
+ .sbtopts if this file exists in the current directory, it is
+ prepended to the runner args
+ /etc/sbt/sbtopts if this file exists, it is prepended to the runner args
+ -Dkey=val pass -Dkey=val directly to the java runtime
+ -J-X pass option -X directly to the java runtime
+ (-J is stripped)
+ -S-X add -X to sbt's scalacOptions (-S is stripped)
+
+In the case of duplicated or conflicting options, the order above
+shows precedence: JAVA_OPTS lowest, command line options highest.
+EOM
+}
+
+
+
+process_my_args () {
+ while [[ $# -gt 0 ]]; do
+ case "$1" in
+ -no-colors) addJava "-Dsbt.log.noformat=true" && shift ;;
+ -no-share) addJava "$noshare_opts" && shift ;;
+ -no-global) addJava "-Dsbt.global.base=$(pwd)/project/.sbtboot" && shift ;;
+ -sbt-boot) require_arg path "$1" "$2" && addJava "-Dsbt.boot.directory=$2" && shift 2 ;;
+ -sbt-dir) require_arg path "$1" "$2" && addJava "-Dsbt.global.base=$2" && shift 2 ;;
+ -debug-inc) addJava "-Dxsbt.inc.debug=true" && shift ;;
+ -batch) exec ^&1') do (
+ if %%~j==java set JAVAINSTALLED=1
+ if %%~j==openjdk set JAVAINSTALLED=1
+)
+
+rem Detect the same thing about javac
+if "%_JAVACCMD%"=="" (
+ if not "%JAVA_HOME%"=="" (
+ if exist "%JAVA_HOME%\bin\javac.exe" set "_JAVACCMD=%JAVA_HOME%\bin\javac.exe"
+ )
+)
+if "%_JAVACCMD%"=="" set _JAVACCMD=javac
+for /F %%j in ('"%_JAVACCMD%" -version 2^>^&1') do (
+ if %%~j==javac set JAVACINSTALLED=1
+)
+
+rem BAT has no logical or, so we do it OLD SCHOOL! Oppan Redmond Style
+set JAVAOK=true
+if not defined JAVAINSTALLED set JAVAOK=false
+if not defined JAVACINSTALLED set JAVAOK=false
+
+if "%JAVAOK%"=="false" (
+ echo.
+ echo A Java JDK is not installed or can't be found.
+ if not "%JAVA_HOME%"=="" (
+ echo JAVA_HOME = "%JAVA_HOME%"
+ )
+ echo.
+ echo Please go to
+ echo http://www.oracle.com/technetwork/java/javase/downloads/index.html
+ echo and download a valid Java JDK and install before running Activator.
+ echo.
+ echo If you think this message is in error, please check
+ echo your environment variables to see if "java.exe" and "javac.exe" are
+ echo available via JAVA_HOME or PATH.
+ echo.
+ if defined DOUBLECLICKED pause
+ exit /B 1
+)
+
+rem Check what Java version is being used to determine what memory options to use
+for /f "tokens=3" %%g in ('java -version 2^>^&1 ^| findstr /i "version"') do (
+ set JAVA_VERSION=%%g
+)
+
+rem Strips away the " characters
+set JAVA_VERSION=%JAVA_VERSION:"=%
+
+rem TODO Check if there are existing mem settings in JAVA_OPTS/CFG_OPTS and use those instead of the below
+for /f "delims=. tokens=1-3" %%v in ("%JAVA_VERSION%") do (
+ set MAJOR=%%v
+ set MINOR=%%w
+ set BUILD=%%x
+
+ set META_SIZE=-XX:MetaspaceSize=64M -XX:MaxMetaspaceSize=256M
+ if "!MINOR!" LSS "8" (
+ set META_SIZE=-XX:PermSize=64M -XX:MaxPermSize=256M
+ )
+
+ set MEM_OPTS=!META_SIZE!
+ )
+
+rem We use the value of the JAVA_OPTS environment variable if defined, rather than the config.
+set _JAVA_OPTS=%JAVA_OPTS%
+if "%_JAVA_OPTS%"=="" set _JAVA_OPTS=%CFG_OPTS%
+
+set DEBUG_OPTS=
+
+rem Loop through the arguments, building remaining args in args variable
+set args=
+:argsloop
+if not "%~1"=="" (
+ rem Checks if the argument contains "-D" and if true, adds argument 1 with 2 and puts an equal sign between them.
+ rem This is done since batch considers "=" to be a delimiter so we need to circumvent this behavior with a small hack.
+ set arg1=%~1
+ if "!arg1:~0,2!"=="-D" (
+ set "args=%args% "%~1"="%~2""
+ shift
+ shift
+ goto argsloop
+ )
+
+ if "%~1"=="-jvm-debug" (
+ if not "%~2"=="" (
+ rem This piece of magic somehow checks that an argument is a number
+ for /F "delims=0123456789" %%i in ("%~2") do (
+ set var="%%i"
+ )
+ if defined var (
+ rem Not a number, assume no argument given and default to 9999
+ set JPDA_PORT=9999
+ ) else (
+ rem Port was given, shift arguments
+ set JPDA_PORT=%~2
+ shift
+ )
+ ) else (
+ set JPDA_PORT=9999
+ )
+ shift
+
+ set DEBUG_OPTS=-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=n,address=!JPDA_PORT!
+ goto argsloop
+ )
+ rem else
+ set "args=%args% "%~1""
+ shift
+ goto argsloop
+)
+
+:run
+
+if "!args!"=="" (
+ if defined DOUBLECLICKED (
+ set CMDS="ui"
+ ) else set CMDS=!args!
+) else set CMDS=!args!
+
+rem We add a / in front, so we get file:///C: instead of file://C:
+rem Java considers the later a UNC path.
+rem We also attempt a solid effort at making it URI friendly.
+rem We don't even bother with UNC paths.
+set JAVA_FRIENDLY_HOME_1=/!ACTIVATOR_HOME:\=/!
+set JAVA_FRIENDLY_HOME=/!JAVA_FRIENDLY_HOME_1: =%%20!
+
+rem Checks if the command contains spaces to know if it should be wrapped in quotes or not
+set NON_SPACED_CMD=%_JAVACMD: =%
+if "%_JAVACMD%"=="%NON_SPACED_CMD%" %_JAVACMD% %DEBUG_OPTS% %MEM_OPTS% %ACTIVATOR_OPTS% %SBT_OPTS% %_JAVA_OPTS% "-Dactivator.home=%JAVA_FRIENDLY_HOME%" -jar "%ACTIVATOR_HOME%\libexec\%ACTIVATOR_LAUNCH_JAR%" %CMDS%
+if NOT "%_JAVACMD%"=="%NON_SPACED_CMD%" "%_JAVACMD%" %DEBUG_OPTS% %MEM_OPTS% %ACTIVATOR_OPTS% %SBT_OPTS% %_JAVA_OPTS% "-Dactivator.home=%JAVA_FRIENDLY_HOME%" -jar "%ACTIVATOR_HOME%\libexec\%ACTIVATOR_LAUNCH_JAR%" %CMDS%
+
+if ERRORLEVEL 1 goto error
+goto end
+
+:error
+set ERROR_CODE=1
+
+:end
+
+@endlocal
+
+exit /B %ERROR_CODE%
diff --git a/routing-in-play/build.sbt b/routing-in-play/build.sbt
new file mode 100644
index 0000000000..083d071676
--- /dev/null
+++ b/routing-in-play/build.sbt
@@ -0,0 +1,13 @@
+name := """webapp"""
+
+version := "1.0-SNAPSHOT"
+
+lazy val root = (project in file(".")).enablePlugins(PlayJava)
+
+scalaVersion := "2.11.7"
+
+libraryDependencies ++= Seq(
+ javaJdbc,
+ cache,
+ javaWs
+)
diff --git a/routing-in-play/conf/application.conf b/routing-in-play/conf/application.conf
new file mode 100644
index 0000000000..489d3f9b3e
--- /dev/null
+++ b/routing-in-play/conf/application.conf
@@ -0,0 +1,353 @@
+# This is the main configuration file for the application.
+# https://www.playframework.com/documentation/latest/ConfigFile
+# ~~~~~
+# Play uses HOCON as its configuration file format. HOCON has a number
+# of advantages over other config formats, but there are two things that
+# can be used when modifying settings.
+#
+# You can include other configuration files in this main application.conf file:
+#include "extra-config.conf"
+#
+# You can declare variables and substitute for them:
+#mykey = ${some.value}
+#
+# And if an environment variable exists when there is no other subsitution, then
+# HOCON will fall back to substituting environment variable:
+#mykey = ${JAVA_HOME}
+
+## Akka
+# https://www.playframework.com/documentation/latest/ScalaAkka#Configuration
+# https://www.playframework.com/documentation/latest/JavaAkka#Configuration
+# ~~~~~
+# Play uses Akka internally and exposes Akka Streams and actors in Websockets and
+# other streaming HTTP responses.
+akka {
+ # "akka.log-config-on-start" is extraordinarly useful because it log the complete
+ # configuration at INFO level, including defaults and overrides, so it s worth
+ # putting at the very top.
+ #
+ # Put the following in your conf/logback.xml file:
+ #
+ #
+ #
+ # And then uncomment this line to debug the configuration.
+ #
+ #log-config-on-start = true
+}
+
+## Secret key
+# http://www.playframework.com/documentation/latest/ApplicationSecret
+# ~~~~~
+# The secret key is used to sign Play's session cookie.
+# This must be changed for production, but we don't recommend you change it in this file.
+play.crypto.secret = "changeme"
+
+## Modules
+# https://www.playframework.com/documentation/latest/Modules
+# ~~~~~
+# Control which modules are loaded when Play starts. Note that modules are
+# the replacement for "GlobalSettings", which are deprecated in 2.5.x.
+# Please see https://www.playframework.com/documentation/latest/GlobalSettings
+# for more information.
+#
+# You can also extend Play functionality by using one of the publically available
+# Play modules: https://playframework.com/documentation/latest/ModuleDirectory
+play.modules {
+ # By default, Play will load any class called Module that is defined
+ # in the root package (the "app" directory), or you can define them
+ # explicitly below.
+ # If there are any built-in modules that you want to disable, you can list them here.
+ #enabled += my.application.Module
+
+ # If there are any built-in modules that you want to disable, you can list them here.
+ #disabled += ""
+}
+
+## IDE
+# https://www.playframework.com/documentation/latest/IDE
+# ~~~~~
+# Depending on your IDE, you can add a hyperlink for errors that will jump you
+# directly to the code location in the IDE in dev mode. The following line makes
+# use of the IntelliJ IDEA REST interface:
+#play.editor="http://localhost:63342/api/file/?file=%s&line=%s"
+
+## Internationalisation
+# https://www.playframework.com/documentation/latest/JavaI18N
+# https://www.playframework.com/documentation/latest/ScalaI18N
+# ~~~~~
+# Play comes with its own i18n settings, which allow the user's preferred language
+# to map through to internal messages, or allow the language to be stored in a cookie.
+play.i18n {
+ # The application languages
+ langs = [ "en" ]
+
+ # Whether the language cookie should be secure or not
+ #langCookieSecure = true
+
+ # Whether the HTTP only attribute of the cookie should be set to true
+ #langCookieHttpOnly = true
+}
+
+## Play HTTP settings
+# ~~~~~
+play.http {
+ ## Router
+ # https://www.playframework.com/documentation/latest/JavaRouting
+ # https://www.playframework.com/documentation/latest/ScalaRouting
+ # ~~~~~
+ # Define the Router object to use for this application.
+ # This router will be looked up first when the application is starting up,
+ # so make sure this is the entry point.
+ # Furthermore, it's assumed your route file is named properly.
+ # So for an application router like `my.application.Router`,
+ # you may need to define a router file `conf/my.application.routes`.
+ # Default to Routes in the root package (aka "apps" folder) (and conf/routes)
+ #router = my.application.Router
+
+ ## Action Creator
+ # https://www.playframework.com/documentation/latest/JavaActionCreator
+ # ~~~~~
+ #actionCreator = null
+
+ ## ErrorHandler
+ # https://www.playframework.com/documentation/latest/JavaRouting
+ # https://www.playframework.com/documentation/latest/ScalaRouting
+ # ~~~~~
+ # If null, will attempt to load a class called ErrorHandler in the root package,
+ #errorHandler = null
+
+ ## Filters
+ # https://www.playframework.com/documentation/latest/ScalaHttpFilters
+ # https://www.playframework.com/documentation/latest/JavaHttpFilters
+ # ~~~~~
+ # Filters run code on every request. They can be used to perform
+ # common logic for all your actions, e.g. adding common headers.
+ # Defaults to "Filters" in the root package (aka "apps" folder)
+ # Alternatively you can explicitly register a class here.
+ #filters = my.application.Filters
+
+ ## Session & Flash
+ # https://www.playframework.com/documentation/latest/JavaSessionFlash
+ # https://www.playframework.com/documentation/latest/ScalaSessionFlash
+ # ~~~~~
+ session {
+ # Sets the cookie to be sent only over HTTPS.
+ #secure = true
+
+ # Sets the cookie to be accessed only by the server.
+ #httpOnly = true
+
+ # Sets the max-age field of the cookie to 5 minutes.
+ # NOTE: this only sets when the browser will discard the cookie. Play will consider any
+ # cookie value with a valid signature to be a valid session forever. To implement a server side session timeout,
+ # you need to put a timestamp in the session and check it at regular intervals to possibly expire it.
+ #maxAge = 300
+
+ # Sets the domain on the session cookie.
+ #domain = "example.com"
+ }
+
+ flash {
+ # Sets the cookie to be sent only over HTTPS.
+ #secure = true
+
+ # Sets the cookie to be accessed only by the server.
+ #httpOnly = true
+ }
+}
+
+## Netty Provider
+# https://www.playframework.com/documentation/latest/SettingsNetty
+# ~~~~~
+play.server.netty {
+ # Whether the Netty wire should be logged
+ #log.wire = true
+
+ # If you run Play on Linux, you can use Netty's native socket transport
+ # for higher performance with less garbage.
+ #transport = "native"
+}
+
+## WS (HTTP Client)
+# https://www.playframework.com/documentation/latest/ScalaWS#Configuring-WS
+# ~~~~~
+# The HTTP client primarily used for REST APIs. The default client can be
+# configured directly, but you can also create different client instances
+# with customized settings. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += ws // or javaWs if using java
+#
+play.ws {
+ # Sets HTTP requests not to follow 302 requests
+ #followRedirects = false
+
+ # Sets the maximum number of open HTTP connections for the client.
+ #ahc.maxConnectionsTotal = 50
+
+ ## WS SSL
+ # https://www.playframework.com/documentation/latest/WsSSL
+ # ~~~~~
+ ssl {
+ # Configuring HTTPS with Play WS does not require programming. You can
+ # set up both trustManager and keyManager for mutual authentication, and
+ # turn on JSSE debugging in development with a reload.
+ #debug.handshake = true
+ #trustManager = {
+ # stores = [
+ # { type = "JKS", path = "exampletrust.jks" }
+ # ]
+ #}
+ }
+}
+
+## Cache
+# https://www.playframework.com/documentation/latest/JavaCache
+# https://www.playframework.com/documentation/latest/ScalaCache
+# ~~~~~
+# Play comes with an integrated cache API that can reduce the operational
+# overhead of repeated requests. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += cache
+#
+play.cache {
+ # If you want to bind several caches, you can bind the individually
+ #bindCaches = ["db-cache", "user-cache", "session-cache"]
+}
+
+## Filters
+# https://www.playframework.com/documentation/latest/Filters
+# ~~~~~
+# There are a number of built-in filters that can be enabled and configured
+# to give Play greater security. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += filters
+#
+play.filters {
+ ## CORS filter configuration
+ # https://www.playframework.com/documentation/latest/CorsFilter
+ # ~~~~~
+ # CORS is a protocol that allows web applications to make requests from the browser
+ # across different domains.
+ # NOTE: You MUST apply the CORS configuration before the CSRF filter, as CSRF has
+ # dependencies on CORS settings.
+ cors {
+ # Filter paths by a whitelist of path prefixes
+ #pathPrefixes = ["/some/path", ...]
+
+ # The allowed origins. If null, all origins are allowed.
+ #allowedOrigins = ["http://www.example.com"]
+
+ # The allowed HTTP methods. If null, all methods are allowed
+ #allowedHttpMethods = ["GET", "POST"]
+ }
+
+ ## CSRF Filter
+ # https://www.playframework.com/documentation/latest/ScalaCsrf#Applying-a-global-CSRF-filter
+ # https://www.playframework.com/documentation/latest/JavaCsrf#Applying-a-global-CSRF-filter
+ # ~~~~~
+ # Play supports multiple methods for verifying that a request is not a CSRF request.
+ # The primary mechanism is a CSRF token. This token gets placed either in the query string
+ # or body of every form submitted, and also gets placed in the users session.
+ # Play then verifies that both tokens are present and match.
+ csrf {
+ # Sets the cookie to be sent only over HTTPS
+ #cookie.secure = true
+
+ # Defaults to CSRFErrorHandler in the root package.
+ #errorHandler = MyCSRFErrorHandler
+ }
+
+ ## Security headers filter configuration
+ # https://www.playframework.com/documentation/latest/SecurityHeaders
+ # ~~~~~
+ # Defines security headers that prevent XSS attacks.
+ # If enabled, then all options are set to the below configuration by default:
+ headers {
+ # The X-Frame-Options header. If null, the header is not set.
+ #frameOptions = "DENY"
+
+ # The X-XSS-Protection header. If null, the header is not set.
+ #xssProtection = "1; mode=block"
+
+ # The X-Content-Type-Options header. If null, the header is not set.
+ #contentTypeOptions = "nosniff"
+
+ # The X-Permitted-Cross-Domain-Policies header. If null, the header is not set.
+ #permittedCrossDomainPolicies = "master-only"
+
+ # The Content-Security-Policy header. If null, the header is not set.
+ #contentSecurityPolicy = "default-src 'self'"
+ }
+
+ ## Allowed hosts filter configuration
+ # https://www.playframework.com/documentation/latest/AllowedHostsFilter
+ # ~~~~~
+ # Play provides a filter that lets you configure which hosts can access your application.
+ # This is useful to prevent cache poisoning attacks.
+ hosts {
+ # Allow requests to example.com, its subdomains, and localhost:9000.
+ #allowed = [".example.com", "localhost:9000"]
+ }
+}
+
+## Evolutions
+# https://www.playframework.com/documentation/latest/Evolutions
+# ~~~~~
+# Evolutions allows database scripts to be automatically run on startup in dev mode
+# for database migrations. You must enable this by adding to build.sbt:
+#
+# libraryDependencies += evolutions
+#
+play.evolutions {
+ # You can disable evolutions for a specific datasource if necessary
+ #db.default.enabled = false
+}
+
+## Database Connection Pool
+# https://www.playframework.com/documentation/latest/SettingsJDBC
+# ~~~~~
+# Play doesn't require a JDBC database to run, but you can easily enable one.
+#
+# libraryDependencies += jdbc
+#
+play.db {
+ # The combination of these two settings results in "db.default" as the
+ # default JDBC pool:
+ #config = "db"
+ #default = "default"
+
+ # Play uses HikariCP as the default connection pool. You can override
+ # settings by changing the prototype:
+ prototype {
+ # Sets a fixed JDBC connection pool size of 50
+ #hikaricp.minimumIdle = 50
+ #hikaricp.maximumPoolSize = 50
+ }
+}
+
+## JDBC Datasource
+# https://www.playframework.com/documentation/latest/JavaDatabase
+# https://www.playframework.com/documentation/latest/ScalaDatabase
+# ~~~~~
+# Once JDBC datasource is set up, you can work with several different
+# database options:
+#
+# Slick (Scala preferred option): https://www.playframework.com/documentation/latest/PlaySlick
+# JPA (Java preferred option): https://playframework.com/documentation/latest/JavaJPA
+# EBean: https://playframework.com/documentation/latest/JavaEbean
+# Anorm: https://www.playframework.com/documentation/latest/ScalaAnorm
+#
+db {
+ # You can declare as many datasources as you want.
+ # By convention, the default datasource is named `default`
+
+ # https://www.playframework.com/documentation/latest/Developing-with-the-H2-Database
+ #default.driver = org.h2.Driver
+ #default.url = "jdbc:h2:mem:play"
+ #default.username = sa
+ #default.password = ""
+
+ # You can turn on SQL logging for any datasource
+ # https://www.playframework.com/documentation/latest/Highlights25#Logging-SQL-statements
+ #default.logSql=true
+}
diff --git a/routing-in-play/conf/logback.xml b/routing-in-play/conf/logback.xml
new file mode 100644
index 0000000000..86ec12c0af
--- /dev/null
+++ b/routing-in-play/conf/logback.xml
@@ -0,0 +1,41 @@
+
+
+
+
+
+
+ ${application.home:-.}/logs/application.log
+
+ %date [%level] from %logger in %thread - %message%n%xException
+
+
+
+
+
+ %coloredLevel %logger{15} - %message%n%xException{10}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/routing-in-play/conf/routes b/routing-in-play/conf/routes
new file mode 100644
index 0000000000..f72d8a1a14
--- /dev/null
+++ b/routing-in-play/conf/routes
@@ -0,0 +1,7 @@
+GET / controllers.HomeController.index(author="Baeldung",id:Int?=1)
+GET /:author controllers.HomeController.index(author,id:Int?=1)
+GET /greet/:name/:age controllers.HomeController.greet(name,age:Integer)
+GET /square/$num<[0-9]+> controllers.HomeController.squareMe(num:Long)
+# Map static resources from the /public folder to the /assets URL path
+GET /assets/*file controllers.Assets.versioned(path="/public", file: Asset)
+GET /*data controllers.HomeController.introduceMe(data)
diff --git a/routing-in-play/libexec/activator-launch-1.3.10.jar b/routing-in-play/libexec/activator-launch-1.3.10.jar
new file mode 100644
index 0000000000..69050e7dec
Binary files /dev/null and b/routing-in-play/libexec/activator-launch-1.3.10.jar differ
diff --git a/routing-in-play/project/build.properties b/routing-in-play/project/build.properties
new file mode 100644
index 0000000000..6d22e3f2d1
--- /dev/null
+++ b/routing-in-play/project/build.properties
@@ -0,0 +1,4 @@
+#Activator-generated Properties
+#Fri Sep 30 14:25:10 EAT 2016
+template.uuid=26c759a5-daf0-4e02-bcfa-ac69725267c0
+sbt.version=0.13.11
diff --git a/routing-in-play/project/plugins.sbt b/routing-in-play/project/plugins.sbt
new file mode 100644
index 0000000000..e8e7f602f7
--- /dev/null
+++ b/routing-in-play/project/plugins.sbt
@@ -0,0 +1,21 @@
+// The Play plugin
+addSbtPlugin("com.typesafe.play" % "sbt-plugin" % "2.5.8")
+
+// Web plugins
+addSbtPlugin("com.typesafe.sbt" % "sbt-coffeescript" % "1.0.0")
+addSbtPlugin("com.typesafe.sbt" % "sbt-less" % "1.1.0")
+addSbtPlugin("com.typesafe.sbt" % "sbt-jshint" % "1.0.4")
+addSbtPlugin("com.typesafe.sbt" % "sbt-rjs" % "1.0.8")
+addSbtPlugin("com.typesafe.sbt" % "sbt-digest" % "1.1.1")
+addSbtPlugin("com.typesafe.sbt" % "sbt-mocha" % "1.1.0")
+addSbtPlugin("org.irundaia.sbt" % "sbt-sassify" % "1.4.6")
+
+// Play enhancer - this automatically generates getters/setters for public fields
+// and rewrites accessors of these fields to use the getters/setters. Remove this
+// plugin if you prefer not to have this feature, or disable on a per project
+// basis using disablePlugins(PlayEnhancer) in your build.sbt
+addSbtPlugin("com.typesafe.sbt" % "sbt-play-enhancer" % "1.1.0")
+
+// Play Ebean support, to enable, uncomment this line, and enable in your build.sbt using
+// enablePlugins(PlayEbean).
+// addSbtPlugin("com.typesafe.sbt" % "sbt-play-ebean" % "3.0.2")
diff --git a/routing-in-play/public/images/favicon.png b/routing-in-play/public/images/favicon.png
new file mode 100644
index 0000000000..c7d92d2ae4
Binary files /dev/null and b/routing-in-play/public/images/favicon.png differ
diff --git a/routing-in-play/public/javascripts/hello.js b/routing-in-play/public/javascripts/hello.js
new file mode 100644
index 0000000000..02ee13c7ca
--- /dev/null
+++ b/routing-in-play/public/javascripts/hello.js
@@ -0,0 +1,3 @@
+if (window.console) {
+ console.log("Welcome to your Play application's JavaScript!");
+}
diff --git a/routing-in-play/public/stylesheets/main.css b/routing-in-play/public/stylesheets/main.css
new file mode 100644
index 0000000000..e69de29bb2
diff --git a/routing-in-play/test/ApplicationTest.java b/routing-in-play/test/ApplicationTest.java
new file mode 100644
index 0000000000..3d7c4875aa
--- /dev/null
+++ b/routing-in-play/test/ApplicationTest.java
@@ -0,0 +1,45 @@
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import com.fasterxml.jackson.databind.JsonNode;
+import org.junit.*;
+
+import play.mvc.*;
+import play.test.*;
+import play.data.DynamicForm;
+import play.data.validation.ValidationError;
+import play.data.validation.Constraints.RequiredValidator;
+import play.i18n.Lang;
+import play.libs.F;
+import play.libs.F.*;
+import play.twirl.api.Content;
+
+import static play.test.Helpers.*;
+import static org.junit.Assert.*;
+
+
+/**
+ *
+ * Simple (JUnit) tests that can call all parts of a play app.
+ * If you are interested in mocking a whole application, see the wiki for more details.
+ *
+ */
+public class ApplicationTest {
+
+ @Test
+ public void simpleCheck() {
+ int a = 1 + 1;
+ assertEquals(2, a);
+ }
+
+ @Test
+ public void renderTemplate() {
+ Content html = views.html.index.render("Your new application is ready.");
+ assertEquals("text/html", html.contentType());
+ assertTrue(html.body().contains("Your new application is ready."));
+ }
+
+
+}
diff --git a/routing-in-play/test/IntegrationTest.java b/routing-in-play/test/IntegrationTest.java
new file mode 100644
index 0000000000..c53c71e124
--- /dev/null
+++ b/routing-in-play/test/IntegrationTest.java
@@ -0,0 +1,25 @@
+import org.junit.*;
+
+import play.mvc.*;
+import play.test.*;
+
+import static play.test.Helpers.*;
+import static org.junit.Assert.*;
+
+import static org.fluentlenium.core.filter.FilterConstructor.*;
+
+public class IntegrationTest {
+
+ /**
+ * add your integration test here
+ * in this example we just check if the welcome page is being shown
+ */
+ @Test
+ public void test() {
+ running(testServer(3333, fakeApplication(inMemoryDatabase())), HTMLUNIT, browser -> {
+ browser.goTo("http://localhost:3333");
+ assertTrue(browser.pageSource().contains("Your new application is ready."));
+ });
+ }
+
+}
diff --git a/spring-akka/src/main/java/org/baeldung/akka/SpringExtension.java b/spring-akka/src/main/java/org/baeldung/akka/SpringExtension.java
index 624e289812..aa5941c763 100644
--- a/spring-akka/src/main/java/org/baeldung/akka/SpringExtension.java
+++ b/spring-akka/src/main/java/org/baeldung/akka/SpringExtension.java
@@ -29,5 +29,4 @@ public class SpringExtension extends AbstractExtensionId
- 4.0.0
- com.baeldung
- spring-all
- 0.1-SNAPSHOT
+
+ 4.0.0
+ com.baeldung
+ spring-all
+ 0.1-SNAPSHOT
- spring-all
- war
+ spring-all
+ war
-
- org.springframework.boot
- spring-boot-starter-parent
- 1.3.6.RELEASE
-
+
+ org.springframework.boot
+ spring-boot-starter-parent
+ 1.3.6.RELEASE
+
-
-
- com.fasterxml.jackson.core
- jackson-databind
-
+
+
+ com.fasterxml.jackson.core
+ jackson-databind
+
-
+
-
- org.springframework
- spring-web
-
-
- org.springframework
- spring-webmvc
-
-
- org.springframework
- spring-orm
-
-
- org.springframework
- spring-context
-
+
+ org.springframework
+ spring-web
+
+
+ org.springframework
+ spring-webmvc
+
+
+ org.springframework
+ spring-orm
+
+
+ org.springframework
+ spring-context
+
-
+
-
- org.springframework
- spring-aspects
-
+
+ org.springframework
+ spring-aspects
+
-
+
-
- org.hibernate
- hibernate-core
- ${hibernate.version}
-
-
- org.javassist
- javassist
-
-
- mysql
- mysql-connector-java
- runtime
-
-
- org.hsqldb
- hsqldb
-
-
-
+
+ org.hibernate
+ hibernate-core
+ ${hibernate.version}
+
+
+ org.javassist
+ javassist
+
+
+ mysql
+ mysql-connector-java
+ runtime
+
+
+ org.hsqldb
+ hsqldb
+
-
- org.hibernate
- hibernate-validator
-
+
-
+
+ org.hibernate
+ hibernate-validator
+
-
- javax.servlet
- javax.servlet-api
- provided
-
+
-
- javax.servlet
- jstl
- runtime
-
+
+ javax.servlet
+ javax.servlet-api
+ provided
+
-
+
+ javax.servlet
+ jstl
+ runtime
+
-
- com.google.guava
- guava
- ${guava.version}
-
-
-
+
-
- org.slf4j
- slf4j-api
-
-
- ch.qos.logback
- logback-classic
-
-
-
- org.slf4j
- jcl-over-slf4j
-
-
-
- org.slf4j
- log4j-over-slf4j
-
+
+ com.google.guava
+ guava
+ ${guava.version}
+
-
+
-
- org.springframework
- spring-test
- test
-
+
+ org.slf4j
+ slf4j-api
+
+
+ ch.qos.logback
+ logback-classic
+
+
+
+ org.slf4j
+ jcl-over-slf4j
+
+
+
+ org.slf4j
+ log4j-over-slf4j
+
-
- junit
- junit
- test
-
+
-
- org.assertj
- assertj-core
- 3.5.1
- test
-
+
+ org.springframework
+ spring-test
+ test
+
-
- org.hamcrest
- hamcrest-core
- test
-
-
- org.hamcrest
- hamcrest-library
- test
-
+
+ junit
+ junit
+ test
+
-
- org.mockito
- mockito-core
- test
-
+
+ org.assertj
+ assertj-core
+ 3.5.1
+ test
+
-
- org.easymock
- easymock
- 3.4
- test
-
+
+ org.hamcrest
+ hamcrest-core
+ test
+
+
+ org.hamcrest
+ hamcrest-library
+ test
+
-
+
+ org.mockito
+ mockito-core
+ test
+
-
+
+ org.easymock
+ easymock
+ 3.4
+ test
+
+
+ org.ehcache
+ ehcache
+ 3.1.3
+
-
+
-
- org.springframework
- spring-framework-bom
- ${org.springframework.version}
- pom
- import
-
+
-
- org.springframework
- spring-core
- ${org.springframework.version}
-
+
-
+
+ org.springframework
+ spring-framework-bom
+ ${org.springframework.version}
+ pom
+ import
+
-
+
+ org.springframework
+ spring-core
+ ${org.springframework.version}
+
-
- spring-all
-
-
- src/main/resources
- true
-
-
+
-
+
-
- org.apache.maven.plugins
- maven-compiler-plugin
-
- 1.8
- 1.8
-
-
+
+ spring-all
+
+
+ src/main/resources
+ true
+
+
-
- org.apache.maven.plugins
- maven-war-plugin
-
- false
-
-
+
-
- org.apache.maven.plugins
- maven-surefire-plugin
-
-
-
-
-
-
-
-
-
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+
+ 1.8
+ 1.8
+
+
-
- org.codehaus.cargo
- cargo-maven2-plugin
- ${cargo-maven2-plugin.version}
-
- true
-
- jetty8x
- embedded
-
-
-
-
-
-
- 8082
-
-
-
-
+
+ org.apache.maven.plugins
+ maven-war-plugin
+
+ false
+
+
-
+
+ org.apache.maven.plugins
+ maven-surefire-plugin
+
+
+
+
+
+
+
+
+
-
+
+ org.codehaus.cargo
+ cargo-maven2-plugin
+ ${cargo-maven2-plugin.version}
+
+ true
+
+ jetty8x
+ embedded
+
+
+
+
+
+
+ 8082
+
+
+
+
-
-
- 4.3.1.RELEASE
- 4.0.4.RELEASE
- 3.20.0-GA
- 1.2
+
-
- 4.3.11.Final
- 5.1.38
+