/*
* JBoss, Home of Professional Open Source
* Copyright 2013, Red Hat, Inc. and/or its affiliates, and individual
* contributors by the @authors tag. See the copyright.txt in the
* distribution for a full listing of individual contributors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file 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.
*/
package org.jboss.as.quickstarts.xa;
import javax.inject.Inject;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
/**
* <p>
* A servlet for triggering the update of a database and a JMS producer within a single XA transaction.
* </p>
*
* <p>
* The servlet is registered and mapped to /XA using the {@linkplain WebServlet
* @HttpServlet}. The {@link XAService} is injected by CDI.
* </p>
*
* @author Michael Musgrove
*
*/
@SuppressWarnings("serial")
@WebServlet("/XA")
public class XAServlet extends HttpServlet {
private static String PAGE_HEADER = "<html><head><title>jta-crash-recovery</title></head><body>";
// page content describing the quickstart and providing a form to perform basic operations against a database
private static String PAGE_CONTENT = "<h2>XA Recovery</h2>" +
"<p>This quickstart demonstrates how to atomically update multiple resources within one XA transaction. " +
"It updates a relational database table using JPA and sends a message using JMS. " +
"In this example, you can perform the following operations:</p>" +
"<ul>" +
"<li>To add a <b>key</b>/<b>value</b> pair, enter values in the input text boxes and click <i>Submit</i></li>" +
"<li>To update a <b>key</b>/<b>value</b> pair, enter the key and click <i>Submit</i></li>" +
"<li>To delete a <b>key</b>/<b>value</b> pair, enter the key and click <i>Delete</i></li>" +
"<li>To delete all <b>key</b>/<b>value</b> pairs, leave the key blank and click <i>Delete</i></li>" +
"<li>To list the existing <b>key</b>/<b>value</b> pairs, leave the key blank and click <i>Submit</i></li>" +
"<li>The refresh the list, click the <i>Refresh Table</i> link.</li>" +
"</ul>" +
"<p>To demonstrate XA recovery, you will take the following steps:</p> " +
"<ol>" +
"<li>Add a <b>key</b>/<b>value</b> as described above.</li>" +
"<li>Stop the JBoss server.</li>" +
"<li>Clear any transaction objectstore data remaining from previous tests.</li>" +
"<li>Configure Byteman to halt the JBoss server.</li>" +
"<li>Start the JBoss server.</li>" +
"<li>Add another <b>key</b>/<b>value</b>. This will cause Byteman to halt the JBoss server.</li>" +
"<li>Verify the database record.</li>" +
"<li>Disable Byteman.</li>" +
"<li>Start the JBoss server.</li>" +
"<li>View the resulting recovered row in the table, indicated by the text \"<i>updated via JMS</i>\".</li>" +
"</ol>"+
"</p> " +
"<p>See the README file located in the root of <i>jta-crash-rec</i> folder in the quickstart distribution " +
"for complete instructions and details about how this quickstart works.</p> " +
"<form>" +
"Key: <input type=\"text\" name=\"key\" />" +
" (Leave blank to list all key/value pairs).<br />" +
"Value: <input type=\"text\" name=\"value\" /><br />" +
"<input type=\"submit\" name=\"submit\" value=\"Submit\" />" +
" Add or update a pair (or list all pairs if key is blank).<br />" +
"<input type=\"submit\" name=\"submit\" value=\"Delete\" />" +
" Delete a pair (or all pairs if key is blank).<br />" +
"</form>" +
"<p><a href=\".\">Refresh Table</a></p>";
private static String PAGE_FOOTER = "</body></html>";
// use CDI to inject a bean that will perform JPA and JMS operations
@Inject
private XAService xaService;
/**
* <p>Servlet entry point.
* </p>
* <p>The behaviour of the servlet is controlled by servlet query parameters:
* </p>
* <p>Database inserts/updates are controlled by the presence of parameters "submit" (with value "Submit") and "key".
* </p>
* <p>Database deletes are controlled by the presence of parameters "submit" (with value "Delete") and "key".
* If the value of "key" is empty then all rows are deleted otherwise just the row with the key value is deleted.
* </p>
* @param req the HTTP request
* @param resp the HTTP response
* @throws ServletException
* @throws IOException
*/
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
/*
* Read servlet parameters to determine which key value pair to use and
* whether this is an insert/update/list request or a delete request
* @see XAServlet#PAGE_CONTENT
*/
String key = req.getParameter("key");
String value = req.getParameter("value");
boolean delete = "Delete".equals(req.getParameter("submit"));
PrintWriter writer = resp.getWriter();
// perform the database operation
String responseText = xaService.updateKeyValueDatabase(delete, key, value);
writer.println(PAGE_HEADER);
writer.println(PAGE_CONTENT);
writer.println(responseText);
writer.println(PAGE_FOOTER);
writer.close();
}
}