001 /****************************************************************
002 * Licensed to the Apache Software Foundation (ASF) under one *
003 * or more contributor license agreements. See the NOTICE file *
004 * distributed with this work for additional information *
005 * regarding copyright ownership. The ASF licenses this file *
006 * to you under the Apache License, Version 2.0 (the *
007 * "License"); you may not use this file except in compliance *
008 * with the License. You may obtain a copy of the License at *
009 * *
010 * http://www.apache.org/licenses/LICENSE-2.0 *
011 * *
012 * Unless required by applicable law or agreed to in writing, *
013 * software distributed under the License is distributed on an *
014 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY *
015 * KIND, either express or implied. See the License for the *
016 * specific language governing permissions and limitations *
017 * under the License. *
018 ****************************************************************/
019
020 package org.apache.james.domainlist.lib;
021
022 import java.net.InetAddress;
023 import java.net.UnknownHostException;
024 import java.util.ArrayList;
025 import java.util.Iterator;
026 import java.util.List;
027 import java.util.Locale;
028
029 import javax.annotation.Resource;
030
031 import org.apache.commons.configuration.ConfigurationException;
032 import org.apache.commons.configuration.HierarchicalConfiguration;
033 import org.apache.james.dnsservice.api.DNSService;
034 import org.apache.james.domainlist.api.DomainList;
035 import org.apache.james.domainlist.api.DomainListException;
036 import org.apache.james.lifecycle.api.Configurable;
037 import org.apache.james.lifecycle.api.LogEnabled;
038 import org.slf4j.Logger;
039
040 /**
041 * All implementations of the DomainList interface should extends this abstract
042 * class
043 */
044 public abstract class AbstractDomainList implements DomainList, LogEnabled, Configurable {
045 private DNSService dns;
046 private boolean autoDetect = true;
047 private boolean autoDetectIP = true;
048 private Logger logger;
049 private String defaultDomain;
050
051 @Resource(name = "dnsservice")
052 public void setDNSService(DNSService dns) {
053 this.dns = dns;
054 }
055
056 public void setLog(Logger logger) {
057 this.logger = logger;
058 }
059
060 protected Logger getLogger() {
061 return logger;
062 }
063
064 /**
065 * @see org.apache.james.lifecycle.api.Configurable#configure(HierarchicalConfiguration)
066 */
067 public void configure(HierarchicalConfiguration config) throws ConfigurationException {
068 defaultDomain = config.getString("defaultDomain", "localhost");
069
070 setAutoDetect(config.getBoolean("autodetect", true));
071 setAutoDetectIP(config.getBoolean("autodetectIP", true));
072 }
073
074 /**
075 * @see org.apache.james.domainlist.api.DomainList#getDefaultDomain()
076 */
077 public String getDefaultDomain() throws DomainListException {
078 return defaultDomain;
079 }
080
081 /**
082 * @see org.apache.james.domainlist.api.DomainList#getDomains()
083 */
084 public String[] getDomains() throws DomainListException {
085 List<String> domains = getDomainListInternal();
086 if (domains != null) {
087
088 String hostName = null;
089 try {
090 hostName = getDNSServer().getHostName(getDNSServer().getLocalHost());
091 } catch (UnknownHostException ue) {
092 hostName = "localhost";
093 }
094
095 getLogger().info("Local host is: " + hostName);
096
097 if (autoDetect == true && (!hostName.equals("localhost"))) {
098 domains.add(hostName.toLowerCase(Locale.US));
099 }
100
101 if (autoDetectIP == true) {
102 domains.addAll(getDomainsIP(domains, dns, getLogger()));
103 }
104
105 if (getLogger().isInfoEnabled()) {
106 for (Iterator<String> i = domains.iterator(); i.hasNext();) {
107 getLogger().debug("Handling mail for: " + i.next());
108 }
109 }
110 if (domains.isEmpty()) {
111 return null;
112 } else {
113 return domains.toArray(new String[domains.size()]);
114 }
115 } else {
116 return null;
117 }
118 }
119
120 /**
121 * Return a List which holds all ipAddress of the domains in the given List
122 *
123 * @param domains
124 * List of domains
125 * @return domainIP List of ipaddress for domains
126 */
127 private static List<String> getDomainsIP(List<String> domains, DNSService dns, Logger log) {
128 List<String> domainIP = new ArrayList<String>();
129 if (domains.size() > 0) {
130 for (int i = 0; i < domains.size(); i++) {
131 List<String> domList = getDomainIP(domains.get(i).toString(), dns, log);
132
133 for (int i2 = 0; i2 < domList.size(); i2++) {
134 if (domainIP.contains(domList.get(i2)) == false) {
135 domainIP.add(domList.get(i2));
136 }
137 }
138 }
139 }
140 return domainIP;
141 }
142
143 /**
144 * @see #getDomainsIP(List, DNSService, Logger)
145 */
146 private static List<String> getDomainIP(String domain, DNSService dns, Logger log) {
147 List<String> domainIP = new ArrayList<String>();
148 try {
149 InetAddress[] addrs = dns.getAllByName(domain);
150 for (int j = 0; j < addrs.length; j++) {
151 String ip = addrs[j].getHostAddress();
152 if (domainIP.contains(ip) == false) {
153 domainIP.add(ip);
154 }
155 }
156 } catch (UnknownHostException e) {
157 log.error("Cannot get IP address(es) for " + domain);
158 }
159 return domainIP;
160 }
161
162 /**
163 * Set to true to autodetect the hostname of the host on which james is
164 * running, and add this to the domain service Default is true
165 *
166 * @param autoDetect
167 * set to <code>false</code> for disable
168 */
169 public synchronized void setAutoDetect(boolean autoDetect) {
170 getLogger().info("Set autodetect to: " + autoDetect);
171 this.autoDetect = autoDetect;
172 }
173
174 /**
175 * Set to true to lookup the ipaddresses for each given domain and add these
176 * to the domain service Default is true
177 *
178 * @param autoDetectIP
179 * set to <code>false</code> for disable
180 */
181 public synchronized void setAutoDetectIP(boolean autoDetectIP) {
182 getLogger().info("Set autodetectIP to: " + autoDetectIP);
183 this.autoDetectIP = autoDetectIP;
184 }
185
186 /**
187 * Return dnsServer
188 *
189 * @return dns
190 */
191 protected DNSService getDNSServer() {
192 return dns;
193 }
194
195 /**
196 * Return domainList
197 *
198 * @return List
199 */
200 protected abstract List<String> getDomainListInternal() throws DomainListException;
201
202 }