]> source.dussan.org Git - sonarqube.git/commitdiff
Fix some quality flaws
authorSimon Brandhof <simon.brandhof@gmail.com>
Sat, 1 Feb 2014 17:15:45 +0000 (18:15 +0100)
committerSimon Brandhof <simon.brandhof@gmail.com>
Sat, 1 Feb 2014 21:54:25 +0000 (22:54 +0100)
60 files changed:
sonar-core/src/main/java/org/sonar/core/technicaldebt/DefaultTechnicalDebtManager.java
sonar-core/src/main/java/org/sonar/core/technicaldebt/db/CharacteristicDao.java
sonar-core/src/main/java/org/sonar/core/technicaldebt/db/CharacteristicMapper.java
sonar-deprecated/src/main/java/org/sonar/api/resources/ProjectUtils.java [new file with mode: 0644]
sonar-plugin-api/src/main/java/org/sonar/api/charts/ChartParameters.java
sonar-plugin-api/src/main/java/org/sonar/api/charts/package-info.java [new file with mode: 0644]
sonar-plugin-api/src/main/java/org/sonar/api/resources/ProjectUtils.java [deleted file]
sonar-server/src/main/java/org/sonar/server/charts/ChartFactory.java
sonar-server/src/main/java/org/sonar/server/charts/package-info.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/es/ESIndex.java
sonar-server/src/main/java/org/sonar/server/exceptions/package-info.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/group/GroupMembershipFinder.java [deleted file]
sonar-server/src/main/java/org/sonar/server/group/GroupMembershipQueryResult.java [deleted file]
sonar-server/src/main/java/org/sonar/server/group/InternalGroupMembershipService.java [deleted file]
sonar-server/src/main/java/org/sonar/server/group/package-info.java [deleted file]
sonar-server/src/main/java/org/sonar/server/issue/IssueChangelogFormatter.java
sonar-server/src/main/java/org/sonar/server/issue/ws/IssueShowWsHandler.java
sonar-server/src/main/java/org/sonar/server/platform/Platform.java
sonar-server/src/main/java/org/sonar/server/plugins/MimeTypes.java
sonar-server/src/main/java/org/sonar/server/startup/CleanDryRunCache.java [deleted file]
sonar-server/src/main/java/org/sonar/server/startup/CleanPreviewAnalysisCache.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/startup/ServerMetadataPersister.java
sonar-server/src/main/java/org/sonar/server/technicaldebt/DebtFormatter.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/technicaldebt/DebtService.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/technicaldebt/InternalRubyTechnicalDebtService.java [deleted file]
sonar-server/src/main/java/org/sonar/server/technicaldebt/TechnicalDebtFormatter.java [deleted file]
sonar-server/src/main/java/org/sonar/server/ui/CompatibilityRealm.java [deleted file]
sonar-server/src/main/java/org/sonar/server/ui/DatabaseSessionFilter.java [deleted file]
sonar-server/src/main/java/org/sonar/server/ui/SecurityRealmFactory.java [deleted file]
sonar-server/src/main/java/org/sonar/server/user/CompatibilityRealm.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/user/DatabaseSessionFilter.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/user/GroupMembershipFinder.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/user/GroupMembershipService.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/user/SecurityRealmFactory.java [new file with mode: 0644]
sonar-server/src/main/java/org/sonar/server/ws/ServletResponse.java
sonar-server/src/main/java/org/sonar/server/ws/WebServiceEngine.java
sonar-server/src/main/webapp/WEB-INF/app/models/internal.rb
sonar-server/src/main/webapp/WEB-INF/app/models/server.rb
sonar-server/src/main/webapp/WEB-INF/lib/need_authentication.rb
sonar-server/src/main/webapp/WEB-INF/web.xml
sonar-server/src/test/java/org/sonar/server/db/EmbeddedDatabaseFactoryTest.java
sonar-server/src/test/java/org/sonar/server/group/GroupMembershipFinderTest.java [deleted file]
sonar-server/src/test/java/org/sonar/server/group/InternalGroupMembershipServiceTest.java [deleted file]
sonar-server/src/test/java/org/sonar/server/issue/IssueChangelogFormatterTest.java
sonar-server/src/test/java/org/sonar/server/issue/ws/IssueShowWsHandlerTest.java
sonar-server/src/test/java/org/sonar/server/startup/CleanPreviewAnalysisCacheTest.java [new file with mode: 0644]
sonar-server/src/test/java/org/sonar/server/startup/ServerMetadataPersisterTest.java
sonar-server/src/test/java/org/sonar/server/technicaldebt/DebtFormatterTest.java [new file with mode: 0644]
sonar-server/src/test/java/org/sonar/server/technicaldebt/DebtServiceTest.java [new file with mode: 0644]
sonar-server/src/test/java/org/sonar/server/technicaldebt/InternalRubyTechnicalDebtServiceTest.java [deleted file]
sonar-server/src/test/java/org/sonar/server/technicaldebt/TechnicalDebtFormatterTest.java [deleted file]
sonar-server/src/test/java/org/sonar/server/ui/CompatibilityRealmTest.java [deleted file]
sonar-server/src/test/java/org/sonar/server/ui/SecurityRealmFactoryTest.java [deleted file]
sonar-server/src/test/java/org/sonar/server/user/CompatibilityRealmTest.java [new file with mode: 0644]
sonar-server/src/test/java/org/sonar/server/user/GroupMembershipFinderTest.java [new file with mode: 0644]
sonar-server/src/test/java/org/sonar/server/user/GroupMembershipServiceTest.java [new file with mode: 0644]
sonar-server/src/test/java/org/sonar/server/user/SecurityRealmFactoryTest.java [new file with mode: 0644]
sonar-server/src/test/java/org/sonar/server/ws/WebServiceEngineTest.java
sonar-server/src/test/resources/org/sonar/server/group/InternalGroupMembershipServiceTest/shared.xml [deleted file]
sonar-server/src/test/resources/org/sonar/server/user/GroupMembershipServiceTest/shared.xml [new file with mode: 0644]

index b417216bca35a765f6ce3afd982a4505088f8089..86913704cf3ca5e674d3d1daa4d3afded0cc31fa 100644 (file)
@@ -31,7 +31,6 @@ import org.sonar.core.technicaldebt.db.CharacteristicDto;
 
 import javax.annotation.CheckForNull;
 import javax.annotation.Nullable;
-
 import java.util.List;
 
 import static com.google.common.collect.Lists.newArrayList;
index fbac58d237c8464217f3922bb53b18efc253bfa9..c94f61d580b9e3ea5f02cb96af703ac6aa0ad536 100644 (file)
@@ -26,10 +26,9 @@ import org.sonar.api.ServerComponent;
 import org.sonar.core.persistence.MyBatis;
 
 import javax.annotation.CheckForNull;
-
 import java.util.List;
 
