Merge branch 'master' of ssh://dev.hostsharing.net:29418/hsadmin/hs.hsadmin

This commit is contained in:
Michael Hierweck 2017-06-29 09:53:42 +02:00
commit 20bf41d827

View File

@ -13,6 +13,7 @@ import de.hsadmin.core.qserv.CompoundProcessor;
import de.hsadmin.core.qserv.CopyFileProcessor; import de.hsadmin.core.qserv.CopyFileProcessor;
import de.hsadmin.core.qserv.CreateFileProcessor; import de.hsadmin.core.qserv.CreateFileProcessor;
import de.hsadmin.core.qserv.EntityProcessorFactory; import de.hsadmin.core.qserv.EntityProcessorFactory;
import de.hsadmin.core.qserv.NullProcessor;
import de.hsadmin.core.qserv.Processor; import de.hsadmin.core.qserv.Processor;
import de.hsadmin.core.qserv.ProcessorException; import de.hsadmin.core.qserv.ProcessorException;
import de.hsadmin.core.qserv.ShellProcessor; import de.hsadmin.core.qserv.ShellProcessor;
@ -47,30 +48,33 @@ public class DomainProcessorFactory implements EntityProcessorFactory {
mainProcessor.appendProcessor(hiveName, createDomainDirectoriesProcessor(dom), "Setup Domain Directories"); mainProcessor.appendProcessor(hiveName, createDomainDirectoriesProcessor(dom), "Setup Domain Directories");
mainProcessor.appendProcessor(hiveName, createApacheVHostSetupProcessor(em, dom), "Setup Apache VHost"); mainProcessor.appendProcessor(hiveName, createApacheVHostSetupProcessor(em, dom), "Setup Apache VHost");
mainProcessor.appendProcessor(hiveName, createACMEBotProcessor(em, dom), "Setup ACMEBot"); mainProcessor.appendProcessor(hiveName, createACMEBotProcessor(em, dom), "Setup ACMEBot");
mainProcessor.appendProcessor(hiveName, createTriggerAcmebotProcessor(em, dom), "Trigger ACMEBot");
return mainProcessor; return mainProcessor;
} }
public <T extends AbstractEntity> Processor createUpdateProcessor(EntityManager em, T entity) throws ProcessorException { public <T extends AbstractEntity> Processor createUpdateProcessor(final EntityManager em, final T entity) throws ProcessorException {
Domain dom = (Domain) entity; final Domain dom = (Domain) entity;
UnixUser domUser = dom.getUser(); final UnixUser domUser = dom.getUser();
Pac pac = domUser.getPac(); final Pac pac = domUser.getPac();
final Processor apacheVHostSetupProcessor = createApacheVHostSetupProcessor(em, dom); final Processor apacheVHostSetupProcessor = createApacheVHostSetupProcessor(em, dom);
final Processor letencryptSetupProcessor = createACMEBotProcessor(em, dom); final Processor letencryptSetupProcessor = createACMEBotProcessor(em, dom);
WaitingTasksProcessor processor = new WaitingTasksProcessor(new CompoundProcessor(apacheVHostSetupProcessor, letencryptSetupProcessor)); final Processor triggerAcmebotProcessor = createTriggerAcmebotProcessor(em, dom);
Config config = Config.getInstance(); final WaitingTasksProcessor processor = new WaitingTasksProcessor(
new CompoundProcessor(apacheVHostSetupProcessor, letencryptSetupProcessor, triggerAcmebotProcessor));
final Config config = Config.getInstance();
for (String queueName : config.getProperty("queues.mail").split(",")) { for (String queueName : config.getProperty("queues.mail").split(",")) {
processor.appendProcessor(queueName, createMailinSetupProcessor(em, dom, pac), queueName + ".hostsharing.net"); processor.appendProcessor(queueName, createMailinSetupProcessor(em, dom, pac), queueName + ".hostsharing.net");
} }
return processor; return processor;
} }
public <T extends AbstractEntity> Processor createDeleteProcessor(EntityManager em, T entity) throws ProcessorException { public <T extends AbstractEntity> Processor createDeleteProcessor(final EntityManager em, final T entity) throws ProcessorException {
Domain dom = (Domain) entity; final Domain dom = (Domain) entity;
String domName = dom.getName(); final String domName = dom.getName();
WaitingTasksProcessor mainProcessor = new WaitingTasksProcessor( final WaitingTasksProcessor mainProcessor = new WaitingTasksProcessor(
createHiveDNSRemoveProcessor(domName) createHiveDNSRemoveProcessor(domName)
); );
Config config = Config.getInstance(); final Config config = Config.getInstance();
for (String queueName : config.getProperty("queues.dns").split(",")) { for (String queueName : config.getProperty("queues.dns").split(",")) {
mainProcessor.appendProcessor(queueName, createDNSServerConfigProcessor(em), queueName + ".hostsharing.net"); mainProcessor.appendProcessor(queueName, createDNSServerConfigProcessor(em), queueName + ".hostsharing.net");
} }
@ -83,8 +87,8 @@ public class DomainProcessorFactory implements EntityProcessorFactory {
} }
private Processor createDNSServerConfigProcessor(EntityManager em) { private Processor createDNSServerConfigProcessor(EntityManager em) {
Query query = em.createQuery("SELECT d FROM Domains d"); final Query query = em.createQuery("SELECT d FROM Domains d");
HashMap<String, Object> templateVars = new HashMap<String, Object>(); final HashMap<String, Object> templateVars = new HashMap<String, Object>();
templateVars.put("domains", query.getResultList()); templateVars.put("domains", query.getResultList());
return new CompoundProcessor( return new CompoundProcessor(
new VelocityProcessor("/de/hsadmin/mods/dom/named-hsh-conf.vm", new VelocityProcessor("/de/hsadmin/mods/dom/named-hsh-conf.vm",
@ -95,25 +99,25 @@ public class DomainProcessorFactory implements EntityProcessorFactory {
} }
private Processor createHiveDNSSetupProcessor(EntityManager em, Domain dom) throws ProcessorException { private Processor createHiveDNSSetupProcessor(EntityManager em, Domain dom) throws ProcessorException {
Map<String, Object> templateVars = new HashMap<String, Object>(); final Map<String, Object> zonefileTemplateVars = new HashMap<String, Object>();
templateVars.put("sio", Long.toString(System.currentTimeMillis()/1000L)); zonefileTemplateVars.put("sio", Long.toString(System.currentTimeMillis()/1000L));
String domName = dom.getName(); final String domName = dom.getName();
String zonefileTargetPath = "/etc/bind/pri." + domName; final String zonefileTargetPath = "/etc/bind/pri." + domName;
Processor zonefileTemplateProcessor = final Processor zonefileTemplateProcessor =
new VelocityProcessor("/de/hsadmin/mods/dom/zonefile.vm", templateVars, dom, zonefileTargetPath, false); new VelocityProcessor("/de/hsadmin/mods/dom/zonefile.vm", zonefileTemplateVars, dom, zonefileTargetPath, false);
Processor zonefileACLProcessor = final Processor zonefileACLProcessor =
new ShellProcessor("chown root:bind " + zonefileTargetPath + " && chmod 644 " + zonefileTargetPath); new ShellProcessor("chown root:bind " + zonefileTargetPath + " && chmod 644 " + zonefileTargetPath);
Query query = em.createQuery("SELECT d FROM Domains d WHERE d.user.pac.hive.name = :hivename"); final Query query = em.createQuery("SELECT d FROM Domains d WHERE d.user.pac.hive.name = :hivename");
query.setParameter("hivename", dom.getUser().getHiveName()); query.setParameter("hivename", dom.getUser().getHiveName());
templateVars = new HashMap<String, Object>(); final Map<String, Object> namedZonesTemplateVars = new HashMap<String, Object>();
templateVars.put("domains", query.getResultList()); namedZonesTemplateVars.put("domains", query.getResultList());
Processor prizonesFileProcessor = new CompoundProcessor( final Processor prizonesFileProcessor = new CompoundProcessor(
new VelocityProcessor("/de/hsadmin/mods/dom/named-pri-zones.vm", new VelocityProcessor("/de/hsadmin/mods/dom/named-pri-zones.vm",
templateVars, dom, "/etc/bind/named.pri-zones.tmp", true), namedZonesTemplateVars, dom, "/etc/bind/named.pri-zones.tmp", true),
new ShellProcessor(" ( diff -q /etc/bind/named.pri-zones.tmp /etc/bind/named.pri-zones && rm /etc/bind/named.pri-zones.tmp ) " + new ShellProcessor(" ( diff -q /etc/bind/named.pri-zones.tmp /etc/bind/named.pri-zones && rm /etc/bind/named.pri-zones.tmp ) " +
"|| ( mv /etc/bind/named.pri-zones.tmp /etc/bind/named.pri-zones && invoke-rc.d bind9 reload )") "|| ( mv /etc/bind/named.pri-zones.tmp /etc/bind/named.pri-zones && invoke-rc.d bind9 reload )")
); );
Processor dnsSetupProcessor = final Processor dnsSetupProcessor =
new CompoundProcessor(zonefileTemplateProcessor, zonefileACLProcessor, prizonesFileProcessor); new CompoundProcessor(zonefileTemplateProcessor, zonefileACLProcessor, prizonesFileProcessor);
return dnsSetupProcessor; return dnsSetupProcessor;
} }
@ -126,28 +130,28 @@ public class DomainProcessorFactory implements EntityProcessorFactory {
} }
private CompoundProcessor createHiveEMailSetupProcessor(EntityManager em, Domain dom) { private CompoundProcessor createHiveEMailSetupProcessor(EntityManager em, Domain dom) {
EMailAddressProcessorFactory eMailAddressProcessorFactory = new EMailAddressProcessorFactory(); final EMailAddressProcessorFactory eMailAddressProcessorFactory = new EMailAddressProcessorFactory();
CompoundProcessor emailAdrProcessor = new CompoundProcessor(); final CompoundProcessor emailAdrProcessor = new CompoundProcessor();
Query query = em.createQuery( final Query query = em.createQuery(
"SELECT adr FROM " + "SELECT adr FROM " +
EMailAddress.class.getAnnotation(javax.persistence.Entity.class).name() + " adr " + EMailAddress.class.getAnnotation(javax.persistence.Entity.class).name() + " adr " +
"WHERE adr.domain.name='" + dom.getName() + "'"); "WHERE adr.domain.name='" + dom.getName() + "'");
List<?> resultList = query.getResultList(); final List<?> resultList = query.getResultList();
for (Object obj : resultList) { for (final Object obj : resultList) {
EMailAddress eMailAddress = (EMailAddress) obj; final EMailAddress eMailAddress = (EMailAddress) obj;
emailAdrProcessor.appendProcessor(eMailAddressProcessorFactory.createCreateProcessor(em, eMailAddress)); emailAdrProcessor.appendProcessor(eMailAddressProcessorFactory.createCreateProcessor(em, eMailAddress));
} }
return emailAdrProcessor; return emailAdrProcessor;
} }
private Processor createMailinSetupProcessor(EntityManager em, Domain dom, Pac pac) throws ProcessorException { private Processor createMailinSetupProcessor(EntityManager em, Domain dom, Pac pac) throws ProcessorException {
String inetAddr = pac.getCurINetAddr().getInetAddr(); final String inetAddr = pac.getCurINetAddr().getInetAddr();
CompoundProcessor cp = new CompoundProcessor( final CompoundProcessor cp = new CompoundProcessor(
createPostgreyConfiguration(em), createPostgreyConfiguration(em),
new ShellProcessor("postmap -r -i /etc/postfix-mailin/relaydomains", new ShellProcessor("postmap -r -i /etc/postfix-mailin/relaydomains",
dom.getName() + " anything\n" + dom.getName() + " anything\n" +
"." + dom.getName() + " anything\n")); "." + dom.getName() + " anything\n"));
Query query = em.createQuery("SELECT d FROM Domains d WHERE d.domainoptions.name = :option AND d.name = :domname"); final Query query = em.createQuery("SELECT d FROM Domains d WHERE d.domainoptions.name = :option AND d.name = :domname");
query.setParameter("domname", dom.getName()); query.setParameter("domname", dom.getName());
query.setParameter("option", "backupmxforexternalmx"); query.setParameter("option", "backupmxforexternalmx");
if (query.getResultList().isEmpty()) { if (query.getResultList().isEmpty()) {
@ -167,19 +171,19 @@ public class DomainProcessorFactory implements EntityProcessorFactory {
} }
private Processor createPostgreyConfiguration(EntityManager em) throws ProcessorException { private Processor createPostgreyConfiguration(EntityManager em) throws ProcessorException {
List<Domain> whitelistDoms = new ArrayList<Domain>(); final List<Domain> whitelistDoms = new ArrayList<Domain>();
Query query = em.createQuery("SELECT DISTINCT dom FROM Domains dom WHERE NOT EXISTS " + final Query query = em.createQuery("SELECT DISTINCT dom FROM Domains dom WHERE NOT EXISTS " +
"( SELECT postgreyDom FROM Domains postgreyDom " + "( SELECT postgreyDom FROM Domains postgreyDom " +
" WHERE postgreyDom.domainoptions.name = :option" + " WHERE postgreyDom.domainoptions.name = :option" +
" AND postgreyDom.name = dom.name )"); " AND postgreyDom.name = dom.name )");
query.setParameter("option", "greylisting"); query.setParameter("option", "greylisting");
List<?> result = query.getResultList(); final List<?> result = query.getResultList();
for (Object dom : result) { for (Object dom : result) {
if (dom instanceof Domain) { if (dom instanceof Domain) {
whitelistDoms.add((Domain) dom); whitelistDoms.add((Domain) dom);
} }
} }
HashMap<String, Object> templateVars = new HashMap<String, Object>(); final HashMap<String, Object> templateVars = new HashMap<String, Object>();
templateVars.put("whitelist", whitelistDoms); templateVars.put("whitelist", whitelistDoms);
return new CompoundProcessor( return new CompoundProcessor(
new VelocityProcessor("/de/hsadmin/mods/dom/postgrey-whitelist-recipients.vm", new VelocityProcessor("/de/hsadmin/mods/dom/postgrey-whitelist-recipients.vm",
@ -201,15 +205,15 @@ public class DomainProcessorFactory implements EntityProcessorFactory {
} }
private CompoundProcessor createDomainDirectoriesProcessor(Domain dom) throws ProcessorException { private CompoundProcessor createDomainDirectoriesProcessor(Domain dom) throws ProcessorException {
Map<String, Object> templateVars = new HashMap<String, Object>(); final Map<String, Object> templateVars = new HashMap<String, Object>();
UnixUser domUser = dom.getUser(); final UnixUser domUser = dom.getUser();
String domName = dom.getName(); final String domName = dom.getName();
Pac pac = domUser.getPac(); final Pac pac = domUser.getPac();
String pacName = pac.getName(); final String pacName = pac.getName();
String homeDir = domUser.getHomedir(); final String homeDir = domUser.getHomedir();
String domsDir = homeDir + "/doms"; final String domsDir = homeDir + "/doms";
String userName = domUser.getName(); final String userName = domUser.getName();
String domainDir = domsDir + "/" + dom.getName(); final String domainDir = domsDir + "/" + dom.getName();
String httpdRights = ""; String httpdRights = "";
if (pacName != userName) { if (pacName != userName) {
httpdRights = httpdRights =
@ -308,24 +312,43 @@ public class DomainProcessorFactory implements EntityProcessorFactory {
} }
private Processor createApacheVHostDeleteProcessor(Domain dom) { private Processor createApacheVHostDeleteProcessor(Domain dom) {
String domName = dom.getName(); final String domName = dom.getName();
int level = domName.split("\\.").length; final int level = domName.split("\\.").length;
String linkPrefix = Integer.toString(100 - level); final String linkPrefix = Integer.toString(100 - level);
Processor vhostDelProcessor = final Processor vhostDelProcessor =
new ShellProcessor("rm -f /home/doms/" + domName + new ShellProcessor("rm -f /home/doms/" + domName +
" && rm -f /etc/apache2/sites-enabled/" + linkPrefix + "-" + domName + " && rm -f /etc/apache2/sites-enabled/" + linkPrefix + "-" + domName +
" && rm -f /etc/apache2/sites-available/" + domName + " && rm -f /etc/apache2/sites-available/" + domName +
" && rm -f /etc/apache2/pems-enabled/" + domName + ".crt" + " && rm -f /etc/apache2/pems-enabled/" + domName + ".crt" +
" && rm -f /etc/apache2/pems-enabled/" + domName + ".key" + " && rm -f /etc/apache2/pems-enabled/" + domName + ".key" +
" && rm -f /etc/apache2/pems-enabled/" + domName + ".chain" + " && rm -f /etc/apache2/pems-enabled/" + domName + ".chain" +
" && rm -f /etc/apache2/pems-generated/_." + domName + ".crt" + " && rm -f /etc/apache2/pems-generated/" + domName + ".crt" +
" && rm -f /etc/apache2/pems-generated/_." + domName + ".key" + " && rm -f /etc/apache2/pems-generated/" + domName + ".key" +
" && rm -f /etc/apache2/pems-generated/_." + domName + ".chain" + " && rm -f /etc/apache2/pems-generated/" + domName + ".chain" +
" && rm -rf " + dom.getUser().getHomedir() + "/doms/" + domName + " && rm -rf " + dom.getUser().getHomedir() + "/doms/" + domName +
" && invoke-rc.d apache2 reload >/dev/null 2>&1"); " && invoke-rc.d apache2 reload >/dev/null 2>&1");
return vhostDelProcessor; return vhostDelProcessor;
} }
private Processor createTriggerAcmebotProcessor(final EntityManager em, final Domain dom) {
final String domName = dom.getName();
final Query query = em.createQuery("SELECT d FROM Domains d WHERE d.domainoptions.name = :option AND d.name = :domname");
query.setParameter("domname", domName);
query.setParameter("option", "letsencrypt");
if (query.getResultList().isEmpty()) {
return new NullProcessor();
} else {
return new ShellProcessor(
"rm -f /etc/apache2/pems-enabled/" + domName + ".crt" +
" && rm -f /etc/apache2/pems-enabled/" + domName + ".key" +
" && rm -f /etc/apache2/pems-enabled/" + domName + ".chain" +
" && ln -s /etc/apache2/pems-generated/" + domName + ".key /etc/apache2/pems-enabled/" + domName + ".key" +
" && ln -s /etc/apache2/pems-generated/" + domName + ".crt /etc/apache2/pems-enabled/" + domName + ".crt" +
" && ln -s /etc/apache2/pems-generated/" + domName + ".chain /etc/apache2/pems-enabled/" + domName + ".chain" +
" && sudo -u acmebot /usr/sbin/acmebot -d " + domName);
}
}
private Processor createACMEBotProcessor(final EntityManager em, final Domain dom) throws ProcessorException { private Processor createACMEBotProcessor(final EntityManager em, final Domain dom) throws ProcessorException {
final Query query = em.createQuery("SELECT d FROM Domains d WHERE d.domainoptions.name = :option AND d.user.pac.hive.name = :hivename"); final Query query = em.createQuery("SELECT d FROM Domains d WHERE d.domainoptions.name = :option AND d.user.pac.hive.name = :hivename");
final String hiveName = dom.getHiveName(); final String hiveName = dom.getHiveName();