]> source.dussan.org Git - sonarqube.git/blob
f74bcc637f2866999d6f95b737c301bf9aa457fd
[sonarqube.git] /
1 /*
2  * SonarQube
3  * Copyright (C) 2009-2020 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.qualityprofile.ws;
21
22 import java.io.IOException;
23 import java.io.Reader;
24 import java.io.Writer;
25 import javax.annotation.Nullable;
26 import org.apache.commons.io.IOUtils;
27 import org.junit.Rule;
28 import org.junit.Test;
29 import org.junit.rules.ExpectedException;
30 import org.sonar.api.resources.Languages;
31 import org.sonar.api.server.ws.WebService;
32 import org.sonar.db.DbSession;
33 import org.sonar.db.DbTester;
34 import org.sonar.db.organization.OrganizationDto;
35 import org.sonar.db.qualityprofile.QProfileDto;
36 import org.sonar.server.exceptions.ForbiddenException;
37 import org.sonar.server.exceptions.UnauthorizedException;
38 import org.sonar.server.language.LanguageTesting;
39 import org.sonar.server.organization.DefaultOrganizationProvider;
40 import org.sonar.server.organization.TestDefaultOrganizationProvider;
41 import org.sonar.server.qualityprofile.BulkChangeResult;
42 import org.sonar.server.qualityprofile.QProfileBackuper;
43 import org.sonar.server.qualityprofile.QProfileRestoreSummary;
44 import org.sonar.server.tester.UserSessionRule;
45 import org.sonar.server.ws.TestRequest;
46 import org.sonar.server.ws.TestResponse;
47 import org.sonar.server.ws.WsActionTester;
48 import org.sonar.test.JsonAssert;
49
50 import static org.assertj.core.api.Assertions.assertThat;
51 import static org.sonar.db.permission.GlobalPermission.ADMINISTER_QUALITY_PROFILES;
52
53 public class RestoreActionTest {
54
55   private static final String A_LANGUAGE = "xoo";
56
57   @Rule
58   public ExpectedException expectedException = ExpectedException.none();
59   @Rule
60   public DbTester db = DbTester.create();
61   @Rule
62   public UserSessionRule userSession = UserSessionRule.standalone();
63
64   private TestBackuper backuper = new TestBackuper();
65   private DefaultOrganizationProvider defaultOrganizationProvider = TestDefaultOrganizationProvider.from(db);
66   private Languages languages = LanguageTesting.newLanguages(A_LANGUAGE);
67   private WsActionTester tester = new WsActionTester(new RestoreAction(db.getDbClient(), backuper, languages, userSession));
68
69   @Test
70   public void test_definition() {
71     WebService.Action definition = tester.getDef();
72
73     assertThat(definition.key()).isEqualTo("restore");
74     assertThat(definition.isPost()).isTrue();
75     assertThat(definition.responseExampleAsString()).isNull();
76     assertThat(definition.description()).isNotEmpty();
77
78     // parameters
79     assertThat(definition.params()).hasSize(1);
80     WebService.Param backupParam = definition.param("backup");
81     assertThat(backupParam.isRequired()).isTrue();
82     assertThat(backupParam.since()).isNull();
83   }
84
85   @Test
86   public void profile_is_restored_on_default_organization_with_the_name_provided_in_backup() {
87     logInAsQProfileAdministrator();
88     TestResponse response = restore("<backup/>", null);
89
90     assertThat(backuper.restoredBackup).isEqualTo("<backup/>");
91     assertThat(backuper.restoredSummary.getProfile().getName()).isEqualTo("the-name-in-backup");
92     JsonAssert.assertJson(response.getInput()).isSimilarTo("{" +
93       "  \"profile\": {" +
94       "    \"name\": \"the-name-in-backup\"," +
95       "    \"language\": \"xoo\"," +
96       "    \"languageName\": \"Xoo\"," +
97       "    \"isDefault\": false," +
98       "    \"isInherited\": false" +
99       "  }," +
100       "  \"ruleSuccesses\": 0," +
101       "  \"ruleFailures\": 0" +
102       "}");
103   }
104
105   @Test
106   public void profile_is_restored_on_specified_organization_with_the_name_provided_in_backup() {
107     OrganizationDto org = db.organizations().insert();
108     logInAsQProfileAdministrator();
109     TestResponse response = restore("<backup/>", org.getKey());
110
111     assertThat(backuper.restoredBackup).isEqualTo("<backup/>");
112     assertThat(backuper.restoredSummary.getProfile().getName()).isEqualTo("the-name-in-backup");
113     JsonAssert.assertJson(response.getInput()).isSimilarTo("{" +
114       "  \"profile\": {" +
115       "    \"name\": \"the-name-in-backup\"," +
116       "    \"language\": \"xoo\"," +
117       "    \"languageName\": \"Xoo\"," +
118       "    \"isDefault\": false," +
119       "    \"isInherited\": false" +
120       "  }," +
121       "  \"ruleSuccesses\": 0," +
122       "  \"ruleFailures\": 0" +
123       "}");
124
125   }
126
127   @Test
128   public void throw_IAE_if_backup_is_missing() {
129     logInAsQProfileAdministrator();
130
131     expectedException.expect(IllegalArgumentException.class);
132     expectedException.expectMessage("A backup file must be provided");
133
134     tester.newRequest()
135       .setMethod("POST")
136       .execute();
137   }
138
139   @Test
140   public void throw_ForbiddenException_if_not_profile_administrator() {
141     userSession.logIn();
142
143     expectedException.expect(ForbiddenException.class);
144     expectedException.expectMessage("Insufficient privileges");
145
146     restore("<backup/>", null);
147   }
148
149   @Test
150   public void throw_UnauthorizedException_if_not_logged_in() {
151     userSession.anonymous();
152
153     expectedException.expect(UnauthorizedException.class);
154     expectedException.expectMessage("Authentication is required");
155
156     restore("<backup/>", null);
157   }
158
159   private void logInAsQProfileAdministrator() {
160     userSession
161       .logIn()
162       .addPermission(ADMINISTER_QUALITY_PROFILES);
163   }
164
165   private TestResponse restore(String backupContent, @Nullable String organizationKey) {
166     TestRequest request = tester.newRequest()
167       .setMethod("POST")
168       .setParam("backup", backupContent);
169     if (organizationKey != null) {
170       request.setParam("organization", organizationKey);
171     }
172     return request.execute();
173   }
174
175   private static class TestBackuper implements QProfileBackuper {
176
177     private String restoredBackup;
178     private QProfileRestoreSummary restoredSummary;
179
180     @Override
181     public void backup(DbSession dbSession, QProfileDto profile, Writer backupWriter) {
182       throw new UnsupportedOperationException();
183     }
184
185     @Override
186     public QProfileRestoreSummary restore(DbSession dbSession, Reader backup, @Nullable String overriddenProfileName) {
187       if (restoredSummary != null) {
188         throw new IllegalStateException("Already restored");
189       }
190       try {
191         restoredBackup = IOUtils.toString(backup);
192       } catch (IOException e) {
193         throw new IllegalStateException(e);
194       }
195       QProfileDto profile = new QProfileDto()
196         .setKee("P1")
197         .setRulesProfileUuid("rp-P1")
198         .setLanguage("xoo")
199         .setName(overriddenProfileName != null ? overriddenProfileName : "the-name-in-backup");
200       restoredSummary = new QProfileRestoreSummary(profile, new BulkChangeResult());
201       return restoredSummary;
202     }
203
204     @Override
205     public QProfileRestoreSummary restore(DbSession dbSession, Reader backup, QProfileDto profile) {
206       throw new UnsupportedOperationException();
207     }
208
209     @Override public QProfileRestoreSummary copy(DbSession dbSession, QProfileDto from, QProfileDto to) {
210       throw new UnsupportedOperationException();
211     }
212   }
213 }