-public class CharacteristicDao implements BatchComponent, ServerComponent  {
+public class CharacteristicDao implements BatchComponent, ServerComponent {
 
   private final MyBatis mybatis;
 
@@ -75,7 +74,7 @@ public class CharacteristicDao implements BatchComponent, ServerComponent  {
   }
 
   @CheckForNull
-  public CharacteristicDto selectById(Integer id) {
+  public CharacteristicDto selectById(int id) {
     SqlSession session = mybatis.openSession();
     CharacteristicMapper mapper = session.getMapper(CharacteristicMapper.class);
     try {
index be97266890817ef07dfd6b18d456efd7721525b9..78b0e2b17c9bcb56892db90962bc214dd57aad7a 100644 (file)
@@ -30,7 +30,7 @@ public interface CharacteristicMapper {
 
   CharacteristicDto selectByKey(String key);
 
-  CharacteristicDto selectById(Integer id);
+  CharacteristicDto selectById(int id);
 
   CharacteristicDto selectByRuleId(Integer ruleId);
 
diff --git a/sonar-deprecated/src/main/java/org/sonar/api/resources/ProjectUtils.java b/sonar-deprecated/src/main/java/org/sonar/api/resources/ProjectUtils.java
new file mode 100644 (file)
index 0000000..7540d7d
--- /dev/null
@@ -0,0 +1,69 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.api.resources;
+
+import com.google.common.collect.Lists;
+import org.apache.commons.lang.StringUtils;
+
+import java.util.Collection;
+import java.util.List;
+
+/**
+ * @since 1.10
+ * @deprecated see method comments
+ */
+@Deprecated
+public final class ProjectUtils {
+
+  private ProjectUtils() {
+    // utility class with only static methods
+  }
+
+  /**
+   * @deprecated since 2.6 use JavaUtils.getTargetVersion() instead.
+   */
+  @Deprecated
+  public static String getJavaVersion(Project project) {
+    String version = project.getConfiguration() != null ? project.getConfiguration().getString("sonar.java.target") : null;
+    return StringUtils.isNotBlank(version) ? version : "1.5";
+  }
+
+  /**
+   * @deprecated since 2.6 use JavaUtils.getSourceVersion() instead.
+   */
+  @Deprecated
+  public static String getJavaSourceVersion(Project project) {
+    String version = project.getConfiguration() != null ? project.getConfiguration().getString("sonar.java.source") : null;
+    return StringUtils.isNotBlank(version) ? version : "1.5";
+  }
+
+  /**
+   * @since 2.7
+   * @deprecated in 4.2. Replaced by org.sonar.api.resources.InputFileUtils#toFiles()
+   */
+  @Deprecated
+  public static List<java.io.File> toIoFiles(Collection<InputFile> inputFiles) {
+    List<java.io.File> files = Lists.newArrayList();
+    for (InputFile inputFile : inputFiles) {
+      files.add(inputFile.getFile());
+    }
+    return files;
+  }
+}
index 71019742ef2d58bdb484bf846418711824a46223..0b299dbd426e3db80f8f917efd26931198467035 100644 (file)
@@ -49,7 +49,7 @@ public class ChartParameters {
   public static final int DEFAULT_HEIGHT = 200;
 
 
-  private Map<String, String> params;
+  private final Map<String, String> params;
 
   /**
    * Creates a ChartParameter based on a list of parameters
diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/charts/package-info.java b/sonar-plugin-api/src/main/java/org/sonar/api/charts/package-info.java
new file mode 100644 (file)
index 0000000..9d4eff6
--- /dev/null
@@ -0,0 +1,23 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+@ParametersAreNonnullByDefault
+package org.sonar.api.charts;
+
+import javax.annotation.ParametersAreNonnullByDefault;
diff --git a/sonar-plugin-api/src/main/java/org/sonar/api/resources/ProjectUtils.java b/sonar-plugin-api/src/main/java/org/sonar/api/resources/ProjectUtils.java
deleted file mode 100644 (file)
index fc75e6b..0000000
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.api.resources;
-
-import com.google.common.collect.Lists;
-import org.apache.commons.lang.StringUtils;
-
-import java.util.Collection;
-import java.util.List;
-
-/**
- * TODO Actually this class incorrectly named, because provides information not about project, but about Java project.
- *       And seems that only core plugins use this class.
- * 
- * @since 1.10
- */
-public final class ProjectUtils {
-
-  private ProjectUtils() {
-    // utility class with only static methods
-  }
-
-  /**
-   * @deprecated since 2.6 use JavaUtils.getTargetVersion() instead.
-   */
-  @Deprecated
-  public static String getJavaVersion(Project project) {
-    String version = project.getConfiguration() != null ? project.getConfiguration().getString("sonar.java.target") : null;
-    return StringUtils.isNotBlank(version) ? version : "1.5";
-  }
-
-  /**
-   * @deprecated since 2.6 use JavaUtils.getSourceVersion() instead.
-   */
-  @Deprecated
-  public static String getJavaSourceVersion(Project project) {
-    String version = project.getConfiguration() != null ? project.getConfiguration().getString("sonar.java.source") : null;
-    return StringUtils.isNotBlank(version) ? version : "1.5";
-  }
-
-  /**
-   * @since 2.7
-   */
-  public static List<java.io.File> toIoFiles(Collection<InputFile> inputFiles) {
-    List<java.io.File> files = Lists.newArrayList();
-    for (InputFile inputFile : inputFiles) {
-      files.add(inputFile.getFile());
-    }
-    return files;
-  }
-}
index 202b035dd88a265ba8dbd67218d4aeb4adf14468..87ac84d93cad97eacc557df75624458fdd916149 100644 (file)
@@ -25,11 +25,12 @@ import org.slf4j.LoggerFactory;
 import org.sonar.api.ServerComponent;
 import org.sonar.api.charts.Chart;
 
+import javax.annotation.CheckForNull;
 import java.util.Map;
 
 public final class ChartFactory implements ServerComponent {
   private static final Logger LOG = LoggerFactory.getLogger(ChartFactory.class);
-  private Map<String, Chart> chartsByKey = Maps.newHashMap();
+  private final Map<String, Chart> chartsByKey = Maps.newHashMap();
 
 
   public ChartFactory(Chart[] charts) {
@@ -47,6 +48,7 @@ public final class ChartFactory implements ServerComponent {
     // DO NOT SUPPRESS : used by picocontainer if no charts
   }
 
+  @CheckForNull
   public Chart getChart(String key) {
     return chartsByKey.get(key);
   }
diff --git a/sonar-server/src/main/java/org/sonar/server/charts/package-info.java b/sonar-server/src/main/java/org/sonar/server/charts/package-info.java
new file mode 100644 (file)
index 0000000..4991802
--- /dev/null
@@ -0,0 +1,23 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+@ParametersAreNonnullByDefault
+package org.sonar.server.charts;
+
+import javax.annotation.ParametersAreNonnullByDefault;
index 28edb3483a0be9637d6bde8885d7a0b031362ded..32e2872f8e75755ce1cc6d3453460a81c4abc81b 100644 (file)
@@ -60,27 +60,26 @@ public class ESIndex implements Startable {
 
   private static final String BULK_EXECUTE_FAILED = "Execution of bulk operation failed";
   private static final String BULK_INTERRUPTED = "Interrupted during bulk operation";
-
   private static final String PROFILE_DOMAIN = "es";
   private static final Logger LOG = LoggerFactory.getLogger(ESIndex.class);
 
-  private ESNode searchNode;
+  private final ESNode node;
+  private final Profiling profiling;
   private Client client;
-  private Profiling profiling;
 
-  public ESIndex(ESNode searchNode, Profiling profiling) {
-    this.searchNode = searchNode;
+  public ESIndex(ESNode node, Profiling profiling) {
+    this.node = node;
     this.profiling = profiling;
   }
 
   @Override
   public void start() {
-    this.client = searchNode.client();
+    this.client = node.client();
   }
 
   @Override
   public void stop() {
-    if(client != null) {
+    if (client != null) {
       client.close();
     }
   }
@@ -120,7 +119,7 @@ public class ESIndex implements Startable {
 
   public void bulkIndex(String index, String type, String[] ids, BytesStream[] sources) {
     BulkRequestBuilder builder = new BulkRequestBuilder(client);
-    for (int i=0; i<ids.length; i++) {
+    for (int i = 0; i < ids.length; i++) {
       builder.add(client.prepareIndex(index, type, ids[i]).setSource(sources[i].bytes()));
     }
     StopWatch watch = createWatch();
@@ -133,7 +132,7 @@ public class ESIndex implements Startable {
 
   public void bulkIndex(String index, String type, String[] ids, BytesStream[] sources, String[] parentIds) {
     BulkRequestBuilder builder = new BulkRequestBuilder(client);
-    for (int i=0; i<ids.length; i++) {
+    for (int i = 0; i < ids.length; i++) {
       builder.add(client.prepareIndex(index, type, ids[i]).setParent(parentIds[i]).setSource(sources[i].bytes()));
     }
     StopWatch watch = createWatch();
@@ -151,7 +150,7 @@ public class ESIndex implements Startable {
         throw new IllegalArgumentException("Could not load unexisting file at " + resourcePath);
       }
       addMapping(index, type, IOUtils.toString(resource));
-    } catch(IOException ioException) {
+    } catch (IOException ioException) {
       throw new IllegalArgumentException("Problem loading file at " + resourcePath, ioException);
     }
   }
@@ -160,7 +159,7 @@ public class ESIndex implements Startable {
     IndicesAdminClient indices = client.admin().indices();
     StopWatch watch = createWatch();
     try {
-      if (! indices.exists(indices.prepareExists(index).request()).get().isExists()) {
+      if (!indices.exists(indices.prepareExists(index).request()).get().isExists()) {
         indices.prepareCreate(index)
           .execute().actionGet();
       }
@@ -173,7 +172,7 @@ public class ESIndex implements Startable {
     watch = createWatch();
     try {
       indices.putMapping(Requests.putMappingRequest(index).type(type).source(mapping)).actionGet();
-    } catch(ElasticSearchParseException parseException) {
+    } catch (ElasticSearchParseException parseException) {
       throw new IllegalArgumentException("Invalid mapping file", parseException);
     } finally {
       watch.stop("put mapping on index '%s' for type '%s'", index, type);
@@ -248,7 +247,7 @@ public class ESIndex implements Startable {
   private String builderToString(SearchRequestBuilder builder) {
     try {
       return builder.internalBuilder().toXContent(XContentFactory.jsonBuilder(), ToXContent.EMPTY_PARAMS)
-          .humanReadable(false).string();
+        .humanReadable(false).string();
     } catch (IOException ioException) {
       LOG.warn("Could not serialize request: " + builder.internalBuilder().toString(), ioException);
       return "<IOException in serialize>";
@@ -273,7 +272,7 @@ public class ESIndex implements Startable {
       BulkResponse bulkResponse = client.bulk(builder.setRefresh(true).request()).get();
       if (bulkResponse.hasFailures()) {
         for (BulkItemResponse bulkItemResponse : bulkResponse.getItems()) {
-          if(bulkItemResponse.isFailed()) {
+          if (bulkItemResponse.isFailed()) {
             throw new IllegalStateException("Bulk operation partially executed: " + bulkItemResponse.getFailure().getMessage());
           }
         }
diff --git a/sonar-server/src/main/java/org/sonar/server/exceptions/package-info.java b/sonar-server/src/main/java/org/sonar/server/exceptions/package-info.java
new file mode 100644 (file)
index 0000000..643797f
--- /dev/null
@@ -0,0 +1,25 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+@ParametersAreNonnullByDefault
+package org.sonar.server.exceptions;
+
+import javax.annotation.ParametersAreNonnullByDefault;
+
diff --git a/sonar-server/src/main/java/org/sonar/server/group/GroupMembershipFinder.java b/sonar-server/src/main/java/org/sonar/server/group/GroupMembershipFinder.java
deleted file mode 100644 (file)
index 07c3d48..0000000
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-package org.sonar.server.group;
-
-import org.sonar.api.ServerComponent;
-import org.sonar.core.user.*;
-import org.sonar.server.exceptions.NotFoundException;
-
-import java.util.List;
-
-import static com.google.common.collect.Lists.newArrayList;
-
-public class GroupMembershipFinder implements ServerComponent {
-
-  private final UserDao userDao;
-  private final GroupMembershipDao groupMembershipDao;
-
-  public GroupMembershipFinder(UserDao userDao, GroupMembershipDao groupMembershipDao) {
-    this.userDao = userDao;
-    this.groupMembershipDao = groupMembershipDao;
-  }
-
-  public GroupMembershipQueryResult find(GroupMembershipQuery query) {
-    Long userId = userId(query.login());
-    int pageSize = query.pageSize();
-    int pageIndex = query.pageIndex();
-
-    int offset = (pageIndex - 1) * pageSize;
-    // Add one to page size in order to be able to know if there's more results or not
-    int limit = pageSize + 1;
-    List<GroupMembershipDto> dtos = groupMembershipDao.selectGroups(query, userId, offset, limit);
-    boolean hasMoreResults = false;
-    if (dtos.size() == limit) {
-      hasMoreResults = true;
-      // Removed last entry as it's only need to know if there more results or not
-      dtos.remove(dtos.size() - 1);
-    }
-    return new GroupMembershipQueryResult(toGroupMembership(dtos), hasMoreResults);
-  }
-
-  private Long userId(String login) {
-    UserDto userDto = userDao.selectActiveUserByLogin(login);
-    if (userDto == null) {
-      throw new NotFoundException("User '"+ login +"' does not exists.");
-    }
-    return userDto.getId();
-  }
-
-  private List<GroupMembership> toGroupMembership(List<GroupMembershipDto> dtos) {
-    List<GroupMembership> groups = newArrayList();
-    for (GroupMembershipDto groupMembershipDto : dtos) {
-      groups.add(groupMembershipDto.toGroupMembership());
-    }
-    return groups;
-  }
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/group/GroupMembershipQueryResult.java b/sonar-server/src/main/java/org/sonar/server/group/GroupMembershipQueryResult.java
deleted file mode 100644 (file)
index 647f0a2..0000000
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.group;
-
-import org.sonar.core.user.GroupMembership;
-
-import java.util.List;
-
-public class GroupMembershipQueryResult {
-
-  private List<GroupMembership> groups;
-  private boolean hasMoreResults;
-
-  public GroupMembershipQueryResult(List<GroupMembership> groups, boolean hasMoreResults) {
-    this.groups = groups;
-    this.hasMoreResults = hasMoreResults;
-  }
-
-  public List<GroupMembership> groups() {
-    return groups;
-  }
-
-  public boolean hasMoreResults() {
-    return hasMoreResults;
-  }
-
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/group/InternalGroupMembershipService.java b/sonar-server/src/main/java/org/sonar/server/group/InternalGroupMembershipService.java
deleted file mode 100644 (file)
index 1746f8d..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-package org.sonar.server.group;
-
-import org.sonar.api.ServerComponent;
-import org.sonar.core.user.GroupMembershipQuery;
-import org.sonar.server.util.RubyUtils;
-
-import java.util.Map;
-
-/**
- * Used by ruby code <pre>Internal.group_membership</pre>
- */
-public class InternalGroupMembershipService implements ServerComponent {
-
-  private static final String SELECTED_MEMBERSHIP = "selected";
-  private static final String DESELECTED_MEMBERSHIP = "deselected";
-
-  private final GroupMembershipFinder finder;
-
-  public InternalGroupMembershipService(GroupMembershipFinder finder) {
-    this.finder = finder;
-  }
-
-  public GroupMembershipQueryResult find(Map<String, Object> params) {
-    return finder.find(parseQuery(params));
-  }
-
-  private GroupMembershipQuery parseQuery(Map<String, Object> params) {
-    GroupMembershipQuery.Builder builder = GroupMembershipQuery.builder();
-    builder.membership(membership(params));
-    builder.groupSearch((String) params.get("query"));
-    builder.pageIndex(RubyUtils.toInteger(params.get("page")));
-    builder.pageSize(RubyUtils.toInteger(params.get("pageSize")));
-    builder.login((String) params.get("user"));
-    return builder.build();
-  }
-
-  private String membership(Map<String, Object> params) {
-    String selected = (String) params.get("selected");
-    if (SELECTED_MEMBERSHIP.equals(selected)) {
-      return GroupMembershipQuery.IN;
-    } else if (DESELECTED_MEMBERSHIP.equals(selected)) {
-      return GroupMembershipQuery.OUT;
-    } else {
-      return GroupMembershipQuery.ANY;
-    }
-  }
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/group/package-info.java b/sonar-server/src/main/java/org/sonar/server/group/package-info.java
deleted file mode 100644 (file)
index e27d339..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-@ParametersAreNonnullByDefault
-package org.sonar.server.group;
-
-import javax.annotation.ParametersAreNonnullByDefault;
-
index 037ba13280c03d629e408a91e5c69a35e8d9f59c..56d38affc159080f4e20fa373b01c9d170bde21f 100644 (file)
@@ -24,7 +24,7 @@ import org.sonar.api.issue.internal.FieldDiffs;
 import org.sonar.api.issue.internal.WorkDayDuration;
 import org.sonar.core.i18n.DefaultI18n;
 import org.sonar.core.issue.IssueUpdater;
-import org.sonar.server.technicaldebt.TechnicalDebtFormatter;
+import org.sonar.server.technicaldebt.DebtFormatter;
 
 import java.io.Serializable;
 import java.util.List;
@@ -38,11 +38,11 @@ public class IssueChangelogFormatter implements ServerComponent {
   private static final String ISSUE_CHANGELOG_FIELD = "issue.changelog.field.";
 
   private final DefaultI18n defaultI18n;
-  private final TechnicalDebtFormatter technicalDebtFormatter;
+  private final DebtFormatter debtFormatter;
 
-  public IssueChangelogFormatter(DefaultI18n defaultI18n, TechnicalDebtFormatter technicalDebtFormatter) {
+  public IssueChangelogFormatter(DefaultI18n defaultI18n, DebtFormatter debtFormatter) {
     this.defaultI18n = defaultI18n;
-    this.technicalDebtFormatter = technicalDebtFormatter;
+    this.debtFormatter = debtFormatter;
   }
 
   public List<String> format(Locale locale, FieldDiffs diffs) {
@@ -74,10 +74,10 @@ public class IssueChangelogFormatter implements ServerComponent {
     String oldValueString = oldValue != null && !"".equals(oldValue) ? oldValue.toString() : null;
     if (IssueUpdater.TECHNICAL_DEBT.equals(key)) {
       if (newValueString != null) {
-        newValueString = technicalDebtFormatter.format(locale, WorkDayDuration.fromLong(Long.parseLong(newValueString)));
+        newValueString = debtFormatter.format(locale, WorkDayDuration.fromLong(Long.parseLong(newValueString)));
       }
       if (oldValueString != null) {
-        oldValueString = technicalDebtFormatter.format(locale, WorkDayDuration.fromLong(Long.parseLong(oldValueString)));
+        oldValueString = debtFormatter.format(locale, WorkDayDuration.fromLong(Long.parseLong(oldValueString)));
       }
     }
     return new IssueChangelogDiffFormat(oldValueString, newValueString);
index ff0a494ba4bee44723db62d01441cfc0398573b4..46e1c997b7049bf0f6addc9a3d6e89ee3ab795af 100644 (file)
@@ -42,12 +42,11 @@ import org.sonar.server.issue.ActionService;
 import org.sonar.server.issue.IssueChangelog;
 import org.sonar.server.issue.IssueChangelogService;
 import org.sonar.server.issue.IssueService;
-import org.sonar.server.technicaldebt.TechnicalDebtFormatter;
+import org.sonar.server.technicaldebt.DebtFormatter;
 import org.sonar.server.user.UserSession;
 
 import javax.annotation.CheckForNull;
 import javax.annotation.Nullable;
-
 import java.util.Arrays;
 import java.util.Date;
 import java.util.List;
@@ -60,17 +59,17 @@ public class IssueShowWsHandler implements RequestHandler {
   private final IssueService issueService;
   private final IssueChangelogService issueChangelogService;
   private final ActionService actionService;
-  private final TechnicalDebtFormatter technicalDebtFormatter;
+  private final DebtFormatter debtFormatter;
   private final DefaultTechnicalDebtManager technicalDebtManager;
   private final I18n i18n;
 
   public IssueShowWsHandler(IssueFinder issueFinder, IssueService issueService, IssueChangelogService issueChangelogService, ActionService actionService,
-                            TechnicalDebtFormatter technicalDebtFormatter, DefaultTechnicalDebtManager technicalDebtManager, I18n i18n) {
+                            DebtFormatter debtFormatter, DefaultTechnicalDebtManager technicalDebtManager, I18n i18n) {
     this.issueFinder = issueFinder;
     this.issueService = issueService;
     this.issueChangelogService = issueChangelogService;
     this.actionService = actionService;
-    this.technicalDebtFormatter = technicalDebtFormatter;
+    this.debtFormatter = debtFormatter;
     this.technicalDebtManager = technicalDebtManager;
     this.i18n = i18n;
   }
@@ -122,7 +121,7 @@ public class IssueShowWsHandler implements RequestHandler {
       .prop("severity", issue.severity())
       .prop("author", issue.authorLogin())
       .prop("actionPlan", actionPlanKey)
-      .prop("debt", technicalDebt != null ? technicalDebtFormatter.format(UserSession.get().locale(), technicalDebt) : null)
+      .prop("debt", technicalDebt != null ? debtFormatter.format(UserSession.get().locale(), technicalDebt) : null)
       .prop("actionPlanName", actionPlanKey != null ? result.actionPlan(issue).name() : null)
       .prop("creationDate", DateUtils.formatDateTime(issue.creationDate()))
       .prop("fCreationDate", formatDate(issue.creationDate()))
index 597ec30f4093070f1515830d80bcb4daeae0f03f..513be22291e494997ff18b2adb7f1ac363f9ff55 100644 (file)
@@ -74,15 +74,12 @@ import org.sonar.jpa.session.ThreadLocalDatabaseSessionFactory;
 import org.sonar.server.charts.ChartFactory;
 import org.sonar.server.component.DefaultComponentFinder;
 import org.sonar.server.component.DefaultRubyComponentService;
-import org.sonar.server.qualityprofile.ProfilesManager;
 import org.sonar.server.db.EmbeddedDatabaseFactory;
 import org.sonar.server.db.migrations.DatabaseMigration;
 import org.sonar.server.db.migrations.DatabaseMigrations;
 import org.sonar.server.db.migrations.DatabaseMigrator;
 import org.sonar.server.es.ESIndex;
 import org.sonar.server.es.ESNode;
-import org.sonar.server.group.GroupMembershipFinder;
-import org.sonar.server.group.InternalGroupMembershipService;
 import org.sonar.server.issue.*;
 import org.sonar.server.issue.filter.IssueFilterService;
 import org.sonar.server.issue.filter.IssueFilterWs;
@@ -104,13 +101,15 @@ import org.sonar.server.source.SourceService;
 import org.sonar.server.source.ws.SourcesShowWsHandler;
 import org.sonar.server.source.ws.SourcesWs;
 import org.sonar.server.startup.*;
-import org.sonar.server.technicaldebt.InternalRubyTechnicalDebtService;
-import org.sonar.server.technicaldebt.TechnicalDebtFormatter;
+import org.sonar.server.technicaldebt.DebtFormatter;
+import org.sonar.server.technicaldebt.DebtService;
 import org.sonar.server.text.MacroInterpreter;
 import org.sonar.server.text.RubyTextService;
-import org.sonar.server.ui.*;
-import org.sonar.server.user.DefaultUserService;
-import org.sonar.server.user.NewUserNotifier;
+import org.sonar.server.ui.JRubyI18n;
+import org.sonar.server.ui.JRubyProfiling;
+import org.sonar.server.ui.PageDecorations;
+import org.sonar.server.ui.Views;
+import org.sonar.server.user.*;
 import org.sonar.server.util.*;
 import org.sonar.server.ws.ListingWs;
 import org.sonar.server.ws.WebServiceEngine;
@@ -299,7 +298,7 @@ public final class Platform {
     servicesContainer.addSingleton(DefaultUserService.class);
 
     // groups
-    servicesContainer.addSingleton(InternalGroupMembershipService.class);
+    servicesContainer.addSingleton(GroupMembershipService.class);
     servicesContainer.addSingleton(GroupMembershipFinder.class);
 
     // permissions
@@ -362,12 +361,12 @@ public final class Platform {
     servicesContainer.addSingleton(RuleTagsWs.class);
 
     // technical debt
-    servicesContainer.addSingleton(InternalRubyTechnicalDebtService.class);
+    servicesContainer.addSingleton(DebtService.class);
     servicesContainer.addSingleton(TechnicalDebtModelSynchronizer.class);
     servicesContainer.addSingleton(TechnicalDebtModelRepository.class);
     servicesContainer.addSingleton(TechnicalDebtXMLImporter.class);
     servicesContainer.addSingleton(TechnicalDebtConverter.class);
-    servicesContainer.addSingleton(TechnicalDebtFormatter.class);
+    servicesContainer.addSingleton(DebtFormatter.class);
     servicesContainer.addSingleton(DefaultTechnicalDebtManager.class);
 
     // source
@@ -426,7 +425,7 @@ public final class Platform {
     startupContainer.addSingleton(RenameDeprecatedPropertyKeys.class);
     startupContainer.addSingleton(LogServerId.class);
     startupContainer.addSingleton(RegisterServletFilters.class);
-    startupContainer.addSingleton(CleanDryRunCache.class);
+    startupContainer.addSingleton(CleanPreviewAnalysisCache.class);
     startupContainer.startComponents();
 
     startupContainer.getComponentByType(ServerLifecycleNotifier.class).notifyStart();
index e1cffe96c99673aa6019c26e4d1d9d7bba8ce817..7ad624f820ae6529d106727b6a89a860b1750ff3 100644 (file)
@@ -31,10 +31,15 @@ import java.util.Map;
  */
 public final class MimeTypes {
   private MimeTypes() {
+    // only static methods
   }
 
+  public static final String JSON = "application/json";
+  public static final String XML = "application/xml";
+  public static final String DEFAULT = "application/octet-stream";
+
   private static final Map<String, String> MAP = new ImmutableMap.Builder<String, String>()
-    .put("json", "application/json")
+    .put("json", JSON)
     .put("zip", "application/zip")
     .put("tgz", "application/tgz")
     .put("ps", "application/postscript")
@@ -43,7 +48,7 @@ public final class MimeTypes {
     .put("xls", "application/vnd.ms-excel")
     .put("ppt", "application/vnd.ms-powerpoint")
     .put("tar", "application/x-tar")
-    .put("xml", "application/xml")
+    .put("xml", XML)
     .put("dtd", "application/xml-dtd")
     .put("xslt", "application/xslt+xml")
     .put("bmp", "image/bmp")
@@ -63,8 +68,6 @@ public final class MimeTypes {
     .put("tsv", "text/tab-separated-values")
     .build();
 
-  public static final String DEFAULT = "application/octet-stream";
-
   public static String getByFilename(String filename) {
     String extension = FilenameUtils.getExtension(filename);
     String mime = null;
diff --git a/sonar-server/src/main/java/org/sonar/server/startup/CleanDryRunCache.java b/sonar-server/src/main/java/org/sonar/server/startup/CleanDryRunCache.java
deleted file mode 100644 (file)
index d70003e..0000000
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.startup;
-
-import org.sonar.core.preview.PreviewCache;
-
-/**
- * @since 4.0
- */
-public class CleanDryRunCache {
-
-  private PreviewCache dryRunCache;
-
-  public CleanDryRunCache(PreviewCache dryRunCache) {
-    this.dryRunCache = dryRunCache;
-  }
-
-  public void start() {
-    dryRunCache.cleanAll();
-  }
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/startup/CleanPreviewAnalysisCache.java b/sonar-server/src/main/java/org/sonar/server/startup/CleanPreviewAnalysisCache.java
new file mode 100644 (file)
index 0000000..e386cde
--- /dev/null
@@ -0,0 +1,45 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.startup;
+
+import org.picocontainer.Startable;
+import org.sonar.core.preview.PreviewCache;
+
+/**
+ * @since 4.0
+ */
+public class CleanPreviewAnalysisCache implements Startable {
+
+  private final PreviewCache cache;
+
+  public CleanPreviewAnalysisCache(PreviewCache cache) {
+    this.cache = cache;
+  }
+
+  @Override
+  public void start() {
+    cache.cleanAll();
+  }
+
+  @Override
+  public void stop() {
+    // nothing
+  }
+}
index 6ef13983f50b324fd999c7f5853bcc1087bf855e..231a3c8e05ed203b201f25d7154c27576f7379a0 100644 (file)
@@ -20,6 +20,7 @@
 package org.sonar.server.startup;
 
 import com.google.common.collect.ImmutableMap;
+import org.picocontainer.Startable;
 import org.slf4j.LoggerFactory;
 import org.sonar.api.CoreProperties;
 import org.sonar.api.platform.Server;
@@ -27,7 +28,7 @@ import org.sonar.server.platform.PersistentSettings;
 
 import java.text.SimpleDateFormat;
 
-public final class ServerMetadataPersister {
+public final class ServerMetadataPersister implements Startable {
 
   private final Server server;
   private final PersistentSettings persistentSettings;
@@ -37,6 +38,7 @@ public final class ServerMetadataPersister {
     this.persistentSettings = persistentSettings;
   }
 
+  @Override
   public void start() {
     LoggerFactory.getLogger(getClass()).debug("Persisting server metadata");
     persistentSettings.saveProperties(ImmutableMap.of(
@@ -44,4 +46,9 @@ public final class ServerMetadataPersister {
       CoreProperties.SERVER_VERSION, server.getVersion(),
       CoreProperties.SERVER_STARTTIME, new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ").format(server.getStartedAt())));
   }
+
+  @Override
+  public void stop() {
+    // nothing
+  }
 }
diff --git a/sonar-server/src/main/java/org/sonar/server/technicaldebt/DebtFormatter.java b/sonar-server/src/main/java/org/sonar/server/technicaldebt/DebtFormatter.java
new file mode 100644 (file)
index 0000000..5a44a0f
--- /dev/null
@@ -0,0 +1,57 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+package org.sonar.server.technicaldebt;
+
+import org.sonar.api.ServerComponent;
+import org.sonar.api.issue.internal.WorkDayDuration;
+import org.sonar.core.i18n.DefaultI18n;
+
+import java.util.Locale;
+
+public class DebtFormatter implements ServerComponent {
+
+  private final DefaultI18n defaultI18n;
+
+  public DebtFormatter(DefaultI18n defaultI18n) {
+    this.defaultI18n = defaultI18n;
+  }
+
+  public String format(Locale locale, WorkDayDuration technicalDebt) {
+    StringBuilder message = new StringBuilder();
+    if (technicalDebt.days() > 0) {
+      message.append(defaultI18n.message(locale, "issue.technical_debt.x_days", null, technicalDebt.days()));
+    }
+    if (technicalDebt.hours() > 0) {
+      if (message.length() > 0) {
+        message.append(" ");
+      }
+      message.append(defaultI18n.message(locale, "issue.technical_debt.x_hours", null, technicalDebt.hours()));
+    }
+    // Do not display minutes if days is not null to not have too much information
+    if (technicalDebt.minutes() > 0 && technicalDebt.days() == 0) {
+      if (message.length() > 0) {
+        message.append(" ");
+      }
+      message.append(defaultI18n.message(locale, "issue.technical_debt.x_minutes", null, technicalDebt.minutes()));
+    }
+    return message.toString();
+  }
+}
diff --git a/sonar-server/src/main/java/org/sonar/server/technicaldebt/DebtService.java b/sonar-server/src/main/java/org/sonar/server/technicaldebt/DebtService.java
new file mode 100644 (file)
index 0000000..464214c
--- /dev/null
@@ -0,0 +1,64 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+package org.sonar.server.technicaldebt;
+
+import org.sonar.api.ServerComponent;
+import org.sonar.api.issue.internal.WorkDayDuration;
+import org.sonar.api.rules.Rule;
+import org.sonar.api.technicaldebt.server.Characteristic;
+import org.sonar.core.technicaldebt.DefaultTechnicalDebtManager;
+import org.sonar.server.user.UserSession;
+
+import javax.annotation.CheckForNull;
+import java.util.List;
+
+public class DebtService implements ServerComponent {
+
+  private final DebtFormatter debtFormatter;
+  private final DefaultTechnicalDebtManager finder;
+
+  public DebtService(DebtFormatter debtFormatter, DefaultTechnicalDebtManager finder) {
+    this.debtFormatter = debtFormatter;
+    this.finder = finder;
+  }
+
+  public String format(WorkDayDuration technicalDebt) {
+    return debtFormatter.format(UserSession.get().locale(), technicalDebt);
+  }
+
+  public WorkDayDuration toTechnicalDebt(String technicalDebtInLong) {
+    return WorkDayDuration.fromLong(Long.parseLong(technicalDebtInLong));
+  }
+
+  public List<Characteristic> findRootCharacteristics() {
+    return finder.findRootCharacteristics();
+  }
+
+  public Characteristic findRequirement(Rule rule) {
+    return finder.findRequirementByRule(rule);
+  }
+
+  @CheckForNull
+  public Characteristic findCharacteristic(int id) {
+    return finder.findCharacteristicById(id);
+  }
+
+}
diff --git a/sonar-server/src/main/java/org/sonar/server/technicaldebt/InternalRubyTechnicalDebtService.java b/sonar-server/src/main/java/org/sonar/server/technicaldebt/InternalRubyTechnicalDebtService.java
deleted file mode 100644 (file)
index 6d87744..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-package org.sonar.server.technicaldebt;
-
-import org.sonar.api.ServerComponent;
-import org.sonar.api.issue.internal.WorkDayDuration;
-import org.sonar.api.rules.Rule;
-import org.sonar.api.technicaldebt.server.Characteristic;
-import org.sonar.core.technicaldebt.DefaultTechnicalDebtManager;
-import org.sonar.server.user.UserSession;
-
-import java.util.List;
-
-public class InternalRubyTechnicalDebtService implements ServerComponent {
-
-  private final TechnicalDebtFormatter technicalDebtFormatter;
-  private final DefaultTechnicalDebtManager finder;
-
-  public InternalRubyTechnicalDebtService(TechnicalDebtFormatter technicalDebtFormatter, DefaultTechnicalDebtManager finder) {
-    this.technicalDebtFormatter = technicalDebtFormatter;
-    this.finder = finder;
-  }
-
-  public String format(WorkDayDuration technicalDebt) {
-    return technicalDebtFormatter.format(UserSession.get().locale(), technicalDebt);
-  }
-
-  public WorkDayDuration toTechnicalDebt(String technicalDebtInLong) {
-    return WorkDayDuration.fromLong(Long.parseLong(technicalDebtInLong));
-  }
-
-  public List<Characteristic> findRootCharacteristics() {
-    return finder.findRootCharacteristics();
-  }
-
-  public Characteristic findRequirement(Rule rule) {
-    return finder.findRequirementByRule(rule);
-  }
-
-  public Characteristic findCharacteristic(Integer id) {
-    return finder.findCharacteristicById(id);
-  }
-
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/technicaldebt/TechnicalDebtFormatter.java b/sonar-server/src/main/java/org/sonar/server/technicaldebt/TechnicalDebtFormatter.java
deleted file mode 100644 (file)
index 6c77f0d..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-package org.sonar.server.technicaldebt;
-
-import org.sonar.api.ServerComponent;
-import org.sonar.api.issue.internal.WorkDayDuration;
-import org.sonar.core.i18n.DefaultI18n;
-
-import java.util.Locale;
-
-public class TechnicalDebtFormatter implements ServerComponent {
-
-  private final DefaultI18n defaultI18n;
-
-  public TechnicalDebtFormatter(DefaultI18n defaultI18n) {
-    this.defaultI18n = defaultI18n;
-  }
-
-  public String format(Locale locale, WorkDayDuration technicalDebt) {
-    StringBuilder message = new StringBuilder();
-    if (technicalDebt.days() > 0) {
-      message.append(defaultI18n.message(locale, "issue.technical_debt.x_days", null, technicalDebt.days()));
-    }
-    if (technicalDebt.hours() > 0) {
-      if (message.length() > 0) {
-        message.append(" ");
-      }
-      message.append(defaultI18n.message(locale, "issue.technical_debt.x_hours", null, technicalDebt.hours()));
-    }
-    // Do not display minutes if days is not null to not have too much information
-    if (technicalDebt.minutes() > 0 && technicalDebt.days() == 0) {
-      if (message.length() > 0) {
-        message.append(" ");
-      }
-      message.append(defaultI18n.message(locale, "issue.technical_debt.x_minutes", null, technicalDebt.minutes()));
-    }
-    return message.toString();
-  }
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/ui/CompatibilityRealm.java b/sonar-server/src/main/java/org/sonar/server/ui/CompatibilityRealm.java
deleted file mode 100644 (file)
index 73d85bf..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.ui;
-
-import org.sonar.api.security.LoginPasswordAuthenticator;
-import org.sonar.api.security.SecurityRealm;
-
-/**
- * Provides backward compatibility for {@link org.sonar.api.CoreProperties#CORE_AUTHENTICATOR_CLASS}.
- *
- * @since 2.14
- */
-class CompatibilityRealm extends SecurityRealm {
-  private final LoginPasswordAuthenticator authenticator;
-
-  public CompatibilityRealm(LoginPasswordAuthenticator authenticator) {
-    this.authenticator = authenticator;
-  }
-
-  @Override
-  public void init() {
-    authenticator.init();
-  }
-
-  @Override
-  public String getName() {
-    return "CompatibilityRealm[" + authenticator.getClass().getName() + "]";
-  }
-
-  @Override
-  public LoginPasswordAuthenticator getLoginPasswordAuthenticator() {
-    return authenticator;
-  }
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/ui/DatabaseSessionFilter.java b/sonar-server/src/main/java/org/sonar/server/ui/DatabaseSessionFilter.java
deleted file mode 100644 (file)
index f6f0893..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.ui;
-
-import org.sonar.jpa.session.DatabaseSessionFactory;
-import org.sonar.server.platform.Platform;
-
-import java.io.IOException;
-import javax.servlet.*;
-
-public class DatabaseSessionFilter implements Filter {
-  @Override
-  public void init(FilterConfig filterConfig) throws ServletException {
-    // nothing to do
-  }
-
-  @Override
-  public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
-    chain.doFilter(request, response);
-
-    DatabaseSessionFactory sessionFactory = Platform.component(DatabaseSessionFactory.class);
-    if (sessionFactory != null) {
-      sessionFactory.clear();
-    }
-  }
-
-  @Override
-  public void destroy() {
-    // nothing to do
-  }
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/ui/SecurityRealmFactory.java b/sonar-server/src/main/java/org/sonar/server/ui/SecurityRealmFactory.java
deleted file mode 100644 (file)
index f3baa37..0000000
+++ /dev/null
@@ -1,118 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.ui;
-
-import org.apache.commons.lang.StringUtils;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-import org.sonar.api.CoreProperties;
-import org.sonar.api.ServerComponent;
-import org.sonar.api.config.Settings;
-import org.sonar.api.security.LoginPasswordAuthenticator;
-import org.sonar.api.security.SecurityRealm;
-import org.sonar.api.utils.SonarException;
-
-/**
- * @since 2.14
- */
-public class SecurityRealmFactory implements ServerComponent {
-
-  private static final Logger INFO = LoggerFactory.getLogger("org.sonar.INFO");
-
-  private final boolean ignoreStartupFailure;
-  private final SecurityRealm realm;
-
-  public SecurityRealmFactory(Settings settings, SecurityRealm[] realms, LoginPasswordAuthenticator[] authenticators) {
-    ignoreStartupFailure = settings.getBoolean(CoreProperties.CORE_AUTHENTICATOR_IGNORE_STARTUP_FAILURE);
-    String realmName = settings.getString(CoreProperties.CORE_AUTHENTICATOR_REALM);
-    String className = settings.getString(CoreProperties.CORE_AUTHENTICATOR_CLASS);
-    SecurityRealm selectedRealm = null;
-    if (!StringUtils.isEmpty(realmName)) {
-      selectedRealm = selectRealm(realms, realmName);
-      if (selectedRealm == null) {
-        throw new SonarException("Realm '" + realmName + "' not found. Please check the property '" + CoreProperties.CORE_AUTHENTICATOR_REALM + "' in conf/sonar.properties");
-      }
-    }
-    if (selectedRealm == null && !StringUtils.isEmpty(className)) {
-      LoginPasswordAuthenticator authenticator = selectAuthenticator(authenticators, className);
-      if (authenticator == null) {
-        throw new SonarException("Authenticator '" + className + "' not found. Please check the property '" + CoreProperties.CORE_AUTHENTICATOR_CLASS
-          + "' in conf/sonar.properties");
-      }
-      selectedRealm = new CompatibilityRealm(authenticator);
-    }
-    realm = selectedRealm;
-  }
-
-  public SecurityRealmFactory(Settings settings, LoginPasswordAuthenticator[] authenticators) {
-    this(settings, null, authenticators);
-  }
-
-  public SecurityRealmFactory(Settings settings, SecurityRealm[] realms) {
-    this(settings, realms, null);
-  }
-
-  public SecurityRealmFactory(Settings settings) {
-    this(settings, null, null);
-  }
-
-  public void start() {
-    if (realm != null) {
-      try {
-        INFO.info("Security realm: " + realm.getName());
-        realm.init();
-        INFO.info("Security realm started");
-      } catch (RuntimeException e) {
-        if (ignoreStartupFailure) {
-          INFO.error("IGNORED - Security realm fails to start: " + e.getMessage());
-        } else {
-          throw new SonarException("Security realm fails to start: " + e.getMessage(), e);
-        }
-      }
-    }
-  }
-
-  public SecurityRealm getRealm() {
-    return realm;
-  }
-
-  private static SecurityRealm selectRealm(SecurityRealm[] realms, String realmName) {
-    if (realms != null) {
-      for (SecurityRealm realm : realms) {
-        if (StringUtils.equals(realmName, realm.getName())) {
-          return realm;
-        }
-      }
-    }
-    return null;
-  }
-
-  private static LoginPasswordAuthenticator selectAuthenticator(LoginPasswordAuthenticator[] authenticators, String className) {
-    if (authenticators != null) {
-      for (LoginPasswordAuthenticator lpa : authenticators) {
-        if (lpa.getClass().getName().equals(className)) {
-          return lpa;
-        }
-      }
-    }
-    return null;
-  }
-
-}
diff --git a/sonar-server/src/main/java/org/sonar/server/user/CompatibilityRealm.java b/sonar-server/src/main/java/org/sonar/server/user/CompatibilityRealm.java
new file mode 100644 (file)
index 0000000..e56ea97
--- /dev/null
@@ -0,0 +1,51 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.user;
+
+import org.sonar.api.security.LoginPasswordAuthenticator;
+import org.sonar.api.security.SecurityRealm;
+
+/**
+ * Provides backward compatibility for {@link org.sonar.api.CoreProperties#CORE_AUTHENTICATOR_CLASS}.
+ *
+ * @since 2.14
+ */
+class CompatibilityRealm extends SecurityRealm {
+  private final LoginPasswordAuthenticator authenticator;
+
+  public CompatibilityRealm(LoginPasswordAuthenticator authenticator) {
+    this.authenticator = authenticator;
+  }
+
+  @Override
+  public void init() {
+    authenticator.init();
+  }
+
+  @Override
+  public String getName() {
+    return "CompatibilityRealm[" + authenticator.getClass().getName() + "]";
+  }
+
+  @Override
+  public LoginPasswordAuthenticator getLoginPasswordAuthenticator() {
+    return authenticator;
+  }
+}
diff --git a/sonar-server/src/main/java/org/sonar/server/user/DatabaseSessionFilter.java b/sonar-server/src/main/java/org/sonar/server/user/DatabaseSessionFilter.java
new file mode 100644 (file)
index 0000000..83b43ff
--- /dev/null
@@ -0,0 +1,48 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.user;
+
+import org.sonar.jpa.session.DatabaseSessionFactory;
+import org.sonar.server.platform.Platform;
+
+import javax.servlet.*;
+import java.io.IOException;
+
+public class DatabaseSessionFilter implements Filter {
+  @Override
+  public void init(FilterConfig filterConfig) throws ServletException {
+    // nothing to do
+  }
+
+  @Override
+  public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
+    chain.doFilter(request, response);
+
+    DatabaseSessionFactory sessionFactory = Platform.component(DatabaseSessionFactory.class);
+    if (sessionFactory != null) {
+      sessionFactory.clear();
+    }
+  }
+
+  @Override
+  public void destroy() {
+    // nothing to do
+  }
+}
diff --git a/sonar-server/src/main/java/org/sonar/server/user/GroupMembershipFinder.java b/sonar-server/src/main/java/org/sonar/server/user/GroupMembershipFinder.java
new file mode 100644 (file)
index 0000000..1aaca4e
--- /dev/null
@@ -0,0 +1,92 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+package org.sonar.server.user;
+
+import org.sonar.api.ServerComponent;
+import org.sonar.core.user.*;
+import org.sonar.server.exceptions.NotFoundException;
+
+import java.util.List;
+
+import static com.google.common.collect.Lists.newArrayList;
+
+public class GroupMembershipFinder implements ServerComponent {
+
+  public static class Membership {
+    private List<GroupMembership> groups;
+    private boolean hasMoreResults;
+
+    private Membership(List<GroupMembership> groups, boolean hasMoreResults) {
+      this.groups = groups;
+      this.hasMoreResults = hasMoreResults;
+    }
+
+    public List<GroupMembership> groups() {
+      return groups;
+    }
+
+    public boolean hasMoreResults() {
+      return hasMoreResults;
+    }
+  }
+
+  private final UserDao userDao;
+  private final GroupMembershipDao groupMembershipDao;
+
+  public GroupMembershipFinder(UserDao userDao, GroupMembershipDao groupMembershipDao) {
+    this.userDao = userDao;
+    this.groupMembershipDao = groupMembershipDao;
+  }
+
+  public Membership find(GroupMembershipQuery query) {
+    Long userId = userId(query.login());
+    int pageSize = query.pageSize();
+    int pageIndex = query.pageIndex();
+
+    int offset = (pageIndex - 1) * pageSize;
+    // Add one to page size in order to be able to know if there's more results or not
+    int limit = pageSize + 1;
+    List<GroupMembershipDto> dtos = groupMembershipDao.selectGroups(query, userId, offset, limit);
+    boolean hasMoreResults = false;
+    if (dtos.size() == limit) {
+      hasMoreResults = true;
+      // Removed last entry as it's only need to know if there more results or not
+      dtos.remove(dtos.size() - 1);
+    }
+    return new Membership(toGroupMembership(dtos), hasMoreResults);
+  }
+
+  private Long userId(String login) {
+    UserDto userDto = userDao.selectActiveUserByLogin(login);
+    if (userDto == null) {
+      throw new NotFoundException("User '" + login + "' does not exists.");
+    }
+    return userDto.getId();
+  }
+
+  private List<GroupMembership> toGroupMembership(List<GroupMembershipDto> dtos) {
+    List<GroupMembership> groups = newArrayList();
+    for (GroupMembershipDto groupMembershipDto : dtos) {
+      groups.add(groupMembershipDto.toGroupMembership());
+    }
+    return groups;
+  }
+}
diff --git a/sonar-server/src/main/java/org/sonar/server/user/GroupMembershipService.java b/sonar-server/src/main/java/org/sonar/server/user/GroupMembershipService.java
new file mode 100644 (file)
index 0000000..ec32e47
--- /dev/null
@@ -0,0 +1,67 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+package org.sonar.server.user;
+
+import org.sonar.api.ServerComponent;
+import org.sonar.core.user.GroupMembershipQuery;
+import org.sonar.server.util.RubyUtils;
+
+import java.util.Map;
+
+/**
+ * Used by ruby code <pre>Internal.group_membership</pre>
+ */
+public class GroupMembershipService implements ServerComponent {
+
+  private static final String SELECTED_MEMBERSHIP = "selected";
+  private static final String DESELECTED_MEMBERSHIP = "deselected";
+
+  private final GroupMembershipFinder finder;
+
+  public GroupMembershipService(GroupMembershipFinder finder) {
+    this.finder = finder;
+  }
+
+  public GroupMembershipFinder.Membership find(Map<String, Object> params) {
+    return finder.find(parseQuery(params));
+  }
+
+  private GroupMembershipQuery parseQuery(Map<String, Object> params) {
+    GroupMembershipQuery.Builder builder = GroupMembershipQuery.builder();
+    builder.membership(membership(params));
+    builder.groupSearch((String) params.get("query"));
+    builder.pageIndex(RubyUtils.toInteger(params.get("page")));
+    builder.pageSize(RubyUtils.toInteger(params.get("pageSize")));
+    builder.login((String) params.get("user"));
+    return builder.build();
+  }
+
+  private String membership(Map<String, Object> params) {
+    String selected = (String) params.get("selected");
+    if (SELECTED_MEMBERSHIP.equals(selected)) {
+      return GroupMembershipQuery.IN;
+    } else if (DESELECTED_MEMBERSHIP.equals(selected)) {
+      return GroupMembershipQuery.OUT;
+    } else {
+      return GroupMembershipQuery.ANY;
+    }
+  }
+}
diff --git a/sonar-server/src/main/java/org/sonar/server/user/SecurityRealmFactory.java b/sonar-server/src/main/java/org/sonar/server/user/SecurityRealmFactory.java
new file mode 100644 (file)
index 0000000..7b048cd
--- /dev/null
@@ -0,0 +1,118 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.user;
+
+import org.apache.commons.lang.StringUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.sonar.api.CoreProperties;
+import org.sonar.api.ServerComponent;
+import org.sonar.api.config.Settings;
+import org.sonar.api.security.LoginPasswordAuthenticator;
+import org.sonar.api.security.SecurityRealm;
+import org.sonar.api.utils.SonarException;
+
+/**
+ * @since 2.14
+ */
+public class SecurityRealmFactory implements ServerComponent {
+
+  private static final Logger INFO = LoggerFactory.getLogger("org.sonar.INFO");
+
+  private final boolean ignoreStartupFailure;
+  private final SecurityRealm realm;
+
+  public SecurityRealmFactory(Settings settings, SecurityRealm[] realms, LoginPasswordAuthenticator[] authenticators) {
+    ignoreStartupFailure = settings.getBoolean(CoreProperties.CORE_AUTHENTICATOR_IGNORE_STARTUP_FAILURE);
+    String realmName = settings.getString(CoreProperties.CORE_AUTHENTICATOR_REALM);
+    String className = settings.getString(CoreProperties.CORE_AUTHENTICATOR_CLASS);
+    SecurityRealm selectedRealm = null;
+    if (!StringUtils.isEmpty(realmName)) {
+      selectedRealm = selectRealm(realms, realmName);
+      if (selectedRealm == null) {
+        throw new SonarException("Realm '" + realmName + "' not found. Please check the property '" + CoreProperties.CORE_AUTHENTICATOR_REALM + "' in conf/sonar.properties");
+      }
+    }
+    if (selectedRealm == null && !StringUtils.isEmpty(className)) {
+      LoginPasswordAuthenticator authenticator = selectAuthenticator(authenticators, className);
+      if (authenticator == null) {
+        throw new SonarException("Authenticator '" + className + "' not found. Please check the property '" + CoreProperties.CORE_AUTHENTICATOR_CLASS
+          + "' in conf/sonar.properties");
+      }
+      selectedRealm = new CompatibilityRealm(authenticator);
+    }
+    realm = selectedRealm;
+  }
+
+  public SecurityRealmFactory(Settings settings, LoginPasswordAuthenticator[] authenticators) {
+    this(settings, null, authenticators);
+  }
+
+  public SecurityRealmFactory(Settings settings, SecurityRealm[] realms) {
+    this(settings, realms, null);
+  }
+
+  public SecurityRealmFactory(Settings settings) {
+    this(settings, null, null);
+  }
+
+  public void start() {
+    if (realm != null) {
+      try {
+        INFO.info("Security realm: " + realm.getName());
+        realm.init();
+        INFO.info("Security realm started");
+      } catch (RuntimeException e) {
+        if (ignoreStartupFailure) {
+          INFO.error("IGNORED - Security realm fails to start: " + e.getMessage());
+        } else {
+          throw new SonarException("Security realm fails to start: " + e.getMessage(), e);
+        }
+      }
+    }
+  }
+
+  public SecurityRealm getRealm() {
+    return realm;
+  }
+
+  private static SecurityRealm selectRealm(SecurityRealm[] realms, String realmName) {
+    if (realms != null) {
+      for (SecurityRealm realm : realms) {
+        if (StringUtils.equals(realmName, realm.getName())) {
+          return realm;
+        }
+      }
+    }
+    return null;
+  }
+
+  private static LoginPasswordAuthenticator selectAuthenticator(LoginPasswordAuthenticator[] authenticators, String className) {
+    if (authenticators != null) {
+      for (LoginPasswordAuthenticator lpa : authenticators) {
+        if (lpa.getClass().getName().equals(className)) {
+          return lpa;
+        }
+      }
+    }
+    return null;
+  }
+
+}
index d884d0753a74da667a9c526d06464abb398939d1..a30d890caf09d10e2cebc7ff02d6177a4fbfac5c 100644 (file)
@@ -22,6 +22,7 @@ package org.sonar.server.ws;
 import org.sonar.api.server.ws.Response;
 import org.sonar.api.utils.text.JsonWriter;
 import org.sonar.api.utils.text.XmlWriter;
+import org.sonar.server.plugins.MimeTypes;
 
 import javax.annotation.CheckForNull;
 import java.io.ByteArrayOutputStream;
@@ -75,13 +76,13 @@ public class ServletResponse implements Response {
 
   @Override
   public JsonWriter newJsonWriter() {
-    stream.setMediaType("application/json");
+    stream.setMediaType(MimeTypes.JSON);
     return JsonWriter.of(new OutputStreamWriter(stream.output()));
   }
 
   @Override
   public XmlWriter newXmlWriter() {
-    stream.setMediaType("application/xml");
+    stream.setMediaType(MimeTypes.XML);
     return XmlWriter.of(new OutputStreamWriter(stream.output()));
   }
 
index 760d8b74f7cce9807625d2c1406e0537bc019b10..e8f19b7c03eb263acddf4022a69c66393865ed65 100644 (file)
@@ -27,6 +27,7 @@ import org.sonar.api.server.ws.WebService;
 import org.sonar.api.utils.text.JsonWriter;
 import org.sonar.server.exceptions.BadRequestException;
 import org.sonar.server.exceptions.ServerException;
+import org.sonar.server.plugins.MimeTypes;
 
 import javax.servlet.http.HttpServletResponse;
 import java.io.OutputStreamWriter;
@@ -110,7 +111,7 @@ public class WebServiceEngine implements ServerComponent, Startable {
     ServletResponse.ServletStream stream = response.stream();
     stream.reset();
     stream.setStatus(status);
-    stream.setMediaType("application/json");
+    stream.setMediaType(MimeTypes.JSON);
     JsonWriter json = JsonWriter.of(new OutputStreamWriter(stream.output()));
     try {
       json.beginObject();
index 4c56be7800dab8a0c4303796cba11b4fded0ecb9..b169243bb19682c74968dab48dd6865f553c9735 100644 (file)
@@ -55,7 +55,7 @@ class Internal
   end
 
   def self.technical_debt
-    component(Java::OrgSonarServerTechnicaldebt::InternalRubyTechnicalDebtService.java_class)
+    component(Java::OrgSonarServerTechnicaldebt::DebtService.java_class)
   end
 
   def self.profiling
@@ -63,7 +63,7 @@ class Internal
   end
 
   def self.group_membership
-    component(Java::OrgSonarServerGroup::InternalGroupMembershipService.java_class)
+    component(Java::OrgSonarServerUser::GroupMembershipService.java_class)
   end
 
   def self.quality_profiles
index a1acde9f0ce915d1c42dfc7a50c4742c8cd5e5a8..b95ef772adb8797e6654503d075437de66d14a51 100644 (file)
@@ -25,60 +25,60 @@ class Server
 
   def system_info
     system_info=[]
-    add_property(system_info, 'System date') {java.util.Date.new()}
-    add_property(system_info, 'JVM Vendor') {java.lang.management.ManagementFactory.getRuntimeMXBean().getVmVendor()}
-    add_property(system_info, 'JVM Name') {java.lang.management.ManagementFactory.getRuntimeMXBean().getVmName()}
-    add_property(system_info, 'JVM Version') {java.lang.management.ManagementFactory.getRuntimeMXBean().getVmVersion() }
-    add_property(system_info, 'Java Version') {java_property('java.runtime.version') }
-    add_property(system_info, 'Java Home') {java_property('java.home')}
-    add_property(system_info, 'JIT Compiler') {java_property('java.compiler')}
-    add_property(system_info, 'Application Server Container') {$servlet_context.getServerInfo()  }
-    add_property(system_info, 'User Name') {java_property('user.name')}
-    add_property(system_info, 'User TimeZone') {java_property('user.timezone')}
-    add_property(system_info, 'OS') {"#{java_property('os.name')} / #{java_property('os.arch')} / #{java_property('os.version')}"}
-    add_property(system_info, 'Processors') {java.lang.Runtime.getRuntime().availableProcessors()}
-    add_property(system_info, 'System Classpath') {java.lang.management.ManagementFactory.getRuntimeMXBean().getClassPath()}
-    add_property(system_info, 'Boot Classpath') {java.lang.management.ManagementFactory.getRuntimeMXBean().getBootClassPath() }
-    add_property(system_info, 'Library Path') {java.lang.management.ManagementFactory.getRuntimeMXBean().getLibraryPath()  }
+    add_property(system_info, 'System date') { java.util.Date.new() }
+    add_property(system_info, 'JVM Vendor') { java.lang.management.ManagementFactory.getRuntimeMXBean().getVmVendor() }
+    add_property(system_info, 'JVM Name') { java.lang.management.ManagementFactory.getRuntimeMXBean().getVmName() }
+    add_property(system_info, 'JVM Version') { java.lang.management.ManagementFactory.getRuntimeMXBean().getVmVersion() }
+    add_property(system_info, 'Java Version') { java_property('java.runtime.version') }
+    add_property(system_info, 'Java Home') { java_property('java.home') }
+    add_property(system_info, 'JIT Compiler') { java_property('java.compiler') }
+    add_property(system_info, 'Application Server Container') { $servlet_context.getServerInfo() }
+    add_property(system_info, 'User Name') { java_property('user.name') }
+    add_property(system_info, 'User TimeZone') { java_property('user.timezone') }
+    add_property(system_info, 'OS') { "#{java_property('os.name')} / #{java_property('os.arch')} / #{java_property('os.version')}" }
+    add_property(system_info, 'Processors') { java.lang.Runtime.getRuntime().availableProcessors() }
+    add_property(system_info, 'System Classpath') { java.lang.management.ManagementFactory.getRuntimeMXBean().getClassPath() }
+    add_property(system_info, 'Boot Classpath') { java.lang.management.ManagementFactory.getRuntimeMXBean().getBootClassPath() }
+    add_property(system_info, 'Library Path') { java.lang.management.ManagementFactory.getRuntimeMXBean().getLibraryPath() }
     system_info
   end
 
   def system_statistics
     system_statistics=[]
-    add_property(system_statistics, 'Total Memory') {"#{java.lang.Runtime.getRuntime().totalMemory() / 1000000} MB"}
-    add_property(system_statistics, 'Free Memory') {"#{java.lang.Runtime.getRuntime().freeMemory() / 1000000} MB"}
-    add_property(system_statistics, 'Max Memory') {"#{java.lang.Runtime.getRuntime().maxMemory() / 1000000} MB"}
-    add_property(system_statistics, 'Heap') {"#{java.lang.management.ManagementFactory.getMemoryMXBean().getHeapMemoryUsage()}"}
-    add_property(system_statistics, 'Non Heap') {"#{java.lang.management.ManagementFactory.getMemoryMXBean().getNonHeapMemoryUsage()}"}
-    add_property(system_statistics, 'System Load Average (last minute)') {system_load_average()}
-    add_property(system_statistics, 'Loaded Classes (currently/total/unloaded)') {"#{java.lang.management.ManagementFactory.getClassLoadingMXBean().getLoadedClassCount()} / #{java.lang.management.ManagementFactory.getClassLoadingMXBean().getTotalLoadedClassCount()} / #{java.lang.management.ManagementFactory.getClassLoadingMXBean().getUnloadedClassCount()}"}
-    add_property(system_statistics, 'Start Time') {"#{format_date(java.util.Date.new(java.lang.management.ManagementFactory.getRuntimeMXBean().getStartTime()))}"}
-    add_property(system_statistics, 'Threads (total/peak/daemon)') {"#{java.lang.management.ManagementFactory.getThreadMXBean().getThreadCount()} / #{java.lang.management.ManagementFactory.getThreadMXBean().getPeakThreadCount()} / #{java.lang.management.ManagementFactory.getThreadMXBean().getDaemonThreadCount() }" }
+    add_property(system_statistics, 'Total Memory') { "#{java.lang.Runtime.getRuntime().totalMemory() / 1000000} MB" }
+    add_property(system_statistics, 'Free Memory') { "#{java.lang.Runtime.getRuntime().freeMemory() / 1000000} MB" }
+    add_property(system_statistics, 'Max Memory') { "#{java.lang.Runtime.getRuntime().maxMemory() / 1000000} MB" }
+    add_property(system_statistics, 'Heap') { "#{java.lang.management.ManagementFactory.getMemoryMXBean().getHeapMemoryUsage()}" }
+    add_property(system_statistics, 'Non Heap') { "#{java.lang.management.ManagementFactory.getMemoryMXBean().getNonHeapMemoryUsage()}" }
+    add_property(system_statistics, 'System Load Average (last minute)') { system_load_average() }
+    add_property(system_statistics, 'Loaded Classes (currently/total/unloaded)') { "#{java.lang.management.ManagementFactory.getClassLoadingMXBean().getLoadedClassCount()} / #{java.lang.management.ManagementFactory.getClassLoadingMXBean().getTotalLoadedClassCount()} / #{java.lang.management.ManagementFactory.getClassLoadingMXBean().getUnloadedClassCount()}" }
+    add_property(system_statistics, 'Start Time') { "#{format_date(java.util.Date.new(java.lang.management.ManagementFactory.getRuntimeMXBean().getStartTime()))}" }
+    add_property(system_statistics, 'Threads (total/peak/daemon)') { "#{java.lang.management.ManagementFactory.getThreadMXBean().getThreadCount()} / #{java.lang.management.ManagementFactory.getThreadMXBean().getPeakThreadCount()} / #{java.lang.management.ManagementFactory.getThreadMXBean().getDaemonThreadCount() }" }
     system_statistics
   end
 
   def sonar_info
     sonar_info=[]
-    add_property(sonar_info, 'Server ID') {sonar_property(ServerIdConfigurationController::PROPERTY_SERVER_ID)}
-    add_property(sonar_info, 'Version') {org.sonar.server.platform.Platform.getServer().getVersion()}
-    add_property(sonar_info, 'Started at') {org.sonar.server.platform.Platform.getServer().getStartedAt()}
-    add_property(sonar_info, 'Database') {"#{jdbc_metadata. getDatabaseProductName()} #{jdbc_metadata. getDatabaseProductVersion()}"}
-    add_property(sonar_info, 'Database URL') {sonar_property('sonar.jdbc.url')}
-    add_property(sonar_info, 'Database Login') {sonar_property('sonar.jdbc.username')}
-    add_property(sonar_info, 'Database Driver') {"#{jdbc_metadata.getDriverName()} #{jdbc_metadata.getDriverVersion()}"}
-    add_property(sonar_info, 'Database Driver Class') {sonar_property('sonar.jdbc.driverClassName')}
-    add_property(sonar_info, 'Database Dialect (Hibernate)') {"#{Java::OrgSonarServerUi::JRubyFacade.getInstance().getDatabase().getDialect().getId()} (#{Java::OrgSonarServerUi::JRubyFacade.getInstance().getDatabase().getDialect().getHibernateDialectClass().getName()})"}
-    add_property(sonar_info, 'External User Authentication') {realm_name}
-    add_property(sonar_info, 'Automatic User Creation') {sonar_property(org.sonar.api.CoreProperties.CORE_AUTHENTICATOR_CREATE_USERS)}
-    add_property(sonar_info, 'Allow Users to Sign Up') {sonar_property(org.sonar.api.CoreProperties.CORE_ALLOW_USERS_TO_SIGNUP_PROPERTY)}
-    add_property(sonar_info, 'Force Authentication') {sonar_property(org.sonar.api.CoreProperties.CORE_FORCE_AUTHENTICATION_PROPERTY)}
+    add_property(sonar_info, 'Server ID') { sonar_property(ServerIdConfigurationController::PROPERTY_SERVER_ID) }
+    add_property(sonar_info, 'Version') { org.sonar.server.platform.Platform.getServer().getVersion() }
+    add_property(sonar_info, 'Started at') { org.sonar.server.platform.Platform.getServer().getStartedAt() }
+    add_property(sonar_info, 'Database') { "#{jdbc_metadata.getDatabaseProductName()} #{jdbc_metadata.getDatabaseProductVersion()}" }
+    add_property(sonar_info, 'Database URL') { sonar_property('sonar.jdbc.url') }
+    add_property(sonar_info, 'Database Login') { sonar_property('sonar.jdbc.username') }
+    add_property(sonar_info, 'Database Driver') { "#{jdbc_metadata.getDriverName()} #{jdbc_metadata.getDriverVersion()}" }
+    add_property(sonar_info, 'Database Driver Class') { sonar_property('sonar.jdbc.driverClassName') }
+    add_property(sonar_info, 'Database Dialect (Hibernate)') { "#{Java::OrgSonarServerUi::JRubyFacade.getInstance().getDatabase().getDialect().getId()} (#{Java::OrgSonarServerUi::JRubyFacade.getInstance().getDatabase().getDialect().getHibernateDialectClass().getName()})" }
+    add_property(sonar_info, 'External User Authentication') { realm_name }
+    add_property(sonar_info, 'Automatic User Creation') { sonar_property(org.sonar.api.CoreProperties.CORE_AUTHENTICATOR_CREATE_USERS) }
+    add_property(sonar_info, 'Allow Users to Sign Up') { sonar_property(org.sonar.api.CoreProperties.CORE_ALLOW_USERS_TO_SIGNUP_PROPERTY) }
+    add_property(sonar_info, 'Force Authentication') { sonar_property(org.sonar.api.CoreProperties.CORE_FORCE_AUTHENTICATION_PROPERTY) }
     sonar_info
   end
 
   def sonar_plugins
     sonar_plugins=[]
-    Java::OrgSonarServerUi::JRubyFacade.getInstance().getPluginsMetadata().select{|plugin| !plugin.isCore()}.sort.each do |plugin|
-      add_property(sonar_plugins, plugin.getName()) {plugin.getVersion()}
+    Java::OrgSonarServerUi::JRubyFacade.getInstance().getPluginsMetadata().select { |plugin| !plugin.isCore() }.sort.each do |plugin|
+      add_property(sonar_plugins, plugin.getName()) { plugin.getVersion() }
     end
     sonar_plugins
   end
@@ -87,13 +87,12 @@ class Server
     system_properties=[]
     keys=java.lang.System.getProperties().keySet().sort
     keys.each do |key|
-      add_property(system_properties, key) {java.lang.System.getProperty(key)}
+      add_property(system_properties, key) { java.lang.System.getProperty(key) }
     end
     system_properties
   end
 
 
-
   private
 
   def java_property(key)
@@ -112,7 +111,7 @@ class Server
   end
 
   def format_double(d)
-   (d * 10).to_i / 10.0
+    (d * 10).to_i / 10.0
   end
 
   def format_date(date)
@@ -124,7 +123,7 @@ class Server
   end
 
   def realm_name
-    realm_factory = Api::Utils.java_facade.getCoreComponentByClassname('org.sonar.server.ui.SecurityRealmFactory')
+    realm_factory = Api::Utils.java_facade.getCoreComponentByClassname('org.sonar.server.user.SecurityRealmFactory')
     if realm_factory && realm_factory.getRealm()
       realm_factory.getRealm().getName()
     else
index 9daae83263c26370154f207355d6f262661dcc1c..4e3cfa3b114d08c73c42cb412f43487f84167875 100644 (file)
@@ -186,7 +186,7 @@ class RealmFactory
 
   def self.realm
     if @@realm.nil?
-      realm_factory = Api::Utils.java_facade.getCoreComponentByClassname('org.sonar.server.ui.SecurityRealmFactory')
+      realm_factory = Api::Utils.java_facade.getCoreComponentByClassname('org.sonar.server.user.SecurityRealmFactory')
       if realm_factory
         component = realm_factory.getRealm()
         @@realm = component ? PluginRealm.new(component) : DefaultRealm.new
index 6f130d298c4e6731a330f2f83f60016e97067332..26b0dc019b4596e60f4bb3a0a69dfe7fb429ea4f 100644 (file)
@@ -37,7 +37,7 @@
   </filter>
   <filter>
     <filter-name>DatabaseSessionFilter</filter-name>
-    <filter-class>org.sonar.server.ui.DatabaseSessionFilter</filter-class>
+    <filter-class>org.sonar.server.user.DatabaseSessionFilter</filter-class>
   </filter>
   <filter>
     <filter-name>UserSessionFilter</filter-name>
index 79ed485350dffae6341df971327f150410d703be..ed43851aea66f059680153aad23fc94f37c66ae3 100644 (file)
 
 package org.sonar.server.db;
 
-import org.junit.Before;
 import org.junit.Test;
 import org.sonar.api.config.Settings;
 import org.sonar.api.database.DatabaseProperties;
 
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.never;
-import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.*;
 
 public class EmbeddedDatabaseFactoryTest {
 
-  private Settings settings;
-
-  @Before
-  public void initSettings() {
-    settings = new Settings();
-  }
+  Settings settings = new Settings();
 
   @Test
   public void should_start_and_stop_tcp_h2_database() throws Exception {
diff --git a/sonar-server/src/test/java/org/sonar/server/group/GroupMembershipFinderTest.java b/sonar-server/src/test/java/org/sonar/server/group/GroupMembershipFinderTest.java
deleted file mode 100644 (file)
index 874d9f1..0000000
+++ /dev/null
@@ -1,122 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-package org.sonar.server.group;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.ArgumentCaptor;
-import org.mockito.Mock;
-import org.mockito.runners.MockitoJUnitRunner;
-import org.sonar.core.user.*;
-
-import static com.google.common.collect.Lists.newArrayList;
-import static org.fest.assertions.Assertions.assertThat;
-import static org.mockito.Matchers.*;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.when;
-
-@RunWith(MockitoJUnitRunner.class)
-public class GroupMembershipFinderTest {
-
-  @Mock
-  UserDao userDao;
-
-  @Mock
-  GroupMembershipDao groupMembershipDao;
-
-  GroupMembershipFinder finder;
-
-  @Before
-  public void setUp() throws Exception {
-    when(userDao.selectActiveUserByLogin("arthur")).thenReturn(new UserDto().setId(100L).setName("arthur"));
-    finder = new GroupMembershipFinder(userDao, groupMembershipDao);
-  }
-
-  @Test
-  public void find() throws Exception {
-    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").build();
-    when(groupMembershipDao.selectGroups(eq(query), anyLong(), anyInt(), anyInt())).thenReturn(
-      newArrayList(new GroupMembershipDto().setId(1L).setName("users").setUserId(100L))
-    );
-
-    GroupMembershipQueryResult result = finder.find(query);
-    assertThat(result.groups()).hasSize(1);
-    assertThat(result.hasMoreResults()).isFalse();
-
-    GroupMembership group = result.groups().get(0);
-    assertThat(group.id()).isEqualTo(1);
-    assertThat(group.name()).isEqualTo("users");
-    assertThat(group.isMember()).isTrue();
-  }
-
-  @Test
-  public void find_with_paging() throws Exception {
-    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").pageIndex(3).pageSize(10).build();
-    finder.find(query);
-
-    ArgumentCaptor<Integer> argumentOffset = ArgumentCaptor.forClass(Integer.class);
-    ArgumentCaptor<Integer> argumentLimit = ArgumentCaptor.forClass(Integer.class);
-    verify(groupMembershipDao).selectGroups(eq(query), anyLong(), argumentOffset.capture(), argumentLimit.capture());
-
-    assertThat(argumentOffset.getValue()).isEqualTo(20);
-    assertThat(argumentLimit.getValue()).isEqualTo(11);
-  }
-
-  @Test
-  public void find_with_paging_having_more_results() throws Exception {
-    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").pageIndex(1).pageSize(2).build();
-    when(groupMembershipDao.selectGroups(eq(query), anyLong(), anyInt(), anyInt())).thenReturn(newArrayList(
-      new GroupMembershipDto().setId(1L).setName("group1"),
-      new GroupMembershipDto().setId(2L).setName("group2"),
-      new GroupMembershipDto().setId(3L).setName("group3"))
-    );
-    GroupMembershipQueryResult result = finder.find(query);
-
-    ArgumentCaptor<Integer> argumentOffset = ArgumentCaptor.forClass(Integer.class);
-    ArgumentCaptor<Integer> argumentLimit = ArgumentCaptor.forClass(Integer.class);
-    verify(groupMembershipDao).selectGroups(eq(query), anyLong(), argumentOffset.capture(), argumentLimit.capture());
-
-    assertThat(argumentOffset.getValue()).isEqualTo(0);
-    assertThat(argumentLimit.getValue()).isEqualTo(3);
-    assertThat(result.hasMoreResults()).isTrue();
-  }
-
-  @Test
-  public void find_with_paging_having_no_more_results() throws Exception {
-    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").pageIndex(1).pageSize(10).build();
-    when(groupMembershipDao.selectGroups(eq(query), anyLong(), anyInt(), anyInt())).thenReturn(newArrayList(
-      new GroupMembershipDto().setId(1L).setName("group1"),
-      new GroupMembershipDto().setId(2L).setName("group2"),
-      new GroupMembershipDto().setId(3L).setName("group3"),
-      new GroupMembershipDto().setId(4L).setName("group4"))
-    );
-    GroupMembershipQueryResult result = finder.find(query);
-
-    ArgumentCaptor<Integer> argumentOffset = ArgumentCaptor.forClass(Integer.class);
-    ArgumentCaptor<Integer> argumentLimit = ArgumentCaptor.forClass(Integer.class);
-    verify(groupMembershipDao).selectGroups(eq(query), anyLong(), argumentOffset.capture(), argumentLimit.capture());
-
-    assertThat(argumentOffset.getValue()).isEqualTo(0);
-    assertThat(argumentLimit.getValue()).isEqualTo(11);
-    assertThat(result.hasMoreResults()).isFalse();
-  }
-}
diff --git a/sonar-server/src/test/java/org/sonar/server/group/InternalGroupMembershipServiceTest.java b/sonar-server/src/test/java/org/sonar/server/group/InternalGroupMembershipServiceTest.java
deleted file mode 100644 (file)
index aa68769..0000000
+++ /dev/null
@@ -1,172 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-package org.sonar.server.group;
-
-import com.google.common.collect.ImmutableMap;
-import org.junit.Before;
-import org.junit.Test;
-import org.sonar.core.persistence.AbstractDaoTestCase;
-import org.sonar.core.user.GroupMembership;
-import org.sonar.core.user.GroupMembershipDao;
-import org.sonar.core.user.UserDao;
-import org.sonar.server.exceptions.NotFoundException;
-
-import java.util.List;
-
-import static org.fest.assertions.Assertions.assertThat;
-import static org.fest.assertions.Fail.fail;
-
-/**
- * Use BbUnit tests because there's no IT on this feature for the moment
- */
-public class InternalGroupMembershipServiceTest extends AbstractDaoTestCase {
-
-  private InternalGroupMembershipService service;
-
-  @Before
-  public void before() throws Exception {
-    GroupMembershipDao groupMembershipDao = new GroupMembershipDao(getMyBatis());
-    UserDao userDao = new UserDao(getMyBatis());
-    GroupMembershipFinder finder = new GroupMembershipFinder(userDao, groupMembershipDao);
-    service = new InternalGroupMembershipService(finder);
-  }
-
-  @Test
-  public void find_all_member_groups() {
-    setupData("shared");
-
-    GroupMembershipQueryResult queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1",
-      "selected", "all"));
-    List<GroupMembership> result = queryResult.groups();
-    assertThat(result).hasSize(3);
-    check(result.get(0), "sonar-administrators", false);
-    check(result.get(1), "sonar-reviewers", false);
-    check(result.get(2), "sonar-users", true);
-  }
-
-  @Test
-  public void find_all_member_groups_when_no_selected_parameter() {
-    setupData("shared");
-
-    GroupMembershipQueryResult queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1"));
-    List<GroupMembership> result = queryResult.groups();
-    assertThat(result).hasSize(3);
-    check(result.get(0), "sonar-administrators", false);
-    check(result.get(1), "sonar-reviewers", false);
-    check(result.get(2), "sonar-users", true);
-  }
-
-  @Test
-  public void find_member_groups() {
-    setupData("shared");
-
-    GroupMembershipQueryResult queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1",
-      "selected", "selected"));
-    List<GroupMembership> result = queryResult.groups();
-    assertThat(result).hasSize(1);
-    check(result.get(0), "sonar-users", true);
-  }
-
-  @Test
-  public void find_not_member_groups() {
-    setupData("shared");
-
-    GroupMembershipQueryResult queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1",
-      "selected", "deselected"));
-    List<GroupMembership> result = queryResult.groups();
-    assertThat(result).hasSize(2);
-    check(result.get(0), "sonar-administrators", false);
-    check(result.get(1), "sonar-reviewers", false);
-  }
-
-  @Test
-  public void find_with_paging_with_more_results() {
-    setupData("shared");
-
-    GroupMembershipQueryResult queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1",
-      "selected", "all",
-      "page", 1,
-      "pageSize", 2
-    ));
-    List<GroupMembership> result = queryResult.groups();
-    assertThat(result).hasSize(2);
-    assertThat(queryResult.hasMoreResults()).isTrue();
-  }
-
-  @Test
-  public void find_with_paging_with_no_more_results() {
-    setupData("shared");
-
-    GroupMembershipQueryResult queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1",
-      "selected", "all",
-      "page", 3,
-      "pageSize", 1
-    ));
-    List<GroupMembership> result = queryResult.groups();
-    assertThat(result).hasSize(1);
-    assertThat(queryResult.hasMoreResults()).isFalse();
-  }
-
-  @Test
-  public void fail_if_user_not_found() {
-    setupData("shared");
-
-    try {
-      service.find(ImmutableMap.<String, Object>of(
-        "user", "user_not_existing",
-        "selected", "all"));
-      fail();
-    } catch (Exception e) {
-      assertThat(e).isInstanceOf(NotFoundException.class).hasMessage("User 'user_not_existing' does not exists.");
-    }
-  }
-
-  @Test
-  public void find_matched_groups_name() {
-    setupData("shared");
-
-    GroupMembershipQueryResult queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1",
-      "selected", "all",
-      "query", "user"));
-    List<GroupMembership> result = queryResult.groups();
-    assertThat(result).hasSize(1);
-    check(result.get(0), "sonar-users", true);
-
-    queryResult = service.find(ImmutableMap.<String, Object>of(
-      "user", "user1",
-      "selected", "all",
-      "query", "sonar"));
-    result = queryResult.groups();
-    assertThat(result).hasSize(3);
-  }
-
-  private void check(GroupMembership groupMembership, String expectedName, boolean isMember) {
-    assertThat(groupMembership.name()).isEqualTo(expectedName);
-    assertThat(groupMembership.isMember()).isEqualTo(isMember);
-  }
-}
index c214dac11a1d307fb08c96beeffcd9883a99e558..ff90a7cc425ad670ae2e8e9d226b4ea08fddbcc7 100644 (file)
@@ -27,7 +27,7 @@ import org.mockito.runners.MockitoJUnitRunner;
 import org.sonar.api.issue.internal.FieldDiffs;
 import org.sonar.api.issue.internal.WorkDayDuration;
 import org.sonar.core.i18n.DefaultI18n;
-import org.sonar.server.technicaldebt.TechnicalDebtFormatter;
+import org.sonar.server.technicaldebt.DebtFormatter;
 
 import java.util.List;
 import java.util.Locale;
@@ -41,26 +41,26 @@ public class IssueChangelogFormatterTest {
   private static final Locale DEFAULT_LOCALE = Locale.getDefault();
 
   @Mock
-  private DefaultI18n defaultI18n;
+  private DefaultI18n i18n;
 
   @Mock
-  private TechnicalDebtFormatter technicalDebtFormatter;
+  private DebtFormatter debtFormatter;
 
   private IssueChangelogFormatter formatter;
 
   @Before
-  public void before(){
-    formatter = new IssueChangelogFormatter(defaultI18n, technicalDebtFormatter);
+  public void before() {
+    formatter = new IssueChangelogFormatter(i18n, debtFormatter);
   }
 
   @Test
-  public void format_field_diffs_with_new_and_old_value(){
+  public void format_field_diffs_with_new_and_old_value() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("severity", "BLOCKER", "INFO");
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Severity", "INFO")).thenReturn("Severity changed to INFO");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.was", null, "BLOCKER")).thenReturn("was BLOCKER");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Severity", "INFO")).thenReturn("Severity changed to INFO");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.was", null, "BLOCKER")).thenReturn("was BLOCKER");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
@@ -69,12 +69,12 @@ public class IssueChangelogFormatterTest {
   }
 
   @Test
-  public void format_field_diffs_with_only_new_value(){
+  public void format_field_diffs_with_only_new_value() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("severity", null, "INFO");
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Severity", "INFO")).thenReturn("Severity changed to INFO");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Severity", "INFO")).thenReturn("Severity changed to INFO");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
@@ -83,13 +83,13 @@ public class IssueChangelogFormatterTest {
   }
 
   @Test
-  public void format_field_diffs_with_only_old_value(){
+  public void format_field_diffs_with_only_old_value() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("severity", "BLOCKER", null);
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Severity")).thenReturn("Severity removed");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.was", null, "BLOCKER")).thenReturn("was BLOCKER");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Severity")).thenReturn("Severity removed");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.was", null, "BLOCKER")).thenReturn("was BLOCKER");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
@@ -98,12 +98,12 @@ public class IssueChangelogFormatterTest {
   }
 
   @Test
-  public void format_field_diffs_without_value(){
+  public void format_field_diffs_without_value() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("severity", null, null);
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Severity")).thenReturn("Severity removed");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Severity")).thenReturn("Severity removed");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
@@ -112,12 +112,12 @@ public class IssueChangelogFormatterTest {
   }
 
   @Test
-  public void format_field_diffs_with_empty_old_value(){
+  public void format_field_diffs_with_empty_old_value() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("severity", "", null);
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Severity")).thenReturn("Severity removed");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.severity", null)).thenReturn("Severity");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Severity")).thenReturn("Severity removed");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
@@ -126,16 +126,16 @@ public class IssueChangelogFormatterTest {
   }
 
   @Test
-  public void format_technical_debt_with_old_and_new_value(){
+  public void format_technical_debt_with_old_and_new_value() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("technicalDebt", "500", "10000");
 
-    when(technicalDebtFormatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 5, 0))).thenReturn("5 hours");
-    when(technicalDebtFormatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 0, 1))).thenReturn("1 days");
+    when(debtFormatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 5, 0))).thenReturn("5 hours");
+    when(debtFormatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 0, 1))).thenReturn("1 days");
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.technicalDebt", null)).thenReturn("Technical Debt");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Technical Debt", "1 days")).thenReturn("Technical Debt changed to 1 days");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.was", null, "5 hours")).thenReturn("was 5 hours");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.technicalDebt", null)).thenReturn("Technical Debt");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Technical Debt", "1 days")).thenReturn("Technical Debt changed to 1 days");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.was", null, "5 hours")).thenReturn("was 5 hours");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
@@ -144,14 +144,14 @@ public class IssueChangelogFormatterTest {
   }
 
   @Test
-  public void format_technical_debt_with_new_value_only(){
+  public void format_technical_debt_with_new_value_only() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("technicalDebt", null, "10000");
 
-    when(technicalDebtFormatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 0, 1))).thenReturn("1 days");
+    when(debtFormatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 0, 1))).thenReturn("1 days");
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.technicalDebt", null)).thenReturn("Technical Debt");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Technical Debt", "1 days")).thenReturn("Technical Debt changed to 1 days");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.technicalDebt", null)).thenReturn("Technical Debt");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.changed_to", null, "Technical Debt", "1 days")).thenReturn("Technical Debt changed to 1 days");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
@@ -160,12 +160,12 @@ public class IssueChangelogFormatterTest {
   }
 
   @Test
-  public void format_technical_debt_without_value(){
+  public void format_technical_debt_without_value() {
     FieldDiffs diffs = new FieldDiffs();
     diffs.setDiff("technicalDebt", null, null);
 
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.field.technicalDebt", null)).thenReturn("Technical Debt");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Technical Debt")).thenReturn("Technical Debt removed");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.field.technicalDebt", null)).thenReturn("Technical Debt");
+    when(i18n.message(DEFAULT_LOCALE, "issue.changelog.removed", null, "Technical Debt")).thenReturn("Technical Debt removed");
 
     List<String> result = formatter.format(DEFAULT_LOCALE, diffs);
     assertThat(result).hasSize(1);
index f123ae99f8a9889dc7c5b8d4e531d6eff2e226f3..c8337a872792501064ea8e57fa8da5bbfea5c558 100644 (file)
@@ -53,7 +53,7 @@ import org.sonar.server.issue.ActionService;
 import org.sonar.server.issue.IssueChangelog;
 import org.sonar.server.issue.IssueChangelogService;
 import org.sonar.server.issue.IssueService;
-import org.sonar.server.technicaldebt.TechnicalDebtFormatter;
+import org.sonar.server.technicaldebt.DebtFormatter;
 import org.sonar.server.user.MockUserSession;
 import org.sonar.server.user.UserSession;
 
@@ -84,7 +84,7 @@ public class IssueShowWsHandlerTest {
   ActionService actionService;
 
   @Mock
-  TechnicalDebtFormatter technicalDebtFormatter;
+  DebtFormatter debtFormatter;
 
   @Mock
   DefaultTechnicalDebtManager technicalDebtManager;
@@ -113,7 +113,7 @@ public class IssueShowWsHandlerTest {
 
     when(i18n.message(any(Locale.class), eq("created"), eq((String) null))).thenReturn("Created");
 
-    tester = new WsTester(new IssuesWs(new IssueShowWsHandler(issueFinder, issueService, issueChangelogService, actionService, technicalDebtFormatter, technicalDebtManager, i18n)));
+    tester = new WsTester(new IssuesWs(new IssueShowWsHandler(issueFinder, issueService, issueChangelogService, actionService, debtFormatter, technicalDebtManager, i18n)));
   }
 
   @Test
@@ -214,7 +214,7 @@ public class IssueShowWsHandlerTest {
       .setTechnicalDebt(technicalDebt);
     issues.add(issue);
 
-    when(technicalDebtFormatter.format(any(Locale.class), eq(technicalDebt))).thenReturn("2 hours 1 minutes");
+    when(debtFormatter.format(any(Locale.class), eq(technicalDebt))).thenReturn("2 hours 1 minutes");
 
     MockUserSession.set();
     WsTester.TestRequest request = tester.newRequest("show").setParam("key", issue.key());
diff --git a/sonar-server/src/test/java/org/sonar/server/startup/CleanPreviewAnalysisCacheTest.java b/sonar-server/src/test/java/org/sonar/server/startup/CleanPreviewAnalysisCacheTest.java
new file mode 100644 (file)
index 0000000..2ae9b5b
--- /dev/null
@@ -0,0 +1,38 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.startup;
+
+import org.junit.Test;
+import org.sonar.core.preview.PreviewCache;
+
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+
+public class CleanPreviewAnalysisCacheTest {
+  @Test
+  public void clean_cache_on_startup() throws Exception {
+    PreviewCache cache = mock(PreviewCache.class);
+    CleanPreviewAnalysisCache cleaner = new CleanPreviewAnalysisCache(cache);
+
+    cleaner.start();
+    verify(cache).cleanAll();
+    cleaner.stop();
+  }
+}
index 9ddeeaae9e0b01f35d4abe66952440ae167c84ca..f5c8bf13c92578c429baf3a3a79981c658afdb94 100644 (file)
@@ -32,14 +32,12 @@ import java.text.SimpleDateFormat;
 import java.util.Date;
 import java.util.TimeZone;
 
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.when;
+import static org.mockito.Mockito.*;
 
 public class ServerMetadataPersisterTest {
 
-  private TimeZone initialTimeZone;
-  private PersistentSettings persistentSettings;
+  TimeZone initialTimeZone;
+  PersistentSettings persistentSettings;
 
   @Before
   public void fixTimeZone() {
@@ -65,9 +63,11 @@ public class ServerMetadataPersisterTest {
     persister.start();
 
     verify(persistentSettings).saveProperties(ImmutableMap.of(
-        CoreProperties.SERVER_ID, "123",
-        CoreProperties.SERVER_VERSION, "3.2",
-        CoreProperties.SERVER_STARTTIME, "2010-05-18T17:59:00+0000"));
+      CoreProperties.SERVER_ID, "123",
+      CoreProperties.SERVER_VERSION, "3.2",
+      CoreProperties.SERVER_STARTTIME, "2010-05-18T17:59:00+0000"));
+
+    persister.stop();
   }
 
 }
diff --git a/sonar-server/src/test/java/org/sonar/server/technicaldebt/DebtFormatterTest.java b/sonar-server/src/test/java/org/sonar/server/technicaldebt/DebtFormatterTest.java
new file mode 100644 (file)
index 0000000..f7249fb
--- /dev/null
@@ -0,0 +1,56 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+package org.sonar.server.technicaldebt;
+
+import org.junit.Test;
+import org.sonar.api.issue.internal.WorkDayDuration;
+import org.sonar.core.i18n.DefaultI18n;
+
+import java.util.Locale;
+
+import static org.fest.assertions.Assertions.assertThat;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+public class DebtFormatterTest {
+
+  private static final Locale DEFAULT_LOCALE = Locale.getDefault();
+
+  DefaultI18n i18n = mock(DefaultI18n.class);
+  DebtFormatter formatter = new DebtFormatter(i18n);
+
+  @Test
+  public void format() {
+    when(i18n.message(DEFAULT_LOCALE, "issue.technical_debt.x_days", null, 5)).thenReturn("5 days");
+    when(i18n.message(DEFAULT_LOCALE, "issue.technical_debt.x_hours", null, 2)).thenReturn("2 hours");
+    when(i18n.message(DEFAULT_LOCALE, "issue.technical_debt.x_minutes", null, 1)).thenReturn("1 minutes");
+
+    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 0, 5))).isEqualTo("5 days");
+    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 2, 0))).isEqualTo("2 hours");
+    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(1, 0, 0))).isEqualTo("1 minutes");
+
+    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 2, 5))).isEqualTo("5 days 2 hours");
+    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(1, 2, 0))).isEqualTo("2 hours 1 minutes");
+    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(1, 2, 5))).isEqualTo("5 days 2 hours");
+  }
+
+
+}
diff --git a/sonar-server/src/test/java/org/sonar/server/technicaldebt/DebtServiceTest.java b/sonar-server/src/test/java/org/sonar/server/technicaldebt/DebtServiceTest.java
new file mode 100644 (file)
index 0000000..b0a1cd6
--- /dev/null
@@ -0,0 +1,78 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.technicaldebt;
+
+import org.junit.Test;
+import org.sonar.api.issue.internal.WorkDayDuration;
+import org.sonar.api.rules.Rule;
+import org.sonar.api.technicaldebt.server.Characteristic;
+import org.sonar.api.technicaldebt.server.internal.DefaultCharacteristic;
+import org.sonar.core.technicaldebt.DefaultTechnicalDebtManager;
+
+import java.util.List;
+import java.util.Locale;
+
+import static com.google.common.collect.Lists.newArrayList;
+import static org.fest.assertions.Assertions.assertThat;
+import static org.mockito.Matchers.any;
+import static org.mockito.Matchers.eq;
+import static org.mockito.Mockito.*;
+
+public class DebtServiceTest {
+
+  DebtFormatter debtFormatter = mock(DebtFormatter.class);
+  DefaultTechnicalDebtManager finder = mock(DefaultTechnicalDebtManager.class);
+  DebtService service = new DebtService(debtFormatter, finder);
+
+  @Test
+  public void format() {
+    WorkDayDuration technicalDebt = WorkDayDuration.of(5, 0, 0);
+    service.format(technicalDebt);
+    verify(debtFormatter).format(any(Locale.class), eq(technicalDebt));
+  }
+
+  @Test
+  public void to_technical_debt() {
+    assertThat(service.toTechnicalDebt("500")).isEqualTo(WorkDayDuration.of(0, 5, 0));
+  }
+
+  @Test
+  public void find_root_characteristics() {
+    List<Characteristic> rootCharacteristics = newArrayList();
+    when(finder.findRootCharacteristics()).thenReturn(rootCharacteristics);
+    assertThat(service.findRootCharacteristics()).isEqualTo(rootCharacteristics);
+  }
+
+  @Test
+  public void find_requirement() {
+    Rule rule = Rule.create("repo", "key");
+    Characteristic requirement = new DefaultCharacteristic();
+    when(finder.findRequirementByRule(rule)).thenReturn(requirement);
+    assertThat(service.findRequirement(rule)).isEqualTo(requirement);
+  }
+
+  @Test
+  public void find_characteristic() {
+    Characteristic characteristic = new DefaultCharacteristic();
+    when(finder.findCharacteristicById(1)).thenReturn(characteristic);
+    assertThat(service.findCharacteristic(1)).isEqualTo(characteristic);
+  }
+
+}
diff --git a/sonar-server/src/test/java/org/sonar/server/technicaldebt/InternalRubyTechnicalDebtServiceTest.java b/sonar-server/src/test/java/org/sonar/server/technicaldebt/InternalRubyTechnicalDebtServiceTest.java
deleted file mode 100644 (file)
index f3f836a..0000000
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.technicaldebt;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mock;
-import org.mockito.runners.MockitoJUnitRunner;
-import org.sonar.api.issue.internal.WorkDayDuration;
-import org.sonar.api.rules.Rule;
-import org.sonar.api.technicaldebt.server.Characteristic;
-import org.sonar.api.technicaldebt.server.internal.DefaultCharacteristic;
-import org.sonar.core.technicaldebt.DefaultTechnicalDebtManager;
-
-import java.util.List;
-import java.util.Locale;
-
-import static com.google.common.collect.Lists.newArrayList;
-import static org.fest.assertions.Assertions.assertThat;
-import static org.mockito.Matchers.any;
-import static org.mockito.Matchers.eq;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.when;
-
-@RunWith(MockitoJUnitRunner.class)
-public class InternalRubyTechnicalDebtServiceTest {
-
-  @Mock
-  TechnicalDebtFormatter technicalDebtFormatter;
-
-  @Mock
-  DefaultTechnicalDebtManager finder;
-
-  private InternalRubyTechnicalDebtService service;
-
-  @Before
-  public void before() {
-    service = new InternalRubyTechnicalDebtService(technicalDebtFormatter, finder);
-  }
-
-  @Test
-  public void format() {
-    WorkDayDuration technicalDebt = WorkDayDuration.of(5, 0, 0);
-    service.format(technicalDebt);
-    verify(technicalDebtFormatter).format(any(Locale.class), eq(technicalDebt));
-  }
-
-  @Test
-  public void to_technical_debt() {
-    assertThat(service.toTechnicalDebt("500")).isEqualTo(WorkDayDuration.of(0, 5, 0));
-  }
-
-  @Test
-  public void find_root_characteristics() {
-    List<Characteristic> rootCharacteristics = newArrayList();
-    when(finder.findRootCharacteristics()).thenReturn(rootCharacteristics);
-    assertThat(service.findRootCharacteristics()).isEqualTo(rootCharacteristics);
-  }
-
-  @Test
-  public void find_requirement() {
-    Rule rule = Rule.create("repo", "key");
-    Characteristic requirement = new DefaultCharacteristic();
-    when(finder.findRequirementByRule(rule)).thenReturn(requirement);
-    assertThat(service.findRequirement(rule)).isEqualTo(requirement);
-  }
-
-  @Test
-  public void find_characteristic() {
-    Characteristic characteristic = new DefaultCharacteristic();
-    when(finder.findCharacteristicById(1)).thenReturn(characteristic);
-    assertThat(service.findCharacteristic(1)).isEqualTo(characteristic);
-  }
-
-}
diff --git a/sonar-server/src/test/java/org/sonar/server/technicaldebt/TechnicalDebtFormatterTest.java b/sonar-server/src/test/java/org/sonar/server/technicaldebt/TechnicalDebtFormatterTest.java
deleted file mode 100644 (file)
index 0de635b..0000000
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-
-package org.sonar.server.technicaldebt;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mock;
-import org.mockito.runners.MockitoJUnitRunner;
-import org.sonar.api.issue.internal.WorkDayDuration;
-import org.sonar.core.i18n.DefaultI18n;
-
-import java.util.Locale;
-
-import static org.fest.assertions.Assertions.assertThat;
-import static org.mockito.Mockito.when;
-
-@RunWith(MockitoJUnitRunner.class)
-public class TechnicalDebtFormatterTest {
-
-  private static final Locale DEFAULT_LOCALE = Locale.getDefault();
-
-  @Mock
-  private DefaultI18n defaultI18n;
-
-  private TechnicalDebtFormatter formatter;
-
-  @Before
-  public void before() {
-    formatter = new TechnicalDebtFormatter(defaultI18n);
-  }
-
-  @Test
-  public void format() {
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.technical_debt.x_days", null, 5)).thenReturn("5 days");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.technical_debt.x_hours", null, 2)).thenReturn("2 hours");
-    when(defaultI18n.message(DEFAULT_LOCALE, "issue.technical_debt.x_minutes", null, 1)).thenReturn("1 minutes");
-
-    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 0, 5))).isEqualTo("5 days");
-    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 2, 0))).isEqualTo("2 hours");
-    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(1, 0, 0))).isEqualTo("1 minutes");
-
-    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(0, 2, 5))).isEqualTo("5 days 2 hours");
-    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(1, 2, 0))).isEqualTo("2 hours 1 minutes");
-    assertThat(formatter.format(DEFAULT_LOCALE, WorkDayDuration.of(1, 2, 5))).isEqualTo("5 days 2 hours");
-  }
-
-
-}
diff --git a/sonar-server/src/test/java/org/sonar/server/ui/CompatibilityRealmTest.java b/sonar-server/src/test/java/org/sonar/server/ui/CompatibilityRealmTest.java
deleted file mode 100644 (file)
index 3b68e4c..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.ui;
-
-import org.junit.Test;
-import org.sonar.api.security.LoginPasswordAuthenticator;
-
-import static org.hamcrest.Matchers.is;
-import static org.junit.Assert.assertThat;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.verify;
-
-public class CompatibilityRealmTest {
-
-  @Test
-  public void shouldDelegate() {
-    LoginPasswordAuthenticator authenticator = mock(LoginPasswordAuthenticator.class);
-    CompatibilityRealm realm = new CompatibilityRealm(authenticator);
-    realm.init();
-    verify(authenticator).init();
-    assertThat(realm.getLoginPasswordAuthenticator(), is(authenticator));
-    assertThat(realm.getName(), is("CompatibilityRealm[" + authenticator.getClass().getName() + "]"));
-  }
-
-}
diff --git a/sonar-server/src/test/java/org/sonar/server/ui/SecurityRealmFactoryTest.java b/sonar-server/src/test/java/org/sonar/server/ui/SecurityRealmFactoryTest.java
deleted file mode 100644 (file)
index c2e134f..0000000
+++ /dev/null
@@ -1,162 +0,0 @@
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2013 SonarSource
- * mailto:contact AT sonarsource DOT com
- *
- * SonarQube is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * SonarQube is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
- */
-package org.sonar.server.ui;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.sonar.api.CoreProperties;
-import org.sonar.api.config.Settings;
-import org.sonar.api.security.LoginPasswordAuthenticator;
-import org.sonar.api.security.SecurityRealm;
-import org.sonar.api.utils.SonarException;
-
-import static org.hamcrest.Matchers.containsString;
-import static org.hamcrest.Matchers.instanceOf;
-import static org.hamcrest.Matchers.is;
-import static org.hamcrest.Matchers.nullValue;
-import static org.junit.Assert.assertThat;
-import static org.junit.Assert.fail;
-import static org.mockito.Mockito.spy;
-import static org.mockito.Mockito.verify;
-
-public class SecurityRealmFactoryTest {
-
-  private Settings settings;
-
-  @Before
-  public void setUp() {
-    settings = new Settings();
-  }
-
-  /**
-   * Typical usage.
-   */
-  @Test
-  public void should_select_realm_and_start() {
-    SecurityRealm realm = spy(new FakeRealm());
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
-
-    SecurityRealmFactory factory = new SecurityRealmFactory(settings, new SecurityRealm[]{realm});
-    factory.start();
-    assertThat(factory.getRealm(), is(realm));
-    verify(realm).init();
-  }
-
-  @Test
-  public void do_not_fail_if_no_realms() {
-    SecurityRealmFactory factory = new SecurityRealmFactory(settings);
-    factory.start();
-    assertThat(factory.getRealm(), nullValue());
-  }
-
-  @Test
-  public void realm_not_found() {
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, "Fake");
-
-    try {
-      new SecurityRealmFactory(settings);
-      fail();
-    } catch (SonarException e) {
-      assertThat(e.getMessage(), containsString("Realm 'Fake' not found."));
-    }
-  }
-
-  @Test
-  public void should_provide_compatibility_for_authenticator() {
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_CLASS, FakeAuthenticator.class.getName());
-    LoginPasswordAuthenticator authenticator = new FakeAuthenticator();
-
-    SecurityRealmFactory factory = new SecurityRealmFactory(settings, new LoginPasswordAuthenticator[]{authenticator});
-    SecurityRealm realm = factory.getRealm();
-    assertThat(realm, instanceOf(CompatibilityRealm.class));
-  }
-
-  @Test
-  public void should_take_precedence_over_authenticator() {
-    SecurityRealm realm = new FakeRealm();
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
-    LoginPasswordAuthenticator authenticator = new FakeAuthenticator();
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_CLASS, FakeAuthenticator.class.getName());
-
-    SecurityRealmFactory factory = new SecurityRealmFactory(settings, new SecurityRealm[]{realm},
-        new LoginPasswordAuthenticator[]{authenticator});
-    assertThat(factory.getRealm(), is(realm));
-  }
-
-  @Test
-  public void authenticator_not_found() {
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_CLASS, "Fake");
-
-    try {
-      new SecurityRealmFactory(settings);
-      fail();
-    } catch (SonarException e) {
-      assertThat(e.getMessage(), containsString("Authenticator 'Fake' not found."));
-    }
-  }
-
-  @Test
-  public void ignore_startup_failure() {
-    SecurityRealm realm = spy(new AlwaysFailsRealm());
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_IGNORE_STARTUP_FAILURE, true);
-
-    new SecurityRealmFactory(settings, new SecurityRealm[]{realm}).start();
-    verify(realm).init();
-  }
-
-  @Test
-  public void should_fail() {
-    SecurityRealm realm = spy(new AlwaysFailsRealm());
-    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
-
-    try {
-      new SecurityRealmFactory(settings, new SecurityRealm[]{realm}).start();
-      fail();
-    } catch (SonarException e) {
-      assertThat(e.getCause(), instanceOf(IllegalStateException.class));
-      assertThat(e.getMessage(), containsString("Security realm fails to start"));
-    }
-  }
-
-  private static class AlwaysFailsRealm extends FakeRealm {
-    @Override
-    public void init() {
-      throw new IllegalStateException();
-    }
-  }
-
-  private static class FakeRealm extends SecurityRealm {
-    @Override
-    public LoginPasswordAuthenticator getLoginPasswordAuthenticator() {
-      return null;
-    }
-  }
-
-  private static class FakeAuthenticator implements LoginPasswordAuthenticator {
-    public void init() {
-    }
-
-    public boolean authenticate(String login, String password) {
-      return false;
-    }
-  }
-
-}
diff --git a/sonar-server/src/test/java/org/sonar/server/user/CompatibilityRealmTest.java b/sonar-server/src/test/java/org/sonar/server/user/CompatibilityRealmTest.java
new file mode 100644 (file)
index 0000000..ee47aea
--- /dev/null
@@ -0,0 +1,42 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.user;
+
+import org.junit.Test;
+import org.sonar.api.security.LoginPasswordAuthenticator;
+
+import static org.hamcrest.Matchers.is;
+import static org.junit.Assert.assertThat;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.verify;
+
+public class CompatibilityRealmTest {
+
+  @Test
+  public void shouldDelegate() {
+    LoginPasswordAuthenticator authenticator = mock(LoginPasswordAuthenticator.class);
+    CompatibilityRealm realm = new CompatibilityRealm(authenticator);
+    realm.init();
+    verify(authenticator).init();
+    assertThat(realm.getLoginPasswordAuthenticator(), is(authenticator));
+    assertThat(realm.getName(), is("CompatibilityRealm[" + authenticator.getClass().getName() + "]"));
+  }
+
+}
diff --git a/sonar-server/src/test/java/org/sonar/server/user/GroupMembershipFinderTest.java b/sonar-server/src/test/java/org/sonar/server/user/GroupMembershipFinderTest.java
new file mode 100644 (file)
index 0000000..2b4eff3
--- /dev/null
@@ -0,0 +1,115 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+package org.sonar.server.user;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.mockito.ArgumentCaptor;
+import org.sonar.core.user.*;
+
+import static com.google.common.collect.Lists.newArrayList;
+import static org.fest.assertions.Assertions.assertThat;
+import static org.mockito.Matchers.anyInt;
+import static org.mockito.Matchers.anyLong;
+import static org.mockito.Matchers.eq;
+import static org.mockito.Mockito.*;
+
+public class GroupMembershipFinderTest {
+
+  UserDao userDao = mock(UserDao.class);
+  GroupMembershipDao groupMembershipDao = mock(GroupMembershipDao.class);
+  GroupMembershipFinder finder;
+
+  @Before
+  public void setUp() throws Exception {
+    when(userDao.selectActiveUserByLogin("arthur")).thenReturn(new UserDto().setId(100L).setName("arthur"));
+    finder = new GroupMembershipFinder(userDao, groupMembershipDao);
+  }
+
+  @Test
+  public void find() throws Exception {
+    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").build();
+    when(groupMembershipDao.selectGroups(eq(query), anyLong(), anyInt(), anyInt())).thenReturn(
+      newArrayList(new GroupMembershipDto().setId(1L).setName("users").setUserId(100L))
+    );
+
+    GroupMembershipFinder.Membership result = finder.find(query);
+    assertThat(result.groups()).hasSize(1);
+    assertThat(result.hasMoreResults()).isFalse();
+
+    GroupMembership group = result.groups().get(0);
+    assertThat(group.id()).isEqualTo(1);
+    assertThat(group.name()).isEqualTo("users");
+    assertThat(group.isMember()).isTrue();
+  }
+
+  @Test
+  public void find_with_paging() throws Exception {
+    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").pageIndex(3).pageSize(10).build();
+    finder.find(query);
+
+    ArgumentCaptor<Integer> argumentOffset = ArgumentCaptor.forClass(Integer.class);
+    ArgumentCaptor<Integer> argumentLimit = ArgumentCaptor.forClass(Integer.class);
+    verify(groupMembershipDao).selectGroups(eq(query), anyLong(), argumentOffset.capture(), argumentLimit.capture());
+
+    assertThat(argumentOffset.getValue()).isEqualTo(20);
+    assertThat(argumentLimit.getValue()).isEqualTo(11);
+  }
+
+  @Test
+  public void find_with_paging_having_more_results() throws Exception {
+    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").pageIndex(1).pageSize(2).build();
+    when(groupMembershipDao.selectGroups(eq(query), anyLong(), anyInt(), anyInt())).thenReturn(newArrayList(
+      new GroupMembershipDto().setId(1L).setName("group1"),
+      new GroupMembershipDto().setId(2L).setName("group2"),
+      new GroupMembershipDto().setId(3L).setName("group3"))
+    );
+    GroupMembershipFinder.Membership result = finder.find(query);
+
+    ArgumentCaptor<Integer> argumentOffset = ArgumentCaptor.forClass(Integer.class);
+    ArgumentCaptor<Integer> argumentLimit = ArgumentCaptor.forClass(Integer.class);
+    verify(groupMembershipDao).selectGroups(eq(query), anyLong(), argumentOffset.capture(), argumentLimit.capture());
+
+    assertThat(argumentOffset.getValue()).isEqualTo(0);
+    assertThat(argumentLimit.getValue()).isEqualTo(3);
+    assertThat(result.hasMoreResults()).isTrue();
+  }
+
+  @Test
+  public void find_with_paging_having_no_more_results() throws Exception {
+    GroupMembershipQuery query = GroupMembershipQuery.builder().login("arthur").pageIndex(1).pageSize(10).build();
+    when(groupMembershipDao.selectGroups(eq(query), anyLong(), anyInt(), anyInt())).thenReturn(newArrayList(
+      new GroupMembershipDto().setId(1L).setName("group1"),
+      new GroupMembershipDto().setId(2L).setName("group2"),
+      new GroupMembershipDto().setId(3L).setName("group3"),
+      new GroupMembershipDto().setId(4L).setName("group4"))
+    );
+    GroupMembershipFinder.Membership result = finder.find(query);
+
+    ArgumentCaptor<Integer> argumentOffset = ArgumentCaptor.forClass(Integer.class);
+    ArgumentCaptor<Integer> argumentLimit = ArgumentCaptor.forClass(Integer.class);
+    verify(groupMembershipDao).selectGroups(eq(query), anyLong(), argumentOffset.capture(), argumentLimit.capture());
+
+    assertThat(argumentOffset.getValue()).isEqualTo(0);
+    assertThat(argumentLimit.getValue()).isEqualTo(11);
+    assertThat(result.hasMoreResults()).isFalse();
+  }
+}
diff --git a/sonar-server/src/test/java/org/sonar/server/user/GroupMembershipServiceTest.java b/sonar-server/src/test/java/org/sonar/server/user/GroupMembershipServiceTest.java
new file mode 100644 (file)
index 0000000..ff99af0
--- /dev/null
@@ -0,0 +1,172 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+
+package org.sonar.server.user;
+
+import com.google.common.collect.ImmutableMap;
+import org.junit.Before;
+import org.junit.Test;
+import org.sonar.core.persistence.AbstractDaoTestCase;
+import org.sonar.core.user.GroupMembership;
+import org.sonar.core.user.GroupMembershipDao;
+import org.sonar.core.user.UserDao;
+import org.sonar.server.exceptions.NotFoundException;
+
+import java.util.List;
+
+import static org.fest.assertions.Assertions.assertThat;
+import static org.fest.assertions.Fail.fail;
+
+/**
+ * Use BbUnit tests because there's no IT on this feature for the moment
+ */
+public class GroupMembershipServiceTest extends AbstractDaoTestCase {
+
+  GroupMembershipService service;
+
+  @Before
+  public void before() throws Exception {
+    GroupMembershipDao membershipDao = new GroupMembershipDao(getMyBatis());
+    UserDao userDao = new UserDao(getMyBatis());
+    GroupMembershipFinder finder = new GroupMembershipFinder(userDao, membershipDao);
+    service = new GroupMembershipService(finder);
+  }
+
+  @Test
+  public void find_all_member_groups() {
+    setupData("shared");
+
+    GroupMembershipFinder.Membership queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1",
+      "selected", "all"));
+    List<GroupMembership> result = queryResult.groups();
+    assertThat(result).hasSize(3);
+    check(result.get(0), "sonar-administrators", false);
+    check(result.get(1), "sonar-reviewers", false);
+    check(result.get(2), "sonar-users", true);
+  }
+
+  @Test
+  public void find_all_member_groups_when_no_selected_parameter() {
+    setupData("shared");
+
+    GroupMembershipFinder.Membership queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1"));
+    List<GroupMembership> result = queryResult.groups();
+    assertThat(result).hasSize(3);
+    check(result.get(0), "sonar-administrators", false);
+    check(result.get(1), "sonar-reviewers", false);
+    check(result.get(2), "sonar-users", true);
+  }
+
+  @Test
+  public void find_member_groups() {
+    setupData("shared");
+
+    GroupMembershipFinder.Membership queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1",
+      "selected", "selected"));
+    List<GroupMembership> result = queryResult.groups();
+    assertThat(result).hasSize(1);
+    check(result.get(0), "sonar-users", true);
+  }
+
+  @Test
+  public void find_not_member_groups() {
+    setupData("shared");
+
+    GroupMembershipFinder.Membership queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1",
+      "selected", "deselected"));
+    List<GroupMembership> result = queryResult.groups();
+    assertThat(result).hasSize(2);
+    check(result.get(0), "sonar-administrators", false);
+    check(result.get(1), "sonar-reviewers", false);
+  }
+
+  @Test
+  public void find_with_paging_with_more_results() {
+    setupData("shared");
+
+    GroupMembershipFinder.Membership queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1",
+      "selected", "all",
+      "page", 1,
+      "pageSize", 2
+    ));
+    List<GroupMembership> result = queryResult.groups();
+    assertThat(result).hasSize(2);
+    assertThat(queryResult.hasMoreResults()).isTrue();
+  }
+
+  @Test
+  public void find_with_paging_with_no_more_results() {
+    setupData("shared");
+
+    GroupMembershipFinder.Membership queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1",
+      "selected", "all",
+      "page", 3,
+      "pageSize", 1
+    ));
+    List<GroupMembership> result = queryResult.groups();
+    assertThat(result).hasSize(1);
+    assertThat(queryResult.hasMoreResults()).isFalse();
+  }
+
+  @Test
+  public void fail_if_user_not_found() {
+    setupData("shared");
+
+    try {
+      service.find(ImmutableMap.<String, Object>of(
+        "user", "user_not_existing",
+        "selected", "all"));
+      fail();
+    } catch (Exception e) {
+      assertThat(e).isInstanceOf(NotFoundException.class).hasMessage("User 'user_not_existing' does not exists.");
+    }
+  }
+
+  @Test
+  public void find_matched_groups_name() {
+    setupData("shared");
+
+    GroupMembershipFinder.Membership queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1",
+      "selected", "all",
+      "query", "user"));
+    List<GroupMembership> result = queryResult.groups();
+    assertThat(result).hasSize(1);
+    check(result.get(0), "sonar-users", true);
+
+    queryResult = service.find(ImmutableMap.<String, Object>of(
+      "user", "user1",
+      "selected", "all",
+      "query", "sonar"));
+    result = queryResult.groups();
+    assertThat(result).hasSize(3);
+  }
+
+  private void check(GroupMembership groupMembership, String expectedName, boolean isMember) {
+    assertThat(groupMembership.name()).isEqualTo(expectedName);
+    assertThat(groupMembership.isMember()).isEqualTo(isMember);
+  }
+}
diff --git a/sonar-server/src/test/java/org/sonar/server/user/SecurityRealmFactoryTest.java b/sonar-server/src/test/java/org/sonar/server/user/SecurityRealmFactoryTest.java
new file mode 100644 (file)
index 0000000..70bd0be
--- /dev/null
@@ -0,0 +1,152 @@
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2013 SonarSource
+ * mailto:contact AT sonarsource DOT com
+ *
+ * SonarQube is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * SonarQube is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ */
+package org.sonar.server.user;
+
+import org.junit.Test;
+import org.sonar.api.CoreProperties;
+import org.sonar.api.config.Settings;
+import org.sonar.api.security.LoginPasswordAuthenticator;
+import org.sonar.api.security.SecurityRealm;
+import org.sonar.api.utils.SonarException;
+
+import static org.fest.assertions.Assertions.assertThat;
+import static org.junit.Assert.fail;
+import static org.mockito.Mockito.spy;
+import static org.mockito.Mockito.verify;
+
+public class SecurityRealmFactoryTest {
+
+  Settings settings = new Settings();
+
+  /**
+   * Typical usage.
+   */
+  @Test
+  public void should_select_realm_and_start() {
+    SecurityRealm realm = spy(new FakeRealm());
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
+
+    SecurityRealmFactory factory = new SecurityRealmFactory(settings, new SecurityRealm[]{realm});
+    factory.start();
+    assertThat(factory.getRealm()).isSameAs(realm);
+    verify(realm).init();
+  }
+
+  @Test
+  public void do_not_fail_if_no_realms() {
+    SecurityRealmFactory factory = new SecurityRealmFactory(settings);
+    factory.start();
+    assertThat(factory.getRealm()).isNull();
+  }
+
+  @Test
+  public void realm_not_found() {
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, "Fake");
+
+    try {
+      new SecurityRealmFactory(settings);
+      fail();
+    } catch (SonarException e) {
+      assertThat(e.getMessage()).contains("Realm 'Fake' not found.");
+    }
+  }
+
+  @Test
+  public void should_provide_compatibility_for_authenticator() {
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_CLASS, FakeAuthenticator.class.getName());
+    LoginPasswordAuthenticator authenticator = new FakeAuthenticator();
+
+    SecurityRealmFactory factory = new SecurityRealmFactory(settings, new LoginPasswordAuthenticator[]{authenticator});
+    SecurityRealm realm = factory.getRealm();
+    assertThat(realm).isInstanceOf(CompatibilityRealm.class);
+  }
+
+  @Test
+  public void should_take_precedence_over_authenticator() {
+    SecurityRealm realm = new FakeRealm();
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
+    LoginPasswordAuthenticator authenticator = new FakeAuthenticator();
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_CLASS, FakeAuthenticator.class.getName());
+
+    SecurityRealmFactory factory = new SecurityRealmFactory(settings, new SecurityRealm[]{realm},
+      new LoginPasswordAuthenticator[]{authenticator});
+    assertThat(factory.getRealm()).isSameAs(realm);
+  }
+
+  @Test
+  public void authenticator_not_found() {
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_CLASS, "Fake");
+
+    try {
+      new SecurityRealmFactory(settings);
+      fail();
+    } catch (SonarException e) {
+      assertThat(e.getMessage()).contains("Authenticator 'Fake' not found.");
+    }
+  }
+
+  @Test
+  public void ignore_startup_failure() {
+    SecurityRealm realm = spy(new AlwaysFailsRealm());
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_IGNORE_STARTUP_FAILURE, true);
+
+    new SecurityRealmFactory(settings, new SecurityRealm[]{realm}).start();
+    verify(realm).init();
+  }
+
+  @Test
+  public void should_fail() {
+    SecurityRealm realm = spy(new AlwaysFailsRealm());
+    settings.setProperty(CoreProperties.CORE_AUTHENTICATOR_REALM, realm.getName());
+
+    try {
+      new SecurityRealmFactory(settings, new SecurityRealm[]{realm}).start();
+      fail();
+    } catch (SonarException e) {
+      assertThat(e.getCause()).isInstanceOf(IllegalStateException.class);
+      assertThat(e.getMessage()).contains("Security realm fails to start");
+    }
+  }
+
+  private static class AlwaysFailsRealm extends FakeRealm {
+    @Override
+    public void init() {
+      throw new IllegalStateException();
+    }
+  }
+
+  private static class FakeRealm extends SecurityRealm {
+    @Override
+    public LoginPasswordAuthenticator getLoginPasswordAuthenticator() {
+      return null;
+    }
+  }
+
+  private static class FakeAuthenticator implements LoginPasswordAuthenticator {
+    public void init() {
+    }
+
+    public boolean authenticate(String login, String password) {
+      return false;
+    }
+  }
+
+}
index 0ca4143ddea36013de3a03a5a410a272858d36e3..f17386c287fcd45b585b10ec1dc6eab143adc0e1 100644 (file)
@@ -30,6 +30,7 @@ import org.sonar.api.server.ws.Response;
 import org.sonar.api.server.ws.WebService;
 import org.sonar.api.utils.text.JsonWriter;
 import org.sonar.api.utils.text.XmlWriter;
