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 020package org.apache.james.user.lib; 021 022import javax.inject.Inject; 023 024import org.apache.commons.configuration.ConfigurationException; 025import org.apache.commons.configuration.HierarchicalConfiguration; 026import org.apache.james.domainlist.api.DomainList; 027import org.apache.james.domainlist.api.DomainListException; 028import org.apache.james.lifecycle.api.Configurable; 029import org.apache.james.lifecycle.api.LogEnabled; 030import org.apache.james.user.api.AlreadyExistInUsersRepositoryException; 031import org.apache.james.user.api.UsersRepository; 032import org.apache.james.user.api.UsersRepositoryException; 033import org.apache.mailet.MailAddress; 034import org.slf4j.Logger; 035 036import com.google.common.annotations.VisibleForTesting; 037import com.google.common.base.Optional; 038 039public abstract class AbstractUsersRepository implements UsersRepository, LogEnabled, Configurable { 040 041 private DomainList domainList; 042 private boolean virtualHosting; 043 private Logger logger; 044 private Optional<String> administratorId; 045 046 protected Logger getLogger() { 047 return logger; 048 } 049 050 /** 051 * @see org.apache.james.lifecycle.api.LogEnabled#setLog(org.slf4j.Logger) 052 */ 053 public void setLog(Logger logger) { 054 this.logger = logger; 055 } 056 057 /** 058 * @see 059 * org.apache.james.lifecycle.api.Configurable#configure(org.apache.commons.configuration.HierarchicalConfiguration) 060 */ 061 public void configure(HierarchicalConfiguration configuration) throws ConfigurationException { 062 063 virtualHosting = configuration.getBoolean("enableVirtualHosting", getDefaultVirtualHostingValue()); 064 administratorId = Optional.fromNullable(configuration.getString("administratorId")); 065 066 doConfigure(configuration); 067 } 068 069 protected boolean getDefaultVirtualHostingValue() { 070 return false; 071 } 072 073 protected void doConfigure(HierarchicalConfiguration config) throws ConfigurationException { 074 } 075 076 public void setEnableVirtualHosting(boolean virtualHosting) { 077 this.virtualHosting = virtualHosting; 078 } 079 080 @Inject 081 public void setDomainList(DomainList domainList) { 082 this.domainList = domainList; 083 } 084 085 protected void isValidUsername(String username) throws UsersRepositoryException { 086 int i = username.indexOf("@"); 087 if (supportVirtualHosting()) { 088 // need a @ in the username 089 if (i == -1) { 090 throw new UsersRepositoryException("Given Username needs to contain a @domainpart"); 091 } else { 092 String domain = username.substring(i + 1); 093 try { 094 if (!domainList.containsDomain(domain)) { 095 throw new UsersRepositoryException("Domain does not exist in DomainList"); 096 } else { 097 } 098 } catch (DomainListException e) { 099 throw new UsersRepositoryException("Unable to query DomainList", e); 100 } 101 } 102 } else { 103 // @ only allowed when virtualhosting is supported 104 if (i != -1) { 105 throw new UsersRepositoryException("Given Username contains a @domainpart but virtualhosting support is disabled"); 106 } 107 } 108 } 109 110 /** 111 * @see org.apache.james.user.api.UsersRepository#addUser(java.lang.String, 112 * java.lang.String) 113 */ 114 public void addUser(String username, String password) throws UsersRepositoryException { 115 116 if (!contains(username)) { 117 isValidUsername(username); 118 doAddUser(username, password); 119 } else { 120 throw new AlreadyExistInUsersRepositoryException("User with username " + username + " already exists!"); 121 } 122 123 } 124 125 /** 126 * @see org.apache.james.user.api.UsersRepository#supportVirtualHosting() 127 */ 128 public boolean supportVirtualHosting() { 129 return virtualHosting; 130 } 131 132 /** 133 * Add the user with the given username and password 134 * 135 * @param username 136 * @param password 137 * @throws UsersRepositoryException 138 * If an error occurred 139 */ 140 protected abstract void doAddUser(String username, String password) throws UsersRepositoryException; 141 142 @Override 143 public String getUser(MailAddress mailAddress) throws UsersRepositoryException { 144 if (supportVirtualHosting()) { 145 return mailAddress.asString(); 146 } else { 147 return mailAddress.getLocalPart(); 148 } 149 } 150 151 @VisibleForTesting void setAdministratorId(Optional<String> username) { 152 this.administratorId = username; 153 } 154 155 @Override 156 public boolean isAdministrator(String username) throws UsersRepositoryException { 157 if (administratorId.isPresent()) { 158 return administratorId.get().equals(username); 159 } 160 return false; 161 } 162}