]> source.dussan.org Git - sonarqube.git/blob
c43fdb7f61679726c09fb1a985d7898f4bb5d828
[sonarqube.git] /
1 /*
2  * SonarQube
3  * Copyright (C) 2009-2019 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 com.google.common.collect.ImmutableSet;
23 import org.junit.Rule;
24 import org.junit.Test;
25 import org.junit.rules.ExpectedException;
26 import org.sonar.api.config.internal.MapSettings;
27 import org.sonar.api.impl.utils.AlwaysIncreasingSystem2;
28 import org.sonar.api.resources.Qualifiers;
29 import org.sonar.api.resources.ResourceTypes;
30 import org.sonar.api.server.authentication.UserIdentity;
31 import org.sonar.api.utils.System2;
32 import org.sonar.db.DbTester;
33 import org.sonar.db.alm.AlmAppInstallDto;
34 import org.sonar.db.component.ResourceTypesRule;
35 import org.sonar.db.organization.OrganizationDto;
36 import org.sonar.db.user.UserDto;
37 import org.sonar.server.authentication.UserRegistration.ExistingEmailStrategy;
38 import org.sonar.server.authentication.event.AuthenticationEvent.Source;
39 import org.sonar.server.es.EsTester;
40 import org.sonar.server.organization.DefaultOrganizationProvider;
41 import org.sonar.server.organization.MemberUpdater;
42 import org.sonar.server.organization.OrganizationUpdater;
43 import org.sonar.server.organization.TestDefaultOrganizationProvider;
44 import org.sonar.server.organization.TestOrganizationFlags;
45 import org.sonar.server.permission.PermissionService;
46 import org.sonar.server.permission.PermissionServiceImpl;
47 import org.sonar.server.user.NewUserNotifier;
48 import org.sonar.server.user.UserUpdater;
49 import org.sonar.server.user.index.UserIndexer;
50 import org.sonar.server.usergroups.DefaultGroupFinder;
51
52 import static org.mockito.Mockito.mock;
53 import static org.sonar.db.alm.ALM.BITBUCKETCLOUD;
54 import static org.sonar.db.alm.ALM.GITHUB;
55 import static org.sonar.server.authentication.event.AuthenticationEvent.Method.BASIC;
56
57 public class UserRegistrarImplOrgMembershipSyncTest {
58
59   private System2 system2 = new AlwaysIncreasingSystem2();
60
61   private static String USER_LOGIN = "github-johndoo";
62
63   private static UserIdentity USER_IDENTITY = UserIdentity.builder()
64     .setProviderId("ABCD")
65     .setProviderLogin("johndoo")
66     .setLogin(USER_LOGIN)
67     .setName("John")
68     .setEmail("john@email.com")
69     .build();
70
71   private static TestIdentityProvider GITHUB_PROVIDER = new TestIdentityProvider()
72     .setKey("github")
73     .setName("Github")
74     .setEnabled(true)
75     .setAllowsUsersToSignUp(true);
76
77   private static TestIdentityProvider BITBUCKET_PROVIDER = new TestIdentityProvider()
78     .setKey("bitbucket")
79     .setName("Bitbucket")
80     .setEnabled(true)
81     .setAllowsUsersToSignUp(true);
82
83   private MapSettings settings = new MapSettings();
84
85   @Rule
86   public ExpectedException expectedException = ExpectedException.none();
87   @Rule
88   public DbTester db = DbTester.create(new AlwaysIncreasingSystem2());
89   @Rule
90   public EsTester es = EsTester.create();
91   private UserIndexer userIndexer = new UserIndexer(db.getDbClient(), es.client());
92   private DefaultOrganizationProvider defaultOrganizationProvider = TestDefaultOrganizationProvider.from(db);
93   private OrganizationUpdater organizationUpdater = mock(OrganizationUpdater.class);
94   private TestOrganizationFlags organizationFlags = TestOrganizationFlags.standalone();
95   private CredentialsLocalAuthentication localAuthentication = new CredentialsLocalAuthentication(db.getDbClient());
96   private UserUpdater userUpdater = new UserUpdater(
97     system2,
98     mock(NewUserNotifier.class),
99     db.getDbClient(),
100     userIndexer,
101     organizationFlags,
102     defaultOrganizationProvider,
103     new DefaultGroupFinder(db.getDbClient()),
104     settings.asConfig(),
105     localAuthentication);
106
107   private ResourceTypes resourceTypes = new ResourceTypesRule().setRootQualifiers(Qualifiers.PROJECT);
108   private PermissionService permissionService = new PermissionServiceImpl(resourceTypes);
109   private DefaultGroupFinder defaultGroupFinder = new DefaultGroupFinder(db.getDbClient());
110
111   private UserRegistrarImpl underTest = new UserRegistrarImpl(db.getDbClient(), userUpdater, defaultOrganizationProvider, organizationFlags,
112     defaultGroupFinder, new MemberUpdater(db.getDbClient(), defaultGroupFinder, userIndexer));
113
114   @Test
115   public void authenticate_new_github_user_syncs_organization() {
116     organizationFlags.setEnabled(true);
117     OrganizationDto organization = db.organizations().insert();
118     db.users().insertDefaultGroup(organization, "Members");
119     AlmAppInstallDto gitHubInstall = db.alm().insertAlmAppInstall(a -> a.setAlm(GITHUB));
120     db.alm().insertOrganizationAlmBinding(organization, gitHubInstall, true);
121
122     underTest.register(UserRegistration.builder()
123       .setUserIdentity(USER_IDENTITY)
124       .setProvider(GITHUB_PROVIDER)
125       .setSource(Source.realm(BASIC, GITHUB_PROVIDER.getName()))
126       .setExistingEmailStrategy(ExistingEmailStrategy.ALLOW)
127       .setOrganizationAlmIds(ImmutableSet.of(gitHubInstall.getOrganizationAlmId()))
128       .build());
129
130     UserDto user = db.users().selectUserByLogin(USER_LOGIN).get();
131     db.organizations().assertUserIsMemberOfOrganization(organization, user);
132   }
133
134   @Test
135   public void authenticate_new_github_user_does_not_sync_organization_when_no_org_alm_ids_provided() {
136     organizationFlags.setEnabled(true);
137     OrganizationDto organization = db.organizations().insert();
138     db.users().insertDefaultGroup(organization, "Members");
139     AlmAppInstallDto gitHubInstall = db.alm().insertAlmAppInstall(a -> a.setAlm(GITHUB));
140     db.alm().insertOrganizationAlmBinding(organization, gitHubInstall, true);
141
142     underTest.register(UserRegistration.builder()
143       .setUserIdentity(USER_IDENTITY)
144       .setProvider(GITHUB_PROVIDER)
145       .setSource(Source.realm(BASIC, GITHUB_PROVIDER.getName()))
146       .setExistingEmailStrategy(ExistingEmailStrategy.ALLOW)
147       .setOrganizationAlmIds(null)
148       .build());
149
150     UserDto user = db.users().selectUserByLogin(USER_LOGIN).get();
151     db.organizations().assertUserIsNotMemberOfOrganization(organization, user);
152   }
153
154   @Test
155   public void authenticate_new_bitbucket_user_does_not_sync_organization() {
156     organizationFlags.setEnabled(true);
157     OrganizationDto organization = db.organizations().insert();
158     db.users().insertDefaultGroup(organization, "Members");
159     AlmAppInstallDto gitHubInstall = db.alm().insertAlmAppInstall(a -> a.setAlm(BITBUCKETCLOUD));
160     db.alm().insertOrganizationAlmBinding(organization, gitHubInstall, true);
161
162     underTest.register(UserRegistration.builder()
163       .setUserIdentity(USER_IDENTITY)
164       .setProvider(BITBUCKET_PROVIDER)
165       .setSource(Source.realm(BASIC, BITBUCKET_PROVIDER.getName()))
166       .setExistingEmailStrategy(ExistingEmailStrategy.ALLOW)
167       .setOrganizationAlmIds(ImmutableSet.of(gitHubInstall.getOrganizationAlmId()))
168       .build());
169
170     UserDto user = db.users().selectUserByLogin(USER_LOGIN).get();
171     db.organizations().assertUserIsNotMemberOfOrganization(organization, user);
172   }
173
174   @Test
175   public void authenticate_new_user_using_unknown_alm_does_not_sync_organization() {
176     organizationFlags.setEnabled(true);
177     OrganizationDto organization = db.organizations().insert();
178     db.users().insertDefaultGroup(organization, "Members");
179     AlmAppInstallDto almAppInstall = db.alm().insertAlmAppInstall(a -> a.setAlm(GITHUB));
180     db.alm().insertOrganizationAlmBinding(organization, almAppInstall, true);
181     TestIdentityProvider identityProvider = new TestIdentityProvider()
182       .setKey("unknown")
183       .setName("unknown")
184       .setEnabled(true)
185       .setAllowsUsersToSignUp(true);
186
187     underTest.register(UserRegistration.builder()
188       .setUserIdentity(USER_IDENTITY)
189       .setProvider(identityProvider)
190       .setSource(Source.realm(BASIC, identityProvider.getName()))
191       .setExistingEmailStrategy(ExistingEmailStrategy.ALLOW)
192       .setOrganizationAlmIds(ImmutableSet.of(almAppInstall.getOrganizationAlmId()))
193       .build());
194
195     UserDto user = db.users().selectUserByLogin(USER_LOGIN).get();
196     db.organizations().assertUserIsNotMemberOfOrganization(organization, user);
197   }
198
199   @Test
200   public void authenticate_existing_github_user_does_not_sync_organization() {
201     organizationFlags.setEnabled(true);
202     OrganizationDto organization = db.organizations().insert();
203     db.users().insertDefaultGroup(organization, "Members");
204     AlmAppInstallDto gitHubInstall = db.alm().insertAlmAppInstall(a -> a.setAlm(GITHUB));
205     db.alm().insertOrganizationAlmBinding(organization, gitHubInstall, true);
206     UserDto user = db.users().insertUser(u -> u
207       .setLogin("Old login")
208       .setExternalId(USER_IDENTITY.getProviderId())
209       .setExternalIdentityProvider(GITHUB_PROVIDER.getKey()));
210
211     underTest.register(UserRegistration.builder()
212       .setUserIdentity(USER_IDENTITY)
213       .setProvider(GITHUB_PROVIDER)
214       .setSource(Source.local(BASIC))
215       .setExistingEmailStrategy(ExistingEmailStrategy.FORBID)
216       .setOrganizationAlmIds(ImmutableSet.of(gitHubInstall.getOrganizationAlmId()))
217       .build());
218
219     db.organizations().assertUserIsNotMemberOfOrganization(organization, user);
220   }
221
222   @Test
223   public void authenticate_disabled_github_user_syncs_organization() {
224     organizationFlags.setEnabled(true);
225     OrganizationDto organization = db.organizations().insert();
226     db.users().insertDefaultGroup(organization, "Members");
227     AlmAppInstallDto gitHubInstall = db.alm().insertAlmAppInstall(a -> a.setAlm(GITHUB));
228     db.alm().insertOrganizationAlmBinding(organization, gitHubInstall, true);
229     UserDto user = db.users().insertDisabledUser(u -> u.setLogin(USER_LOGIN));
230
231     underTest.register(UserRegistration.builder()
232       .setUserIdentity(USER_IDENTITY)
233       .setProvider(GITHUB_PROVIDER)
234       .setSource(Source.local(BASIC))
235       .setExistingEmailStrategy(ExistingEmailStrategy.FORBID)
236       .setOrganizationAlmIds(ImmutableSet.of(gitHubInstall.getOrganizationAlmId()))
237       .build());
238
239     db.organizations().assertUserIsMemberOfOrganization(organization, user);
240   }
241 }