new pattern: Issue#1264: Implemented Composite-View Pattern (#1923)

* initial commit, created package, README, pom, and directory structure.

* Issue#1264, continue working on JavaBeans, added getters, setters, and private fields. Created test file for JavaBeans.

* set up junit for tests folder.

* Issue#1264, set up local server and added web-application framework to composite-view to allow the JSP to run on a local Tomcat container. Wrote unit tests for Java-bean class, working on JSP pages.

* Issue#1264, Added forwarding functionality to servlet and main composite view page.

* Issue#1264, Finished composite view template in newsDisplay.jsp and created atomic sub-view components in businessNews.jsp, header.jsp, localNews.jsp, scienceNews.jsp, sportsNews.jsp, worldNews.jsp. Composite view page renders correctly, atomic views are inserted in and substituted in the template page depending on request parameters.

* Issue#1264, Added all views, updated README.md with documentation.

* Issue#1264, updated README.md, moved images folder into etc folder.

* Issue#1264, removed build artifacts from tracked files.

* Issue#1264, updated README.md

* Issue#1264, updated README.md

* Issue#1264, removed unused import, made AppServlet class final, changed to .equals() for string comparison.

* Issue#1264, in AppServlet, put the output writing into try blocks to ensure writers are closed.

* Issue#1264, added tests for Servlet, coverage up to 100%, used lombok to reduce boilerplate setters and getter, updated README.md with better grammar, appropriate tags and links to related patterns. Updated pom.xml to get rid of superfluous lines.

* Issue#1264, made changes as requested in README.md.

Co-authored-by: Ilkka Seppälä <iluwatar@users.noreply.github.com>
This commit is contained in:
Kevin
2022-01-18 13:51:53 -06:00
committed by GitHub
parent 07ee94d671
commit 7652b11bca
20 changed files with 978 additions and 0 deletions

View File

@ -0,0 +1,64 @@
package com.iluwatar.compositeview;
import jakarta.servlet.RequestDispatcher;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.HttpServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
/**
* A servlet object that extends HttpServlet.
* Runs on Tomcat 10 and handles Http requests
*/
public final class AppServlet extends HttpServlet {
private String msgPartOne = "<h1>This Server Doesn't Support";
private String msgPartTwo = "Requests</h1>\n"
+ "<h2>Use a GET request with boolean values for the following parameters<h2>\n"
+ "<h3>'name'</h3>\n<h3>'bus'</h3>\n<h3>'sports'</h3>\n<h3>'sci'</h3>\n<h3>'world'</h3>";
private String destination = "newsDisplay.jsp";
public AppServlet() {
}
@Override
public void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
RequestDispatcher requestDispatcher = req.getRequestDispatcher(destination);
ClientPropertiesBean reqParams = new ClientPropertiesBean(req);
req.setAttribute("properties", reqParams);
requestDispatcher.forward(req, resp);
}
@Override
public void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
resp.setContentType("text/html");
try (PrintWriter out = resp.getWriter()) {
out.println(msgPartOne + " Post " + msgPartTwo);
}
}
@Override
public void doDelete(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
resp.setContentType("text/html");
try (PrintWriter out = resp.getWriter()) {
out.println(msgPartOne + " Delete " + msgPartTwo);
}
}
@Override
public void doPut(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
resp.setContentType("text/html");
try (PrintWriter out = resp.getWriter()) {
out.println(msgPartOne + " Put " + msgPartTwo);
}
}
}

View File

@ -0,0 +1,53 @@
package com.iluwatar.compositeview;
import jakarta.servlet.http.HttpServletRequest;
import java.io.Serializable;
import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
/**
* A Java beans class that parses a http request and stores parameters.
* Java beans used in JSP's to dynamically include elements in view.
* DEFAULT_NAME = a constant, default name to be used for the default constructor
* worldNewsInterest = whether current request has world news interest
* sportsInterest = whether current request has a sportsInterest
* businessInterest = whether current request has a businessInterest
* scienceNewsInterest = whether current request has a scienceNewsInterest
*/
@Getter
@Setter
@NoArgsConstructor
public class ClientPropertiesBean implements Serializable {
private static final String WORLD_PARAM = "world";
private static final String SCIENCE_PARAM = "sci";
private static final String SPORTS_PARAM = "sport";
private static final String BUSINESS_PARAM = "bus";
private static final String NAME_PARAM = "name";
private static final String DEFAULT_NAME = "DEFAULT_NAME";
private boolean worldNewsInterest = true;
private boolean sportsInterest = true;
private boolean businessInterest = true;
private boolean scienceNewsInterest = true;
private String name = DEFAULT_NAME;
/**
* Constructor that parses an HttpServletRequest and stores all the request parameters.
*
* @param req the HttpServletRequest object that is passed in
*/
public ClientPropertiesBean(HttpServletRequest req) {
worldNewsInterest = Boolean.parseBoolean(req.getParameter(WORLD_PARAM));
sportsInterest = Boolean.parseBoolean(req.getParameter(SPORTS_PARAM));
businessInterest = Boolean.parseBoolean(req.getParameter(BUSINESS_PARAM));
scienceNewsInterest = Boolean.parseBoolean(req.getParameter(SCIENCE_PARAM));
String tempName = req.getParameter(NAME_PARAM);
if (tempName == null || tempName.equals("")) {
tempName = DEFAULT_NAME;
}
name = tempName;
}
}

View File

