Lesson 4 | Generating part of a page from a Java Servlet |
Objective | Write a servlet and HTML to combine static and dynamic content. |
Generating section of HTML Page using Servlet
The servlet in the last lesson generated an entire page of HTML. That's equivalent to the way a CGI program or script works.
But servlets can also be used to generate just part of a page.
Changing the extension of the file just alerts the server that it may be getting some of the HTML from a server side include. It has no effect on the way the browser renders the HTML. The Web server will run the servlet, and substitute the servlet output where the tag was in the source HTML.
Include the Java Servlet Output in a HTML page
To include Java Servlet output in an HTML page using **modern Java web development practices (Jakarta EE or Spring Boot)**, follow these approaches:
- ✅ Use a Servlet to Set Data and Forward to a JSP
- This is the most common method in modern Java EE applications.
- Servlet Example (`MessageServlet.java`):
import jakarta.servlet.*;
import jakarta.servlet.http.*;
import jakarta.servlet.annotation.*;
import java.io.IOException;
@WebServlet("/message")
public class MessageServlet extends HttpServlet {
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.setAttribute("message", "This content is generated by a Java Servlet.");
RequestDispatcher dispatcher = request.getRequestDispatcher("/display.jsp");
dispatcher.forward(request, response);
}
}
- JSP Example (`display.jsp`):
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<!DOCTYPE html>
<html>
<head>
<title>Servlet Output</title>
</head>
<body>
<h1>Included Servlet Output:</h1>
<p></p>
</body>
</html>
- ✅ Use `<jsp:include>` to Dynamically Include Another Servlet or JSP
- ✅ Use a Frontend (HTML/JS) to Fetch Servlet Output via AJAX
- If you're using a frontend-first approach:
JavaScript Example:
<!DOCTYPE html>
<html>
<head>
<title>Servlet Output via Fetch</title>
</head>
<body>
<h1>Output from Servlet:</h1>
<div id="output"></div>
<script>
fetch('/message')
.then(response => response.text())
.then(data => {
document.getElementById('output').innerHTML = data;
});
</script>
</body>
</html>
Servlet Response (text/plain or HTML)**:
response.setContentType("text/plain");
response.getWriter().write("This is dynamic servlet output.");
Summary
Approach |
Best For |
RequestDispatcher + JSP |
MVC applications |
<jsp:include page="..."/> |
Reusable JSP components or servlet inclusion |
fetch() or XMLHttpRequest |
Dynamic updates in SPA or HTML5 frontend |
Server Side Includes are considered a Legacy Technology
While Server-Side Includes (SSI) with the `.shtml` extension haven't been formally "deprecated" in the sense of being removed from major web servers like Apache or Nginx, their usage has significantly declined and they are generally considered a legacy technology in modern web development.
Here is why and what the current landscape looks like:
- Limited Functionality: SSI offers very basic templating features, primarily for including common elements like headers, footers, or simple dynamic content like the current date. Modern web development demands much more complex dynamic content, data manipulation, and user interaction, which SSI cannot handle.
- Modern Alternatives: Developers now have a plethora of more powerful and flexible alternatives for dynamic content and templating:
- Server-Side Scripting Languages: PHP, Node.js, Python (with frameworks like Django/Flask), Ruby on Rails, ASP.NET, etc., provide full-fledged programming capabilities to generate dynamic HTML, interact with databases, handle user input, and more.
- Client-Side Frameworks/Libraries: JavaScript frameworks like React, Angular, and Vue.js allow for highly interactive and dynamic front-ends, often fetching data from APIs.
- Static Site Generators: Tools like Jekyll, Hugo, Next.js, and Gatsby allow developers to build entire websites from templates and data at build time, resulting in highly optimized static HTML files that can then be served by any web server. This provides the benefit of reusable components (like SSI) but with much greater power and performance.
- Templating Engines: Even when using server-side languages, dedicated templating engines (e.g., Twig for PHP, Jinja2 for Python, EJS/Pug for Node.js) offer robust features for creating reusable layouts and injecting dynamic data.
- Performance Concerns (for heavy usage): While SSI is lightweight for simple inclusions, if a server has to parse a large number of
.shtml
files for many directives, it can introduce a small overhead compared to serving pure static HTML or pre-generated content.
- Security Concerns (historical): While generally safe for simple inclusions, older or misconfigured SSI implementations could sometimes be vulnerable to injection attacks if user input was not properly sanitized. Modern frameworks often have built-in protections against common web vulnerabilities.
- Cloud Hosting Limitations: Some modern cloud hosting platforms, especially those designed for serving static content (like Azure Static Web Apps), may not support server-side processing like SSI, pushing developers towards build-time solutions or serverless functions for dynamic needs.
When might you still encounter or use SSI?
- Legacy Systems: You'll most likely see SSI in older websites that haven't been updated to modern technologies.
- Extremely Simple Static Sites: For very basic static websites where you only need to include a few common elements and don't want to introduce a full server-side language or build process, SSI can still technically work if your web server supports it.
- Specific Niche Cases: In some very specific scenarios where a web server is heavily optimized for static file delivery and a small amount of dynamic content is needed without full scripting capabilities.
In summary, while `.shtml` files and SSI are still technically supported by most major web servers (like Apache and Nginx), they are rarely chosen for new projects. Modern web development practices favor more powerful, flexible, and often more performant alternatives.
JSP Front End for the Servlet backend
JSP file that includes the output of the `Include` servlet using <jsp:include> syntax:
<%@ page contentType="text/html; charset=UTF-8" language="java" %>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Including Servlet Output in Your JSP</title>
</head>
<body>
<h1>Servlet output is between the lines</h1>
<hr>
<!-- Include the output of the Include servlet -->
<jsp:include page="/include" />
<hr>
</body>
</html>
Key Points:
<jsp:include page="/include" />
dynamically includes the response of the servlet mapped to /include
.
- This is a runtime include, so any dynamic output from the servlet is injected into the JSP's response.
- Make sure the servlet is registered using
@WebServlet("/include")
or mapped in web.xml
.
Servlet using the Jakarta EE 10+ `jakarta.servlet` package
import java.io.IOException;
import java.io.PrintWriter;
import jakarta.servlet.ServletException;
import jakarta.servlet.http.HttpServlet;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
// Annotation-based configuration (recommended in modern Jakarta EE)
@jakarta.servlet.annotation.WebServlet("/include")
public class Include extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException {
res.setContentType("text/html");
PrintWriter out = res.getWriter();
out.println("Servlets don't have to generate entire pages...");
out.close();
}
}
Key Modernizations:
- ✅ Updated package to
jakarta.servlet.*
— required in Jakarta EE 9 and beyond.
- ✅ Annotation-based servlet registration using
@WebServlet("/include")
instead of web.xml
.
- ✅ Follows Jakarta EE 10+ conventions and is forward-compatible with cloud-native runtimes.
This is similar to the servlets that you saw last lesson, except it generates only some text output, not an entire HTML page, which would need to include the
<HTML>
and
</HTML>
tags.
Testing the servlet
You have tested your earlier servlets with the JSDK mini-server, but it only serves out servlets.
To test this servlet, you need a server that can deliver the shtml file to a browser, and include your servlet output.
You will have to use the Tomcat Web Server.
First start the Java Web Server, and then follow these steps:
✅ Starting Apache Tomcat in 2025: Updated Guide
🔧 Prerequisites
- Java Installation: Ensure Java is installed and the
JAVA_HOME
environment variable is set.
- Tomcat Installation: Download and extract the latest version of Apache Tomcat from the official website.
🖥️ Windows
-
Using Command Prompt
-
Using Windows Services
- If Tomcat is installed as a Windows service:
- Open Services:
- Press
Win + R
, type services.msc
, and press Enter.
- Locate Apache Tomcat Service:
- Find the service named "Apache Tomcat" followed by the version number.
- Start/Stop the Service:
- Right-click the service and choose "Start" or "Stop".
🐧 Linux/macOS
-
Using Terminal
-
Using `systemctl` (if configured as a service)
- Start Tomcat:
sudo systemctl start tomcat
- Stop Tomcat:
sudo systemctl stop tomcat
- Enable Tomcat to start on boot:
sudo systemctl enable tomcat
- Check Tomcat status:
sudo systemctl status tomcat
*Note*: For this method, Tomcat must be configured as a systemd service. If not already set up, you can create a systemd service file for Tomcat.
🌐 Accessing Tomcat
Once Tomcat is started:
- Open a web browser.
- Navigate to:
http://localhost:8080
You should see the Tomcat welcome page if everything is set up correctly.
📌 Additional Tips
- Environment Variables:
- Ensure
JAVA_HOME
is set to your Java installation path.
- Optionally, set
CATALINA_HOME
to your Tomcat installation path.
- Permissions:
- Firewall Settings:
- Ensure that port 8080 is open and not blocked by your firewall.
Generating Servlet Page - Exercise
Write a servlet to include in an HTML page using the <servlet> tag.
Generating Servlet Page - Exercise
