]> source.dussan.org Git - sonarqube.git/blob
b1e11e52d673410ee62f470cdbd60f42315f6051
[sonarqube.git] /
1 /*
2  * SonarQube
3  * Copyright (C) 2009-2021 SonarSource SA
4  * mailto:info AT sonarsource DOT com
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 3 of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public License
17  * along with this program; if not, write to the Free Software Foundation,
18  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
19  */
20 package org.sonar.server.authentication;
21
22 import org.picocontainer.Startable;
23 import org.sonar.api.utils.log.Logger;
24 import org.sonar.api.utils.log.Loggers;
25 import org.sonar.db.DbClient;
26 import org.sonar.db.DbSession;
27 import org.sonar.db.user.UserDto;
28 import org.sonar.server.authentication.event.AuthenticationEvent;
29 import org.sonar.server.authentication.event.AuthenticationException;
30 import org.sonar.server.notification.NotificationManager;
31
32 import static org.sonar.server.log.ServerProcessLogging.STARTUP_LOGGER_NAME;
33 import static org.sonar.server.property.InternalProperties.DEFAULT_ADMIN_CREDENTIAL_USAGE_EMAIL;
34
35 /**
36  * Detect usage of an active admin account with default credential in order to ask this account to reset its password during authentication.
37  */
38 public class DefaultAdminCredentialsVerifierImpl implements DefaultAdminCredentialsVerifier {
39
40   private static final Logger LOGGER = Loggers.get(STARTUP_LOGGER_NAME);
41
42   private final DbClient dbClient;
43   private final CredentialsLocalAuthentication localAuthentication;
44   private final NotificationManager notificationManager;
45
46   public DefaultAdminCredentialsVerifierImpl(DbClient dbClient, CredentialsLocalAuthentication localAuthentication, NotificationManager notificationManager) {
47     this.dbClient = dbClient;
48     this.localAuthentication = localAuthentication;
49     this.notificationManager = notificationManager;
50   }
51
52   public void runAtStart() {
53     try (DbSession session = dbClient.openSession(false)) {
54       UserDto admin = getAdminUser(session);
55       if (admin == null || !isDefaultCredentialUser(session, admin)) {
56         return;
57       }
58       addWarningInSonarDotLog();
59       dbClient.userDao().update(session, admin.setResetPassword(true));
60       sendEmailToAdmins(session);
61       session.commit();
62     }
63   }
64
65   @Override
66   public boolean hasDefaultCredentialUser() {
67     try (DbSession session = dbClient.openSession(false)) {
68       UserDto admin = getAdminUser(session);
69       if (admin == null) {
70         return false;
71       } else {
72         return isDefaultCredentialUser(session, admin);
73       }
74     }
75   }
76
77   private UserDto getAdminUser(DbSession session) {
78     return dbClient.userDao().selectActiveUserByLogin(session, "admin");
79   }
80
81   private static void addWarningInSonarDotLog() {
82     String highlighter = "####################################################################################################################";
83     String msg = "Default Administrator credentials are still being used. Make sure to change the password or deactivate the account.";
84
85     LOGGER.warn(highlighter);
86     LOGGER.warn(msg);
87     LOGGER.warn(highlighter);
88   }
89
90   private boolean isDefaultCredentialUser(DbSession dbSession, UserDto user) {
91     try {
92       localAuthentication.authenticate(dbSession, user, "admin", AuthenticationEvent.Method.BASIC);
93       return true;
94     } catch (AuthenticationException ex) {
95       return false;
96     }
97   }
98
99   private void sendEmailToAdmins(DbSession session) {
100     if (dbClient.internalPropertiesDao().selectByKey(session, DEFAULT_ADMIN_CREDENTIAL_USAGE_EMAIL)
101       .map(Boolean::parseBoolean)
102       .orElse(false)) {
103       return;
104     }
105     notificationManager.scheduleForSending(new DefaultAdminCredentialsVerifierNotification());
106     dbClient.internalPropertiesDao().save(session, DEFAULT_ADMIN_CREDENTIAL_USAGE_EMAIL, Boolean.TRUE.toString());
107   }
108 }