@ -0,0 +1,83 @@
package com.iluwatar.compositeview;
import jakarta.servlet.RequestDispatcher;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.junit.jupiter.api.Test;
import org.mockito.Mockito;
import java.io.PrintWriter;
import java.io.StringWriter;
import static org.junit.Assert.*;
/* Written with reference from https://stackoverflow.com/questions/5434419/how-to-test-my-servlet-using-junit
and https://stackoverflow.com/questions/50211433/servlets-unit-testing
*/
public class AppServletTest extends Mockito{
private String msgPartOne = "<h1>This Server Doesn't Support";
private String msgPartTwo = "Requests</h1>\n"
+ "<h2>Use a GET request with boolean values for the following parameters<h2>\n"
+ "<h3>'name'</h3>\n<h3>'bus'</h3>\n<h3>'sports'</h3>\n<h3>'sci'</h3>\n<h3>'world'</h3>";
private String destination = "newsDisplay.jsp";
@Test
public void testDoGet() throws Exception {
HttpServletRequest mockReq = Mockito.mock(HttpServletRequest.class);
HttpServletResponse mockResp = Mockito.mock(HttpServletResponse.class);
RequestDispatcher mockDispatcher = Mockito.mock(RequestDispatcher.class);
StringWriter stringWriter = new StringWriter();
PrintWriter printWriter = new PrintWriter(stringWriter);
when(mockResp.getWriter()).thenReturn(printWriter);
when(mockReq.getRequestDispatcher(destination)).thenReturn(mockDispatcher);
AppServlet curServlet = new AppServlet();
curServlet.doGet(mockReq, mockResp);
verify(mockReq, times(1)).getRequestDispatcher(destination);
verify(mockDispatcher).forward(mockReq, mockResp);
}
@Test
public void testDoPost() throws Exception {
HttpServletRequest mockReq = Mockito.mock(HttpServletRequest.class);
HttpServletResponse mockResp = Mockito.mock(HttpServletResponse.class);
StringWriter stringWriter = new StringWriter();
PrintWriter printWriter = new PrintWriter(stringWriter);
when(mockResp.getWriter()).thenReturn(printWriter);
AppServlet curServlet = new AppServlet();
curServlet.doPost(mockReq, mockResp);
printWriter.flush();
assertTrue(stringWriter.toString().contains(msgPartOne + " Post " + msgPartTwo));
}
@Test
public void testDoPut() throws Exception {
HttpServletRequest mockReq = Mockito.mock(HttpServletRequest.class);
HttpServletResponse mockResp = Mockito.mock(HttpServletResponse.class);
StringWriter stringWriter = new StringWriter();
PrintWriter printWriter = new PrintWriter(stringWriter);
when(mockResp.getWriter()).thenReturn(printWriter);
AppServlet curServlet = new AppServlet();
curServlet.doPut(mockReq, mockResp);
printWriter.flush();
assertTrue(stringWriter.toString().contains(msgPartOne + " Put " + msgPartTwo));
}
@Test
public void testDoDelete() throws Exception {
HttpServletRequest mockReq = Mockito.mock(HttpServletRequest.class);
HttpServletResponse mockResp = Mockito.mock(HttpServletResponse.class);
StringWriter stringWriter = new StringWriter();
PrintWriter printWriter = new PrintWriter(stringWriter);
when(mockResp.getWriter()).thenReturn(printWriter);
AppServlet curServlet = new AppServlet();
curServlet.doDelete(mockReq, mockResp);
printWriter.flush();
assertTrue(stringWriter.toString().contains(msgPartOne + " Delete " + msgPartTwo));
}
}

View File

@ -0,0 +1,71 @@
package com.iluwatar.compositeview;
import jakarta.servlet.http.HttpServletRequest;
import org.junit.jupiter.api.Test;
import org.mockito.Mockito;
import static org.junit.Assert.*;
public class JavaBeansTest {
@Test
public void testDefaultConstructor() {
ClientPropertiesBean newBean = new ClientPropertiesBean();
assertEquals("DEFAULT_NAME", newBean.getName());
assertTrue(newBean.isBusinessInterest());
assertTrue(newBean.isScienceNewsInterest());
assertTrue(newBean.isSportsInterest());
assertTrue(newBean.isWorldNewsInterest());
}
@Test
public void testNameGetterSetter() {
ClientPropertiesBean newBean = new ClientPropertiesBean();
assertEquals("DEFAULT_NAME", newBean.getName());
newBean.setName("TEST_NAME_ONE");
assertEquals("TEST_NAME_ONE", newBean.getName());
}
@Test
public void testBusinessSetterGetter() {
ClientPropertiesBean newBean = new ClientPropertiesBean();
assertTrue(newBean.isBusinessInterest());
newBean.setBusinessInterest(false);
assertFalse(newBean.isBusinessInterest());
}
@Test
public void testScienceSetterGetter() {
ClientPropertiesBean newBean = new ClientPropertiesBean();
assertTrue(newBean.isScienceNewsInterest());
newBean.setScienceNewsInterest(false);
assertFalse(newBean.isScienceNewsInterest());
}
@Test
public void testSportsSetterGetter() {
ClientPropertiesBean newBean = new ClientPropertiesBean();
assertTrue(newBean.isSportsInterest());
newBean.setSportsInterest(false);
assertFalse(newBean.isSportsInterest());
}
@Test
public void testWorldSetterGetter() {
ClientPropertiesBean newBean = new ClientPropertiesBean();
assertTrue(newBean.isWorldNewsInterest());
newBean.setWorldNewsInterest(false);
assertFalse(newBean.isWorldNewsInterest());
}
@Test
public void testRequestConstructor(){
HttpServletRequest mockReq = Mockito.mock(HttpServletRequest.class);
ClientPropertiesBean newBean = new ClientPropertiesBean((mockReq));
assertEquals("DEFAULT_NAME", newBean.getName());
assertFalse(newBean.isWorldNewsInterest());
assertFalse(newBean.isBusinessInterest());
assertFalse(newBean.isScienceNewsInterest());
assertFalse(newBean.isSportsInterest());
}
}