]> source.dussan.org Git - sonarqube.git/commitdiff
SONAR-15825 Escape special characters in like sql query for portfolio projects
authorJacek <jacek.poreda@sonarsource.com>
Tue, 25 Jan 2022 09:28:26 +0000 (10:28 +0100)
committersonartech <sonartech@sonarsource.com>
Wed, 26 Jan 2022 20:02:44 +0000 (20:02 +0000)
server/sonar-db-dao/src/main/java/org/sonar/db/component/ComponentDao.java
server/sonar-db-dao/src/main/resources/org/sonar/db/component/ComponentMapper.xml
server/sonar-db-dao/src/test/java/org/sonar/db/component/ComponentDaoTest.java
server/sonar-server-common/src/main/java/org/sonar/server/view/index/ViewIndexer.java
server/sonar-server-common/src/test/java/org/sonar/server/view/index/ViewIndexerTest.java

index 027eca548781a4ca3948c5554275b1b51dae6ed3..bbdaab776780d994a685b07803599d6264ea6fa4 100644 (file)
@@ -257,7 +257,8 @@ public class ComponentDao implements Dao {
   }
 
   public List<String> selectProjectsFromView(DbSession session, String viewUuid, String projectViewUuid) {
-    return mapper(session).selectProjectsFromView("%." + viewUuid + ".%", projectViewUuid);
+    var escapedViewUuid = viewUuid.replace("_", "\\_").replace("%", "\\%");
+    return mapper(session).selectProjectsFromView("%." + escapedViewUuid + ".%", projectViewUuid);
   }
 
   /**
index 97198772fbca49865f3d7495ea0cddfc55d1a5a8..c93b10d97714f7e151338ceee30c9b3db7c5e52a 100644 (file)
       and p.scope = 'PRJ'
       and p.qualifier in ('VW', 'APP')
   </select>
-
   <select id="selectProjectsFromView" resultType="String">
     select p.copy_component_uuid
     from components p
     where
       p.enabled = ${_true}
       and p.project_uuid = #{projectViewUuid,jdbcType=VARCHAR}
-      and p.module_uuid_path like #{viewUuidLikeQuery,jdbcType=VARCHAR}
+    <choose>
+      <when test="_databaseId == 'mssql'">
+        and p.module_uuid_path like #{viewUuidLikeQuery,jdbcType=VARCHAR} {escape '\'}
+      </when>
+      <otherwise>
+        and p.module_uuid_path like #{viewUuidLikeQuery,jdbcType=VARCHAR} ESCAPE '\'
+      </otherwise>
+    </choose>
       and p.qualifier = 'TRK'
       and p.copy_component_uuid is not null
   </select>
index f440ca6af10c2f9f090059ce408c000f4f2a2e7f..b04c2232f7c1b6bc5f469cfc4145e2f397335742 100644 (file)
@@ -1004,6 +1004,26 @@ public class ComponentDaoTest {
     assertThat(underTest.selectProjectsFromView(dbSession, "Unknown", "Unknown")).isEmpty();
   }
 
+  @Test
+  public void select_projects_from_view_should_escape_like_sensitive_characters() {
+    ComponentDto project1 = db.components().insertPrivateProject();
+    ComponentDto project2 = db.components().insertPrivateProject();
+    ComponentDto project3 = db.components().insertPrivateProject();
+
+    ComponentDto view = db.components().insertPrivatePortfolio();
+
+    //subview with uuid containing special character ( '_' ) for 'like' SQL clause
+    ComponentDto subView1 = db.components().insertComponent(newSubPortfolio(view, "A_C", "A_C-key"));
+    db.components().insertComponent(newProjectCopy(project1, subView1));
+    db.components().insertComponent(newProjectCopy(project2, subView1));
+
+    ComponentDto subView2 = db.components().insertComponent(newSubPortfolio(view, "ABC", "ABC-key"));
+    db.components().insertComponent(newProjectCopy(project3, subView2));
+
+    assertThat(underTest.selectProjectsFromView(dbSession, subView1.uuid(), view.uuid())).containsExactlyInAnyOrder(project1.uuid(), project2.uuid());
+    assertThat(underTest.selectProjectsFromView(dbSession, subView2.uuid(), view.uuid())).containsExactlyInAnyOrder(project3.uuid());
+  }
+
   @Test
   public void select_projects() {
     ComponentDto provisionedProject = db.components().insertPrivateProject();
index 2f31c5af4aa10f5904964a50986f1d086415abde..955253c6953c620825e6218d7ab61e0fbccce8c2 100644 (file)
@@ -19,7 +19,6 @@
  */
 package org.sonar.server.view.index;
 
-import com.google.common.collect.ImmutableSet;
 import java.util.Collection;
 import java.util.HashMap;
 import java.util.List;
@@ -57,7 +56,7 @@ public class ViewIndexer implements ResilientIndexer {
 
   @Override
   public Set<IndexType> getIndexTypes() {
-    return ImmutableSet.of(TYPE_VIEW);
+    return Set.of(TYPE_VIEW);
   }
 
   @Override
index 291595f179a518395c1a27382c317692b1a03ffc..fbb5055f3c506a902dafbf0faacf096c67155d00 100644 (file)
@@ -57,6 +57,11 @@ public class ViewIndexerTest {
   private final DbSession dbSession = db.getSession();
   private final ViewIndexer underTest = new ViewIndexer(dbClient, es.client());
 
+  @Test
+  public void getIndexTypes() {
+    assertThat(underTest.getIndexTypes()).containsExactly(TYPE_VIEW);
+  }
+
   @Test
   public void index_nothing() {
     underTest.indexOnStartup(emptySet());