+import org.sonar.server.plugins.MimeTypes;
 
 import javax.annotation.CheckForNull;
 
@@ -187,7 +188,7 @@ public class WebServiceEngineTest {
 
     assertThat(response.stream().outputAsString()).isEqualTo("{\"errors\":[{\"msg\":\"Unexpected\"}]}");
     assertThat(response.stream().httpStatus()).isEqualTo(500);
-    assertThat(response.stream().mediaType()).isEqualTo("application/json");
+    assertThat(response.stream().mediaType()).isEqualTo(MimeTypes.JSON);
   }
 
   static class SystemWebService implements WebService {
diff --git a/sonar-server/src/test/resources/org/sonar/server/group/InternalGroupMembershipServiceTest/shared.xml b/sonar-server/src/test/resources/org/sonar/server/group/InternalGroupMembershipServiceTest/shared.xml
deleted file mode 100644 (file)
index 166deff..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-<dataset>
-
-  <groups id="100" name="sonar-administrators"/>
-  <groups id="101" name="sonar-users" />
-  <groups id="102" name="sonar-reviewers" />
-
-  <!-- user 1 is in users group -->
-  <groups_users user_id="200" group_id="101"/>
-
-  <!-- user 2 is in all groups -->
-  <groups_users user_id="201" group_id="100"/>
-  <groups_users user_id="201" group_id="101"/>
-  <groups_users user_id="201" group_id="102"/>
-
-  <!-- user 3 is in no group -->
-
-
-  <users id="200" login="user1" name="user1"/>
-  <users id="201" login="user2" name="user2"/>
-  <users id="202" login="user3" name="user3"/>
-
-</dataset>
diff --git a/sonar-server/src/test/resources/org/sonar/server/user/GroupMembershipServiceTest/shared.xml b/sonar-server/src/test/resources/org/sonar/server/user/GroupMembershipServiceTest/shared.xml
new file mode 100644 (file)
index 0000000..018a2be
--- /dev/null
@@ -0,0 +1,22 @@
+<dataset>
+
+  <groups id="100" name="sonar-administrators"/>
+  <groups id="101" name="sonar-users"/>
+  <groups id="102" name="sonar-reviewers"/>
+
+  <!-- user 1 is in users group -->
+  <groups_users user_id="200" group_id="101"/>
+
+  <!-- user 2 is in all groups -->
+  <groups_users user_id="201" group_id="100"/>
+  <groups_users user_id="201" group_id="101"/>
+  <groups_users user_id="201" group_id="102"/>
+
+  <!-- user 3 is in no group -->
+
+
+  <users id="200" login="user1" name="user1"/>
+  <users id="201" login="user2" name="user2"/>
+  <users id="202" login="user3" name="user3"/>
+
+</dataset>