KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > james > transport > mailets > JDBCAlias


1 /***********************************************************************
2  * Copyright (c) 2000-2004 The Apache Software Foundation. *
3  * All rights reserved. *
4  * ------------------------------------------------------------------- *
5  * Licensed under the Apache License, Version 2.0 (the "License"); you *
6  * may not use this file except in compliance with the License. You *
7  * may obtain a copy of the License at: *
8  * *
9  * http://www.apache.org/licenses/LICENSE-2.0 *
10  * *
11  * Unless required by applicable law or agreed to in writing, software *
12  * distributed under the License is distributed on an "AS IS" BASIS, *
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or *
14  * implied. See the License for the specific language governing *
15  * permissions and limitations under the License. *
16  ***********************************************************************/

17
18 package org.apache.james.transport.mailets;
19
20 import org.apache.avalon.cornerstone.services.datasource.DataSourceSelector;
21 import org.apache.avalon.excalibur.datasource.DataSourceComponent;
22 import org.apache.avalon.framework.component.ComponentManager;
23 import org.apache.james.Constants;
24 import org.apache.james.util.JDBCUtil;
25 import org.apache.mailet.GenericMailet;
26 import org.apache.mailet.Mail;
27 import org.apache.mailet.MailAddress;
28 import org.apache.mailet.MailetException;
29
30 import javax.mail.MessagingException JavaDoc;
31 import javax.mail.internet.ParseException JavaDoc;
32 import java.sql.*;
33 import java.util.Collection JavaDoc;
34 import java.util.Iterator JavaDoc;
35 import java.util.Locale JavaDoc;
36 import java.util.Vector JavaDoc;
37
38 /**
39  * Rewrites recipient addresses based on a database table. The connection
40  * is configured by passing the URL to a conn definition. You need to set
41  * the table name to check (or view) along with the source and target columns
42  * to use. For example,
43  * <mailet match="All" class="JDBCAlias">
44  * <mappings>db://maildb/Aliases</mappings>
45  * <source_column>source_email_address</source_column>
46  * <target_column>target_email_address</target_column>
47  * </mailet>
48  *
49  */

50 public class JDBCAlias extends GenericMailet {
51
52     protected DataSourceComponent datasource;
53     protected String JavaDoc query = null;
54
55     // The JDBCUtil helper class
56
private final JDBCUtil theJDBCUtil =
57             new JDBCUtil() {
58                 protected void delegatedLog(String JavaDoc logString) {
59                     log("JDBCAlias: " + logString);
60                 }
61             };
62
63     /**
64      * Initialize the mailet
65      */

66     public void init() throws MessagingException JavaDoc {
67         String JavaDoc mappingsURL = getInitParameter("mappings");
68
69         String JavaDoc datasourceName = mappingsURL.substring(5);
70         int pos = datasourceName.indexOf("/");
71         String JavaDoc tableName = datasourceName.substring(pos + 1);
72         datasourceName = datasourceName.substring(0, pos);
73
74         Connection conn = null;
75         if (getInitParameter("source_column") == null) {
76             throw new MailetException("source_column not specified for JDBCAlias");
77         }
78         if (getInitParameter("target_column") == null) {
79             throw new MailetException("target_column not specified for JDBCAlias");
80         }
81         try {
82             ComponentManager componentManager = (ComponentManager)getMailetContext().getAttribute(Constants.AVALON_COMPONENT_MANAGER);
83             // Get the DataSourceSelector service
84
DataSourceSelector datasources = (DataSourceSelector)componentManager.lookup(DataSourceSelector.ROLE);
85             // Get the data-source required.
86
datasource = (DataSourceComponent)datasources.select(datasourceName);
87
88             conn = datasource.getConnection();
89
90             // Check if the required table exists. If not, complain.
91
DatabaseMetaData dbMetaData = conn.getMetaData();
92             // Need to ask in the case that identifiers are stored, ask the DatabaseMetaInfo.
93
// Try UPPER, lower, and MixedCase, to see if the table is there.
94
if (!(theJDBCUtil.tableExists(dbMetaData, tableName))) {
95                 StringBuffer JavaDoc exceptionBuffer =
96                     new StringBuffer JavaDoc(128)
97                             .append("Could not find table '")
98                             .append(tableName)
99                             .append("' in datasource '")
100                             .append(datasourceName)
101                             .append("'");
102                 throw new MailetException(exceptionBuffer.toString());
103             }
104
105             //Build the query
106
StringBuffer JavaDoc queryBuffer =
107                 new StringBuffer JavaDoc(128)
108                         .append("SELECT ")
109                         .append(getInitParameter("target_column"))
110                         .append(" FROM ")
111                         .append(tableName)
112                         .append(" WHERE ")
113                         .append(getInitParameter("source_column"))
114                         .append(" = ?");
115             query = queryBuffer.toString();
116         } catch (MailetException me) {
117             throw me;
118         } catch (Exception JavaDoc e) {
119             throw new MessagingException JavaDoc("Error initializing JDBCAlias", e);
120         } finally {
121             theJDBCUtil.closeJDBCConnection(conn);
122         }
123     }
124
125     public void service(Mail mail) throws MessagingException JavaDoc {
126         //Then loop through each address in the recipient list and try to map it according to the alias table
127

128         Connection conn = null;
129         PreparedStatement mappingStmt = null;
130         ResultSet mappingRS = null;
131
132         Collection JavaDoc recipients = mail.getRecipients();
133         Collection JavaDoc recipientsToRemove = new Vector JavaDoc();
134         Collection JavaDoc recipientsToAdd = new Vector JavaDoc();
135         try {
136             conn = datasource.getConnection();
137             mappingStmt = conn.prepareStatement(query);
138
139
140             for (Iterator JavaDoc i = recipients.iterator(); i.hasNext(); ) {
141                 try {
142                     MailAddress source = (MailAddress)i.next();
143                     mappingStmt.setString(1, source.toString());
144                     mappingRS = mappingStmt.executeQuery();
145                     if (!mappingRS.next()) {
146                         //This address was not found
147
continue;
148                     }
149                     try {
150                         String JavaDoc targetString = mappingRS.getString(1);
151                         MailAddress target = new MailAddress(targetString);
152
153                         //Mark this source address as an address to remove from the recipient list
154
recipientsToRemove.add(source);
155                         recipientsToAdd.add(target);
156                     } catch (ParseException JavaDoc pe) {
157                         //Don't alias this address... there's an invalid address mapping here
158
StringBuffer JavaDoc exceptionBuffer =
159                             new StringBuffer JavaDoc(128)
160                                     .append("There is an invalid alias from ")
161                                     .append(source)
162                                     .append(" to ")
163                                     .append(mappingRS.getString(1));
164                         log(exceptionBuffer.toString());
165                         continue;
166                     }
167                 } finally {
168                     ResultSet localRS = mappingRS;
169                     // Clear reference to result set
170
mappingRS = null;
171                     theJDBCUtil.closeJDBCResultSet(localRS);
172                 }
173             }
174         } catch (SQLException sqle) {
175             throw new MessagingException JavaDoc("Error accessing database", sqle);
176         } finally {
177             theJDBCUtil.closeJDBCStatement(mappingStmt);
178             theJDBCUtil.closeJDBCConnection(conn);
179         }
180
181         recipients.removeAll(recipientsToRemove);
182         recipients.addAll(recipientsToAdd);
183     }
184
185     /**
186      * Return a string describing this mailet.
187      *
188      * @return a string describing this mailet
189      */

190     public String JavaDoc getMailetInfo() {
191         return "JDBC aliasing mailet";
192     }
193
194 }
195
Popular Tags