package org.jboss.mail;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import java.util.Properties;
import javax.management.ObjectName;
import javax.management.MBeanServer;
import javax.management.MalformedObjectNameException;
import javax.naming.InitialContext;
import javax.naming.Reference;
import javax.naming.StringRefAddr;
import javax.naming.Name;
import javax.naming.Context;
import javax.naming.NamingException;
import javax.naming.NameNotFoundException;
import javax.mail.Session;
import javax.mail.PasswordAuthentication;
import javax.mail.Authenticator;
import org.jboss.system.ServiceMBeanSupport;
import org.jboss.naming.NonSerializableFactory;
public class MailService
extends ServiceMBeanSupport
implements MailServiceMBean
{
public static final String JNDI_NAME = "java:/Mail";
private String user;
private String password;
private String jndiName = JNDI_NAME;
private Element config;
ObjectName mMail;
Properties ourProps = null;
public void setUser(final String user)
{
this.user = user;
}
public String getUser()
{
return user;
}
public void setPassword(final String password)
{
this.password = password;
}
protected String getPassword()
{
return password;
}
public Element getConfiguration()
{
return config;
}
public void setConfiguration(final Element element)
{
config = element;
}
public void setJNDIName(final String name)
{
jndiName = name;
}
public String getJNDIName()
{
return jndiName;
}
public String getStoreProtocol()
{
if (ourProps != null)
return ourProps.getProperty("mail.store.protocol");
else
return null;
}
public String getTransportProtocol()
{
if (ourProps != null)
return ourProps.getProperty("mail.transport.protocol");
else
return null;
}
public String getDefaultSender()
{
if (ourProps != null)
return ourProps.getProperty("mail.from");
else
return null;
}
public String getSMTPServerHost()
{
if (ourProps != null)
return ourProps.getProperty("mail.smtp.host");
else
return null;
}
public String getPOP3ServerHost()
{
if (ourProps != null)
return ourProps.getProperty("mail.pop3.host");
else
return null;
}
protected ObjectName getObjectName(MBeanServer server, ObjectName name)
throws MalformedObjectNameException
{
return name == null ? OBJECT_NAME : name;
}
protected void startService() throws Exception
{
final PasswordAuthentication pa = new PasswordAuthentication(getUser(), getPassword());
Authenticator a = new Authenticator()
{
protected PasswordAuthentication getPasswordAuthentication()
{
return pa;
}
};
Properties props = getProperties();
Session session = Session.getInstance(props, a);
bind(session);
ourProps = props;
}
protected Properties getProperties() throws Exception
{
boolean debug = log.isDebugEnabled();
Properties props = new Properties();
if (config == null)
{
log.warn("No configuration specified; using empty properties map");
return props;
}
NodeList list = config.getElementsByTagName("property");
int len = list.getLength();
for (int i = 0; i < len; i++)
{
Node node = list.item(i);
switch (node.getNodeType())
{
case Node.ELEMENT_NODE:
Element child = (Element) node;
String name, value;
if (child.hasAttribute("name"))
{
name = child.getAttribute("name");
}
else
{
log.warn("Ignoring invalid element; missing 'name' attribute: " + child);
break;
}
if (child.hasAttribute("value"))
{
value = child.getAttribute("value");
}
else
{
log.warn("Ignoring invalid element; missing 'value' attribute: " + child);
break;
}
if (debug)
{
log.debug("setting property " + name + "=" + value);
}
props.setProperty(name, value);
break;
case Node.COMMENT_NODE:
break;
default:
log.debug("ignoring unsupported node type: " + node);
break;
}
}
if (debug)
{
log.debug("Using properties: " + props);
}
return props;
}
protected void stopService() throws Exception
{
unbind();
}
private void bind(Session session) throws NamingException
{
String bindName = getJNDIName();
NonSerializableFactory.bind(bindName, session);
Context ctx = new InitialContext();
try
{
Name n = ctx.getNameParser("").parse(bindName);
while (n.size() > 1)
{
String ctxName = n.get(0);
try
{
ctx = (Context) ctx.lookup(ctxName);
}
catch (NameNotFoundException e)
{
ctx = ctx.createSubcontext(ctxName);
}
n = n.getSuffix(1);
}
StringRefAddr addr = new StringRefAddr("nns", bindName);
Reference ref = new Reference(Session.class.getName(),
addr,
NonSerializableFactory.class.getName(),
null);
ctx.bind(n.get(0), ref);
}
finally
{
ctx.close();
}
log.info("Mail Service bound to " + bindName);
}
private void unbind() throws NamingException
{
String bindName = getJNDIName();
if (bindName != null)
{
InitialContext ctx = new InitialContext();
try
{
ctx.unbind(bindName);
}
finally
{
ctx.close();
}
NonSerializableFactory.unbind(bindName);
log.info("Mail service '" + getJNDIName() + "' removed from JNDI");
}
}
}