Initial commit from SVN.
This commit is contained in:
@@ -0,0 +1,417 @@
|
||||
package com.de22.web.test.application;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
|
||||
import com.common.debug.*;
|
||||
import com.common.orb.Orb;
|
||||
import com.common.thread.*;
|
||||
import com.common.util.*;
|
||||
import com.de22.orb.optional.ServerSocketOptions;
|
||||
import com.de22.orb.optional.SocketOptions;
|
||||
import com.de22.orb.Address;
|
||||
import com.foundation.util.*;
|
||||
import com.foundation.util.xml.INode;
|
||||
import com.foundation.view.*;
|
||||
import com.foundation.controller.*;
|
||||
import com.foundation.application.Application;
|
||||
import com.foundation.tcv.controller.IThinServerController;
|
||||
import com.foundation.tcv.server.controller.ApplicationBrowserService;
|
||||
import com.foundation.tcv.server.controller.IInitialViewFactory;
|
||||
import com.foundation.view.resource.ResourceService;
|
||||
import com.foundation.view.swt.SwtViewContext;
|
||||
import com.foundation.transaction.TransactionErrorInfo;
|
||||
import com.foundation.transaction.TransactionService;
|
||||
import com.foundation.event.IRequestHandler;
|
||||
import com.foundation.web.*;
|
||||
import com.foundation.web.interfaces.*;
|
||||
import com.foundation.web.server.WebServer;
|
||||
import com.foundation.web.server.IServiceListener;
|
||||
|
||||
/**
|
||||
* The starting point for this application. In addition to kicking things off, the application class manages the basic services used by other application components.
|
||||
* <p>Notes for running on OSX: Prevent the main thread from ever dieing (see main method); Add -XstartOnFirstThread to the run command (VM Argument).</p>
|
||||
*/
|
||||
public class TestWebappApplication extends Application {
|
||||
/** The property file location property. */
|
||||
public static final String PROPERTY_FILE = "properties";
|
||||
/** The property name that determines whether we generate proxies. This should only be true during development. */
|
||||
public static final String PROPERTY_GENERATE_PROXIES = "generate.proxies";
|
||||
/** The property name that gives us the ip:port for starting the application browser's server socket listener. */
|
||||
public static final String PROPERTY_APPBROWSER_SERVER_ADDRESS = "application.browser.address";
|
||||
/** Whether debug is on - caching will be turned off in as many places as possible. */
|
||||
public static final String PROPERTY_DEBUG = "debug";
|
||||
|
||||
private static final String APPLICATION_BROWSER_SERVER_SOCKET_NAME = "ApplicationBrowserServerSocket";
|
||||
private static final Object THIN_VIEW_PERMISSION = new Object();
|
||||
private static final String APPLICATION_NAME = "Unlicensed.SampleApplication";
|
||||
private static final TestWebappApplication singleton = new TestWebappApplication();
|
||||
|
||||
/** The base directory for the application. This allows the directory to be modified as needed without affecting other setup code. */
|
||||
private File baseDirectory = new File("./");
|
||||
/** The external base directory for the application. This allows the directory to be modified as needed without affecting other setup code. */
|
||||
private File externalBaseDirectory = null;
|
||||
/** The base directory for the application cache files. This allows the directory to be modified as needed without affecting other setup code. */
|
||||
private File cacheBaseDirectory = null;
|
||||
/** The web server - used to clean up when shutting down the application. */
|
||||
private WebServer webServer = null;
|
||||
/** The properties used by the web application. */
|
||||
private java.util.Properties properties;
|
||||
/**
|
||||
* Starts the Foundation Web Test Webapp application.
|
||||
* <p>Note: This runs the TestWebapp web application in standalone mode.</p>
|
||||
* @param args None expected.
|
||||
*/
|
||||
public static void main(String[] args) {
|
||||
//Setup the debug log.//
|
||||
Debug.setLog(new DefaultLog());
|
||||
getSingleton().startup(System.getProperties());
|
||||
getSingleton().startWebApplication();
|
||||
//Enable the wait for shutdown call on the Mac such that the main thread never dies.//
|
||||
// getSingleton().waitForShutdown();
|
||||
}//main()//
|
||||
/**
|
||||
* Gets the one and only instance of the application.
|
||||
* @return The singleton instance.
|
||||
*/
|
||||
public static TestWebappApplication getSingleton() {
|
||||
return singleton;
|
||||
}//getSingleton()//
|
||||
/**
|
||||
* TestWebappApplication constructor.
|
||||
*/
|
||||
public TestWebappApplication() {
|
||||
super();
|
||||
}//TestWebappApplication()//
|
||||
/**
|
||||
* Gets the set of properties for the application. This should be used in place of System.getProperties().
|
||||
* @return The properties for this application.
|
||||
*/
|
||||
public java.util.Properties getProperties() {
|
||||
return properties;
|
||||
}//getProperties()//
|
||||
/**
|
||||
* Gets the directory containing the application's resources.
|
||||
* @return The file referencing the application's base path.
|
||||
*/
|
||||
public File getBaseDirectory() {
|
||||
return baseDirectory;
|
||||
}//getBaseDirectory()//
|
||||
/**
|
||||
* Sets the directory containing the application's resources.
|
||||
* @param baseDirectory The file referencing the application's base path.
|
||||
*/
|
||||
public void setBaseDirectory(File baseDirectory) {
|
||||
this.baseDirectory = baseDirectory == null ? new File("./") : baseDirectory;
|
||||
}//setBaseDirectory()//
|
||||
/**
|
||||
* Gets the directory containing the application's external resources. External resources are not packaged with the web application, but may not be re-creatable and should be backed up.
|
||||
* @return The file referencing the application's external base path.
|
||||
*/
|
||||
public File getExternalBaseDirectory() {
|
||||
return externalBaseDirectory;
|
||||
}//getExternalBaseDirectory()//
|
||||
/**
|
||||
* Sets the directory containing the application's external resources. External resources are not packaged with the web application, but may not be re-creatable and should be backed up.
|
||||
* @param externalBaseDirectory The file referencing the application's external base path.
|
||||
*/
|
||||
public void setExternalBaseDirectory(File externalBaseDirectory) {
|
||||
this.externalBaseDirectory = externalBaseDirectory == null ? new File("./") : externalBaseDirectory;
|
||||
}//setExternalBaseDirectory()//
|
||||
/**
|
||||
* Gets the directory containing the application's cached resources. Cached resources are not packaged with the web application, but are fully re-creatable, and should not be backed up.
|
||||
* @return The file referencing the application's cache base path.
|
||||
*/
|
||||
public File getCacheBaseDirectory() {
|
||||
return cacheBaseDirectory;
|
||||
}//getCacheBaseDirectory()//
|
||||
/**
|
||||
* Sets the directory containing the application's cached resources. Cached resources are not packaged with the web application, but are fully re-creatable, and should not be backed up.
|
||||
* @param cacheBaseDirectory The file referencing the application's cache base path.
|
||||
*/
|
||||
public void setCacheBaseDirectory(File cacheBaseDirectory) {
|
||||
this.cacheBaseDirectory = cacheBaseDirectory == null ? new File("./") : cacheBaseDirectory;
|
||||
}//setCacheBaseDirectory()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.application.Application#getDefaultRepositoryIdentifier()
|
||||
*/
|
||||
public Object getDefaultRepositoryIdentifier() {
|
||||
return "APPDB";
|
||||
}//getDefaultRepositoryIdentifier()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.application.Application#getMetadataLocation()
|
||||
*/
|
||||
public Object getMetadataLocation() {
|
||||
return new File(getBaseDirectory(), "metadata.xml");
|
||||
}//getMetadataLocation()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.application.Application#getResourcesPath()
|
||||
*/
|
||||
public File getResourcesPath() {
|
||||
return getBaseDirectory() != null ? getBaseDirectory() : super.getResourcesPath();
|
||||
}//getResourcesPath()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.application.Application#initializeResources(com.foundation.view.resource.ResourceService)
|
||||
*/
|
||||
protected void initializeResources(ResourceService resourceService) {
|
||||
}//initializeResources()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.application.Application#internalShutdown()
|
||||
*/
|
||||
protected void internalShutdown() {
|
||||
try {
|
||||
Orb.closeServerSocket(APPLICATION_BROWSER_SERVER_SOCKET_NAME);
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
|
||||
try {
|
||||
Orb.shutdown();
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
|
||||
try {
|
||||
if(webServer != null) {
|
||||
webServer.stop();
|
||||
webServer = null;
|
||||
}//if//
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
|
||||
try {
|
||||
SwtViewContext.getSingleton().shutdown();
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
|
||||
try {
|
||||
Scheduler.shutdown();
|
||||
ActiveScheduler.getSingleton().shutdown();
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
|
||||
super.internalShutdown();
|
||||
}//internalShutdown()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.application.Application#startup()
|
||||
*/
|
||||
protected void startup(java.util.Properties properties) {
|
||||
String generateProxiesProperty;
|
||||
boolean generateProxies;
|
||||
|
||||
this.properties = properties;
|
||||
|
||||
//Load properties from the property file into the system properties.//
|
||||
if(this.properties.getProperty(PROPERTY_FILE) != null) {
|
||||
FileInputStream fin = null;
|
||||
|
||||
try {
|
||||
fin = new FileInputStream(new File(getBaseDirectory(), this.properties.getProperty(PROPERTY_FILE)));
|
||||
|
||||
this.properties.load(fin);
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log("Couldn't load the property file: " + this.properties.getProperty(PROPERTY_FILE));
|
||||
}//catch//
|
||||
finally {
|
||||
try {fin.close();} catch(Throwable e) {}
|
||||
}//finally//
|
||||
}//if//
|
||||
|
||||
generateProxiesProperty = this.properties.getProperty(PROPERTY_GENERATE_PROXIES);
|
||||
generateProxies = (generateProxiesProperty != null) && ((generateProxiesProperty.equals("yes")) || (generateProxiesProperty.equals("on")) || (generateProxiesProperty.equals("true")));
|
||||
|
||||
//Setup the metadata service.//
|
||||
setupMetadataService();
|
||||
//Setup the resource service.//
|
||||
setupResourceService();
|
||||
//Setup the transaction service.//
|
||||
setupTransactionService();
|
||||
getTransactionService().debug(TransactionService.DEBUG_ALL);
|
||||
//Setup the ORB.//
|
||||
Orb.setOrbWrapper(new com.de22.orb.optional.CommonOrbWrapper(generateProxies ? new com.de22.orb.development.OrbClassLoader(new File(getBaseDirectory(), "proxies")) : null, null, null));
|
||||
|
||||
try {
|
||||
//Start the application specific code.//
|
||||
startApplication();
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
//Log all errors that are not caught earlier in the program.//
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
}//startup()//
|
||||
/**
|
||||
* Starts the actual application.
|
||||
*/
|
||||
private void startApplication() {
|
||||
|
||||
}//startApplication()//
|
||||
/**
|
||||
* Starts the web application in non-hosted mode (never called if the app is hosted in the Brainstorm Web Server).
|
||||
*/
|
||||
private void startWebApplication() {
|
||||
//Setup the built in web server. Note that for web applications this will not get run if the web application is run within the Brainstorm Web Server as a hosted application.//
|
||||
try {
|
||||
IWebApplication[] webapps;
|
||||
|
||||
//Create the web server.//
|
||||
webServer = new WebServer(false);
|
||||
|
||||
//Add service listeners. These are referenced by each web application later. SSL/TLS multiplexing is possible.//
|
||||
webServer.addServiceListener(new String[] {"http"}, new com.common.orb.Address(null, 80), IServiceListener.TYPE_HTTP);
|
||||
webServer.addServiceListener(new String[] {"ssl"}, new com.common.orb.Address(null, 443), IServiceListener.TYPE_SSL);
|
||||
//Initialize the base directories.//
|
||||
setExternalBaseDirectory(properties.getProperty("external-base-directory") != null ? new File(properties.getProperty("external-base-directory")) : null);
|
||||
setCacheBaseDirectory(properties.getProperty("cache-base-directory") != null ? new File(properties.getProperty("cache-base-directory")) : null);
|
||||
//Create the web applications.//
|
||||
webapps = createWebApplications(getBaseDirectory(), getExternalBaseDirectory(), getCacheBaseDirectory(), new java.util.Properties());
|
||||
|
||||
//Add all the web applications to the server.//
|
||||
for(int webappIndex = 0; webappIndex < webapps.length; webappIndex++) {
|
||||
//Add the application to the server. The application cannot be modified furthor.//
|
||||
webServer.addWebApplication(webapps[webappIndex]);
|
||||
}//for//
|
||||
|
||||
//Start the web server. Web server settings cannot be modified after calling start.//
|
||||
webServer.start();
|
||||
Debug.log("Web Server Started.");
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log("Unable to open the view service.", e);
|
||||
}//catch//
|
||||
}//startWebApplication()//
|
||||
/**
|
||||
* Creates the web applications for this app.
|
||||
* @param baseDirectory The base directory for the webapp's static resources.
|
||||
* @param externalBaseDirectory The optional external base directory for additional static resources not deployed with the webapp (specific to the server).
|
||||
* @param properties The property map containing future settings needed by the factory.
|
||||
* @return The array of web application objects defined by the webapp.
|
||||
*/
|
||||
public IWebApplication[] createWebApplications(File baseDirectory, File externalBaseDirectory, File cacheBaseDirectory, java.util.Properties properties) {
|
||||
IWebApplication[] result = new IWebApplication[1];
|
||||
|
||||
try {
|
||||
WebOptions options = new WebOptions();
|
||||
|
||||
options.setSessionHandler(new WebApplication.SessionHandler(cacheBaseDirectory != null ? cacheBaseDirectory : externalBaseDirectory != null ? externalBaseDirectory : baseDirectory) {
|
||||
public SecureSessionData createSecureSessionObject(IRequestHandler requestHandler) {
|
||||
//TODO: Create and return an application specific secure session data object to hold the secure session state.
|
||||
return new com.de22.web.test.web.SecureSessionData(requestHandler);
|
||||
}//createSecureSessionObject()//
|
||||
});
|
||||
//TODO: Pass the domain names the webapp is accessable through.
|
||||
//TODO: Setup the SSL mapping (or remove if not using SSL).
|
||||
//TODO: Provide the directory containing the static web resources.
|
||||
//TODO: Modify the base package where java classes will be found by the web server when a resource ending in .java is found.
|
||||
options.setDomains(new String[] {"domain1.com", "www.domain1.com"});
|
||||
options.setServices(new String[] {"http", "ssl"});
|
||||
options.setSslMappings(new WebOptions.SslMapping[] {WebOptions.createSslMapping(new String[] {"domain1.com", "www.domain1.com"}, new File(baseDirectory, ".keystore"), "password", "password")});
|
||||
options.setBaseDirectory(new File(baseDirectory, "web"));
|
||||
options.setExternalBaseDirectory(externalBaseDirectory != null ? new File(externalBaseDirectory, "web") : null);
|
||||
options.setDefaultPackageName("com.de22.web.test.web.");
|
||||
options.setSessionTimeout(3600000);
|
||||
options.setSessionCheckInterval(3600000);
|
||||
options.setBadSessionHandler(new IBadSessionHandler() {
|
||||
public boolean process(IRequest request, IResponse response, ISession session, boolean wasLoggedIn) {
|
||||
if(wasLoggedIn) {
|
||||
response.setCustomHeader("HTTP/1.1 412 Refresh\r\nrefresh: true\r\n");
|
||||
return true;
|
||||
}//if//
|
||||
|
||||
return false;
|
||||
}//process()//
|
||||
});
|
||||
//Note: The resource name is the portion of the URL that comes after the domain & port.//
|
||||
options.addPathSubstitution("/", "/index.html", false);
|
||||
options.setResourceRequestHandler(new IResourceRequestHandler() {
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.web.IResourceRequestHandler#getMaxMessageSize(com.foundation.web.interfaces.IRequest, com.foundation.web.SessionData, com.foundation.web.SecureSessionData)
|
||||
*/
|
||||
public int getMaxMessageSize(IRequest request, SessionData sessionData, SecureSessionData secureSessionData) {
|
||||
return 0;
|
||||
}//getMaxMessageSize()//
|
||||
/**
|
||||
* Verifies that the user has sufficient access for the server to service the request.
|
||||
* Forwards the user to a less secure resource if they fail the permission test.
|
||||
*/
|
||||
private boolean verifyRequestPathAccess(String requestPath, IRequest request, IResponse response, SessionData sessionData, SecureSessionData secureSessionData, boolean isSecure) {
|
||||
return true;
|
||||
}//verifyRequestPathAccess()//
|
||||
/**
|
||||
* Handles a static resource request.
|
||||
*/
|
||||
public void processRequest(String requestPath, IRequest request, IResponse response, SessionData sessionData, SecureSessionData secureSessionData, boolean isSecure) {
|
||||
try {
|
||||
if(verifyRequestPathAccess(requestPath, request, response, sessionData, secureSessionData, isSecure)) {
|
||||
boolean handled = false;
|
||||
|
||||
// if(requestPath.startsWith("/secure/wiki/")) {
|
||||
// int extensionIndex = requestPath.lastIndexOf('.');
|
||||
// String extension = extensionIndex != -1 ? requestPath.substring(extensionIndex + 1) : null;
|
||||
//
|
||||
// if(extension == null) {
|
||||
// IWebRequestHandler handler = new com.petitteton.web.secure.wiki.WikiViewController();
|
||||
//
|
||||
// handler.processRequest(request, response, sessionData, secureSessionData);
|
||||
// handled = true;
|
||||
// }//if//
|
||||
// }//if//
|
||||
// else {
|
||||
int extensionDecimal = requestPath.lastIndexOf('.');
|
||||
boolean cacheIndefinately = false;
|
||||
|
||||
if(extensionDecimal != -1) {
|
||||
String extension = requestPath.substring(extensionDecimal + 1).toLowerCase();
|
||||
|
||||
if(extension.equals("gif") || extension.equals("png") || extension.equals("jpg") || extension.equals("jpeg")) {
|
||||
cacheIndefinately = true;
|
||||
}//if//
|
||||
}//if//
|
||||
|
||||
//Note: We have copied the code from this call so we can customize it to perform more caching of resources.//
|
||||
FileContent.setContentResource(response, requestPath, request, request.getCacheDate(), Boolean.FALSE, cacheIndefinately);
|
||||
handled = true;
|
||||
// }//else//
|
||||
|
||||
if(!handled) {
|
||||
FileContent.setContentResource(response, requestPath, request.getCacheDate());
|
||||
}//if//
|
||||
}//if//
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
}//processRequest()//
|
||||
/**
|
||||
* Handles access to a web controller.
|
||||
*/
|
||||
public void processRequest(IWebRequestHandler handler, String requestPath, IRequest request, IResponse response, SessionData sessionData, SecureSessionData secureSessionData, boolean isSecure) {
|
||||
try {
|
||||
if(verifyRequestPathAccess(requestPath, request, response, sessionData, secureSessionData, isSecure)) {
|
||||
handler.processRequest(request, response, sessionData, secureSessionData);
|
||||
}//if//
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
}//processRequest()//
|
||||
});
|
||||
|
||||
result[0] = new WebApplication("domain1.com", options, this);
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
result = null;
|
||||
}//catch//
|
||||
|
||||
return result;
|
||||
}//createWebApplications()//
|
||||
}//TestWebappApplication//
|
||||
@@ -0,0 +1,42 @@
|
||||
package com.de22.web.test.application;
|
||||
|
||||
import java.io.File;
|
||||
import com.common.debug.*;
|
||||
import com.foundation.web.interfaces.*;
|
||||
|
||||
/**
|
||||
* The factory for the web applications defined by this application.
|
||||
*/
|
||||
public class WebApplicationFactory implements IWebApplicationFactory {
|
||||
/**
|
||||
* WebApplicationFactory constructor.
|
||||
*/
|
||||
public WebApplicationFactory() {
|
||||
super();
|
||||
}//WebApplicationFactory()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.web.interfaces.IWebApplicationFactory#createWebApplications(java.io.File, java.io.File, java.io.File, com.foundation.web.interfaces.IAppLog, java.util.Properties)
|
||||
*/
|
||||
public IWebApplication[] createWebApplications(File baseDirectory, File externalBaseDirectory, File cacheBaseDirectory, final IAppLog log, java.util.Properties properties) {
|
||||
Debug.setLog(new DefaultLog() {
|
||||
public synchronized void log(String note, Throwable exception, int type, boolean display) {
|
||||
log.log(type, note, exception);
|
||||
}//log()//
|
||||
});
|
||||
System.setProperty(TestWebappApplication.PROPERTY_GENERATE_PROXIES, "true");
|
||||
//TODO: Change this to a port that doesn't conflict with anything. This address/port is used to connect the application browser to this running web application.
|
||||
System.setProperty(TestWebappApplication.PROPERTY_APPBROWSER_SERVER_ADDRESS, "5557");
|
||||
TestWebappApplication.getSingleton().setBaseDirectory(baseDirectory);
|
||||
TestWebappApplication.getSingleton().setExternalBaseDirectory(externalBaseDirectory);
|
||||
TestWebappApplication.getSingleton().setCacheBaseDirectory(cacheBaseDirectory);
|
||||
TestWebappApplication.getSingleton().startup(properties);
|
||||
|
||||
return TestWebappApplication.getSingleton().createWebApplications(baseDirectory, externalBaseDirectory, cacheBaseDirectory, properties);
|
||||
}//createWebApplications()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.web.interfaces.IWebApplicationFactory#shutdown()
|
||||
*/
|
||||
public void shutdown() {
|
||||
TestWebappApplication.getSingleton().shutdown();
|
||||
}//shutdown()//
|
||||
}//WebApplicationFactory//
|
||||
@@ -0,0 +1,23 @@
|
||||
package com.de22.web.test.controller;
|
||||
|
||||
import com.foundation.application.*;
|
||||
import com.de22.web.test.application.*;
|
||||
|
||||
/**
|
||||
* The base class for application controllers. Application controllers contain control logic not tied to a model or view. These classes probably need to be thread safe.
|
||||
*/
|
||||
public abstract class AbstractController extends com.foundation.controller.Controller {
|
||||
/**
|
||||
* AbstractController constructor.
|
||||
*/
|
||||
public AbstractController() {
|
||||
super();
|
||||
}//AbstractController()//
|
||||
/**
|
||||
* Gets the application object that this object is running under. The application object provides the object various services that it will need.
|
||||
* @return The application reference for the application this object is running under.
|
||||
*/
|
||||
public IApplication getApplication() {
|
||||
return TestWebappApplication.getSingleton();
|
||||
}//getApplication()//
|
||||
}//AbstractController//
|
||||
@@ -0,0 +1,107 @@
|
||||
package com.de22.web.test.controller;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileOutputStream;
|
||||
import java.util.Date;
|
||||
import java.util.Properties;
|
||||
|
||||
import javax.mail.Authenticator;
|
||||
import javax.mail.MessagingException;
|
||||
import javax.mail.PasswordAuthentication;
|
||||
import javax.mail.Transport;
|
||||
import javax.mail.internet.InternetAddress;
|
||||
import javax.mail.internet.MimeMessage;
|
||||
|
||||
import com.common.debug.Debug;
|
||||
import com.common.io.StreamSupport;
|
||||
|
||||
/**
|
||||
* Provides access to sending emails.<p>
|
||||
*/
|
||||
public class EmailController extends AbstractController {
|
||||
//TODO: Move these values into a property file.
|
||||
private String mailHost = "null";
|
||||
private String mailUser = "w";
|
||||
private String smtpPassword = "null";
|
||||
|
||||
private static final EmailController singleton = new EmailController();
|
||||
/**
|
||||
* Gets the one and only instance of this class.
|
||||
* @return The single email controller instance.
|
||||
*/
|
||||
public static EmailController getSingleton() {
|
||||
return singleton;
|
||||
}//getSingleton()//
|
||||
/**
|
||||
* EmailController constructor.
|
||||
*/
|
||||
private EmailController() {
|
||||
}//EmailController()//
|
||||
/**
|
||||
* Queues an email for sending.
|
||||
* @param fromEmailAddress The address to be sending from.
|
||||
* @param toEmailAddress The address to send to.
|
||||
* @param subject The subject of the email.
|
||||
* @param message The email message.
|
||||
* @return Whether the message could be sent.
|
||||
*/
|
||||
public boolean queueEmail(String fromEmailAddress, String toEmailAddress, String subject, String message) {
|
||||
Properties props = new Properties();
|
||||
javax.mail.Session session = null;
|
||||
boolean result = false;
|
||||
|
||||
props.put("mail.smtp.host", mailHost);
|
||||
props.put("mail.smtp.submitter", mailUser);
|
||||
props.put("mail.smtp.auth", "true");
|
||||
session = javax.mail.Session.getInstance(props, new Authenticator() {
|
||||
public PasswordAuthentication getPasswordAuthentication() {
|
||||
return new PasswordAuthentication(mailUser, smtpPassword);
|
||||
}//getPasswordAuthentication()//
|
||||
});
|
||||
|
||||
try {
|
||||
MimeMessage mimeMessage = new MimeMessage(session);
|
||||
InternetAddress toAddress = new InternetAddress(toEmailAddress);
|
||||
|
||||
mimeMessage.setFrom(new InternetAddress(fromEmailAddress));
|
||||
mimeMessage.setRecipient(javax.mail.Message.RecipientType.TO, toAddress);
|
||||
mimeMessage.setSubject(subject);
|
||||
mimeMessage.setSentDate(new Date());
|
||||
mimeMessage.setText(message);
|
||||
Transport.send(mimeMessage);
|
||||
result = true;
|
||||
}//try//
|
||||
catch(MessagingException e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
|
||||
return result;
|
||||
}//queueEmail()//
|
||||
/**
|
||||
* Reports an error in sending an email.
|
||||
* <p>TODO: This should also store an entry in the database so it shows up in a view somewhere (on server?).</p>
|
||||
* @param fromEmailAddress
|
||||
* @param toEmailAddress
|
||||
* @param subject
|
||||
* @param message
|
||||
*/
|
||||
public void reportEmailError(String fromEmailAddress, String toEmailAddress, String subject, String message) {
|
||||
FileOutputStream fout = null;
|
||||
|
||||
Debug.log(new RuntimeException("Failed to deliver the following message:\n" + " From Email:\n" + fromEmailAddress + "\n To Email:\n" + toEmailAddress + "\n Subject:\n" + subject + "\n Message:\n" + message), true);
|
||||
|
||||
try {
|
||||
File file = new File("./email_errors/" + System.currentTimeMillis() + ".txt");
|
||||
|
||||
file.getParentFile().mkdirs();
|
||||
fout = new FileOutputStream(file);
|
||||
StreamSupport.writeText("Failed to deliver the following message:\r\n" + " From Email:\r\n" + fromEmailAddress + "\r\n To Email:\r\n" + toEmailAddress + "\r\n Subject:\n" + subject + "\r\n Message:\r\n" + message, fout, "UTF8");
|
||||
}//try//
|
||||
catch(Throwable e) {
|
||||
Debug.log(e);
|
||||
}//catch//
|
||||
finally {
|
||||
try {fout.close();}catch(Throwable e) {}
|
||||
}//finally//
|
||||
}//reportEmailError()//
|
||||
}//EmailController//
|
||||
@@ -0,0 +1,23 @@
|
||||
package com.de22.web.test.model;
|
||||
|
||||
import com.foundation.application.*;
|
||||
import com.de22.web.test.application.*;
|
||||
|
||||
/**
|
||||
* The base class for all models for this application. The base class provides an opportunity to customize all models at once.
|
||||
*/
|
||||
public abstract class AbstractModel extends com.foundation.model.Model {
|
||||
/**
|
||||
* AbstractModel constructor.
|
||||
*/
|
||||
public AbstractModel() {
|
||||
super();
|
||||
}//AbstractModel()//
|
||||
/**
|
||||
* Gets the application object that this object is running under. The application object provides the object various services that it will need.
|
||||
* @return The application reference for the application this object is running under.
|
||||
*/
|
||||
public IApplication getApplication() {
|
||||
return TestWebappApplication.getSingleton();
|
||||
}//getApplication()//
|
||||
}//AbstractModel//
|
||||
@@ -0,0 +1,63 @@
|
||||
package com.de22.web.test.web;
|
||||
|
||||
import com.common.debug.Debug;
|
||||
import com.common.thread.Monitor;
|
||||
import com.foundation.attribute.ReflectionContext;
|
||||
import com.foundation.event.IRequestHandler;
|
||||
import com.foundation.util.IManagedList;
|
||||
import com.foundation.util.xml.INode;
|
||||
|
||||
/**
|
||||
* The application data attached to the secure session.
|
||||
*/
|
||||
public class SecureSessionData extends com.foundation.web.SecureSessionData {
|
||||
/** The context used to create and manage reflections during the life of this session data. */
|
||||
private ReflectionContext reflectionContext;
|
||||
/**
|
||||
* SecureSessionData constructor.
|
||||
* @param requestHandler
|
||||
*/
|
||||
public SecureSessionData(IRequestHandler requestHandler) {
|
||||
//The following code utilizes reflections to enable shared access to the session's data with the rest of the system without the programmer needing to handle locking.//
|
||||
//You may want to use the shared data by building local or remote views to display the logged in users (simply have the view reflect the result of calling the WebMetadataController singleton's getWebSessions() method).//
|
||||
//Create a reflection context which can be used to share access to models between multiple threads without any locking.//
|
||||
reflectionContext = new ReflectionContext(requestHandler, null, null);
|
||||
}//SecureSessionData()//
|
||||
/**
|
||||
* SecureSessionData constructor.
|
||||
* @param node The XML node to read the session data from when restoring.
|
||||
* @param requestHandler The optional request handler which may be used to setup a reflection context.
|
||||
*/
|
||||
public SecureSessionData(INode node, IRequestHandler requestHandler) {
|
||||
Integer customerId = node.getAttributeIntegerValue("customerId", null);
|
||||
|
||||
//First setup the reflection context.//
|
||||
reflectionContext = new ReflectionContext(requestHandler, null, null);
|
||||
}//SecureSessionData()//
|
||||
/**
|
||||
* Writes the session data to the XML node.
|
||||
* @param node The node to write the session data to for restoration capabilities.
|
||||
*/
|
||||
public void write(INode node) {
|
||||
/*
|
||||
if(customer != null) {
|
||||
node.addAttribute("customerId", customer != null ? customer.getId() : null);
|
||||
}//if//
|
||||
*/
|
||||
}//write()//
|
||||
/**
|
||||
* Gets the reflection context used to create reflections for this customer.
|
||||
* @return The customer's reflection context.
|
||||
*/
|
||||
public ReflectionContext getReflectionContext() {
|
||||
return reflectionContext;
|
||||
}//getReflectionContext()//
|
||||
/* (non-Javadoc)
|
||||
* @see com.foundation.web.interfaces.ISessionData#release()
|
||||
*/
|
||||
public void release() {
|
||||
reflectionContext.unregisterAll();
|
||||
reflectionContext.release();
|
||||
reflectionContext = null;
|
||||
}//release()//
|
||||
}//SecureSessionData//
|
||||
Reference in New Issue
Block a user