ResourceCache resourceCache = new ResourceCache();
Project project = new Project("foo");
- resourceCache.add(project, null, projectSnapshot);
+ resourceCache.add(project, null).setSnapshot(projectSnapshot);
TimeMachineConfigurationPersister persister = new TimeMachineConfigurationPersister(timeMachineConfiguration, resourceCache, getSession());
private final long batchId;
private final Resource r;
- private final Snapshot s;
+ private Snapshot s;
private final BatchResource parent;
private final Collection<BatchResource> children = new ArrayList<BatchResource>();
- public BatchResource(long batchId, Resource r, Snapshot s, @Nullable BatchResource parent) {
+ public BatchResource(long batchId, Resource r, @Nullable BatchResource parent) {
this.batchId = batchId;
this.r = r;
- this.s = s;
this.parent = parent;
if (parent != null) {
parent.children.add(this);
return r;
}
+ public BatchResource setSnapshot(Snapshot snapshot) {
+ this.s = snapshot;
+ return this;
+ }
+
public int snapshotId() {
return s.getId();
}
import org.sonar.batch.scan.measure.MeasureCache;
import org.sonar.batch.scan2.DefaultSensorContext;
import org.sonar.core.component.ComponentKeys;
-import org.sonar.core.component.ScanGraph;
import javax.annotation.CheckForNull;
import javax.annotation.Nullable;
private static final Logger LOG = LoggerFactory.getLogger(DefaultIndex.class);
- private ResourcePersister resourcePersister;
- private MetricFinder metricFinder;
- private final ScanGraph graph;
+ private final ResourceCache resourceCache;
+ private final MetricFinder metricFinder;
// caches
private Project currentProject;
private final LinkPersister linkPersister;
private final EventPersister eventPersister;
- public DefaultIndex(ResourcePersister resourcePersister, DependencyPersister dependencyPersister,
+ public DefaultIndex(ResourceCache resourceCache, DependencyPersister dependencyPersister,
LinkPersister linkPersister, EventPersister eventPersister, ProjectTree projectTree, MetricFinder metricFinder,
- ScanGraph graph, DeprecatedViolations deprecatedViolations, ResourceKeyMigration migration, MeasureCache measureCache) {
- this.resourcePersister = resourcePersister;
+ DeprecatedViolations deprecatedViolations, ResourceKeyMigration migration, MeasureCache measureCache) {
+ this.resourceCache = resourceCache;
this.dependencyPersister = dependencyPersister;
this.linkPersister = linkPersister;
this.eventPersister = eventPersister;
this.projectTree = projectTree;
this.metricFinder = metricFinder;
- this.graph = graph;
this.deprecatedViolations = deprecatedViolations;
this.migration = migration;
this.measureCache = measureCache;
Bucket bucket = new Bucket(rootProject);
addBucket(rootProject, bucket);
migration.checkIfMigrationNeeded(rootProject);
- resourcePersister.saveProject(rootProject, null);
+ resourceCache.add(rootProject, null);
currentProject = rootProject;
for (Project module : rootProject.getModules()) {
addBucket(resource, bucket);
Resource parentResource = parentBucket != null ? parentBucket.getResource() : null;
- BatchResource batchResource = resourcePersister.saveResource(currentProject, resource, parentResource);
- if (ResourceUtils.isPersistable(resource) && !Qualifiers.LIBRARY.equals(resource.getQualifier())) {
- graph.addComponent(resource, batchResource.snapshotId());
- }
+ resourceCache.add(resource, parentResource);
return bucket;
}
+++ /dev/null
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2014 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.batch.index;
-
-import org.apache.commons.lang.ObjectUtils;
-import org.apache.commons.lang.StringUtils;
-import org.sonar.api.database.DatabaseSession;
-import org.sonar.api.database.model.ResourceModel;
-import org.sonar.api.database.model.Snapshot;
-import org.sonar.api.resources.Language;
-import org.sonar.api.resources.Library;
-import org.sonar.api.resources.Project;
-import org.sonar.api.resources.Qualifiers;
-import org.sonar.api.resources.Resource;
-import org.sonar.api.resources.ResourceUtils;
-import org.sonar.api.resources.Scopes;
-import org.sonar.api.security.ResourcePermissions;
-import org.sonar.api.utils.SonarException;
-import org.sonar.api.utils.internal.Uuids;
-
-import javax.annotation.Nullable;
-import javax.persistence.NonUniqueResultException;
-import javax.persistence.Query;
-
-import java.util.Date;
-import java.util.List;
-
-public final class DefaultResourcePersister implements ResourcePersister {
-
- private static final String RESOURCE_ID = "resourceId";
- private static final String LAST = "last";
- private static final String VERSION = "version";
- private static final String SCOPE = "scope";
- private static final String QUALIFIER = "qualifier";
-
- private final DatabaseSession session;
- private final ResourcePermissions permissions;
- private final ResourceCache resourceCache;
-
- public DefaultResourcePersister(DatabaseSession session, ResourcePermissions permissions, ResourceCache resourceCache) {
- this.session = session;
- this.permissions = permissions;
- this.resourceCache = resourceCache;
- }
-
- @Override
- public void saveProject(Project project, @Nullable Project parent) {
- BatchResource batchResource = resourceCache.get(project.getEffectiveKey());
- if (batchResource == null) {
- Snapshot snapshot = persistProject(project, parent);
- addToCache(project, project.getParent(), snapshot);
- }
- }
-
- private BatchResource addToCache(Resource resource, @Nullable Resource parent, Snapshot snapshot) {
- return resourceCache.add(resource, parent, snapshot);
- }
-
- private Snapshot persistProject(Project project, @Nullable Project parent) {
- // temporary hack
- project.setEffectiveKey(project.getKey());
-
- ResourceModel model = findOrCreateModel(project, parent);
- // Used by ResourceKeyMigration in order to know that a project has already being migrated
- model.setDeprecatedKey(project.getKey());
- // language is null for project since multi-language support
- model.setLanguageKey(null);
-
- // For views
- if (project instanceof ResourceCopy) {
- model.setCopyResourceId(((ResourceCopy) project).getCopyResourceId());
- }
-
- Snapshot parentSnapshot = null;
- if (parent != null) {
- // assume that the parent project has already been saved
- parentSnapshot = resourceCache.get(project.getParent().getEffectiveKey()).snapshot();
- model.setRootId((Integer) ObjectUtils.defaultIfNull(parentSnapshot.getRootProjectId(), parentSnapshot.getResourceId()));
- } else {
- model.setRootId(null);
- }
- model = session.save(model);
- project.setId(model.getId());
- project.setUuid(model.getUuid());
-
- Snapshot snapshot = new Snapshot(model, parentSnapshot);
- snapshot.setVersion(project.getAnalysisVersion());
- snapshot.setCreatedAt(project.getAnalysisDate());
- snapshot.setBuildDate(new Date());
- snapshot = session.save(snapshot);
- session.commit();
-
- if (!permissions.hasRoles(project)) {
- permissions.grantDefaultRoles(project);
- }
-
- return snapshot;
- }
-
- @Override
- public BatchResource saveResource(Project project, Resource resource) {
- return saveResource(project, resource, null);
- }
-
- @Override
- public BatchResource saveResource(Project project, Resource resource, @Nullable Resource parent) {
- BatchResource batchResource = resourceCache.get(resource.getEffectiveKey());
- if (batchResource == null || ResourceUtils.isLibrary(resource)) {
- Snapshot s = persist(project, resource, parent);
- batchResource = addToCache(resource, parent, s);
- }
- return batchResource;
- }
-
- private Snapshot persist(Project project, Resource resource, @Nullable Resource parent) {
- Snapshot snapshot;
- if (resource instanceof Project) {
- // should not occur, please use the method saveProject()
- snapshot = persistProject((Project) resource, (Project) parent);
-
- } else if (resource instanceof Library) {
- snapshot = persistLibrary(project, (Library) resource);
-
- } else {
- snapshot = persistFileOrDirectory(project, resource, parent);
- }
-
- return snapshot;
- }
-
- private Snapshot persistLibrary(Project project, Library library) {
- ResourceModel model = findOrCreateModel(library, null);
- model = session.save(model);
- // TODO to be removed
- library.setId(model.getId());
- library.setUuid(model.getUuid());
- library.setEffectiveKey(library.getKey());
-
- Snapshot snapshot = findLibrarySnapshot(model.getId(), library.getVersion());
- if (snapshot == null) {
- snapshot = new Snapshot(model, null);
- snapshot.setCreatedAt(project.getAnalysisDate());
- snapshot.setBuildDate(new Date());
- snapshot.setVersion(library.getVersion());
- snapshot.setStatus(Snapshot.STATUS_PROCESSED);
-
- // see http://jira.codehaus.org/browse/SONAR-1850
- // The qualifier must be LIB, even if the resource is TRK, because this snapshot has no measures.
- snapshot.setQualifier(Qualifiers.LIBRARY);
- snapshot = session.save(snapshot);
- }
- session.commit();
- return snapshot;
- }
-
- private Snapshot findLibrarySnapshot(Integer resourceId, String version) {
- Query query = session.createQuery("from " + Snapshot.class.getSimpleName() +
- " s WHERE s.resourceId=:resourceId AND s.version=:version AND s.scope=:scope AND s.qualifier<>:qualifier AND s.last=:last");
- query.setParameter(RESOURCE_ID, resourceId);
- query.setParameter(VERSION, version);
- query.setParameter(SCOPE, Scopes.PROJECT);
- query.setParameter(QUALIFIER, Qualifiers.LIBRARY);
- query.setParameter(LAST, Boolean.TRUE);
- List<Snapshot> snapshots = query.getResultList();
- if (snapshots.isEmpty()) {
- snapshots = session.getResults(Snapshot.class, RESOURCE_ID, resourceId, VERSION, version, SCOPE, Scopes.PROJECT, QUALIFIER, Qualifiers.LIBRARY);
- }
- return snapshots.isEmpty() ? null : snapshots.get(0);
- }
-
- /**
- * Everything except project and library
- */
- private Snapshot persistFileOrDirectory(Project project, Resource resource, @Nullable Resource parentReference) {
- BatchResource moduleResource = resourceCache.get(project.getEffectiveKey());
- Integer moduleId = moduleResource.resource().getId();
- ResourceModel model = findOrCreateModel(resource, parentReference != null ? parentReference : project);
- model.setRootId(moduleId);
- model = session.save(model);
- resource.setId(model.getId());
- resource.setUuid(model.getUuid());
-
- Snapshot parentSnapshot;
- if (parentReference != null) {
- parentSnapshot = resourceCache.get(parentReference.getEffectiveKey()).snapshot();
- } else {
- parentSnapshot = moduleResource.snapshot();
- }
-
- Snapshot snapshot = new Snapshot(model, parentSnapshot);
- snapshot.setBuildDate(new Date());
- snapshot = session.save(snapshot);
- session.commit();
- return snapshot;
- }
-
- private ResourceModel findOrCreateModel(Resource resource, @Nullable Resource parentResource) {
- ResourceModel model;
- try {
- model = session.getSingleResult(ResourceModel.class, "key", resource.getEffectiveKey());
- if (model == null) {
- if (StringUtils.isBlank(resource.getEffectiveKey())) {
- throw new SonarException("Unable to persist resource " + resource.toString() + ". Resource effective key is blank. This may be caused by an outdated plugin.");
- }
- model = createModel(resource, parentResource);
-
- } else {
- mergeModel(model, resource);
- }
- updateUuids(resource, parentResource, model);
- return model;
-
- } catch (NonUniqueResultException e) {
- throw new SonarException("The resource '" + resource.getEffectiveKey() + "' is duplicated in database.", e);
- }
- }
-
- ResourceModel createModel(Resource resource, @Nullable Resource parentResource) {
- ResourceModel model = new ResourceModel();
- model.setEnabled(Boolean.TRUE);
- model.setDescription(resource.getDescription());
- model.setKey(resource.getEffectiveKey());
- model.setUuid(Uuids.create());
- model.setPath(resource.getPath());
- Language language = resource.getLanguage();
- if (language != null) {
- model.setLanguageKey(language.getKey());
- }
- if (StringUtils.isNotBlank(resource.getName())) {
- model.setName(resource.getName());
- } else {
- model.setName(resource.getKey());
- }
- model.setLongName(resource.getLongName());
- model.setScope(resource.getScope());
- model.setQualifier(resource.getQualifier());
- return model;
- }
-
- private void updateUuids(Resource resource, Resource parentResource, ResourceModel model) {
- // Don't override uuids when persisting a library and a project already exists
- if (ResourceUtils.isLibrary(resource) && !Qualifiers.LIBRARY.equals(model.getQualifier())) {
- return;
- }
- if (parentResource != null) {
- ResourceModel parentModel = session.getSingleResult(ResourceModel.class, "id", parentResource.getId());
- if (parentModel.getProjectUuid() != null) {
- model.setProjectUuid(parentModel.getProjectUuid());
- } else {
- model.setProjectUuid(parentModel.getUuid());
- }
- if (Scopes.isProject(parentResource)) {
- model.setModuleUuid(parentResource.getUuid());
- String parentModuleUuidPath = parentModel.getModuleUuidPath();
- model.setModuleUuidPath(StringUtils.isNotBlank(parentModuleUuidPath) ? parentModuleUuidPath + "." + parentModel.getUuid() : parentModel.getUuid());
- } else {
- model.setModuleUuid(parentModel.getModuleUuid());
- String parentModuleUuidPath = parentModel.getModuleUuidPath();
- model.setModuleUuidPath(StringUtils.isNotBlank(parentModuleUuidPath) ? parentModuleUuidPath : parentModel.getUuid());
- }
- } else {
- // Root module && libraries
- model.setProjectUuid(model.getUuid());
- model.setModuleUuidPath("");
- }
- }
-
- static void mergeModel(ResourceModel model, Resource resource) {
- model.setEnabled(true);
- model.setKey(resource.getEffectiveKey());
- if (StringUtils.isNotBlank(resource.getName())) {
- model.setName(resource.getName());
- }
- if (StringUtils.isNotBlank(resource.getLongName())) {
- model.setLongName(resource.getLongName());
- }
- if (StringUtils.isNotBlank(resource.getDescription())) {
- model.setDescription(resource.getDescription());
- }
- if (StringUtils.isNotBlank(resource.getPath())) {
- model.setPath(resource.getPath());
- }
- if (!ResourceUtils.isLibrary(resource)) {
- model.setScope(resource.getScope());
- model.setQualifier(resource.getQualifier());
- }
- Language language = resource.getLanguage();
- if (language != null) {
- model.setLanguageKey(language.getKey());
- }
- }
-}
import com.google.common.base.Strings;
import com.google.common.collect.Maps;
import org.sonar.api.BatchComponent;
-import org.sonar.api.database.model.Snapshot;
import org.sonar.api.resources.Library;
import org.sonar.api.resources.Resource;
public class ResourceCache implements BatchComponent {
// resource by component key
- private final Map<String, BatchResource> resources = Maps.newHashMap();
+ private final Map<String, BatchResource> resources = Maps.newLinkedHashMap();
// dedicated cache for libraries
- private final Map<Library, BatchResource> libraries = Maps.newHashMap();
+ private final Map<Library, BatchResource> libraries = Maps.newLinkedHashMap();
@CheckForNull
public BatchResource get(String componentKey) {
}
}
- public BatchResource add(Resource resource, @Nullable Resource parentResource, Snapshot s) {
+ public BatchResource add(Resource resource, @Nullable Resource parentResource) {
String componentKey = resource.getEffectiveKey();
Preconditions.checkState(!Strings.isNullOrEmpty(componentKey), "Missing resource effective key");
BatchResource parent = parentResource != null ? get(parentResource.getEffectiveKey()) : null;
- BatchResource batchResource = new BatchResource((long) resources.size() + 1, resource, s, parent);
+ BatchResource batchResource = new BatchResource((long) resources.size() + 1, resource, parent);
if (!(resource instanceof Library)) {
// Libraries can have the same effective key than a project so we can't cache by effectiveKey
resources.put(componentKey, batchResource);
public Collection<BatchResource> all() {
return resources.values();
}
+
+ public Collection<BatchResource> allLibraries() {
+ return libraries.values();
+ }
}
*/
package org.sonar.batch.index;
+import org.apache.commons.lang.ObjectUtils;
+import org.apache.commons.lang.StringUtils;
+import org.sonar.api.database.DatabaseSession;
+import org.sonar.api.database.model.ResourceModel;
+import org.sonar.api.database.model.Snapshot;
+import org.sonar.api.resources.Language;
+import org.sonar.api.resources.Library;
import org.sonar.api.resources.Project;
+import org.sonar.api.resources.Qualifiers;
import org.sonar.api.resources.Resource;
+import org.sonar.api.resources.ResourceUtils;
+import org.sonar.api.resources.Scopes;
+import org.sonar.api.security.ResourcePermissions;
+import org.sonar.api.utils.SonarException;
+import org.sonar.api.utils.internal.Uuids;
+import org.sonar.batch.ProjectTree;
+import org.sonar.core.component.ScanGraph;
+import javax.annotation.CheckForNull;
import javax.annotation.Nullable;
+import javax.persistence.NonUniqueResultException;
+import javax.persistence.Query;
-public interface ResourcePersister {
+import java.util.Date;
+import java.util.List;
- void saveProject(Project project, @Nullable Project parent);
+public final class ResourcePersister implements ScanPersister {
- /**
- * Persist a resource in database.
- */
- BatchResource saveResource(Project project, Resource resource, @Nullable Resource parent);
+ private static final String RESOURCE_ID = "resourceId";
+ private static final String LAST = "last";
+ private static final String VERSION = "version";
+ private static final String SCOPE = "scope";
+ private static final String QUALIFIER = "qualifier";
+
+ private final DatabaseSession session;
+ private final ResourcePermissions permissions;
+ private final ResourceCache resourceCache;
+ private final ScanGraph graph;
+ private final ProjectTree projectTree;
+
+ public ResourcePersister(ProjectTree projectTree, DatabaseSession session, ResourcePermissions permissions, ResourceCache resourceCache, ScanGraph graph) {
+ this.projectTree = projectTree;
+ this.session = session;
+ this.permissions = permissions;
+ this.resourceCache = resourceCache;
+ this.graph = graph;
+ }
+
+ @Override
+ public void persist() {
+ for (BatchResource resource : resourceCache.all()) {
+ persist(resource);
+ }
+
+ for (BatchResource lib : resourceCache.allLibraries()) {
+ Snapshot s = persistLibrary(projectTree.getRootProject().getAnalysisDate(), (Library) lib.resource());
+ lib.setSnapshot(s);
+ }
+ }
+
+ private void persist(BatchResource batchResource) {
+ if (batchResource.snapshot() != null) {
+ // already persisted
+ return;
+ }
+ BatchResource parentBatchResource = batchResource.parent();
+ if (parentBatchResource != null) {
+ persist(parentBatchResource);
+ }
+ Snapshot s = persist(findParentModule(batchResource), batchResource.resource(), parentBatchResource != null ? parentBatchResource.resource() : null);
+ batchResource.setSnapshot(s);
+ if (ResourceUtils.isPersistable(batchResource.resource())) {
+ graph.addComponent(batchResource.resource(), batchResource.snapshotId());
+ }
+ }
+
+ @CheckForNull
+ private Project findParentModule(BatchResource batchResource) {
+ if (batchResource != null && batchResource.parent() != null) {
+ if (batchResource.parent().resource() instanceof Project) {
+ return (Project) batchResource.parent().resource();
+ } else {
+ return findParentModule(batchResource.parent());
+ }
+ }
+ return null;
+ }
+
+ private Snapshot persistProject(Project project, @Nullable Project parent) {
+ // temporary hack
+ project.setEffectiveKey(project.getKey());
+
+ ResourceModel model = findOrCreateModel(project, parent);
+ // Used by ResourceKeyMigration in order to know that a project has already being migrated
+ model.setDeprecatedKey(project.getKey());
+ // language is null for project since multi-language support
+ model.setLanguageKey(null);
+
+ // For views
+ if (project instanceof ResourceCopy) {
+ model.setCopyResourceId(((ResourceCopy) project).getCopyResourceId());
+ }
+
+ Snapshot parentSnapshot = null;
+ if (parent != null) {
+ // assume that the parent project has already been saved
+ parentSnapshot = resourceCache.get(project.getParent().getEffectiveKey()).snapshot();
+ model.setRootId((Integer) ObjectUtils.defaultIfNull(parentSnapshot.getRootProjectId(), parentSnapshot.getResourceId()));
+ } else {
+ model.setRootId(null);
+ }
+ model = session.save(model);
+ project.setId(model.getId());
+ project.setUuid(model.getUuid());
+
+ Snapshot snapshot = new Snapshot(model, parentSnapshot);
+ snapshot.setVersion(project.getAnalysisVersion());
+ snapshot.setCreatedAt(project.getAnalysisDate());
+ snapshot.setBuildDate(new Date());
+ snapshot = session.save(snapshot);
+ session.commit();
+
+ if (!permissions.hasRoles(project)) {
+ permissions.grantDefaultRoles(project);
+ }
+
+ return snapshot;
+ }
+
+ Snapshot persist(Project project, Resource resource, @Nullable Resource parent) {
+ Snapshot snapshot;
+ if (resource instanceof Project) {
+ // should not occur, please use the method saveProject()
+ snapshot = persistProject((Project) resource, (Project) parent);
+
+ } else if (resource instanceof Library) {
+ snapshot = persistLibrary(project.getAnalysisDate(), (Library) resource);
+
+ } else {
+ snapshot = persistFileOrDirectory(project, resource, parent);
+ }
+
+ return snapshot;
+ }
+
+ private Snapshot persistLibrary(Date analysisDate, Library library) {
+ ResourceModel model = findOrCreateModel(library, null);
+ model = session.save(model);
+ // TODO to be removed
+ library.setId(model.getId());
+ library.setUuid(model.getUuid());
+ library.setEffectiveKey(library.getKey());
+
+ Snapshot snapshot = findLibrarySnapshot(model.getId(), library.getVersion());
+ if (snapshot == null) {
+ snapshot = new Snapshot(model, null);
+ snapshot.setCreatedAt(analysisDate);
+ snapshot.setBuildDate(new Date());
+ snapshot.setVersion(library.getVersion());
+ snapshot.setStatus(Snapshot.STATUS_PROCESSED);
+
+ // see http://jira.codehaus.org/browse/SONAR-1850
+ // The qualifier must be LIB, even if the resource is TRK, because this snapshot has no measures.
+ snapshot.setQualifier(Qualifiers.LIBRARY);
+ snapshot = session.save(snapshot);
+ }
+ session.commit();
+ return snapshot;
+ }
+
+ private Snapshot findLibrarySnapshot(Integer resourceId, String version) {
+ Query query = session.createQuery("from " + Snapshot.class.getSimpleName() +
+ " s WHERE s.resourceId=:resourceId AND s.version=:version AND s.scope=:scope AND s.qualifier<>:qualifier AND s.last=:last");
+ query.setParameter(RESOURCE_ID, resourceId);
+ query.setParameter(VERSION, version);
+ query.setParameter(SCOPE, Scopes.PROJECT);
+ query.setParameter(QUALIFIER, Qualifiers.LIBRARY);
+ query.setParameter(LAST, Boolean.TRUE);
+ List<Snapshot> snapshots = query.getResultList();
+ if (snapshots.isEmpty()) {
+ snapshots = session.getResults(Snapshot.class, RESOURCE_ID, resourceId, VERSION, version, SCOPE, Scopes.PROJECT, QUALIFIER, Qualifiers.LIBRARY);
+ }
+ return snapshots.isEmpty() ? null : snapshots.get(0);
+ }
/**
- * Persist a resource in database.
+ * Everything except project and library
*/
- BatchResource saveResource(Project project, Resource resource);
+ private Snapshot persistFileOrDirectory(Project project, Resource resource, @Nullable Resource parentReference) {
+ BatchResource moduleResource = resourceCache.get(project.getEffectiveKey());
+ Integer moduleId = moduleResource.resource().getId();
+ ResourceModel model = findOrCreateModel(resource, parentReference != null ? parentReference : project);
+ model.setRootId(moduleId);
+ model = session.save(model);
+ resource.setId(model.getId());
+ resource.setUuid(model.getUuid());
+
+ Snapshot parentSnapshot;
+ if (parentReference != null) {
+ parentSnapshot = resourceCache.get(parentReference.getEffectiveKey()).snapshot();
+ } else {
+ parentSnapshot = moduleResource.snapshot();
+ }
+
+ Snapshot snapshot = new Snapshot(model, parentSnapshot);
+ snapshot.setBuildDate(new Date());
+ snapshot = session.save(snapshot);
+ session.commit();
+ return snapshot;
+ }
+
+ private ResourceModel findOrCreateModel(Resource resource, @Nullable Resource parentResource) {
+ ResourceModel model;
+ try {
+ model = session.getSingleResult(ResourceModel.class, "key", resource.getEffectiveKey());
+ if (model == null) {
+ if (StringUtils.isBlank(resource.getEffectiveKey())) {
+ throw new SonarException("Unable to persist resource " + resource.toString() + ". Resource effective key is blank. This may be caused by an outdated plugin.");
+ }
+ model = createModel(resource, parentResource);
+
+ } else {
+ mergeModel(model, resource);
+ }
+ updateUuids(resource, parentResource, model);
+ return model;
+
+ } catch (NonUniqueResultException e) {
+ throw new SonarException("The resource '" + resource.getEffectiveKey() + "' is duplicated in database.", e);
+ }
+ }
+
+ ResourceModel createModel(Resource resource, @Nullable Resource parentResource) {
+ ResourceModel model = new ResourceModel();
+ model.setEnabled(Boolean.TRUE);
+ model.setDescription(resource.getDescription());
+ model.setKey(resource.getEffectiveKey());
+ model.setUuid(Uuids.create());
+ model.setPath(resource.getPath());
+ Language language = resource.getLanguage();
+ if (language != null) {
+ model.setLanguageKey(language.getKey());
+ }
+ if (StringUtils.isNotBlank(resource.getName())) {
+ model.setName(resource.getName());
+ } else {
+ model.setName(resource.getKey());
+ }
+ model.setLongName(resource.getLongName());
+ model.setScope(resource.getScope());
+ model.setQualifier(resource.getQualifier());
+ return model;
+ }
+
+ private void updateUuids(Resource resource, Resource parentResource, ResourceModel model) {
+ // Don't override uuids when persisting a library and a project already exists
+ if (ResourceUtils.isLibrary(resource) && !Qualifiers.LIBRARY.equals(model.getQualifier())) {
+ return;
+ }
+ if (parentResource != null) {
+ ResourceModel parentModel = session.getSingleResult(ResourceModel.class, "id", parentResource.getId());
+ if (parentModel.getProjectUuid() != null) {
+ model.setProjectUuid(parentModel.getProjectUuid());
+ } else {
+ model.setProjectUuid(parentModel.getUuid());
+ }
+ if (Scopes.isProject(parentResource)) {
+ model.setModuleUuid(parentResource.getUuid());
+ String parentModuleUuidPath = parentModel.getModuleUuidPath();
+ model.setModuleUuidPath(StringUtils.isNotBlank(parentModuleUuidPath) ? parentModuleUuidPath + "." + parentModel.getUuid() : parentModel.getUuid());
+ } else {
+ model.setModuleUuid(parentModel.getModuleUuid());
+ String parentModuleUuidPath = parentModel.getModuleUuidPath();
+ model.setModuleUuidPath(StringUtils.isNotBlank(parentModuleUuidPath) ? parentModuleUuidPath : parentModel.getUuid());
+ }
+ } else {
+ // Root module && libraries
+ model.setProjectUuid(model.getUuid());
+ model.setModuleUuidPath("");
+ }
+ }
+ static void mergeModel(ResourceModel model, Resource resource) {
+ model.setEnabled(true);
+ model.setKey(resource.getEffectiveKey());
+ if (StringUtils.isNotBlank(resource.getName())) {
+ model.setName(resource.getName());
+ }
+ if (StringUtils.isNotBlank(resource.getLongName())) {
+ model.setLongName(resource.getLongName());
+ }
+ if (StringUtils.isNotBlank(resource.getDescription())) {
+ model.setDescription(resource.getDescription());
+ }
+ if (StringUtils.isNotBlank(resource.getPath())) {
+ model.setPath(resource.getPath());
+ }
+ if (!ResourceUtils.isLibrary(resource)) {
+ model.setScope(resource.getScope());
+ model.setQualifier(resource.getQualifier());
+ }
+ Language language = resource.getLanguage();
+ if (language != null) {
+ model.setLanguageKey(language.getKey());
+ }
+ }
}
import org.sonar.batch.index.Caches;
import org.sonar.batch.index.ComponentDataCache;
import org.sonar.batch.index.DefaultIndex;
-import org.sonar.batch.index.DefaultResourcePersister;
+import org.sonar.batch.index.ResourcePersister;
import org.sonar.batch.index.DependencyPersister;
import org.sonar.batch.index.DuplicationPersister;
import org.sonar.batch.index.EventPersister;
LinkPersister.class,
MeasurePersister.class,
DuplicationPersister.class,
- DefaultResourcePersister.class,
+ ResourcePersister.class,
SourcePersister.class,
CodeColorizers.class,
DefaultNotificationManager.class,
import org.sonar.api.resources.Project;
import org.sonar.api.resources.Resource;
import org.sonar.batch.index.ResourceKeyMigration;
+import org.sonar.batch.index.ResourcePersister;
import org.sonar.batch.util.DeprecatedKeyUtils;
/**
private final SonarIndex sonarIndex;
private final ResourceKeyMigration migration;
private final Project module;
+ private final ResourcePersister resourcePersister;
- public ComponentIndexer(Project module, Languages languages, SonarIndex sonarIndex, ResourceKeyMigration migration) {
+ public ComponentIndexer(Project module, Languages languages, SonarIndex sonarIndex, ResourceKeyMigration migration,
+ ResourcePersister resourcePersister) {
this.module = module;
this.languages = languages;
this.sonarIndex = sonarIndex;
this.migration = migration;
+ this.resourcePersister = resourcePersister;
+ }
+
+ public ComponentIndexer(Project module, Languages languages, SonarIndex sonarIndex, ResourceKeyMigration migration) {
+ this(module, languages, sonarIndex, migration, null);
}
public void execute(FileSystem fs) {
+ if (resourcePersister != null) {
+ // Force persistence of module structure in order to know if project should be migrated
+ resourcePersister.persist();
+ }
+
migration.migrateIfNeeded(module, fs);
for (InputFile inputFile : fs.inputFiles(fs.predicates().all())) {
}
sonarIndex.index(sonarFile);
}
+
+ if (resourcePersister != null) {
+ // Persist all files in order to have snapshot availables
+ resourcePersister.persist();
+ }
}
}
import org.junit.rules.TemporaryFolder;
import org.sonar.api.batch.bootstrap.ProjectDefinition;
import org.sonar.api.batch.measure.MetricFinder;
-import org.sonar.api.database.model.Snapshot;
import org.sonar.api.measures.CoreMetrics;
import org.sonar.api.measures.Measure;
import org.sonar.api.measures.MeasuresFilters;
import org.sonar.batch.issue.DeprecatedViolations;
import org.sonar.batch.issue.ModuleIssues;
import org.sonar.batch.scan.measure.MeasureCache;
-import org.sonar.core.component.ScanGraph;
import java.io.IOException;
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.anyString;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;
ruleFinder = mock(RuleFinder.class);
ProjectTree projectTree = mock(ProjectTree.class);
- ResourcePersister resourcePersister = mock(ResourcePersister.class);
- index = new DefaultIndex(resourcePersister, null, null, null, projectTree, metricFinder, mock(ScanGraph.class), deprecatedViolations,
+ ResourceCache resourceCache = new ResourceCache();
+ index = new DefaultIndex(resourceCache, null, null, null, projectTree, metricFinder, deprecatedViolations,
mock(ResourceKeyMigration.class),
mock(MeasureCache.class));
moduleB1 = new Project("moduleB1").setParent(moduleB);
when(projectTree.getProjectDefinition(moduleB1)).thenReturn(ProjectDefinition.create().setBaseDir(new java.io.File(baseDir, "moduleB/moduleB1")));
- when(resourcePersister.saveResource(any(Project.class), any(Resource.class), any(Resource.class))).thenReturn(
- new BatchResource(1, mock(Resource.class), new Snapshot().setId(1), null));
-
RulesProfile rulesProfile = RulesProfile.create();
rule = Rule.create("repoKey", "ruleKey", "Rule");
rule.setId(1);
+++ /dev/null
-/*
- * SonarQube, open source software quality management tool.
- * Copyright (C) 2008-2014 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.batch.index;
-
-import org.apache.ibatis.session.SqlSession;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.rules.ExpectedException;
-import org.junit.rules.TemporaryFolder;
-import org.sonar.api.CoreProperties;
-import org.sonar.api.batch.bootstrap.ProjectDefinition;
-import org.sonar.api.batch.measure.MetricFinder;
-import org.sonar.api.config.Settings;
-import org.sonar.api.database.model.Snapshot;
-import org.sonar.api.resources.Directory;
-import org.sonar.api.resources.File;
-import org.sonar.api.resources.Library;
-import org.sonar.api.resources.Project;
-import org.sonar.api.resources.Resource;
-import org.sonar.api.security.ResourcePermissions;
-import org.sonar.batch.ProjectTree;
-import org.sonar.batch.issue.DeprecatedViolations;
-import org.sonar.batch.scan.measure.MeasureCache;
-import org.sonar.core.component.ComponentDto;
-import org.sonar.core.component.ScanGraph;
-import org.sonar.core.component.db.ComponentMapper;
-import org.sonar.jpa.test.AbstractDbUnitTestCase;
-
-import javax.persistence.Query;
-
-import java.io.IOException;
-import java.text.ParseException;
-import java.text.SimpleDateFormat;
-import java.util.Arrays;
-
-import static org.fest.assertions.Assertions.assertThat;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.never;
-import static org.mockito.Mockito.verify;
-import static org.mockito.Mockito.when;
-
-public class DefaultResourcePersisterTest extends AbstractDbUnitTestCase {
-
- @Rule
- public ExpectedException thrown = ExpectedException.none();
-
- @Rule
- public TemporaryFolder temp = new TemporaryFolder();
-
- private Project singleProject, singleCopyProject, multiModuleProject, moduleA, moduleB, moduleB1, existingProject;
- private ResourceCache resourceCache;
-
- @Before
- public void before() throws ParseException {
- resourceCache = new ResourceCache();
-
- SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy");
- singleProject = newProject("foo", "java");
- singleProject.setName("Foo").setDescription("some description").setAnalysisDate(format.parse("25/12/2010"));
-
- existingProject = newProject("my:key", "java");
- existingProject.setName("Other project").setDescription("some description").setAnalysisDate(format.parse("25/12/2010"));
-
- singleCopyProject = newCopyProject("foo", "java", 10);
- singleCopyProject.setName("Foo").setDescription("some description").setAnalysisDate(format.parse("25/12/2010"));
-
- multiModuleProject = newProject("root", "java");
- multiModuleProject.setName("Root").setAnalysisDate(format.parse("25/12/2010"));
-
- moduleA = newProject("a", "java");
- moduleA.setName("A").setAnalysisDate(format.parse("25/12/2010"));
- moduleA.setParent(multiModuleProject);
- moduleA.setPath("/moduleA");
-
- moduleB = newProject("b", "java");
- moduleB.setName("B").setAnalysisDate(format.parse("25/12/2010"));
- moduleB.setParent(multiModuleProject);
- moduleB.setPath("/moduleB");
-
- moduleB1 = newProject("b1", "java");
- moduleB1.setName("B1").setAnalysisDate(format.parse("25/12/2010"));
- moduleB1.setParent(moduleB);
- moduleB1.setPath("/moduleB1");
- }
-
- @Test
- public void shouldSaveNewProject() {
- setupData("shared");
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
- persister.saveProject(singleProject, null);
-
- checkTables("shouldSaveNewProject", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
- "projects", "snapshots");
-
- // Need to enable snapshot to make resource visible using ComponentMapper
- enableSnapshot(1001);
- try (SqlSession session = getMyBatis().openSession(false)) {
- ComponentDto newProject = session.getMapper(ComponentMapper.class).selectByKey("foo");
- assertThat(newProject.uuid()).isNotNull();
- assertThat(newProject.projectUuid()).isEqualTo(newProject.uuid());
- assertThat(newProject.moduleUuid()).isNull();
- assertThat(newProject.moduleUuidPath()).isEmpty();
- // SONAR-3636 : created_at must be fed when inserting a new entry in the 'projects' table
- assertThat(newProject.getCreatedAt()).isNotNull();
- }
- }
-
- @Test
- public void shouldSaveCopyProject() {
- setupData("shared");
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
- persister.saveProject(singleCopyProject, null);
-
- checkTables("shouldSaveCopyProject", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
- "projects", "snapshots");
- // Need to enable snapshot to make resource visible using ComponentMapper
- enableSnapshot(1001);
- try (SqlSession session = getMyBatis().openSession(false)) {
- ComponentDto newProject = session.getMapper(ComponentMapper.class).selectByKey("foo");
- assertThat(newProject.uuid()).isNotNull();
- assertThat(newProject.projectUuid()).isEqualTo(newProject.uuid());
- assertThat(newProject.moduleUuid()).isNull();
- assertThat(newProject.moduleUuidPath()).isEmpty();
- }
- }
-
- @Test
- public void shouldSaveNewMultiModulesProject() {
- setupData("shared");
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
- persister.saveProject(multiModuleProject, null);
- persister.saveProject(moduleA, multiModuleProject);
- persister.saveProject(moduleB, multiModuleProject);
- persister.saveProject(moduleB1, moduleB);
- Resource file = File.create("src/main/java/org/Foo.java").setEffectiveKey("b1:src/main/java/org/Foo.java");
- file.getParent().setEffectiveKey("b1:src/main/java/org");
- persister.saveResource(moduleB1, file.getParent());
- persister.saveResource(moduleB1, file, file.getParent());
-
- checkTables("shouldSaveNewMultiModulesProject",
- new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"}, "projects", "snapshots");
-
- // Need to enable snapshot to make resource visible using ComponentMapper
- enableSnapshot(1001);
- enableSnapshot(1002);
- enableSnapshot(1003);
- enableSnapshot(1004);
- enableSnapshot(1005);
- enableSnapshot(1006);
- try (SqlSession session = getMyBatis().openSession(false)) {
- ComponentDto root = session.getMapper(ComponentMapper.class).selectByKey("root");
- assertThat(root.uuid()).isNotNull();
- assertThat(root.projectUuid()).isEqualTo(root.uuid());
- assertThat(root.moduleUuid()).isNull();
- assertThat(root.moduleUuidPath()).isEmpty();
- ComponentDto a = session.getMapper(ComponentMapper.class).selectByKey("a");
- assertThat(a.uuid()).isNotNull();
- assertThat(a.projectUuid()).isEqualTo(root.uuid());
- assertThat(a.moduleUuid()).isEqualTo(root.uuid());
- assertThat(a.moduleUuidPath()).isEqualTo(root.uuid());
- ComponentDto b = session.getMapper(ComponentMapper.class).selectByKey("b");
- assertThat(b.uuid()).isNotNull();
- assertThat(b.projectUuid()).isEqualTo(root.uuid());
- assertThat(b.moduleUuid()).isEqualTo(root.uuid());
- assertThat(b.moduleUuidPath()).isEqualTo(root.uuid());
- ComponentDto b1 = session.getMapper(ComponentMapper.class).selectByKey("b1");
- assertThat(b1.uuid()).isNotNull();
- assertThat(b1.projectUuid()).isEqualTo(root.uuid());
- assertThat(b1.moduleUuid()).isEqualTo(b.uuid());
- assertThat(b1.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid());
- ComponentDto dir = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org");
- assertThat(dir.uuid()).isNotNull();
- assertThat(dir.projectUuid()).isEqualTo(root.uuid());
- assertThat(dir.moduleUuid()).isEqualTo(b1.uuid());
- assertThat(dir.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
- ComponentDto fileComp = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org/Foo.java");
- assertThat(fileComp.uuid()).isNotNull();
- assertThat(fileComp.projectUuid()).isEqualTo(root.uuid());
- assertThat(fileComp.moduleUuid()).isEqualTo(b1.uuid());
- assertThat(fileComp.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
- }
- }
-
- // FIXME this is a kind of medium test
- @Test
- public void shouldSaveNewMultiModulesProjectUsingIndex() throws IOException {
- setupData("shared");
-
- java.io.File baseDir = temp.newFolder();
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
-
- ProjectTree projectTree = mock(ProjectTree.class);
- when(projectTree.getRootProject()).thenReturn(multiModuleProject);
- when(projectTree.getProjectDefinition(multiModuleProject)).thenReturn(ProjectDefinition.create().setBaseDir(baseDir));
- when(projectTree.getProjectDefinition(moduleA)).thenReturn(ProjectDefinition.create().setBaseDir(new java.io.File(baseDir, "moduleA")));
- when(projectTree.getProjectDefinition(moduleB)).thenReturn(ProjectDefinition.create().setBaseDir(new java.io.File(baseDir, "moduleB")));
- when(projectTree.getProjectDefinition(moduleB1)).thenReturn(ProjectDefinition.create().setBaseDir(new java.io.File(baseDir, "moduleB/moduleB1")));
-
- DefaultIndex index = new DefaultIndex(persister, null, null, null, projectTree, mock(MetricFinder.class), mock(ScanGraph.class),
- mock(DeprecatedViolations.class),
- mock(ResourceKeyMigration.class),
- mock(MeasureCache.class));
-
- index.start();
-
- Resource file = File.create("src/main/java/org/Foo.java");
-
- index.setCurrentProject(moduleB1, null);
- index.index(file);
-
- // Emulate another project having library dependency on moduleA
- index.addResource(new Library(moduleA.getKey(), "1.0"));
-
- checkTables("shouldSaveNewMultiModulesProjectAndLibrary",
- new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"}, "projects", "snapshots");
-
- // Need to enable snapshot to make resource visible using ComponentMapper
- enableSnapshot(1001);
- enableSnapshot(1002);
- enableSnapshot(1003);
- enableSnapshot(1004);
- enableSnapshot(1005);
- enableSnapshot(1006);
- try (SqlSession session = getMyBatis().openSession(false)) {
- ComponentDto root = session.getMapper(ComponentMapper.class).selectByKey("root");
- System.out.println("Root: " + root.uuid());
- assertThat(root.uuid()).isNotNull();
- assertThat(root.projectUuid()).isEqualTo(root.uuid());
- assertThat(root.moduleUuid()).isNull();
- assertThat(root.moduleUuidPath()).isEmpty();
- ComponentDto a = session.getMapper(ComponentMapper.class).selectByKey("a");
- System.out.println("A: " + a.uuid());
- assertThat(a.uuid()).isNotNull();
- assertThat(a.projectUuid()).isEqualTo(root.uuid());
- assertThat(a.moduleUuid()).isEqualTo(root.uuid());
- assertThat(a.moduleUuidPath()).isEqualTo(root.uuid());
- ComponentDto b = session.getMapper(ComponentMapper.class).selectByKey("b");
- System.out.println("B: " + b.uuid());
- assertThat(b.uuid()).isNotNull();
- assertThat(b.projectUuid()).isEqualTo(root.uuid());
- assertThat(b.moduleUuid()).isEqualTo(root.uuid());
- assertThat(b.moduleUuidPath()).isEqualTo(root.uuid());
- ComponentDto b1 = session.getMapper(ComponentMapper.class).selectByKey("b1");
- System.out.println("B1: " + b1.uuid());
- assertThat(b1.uuid()).isNotNull();
- assertThat(b1.projectUuid()).isEqualTo(root.uuid());
- assertThat(b1.moduleUuid()).isEqualTo(b.uuid());
- assertThat(b1.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid());
- ComponentDto dir = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org");
- assertThat(dir.uuid()).isNotNull();
- assertThat(dir.projectUuid()).isEqualTo(root.uuid());
- assertThat(dir.moduleUuid()).isEqualTo(b1.uuid());
- assertThat(dir.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
- ComponentDto fileComp = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org/Foo.java");
- assertThat(fileComp.uuid()).isNotNull();
- assertThat(fileComp.projectUuid()).isEqualTo(root.uuid());
- assertThat(fileComp.moduleUuid()).isEqualTo(b1.uuid());
- assertThat(fileComp.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
- }
- }
-
- @Test
- public void shouldSaveNewDirectory() {
- setupData("shared");
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
- persister.saveProject(singleProject, null);
- persister.saveResource(singleProject,
- Directory.create("src/main/java/org/foo", "org.foo").setEffectiveKey("foo:src/main/java/org/foo"));
- // check that the directory is attached to the project
- checkTables("shouldSaveNewDirectory", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
- "projects", "snapshots");
-
- // Need to enable snapshot to make resource visible using ComponentMapper
- enableSnapshot(1001);
- enableSnapshot(1002);
- try (SqlSession session = getMyBatis().openSession(false)) {
- ComponentDto newProject = session.getMapper(ComponentMapper.class).selectByKey("foo");
- ComponentDto newDir = session.getMapper(ComponentMapper.class).selectByKey("foo:src/main/java/org/foo");
- assertThat(newDir.uuid()).isNotNull();
- assertThat(newDir.projectUuid()).isEqualTo(newProject.uuid());
- assertThat(newDir.moduleUuid()).isEqualTo(newProject.uuid());
- assertThat(newDir.moduleUuidPath()).isEqualTo(newProject.uuid());
- }
- }
-
- private void enableSnapshot(int resourceId) {
- String hql = "UPDATE " + Snapshot.class.getSimpleName() + " SET last=true";
- hql += " WHERE project_id=:resourceId";
- Query query = getSession().createQuery(hql);
- query.setParameter("resourceId", resourceId);
- query.executeUpdate();
- getSession().commit();
- }
-
- @Test
- public void shouldSaveNewLibrary() {
- setupData("shared");
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
- persister.saveProject(singleProject, null);
- persister.saveResource(singleProject, new Library("junit:junit", "4.8.2").setEffectiveKey("junit:junit"));
- persister.saveResource(singleProject, new Library("junit:junit", "4.8.2").setEffectiveKey("junit:junit"));// do nothing, already saved
- persister.saveResource(singleProject, new Library("junit:junit", "3.2").setEffectiveKey("junit:junit"));
-
- checkTables("shouldSaveNewLibrary", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
- "projects", "snapshots");
-
- // Need to enable snapshot to make resource visible using ComponentMapper
- enableSnapshot(1002);
- try (SqlSession session = getMyBatis().openSession(false)) {
- // FIXME selectByKey returns duplicates for libraries because of the join on snapshots table
- ComponentDto newLib = session.getMapper(ComponentMapper.class).findByKeys(Arrays.asList("junit:junit")).get(0);
- assertThat(newLib.uuid()).isNotNull();
- assertThat(newLib.projectUuid()).isEqualTo(newLib.uuid());
- assertThat(newLib.moduleUuid()).isNull();
- assertThat(newLib.moduleUuidPath()).isEmpty();
- }
- }
-
- @Test
- public void shouldUpdateExistingResource() {
- setupData("shouldUpdateExistingResource");
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
- singleProject.setName("new name");
- singleProject.setDescription("new description");
- persister.saveProject(singleProject, null);
-
- checkTables("shouldUpdateExistingResource", new String[] {"build_date", "created_at", "authorization_updated_at"}, "projects", "snapshots");
- }
-
- // SONAR-1700
- @Test
- public void shouldRemoveRootIndexIfResourceIsProject() {
- setupData("shouldRemoveRootIndexIfResourceIsProject");
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), mock(ResourcePermissions.class), resourceCache);
- persister.saveProject(singleProject, null);
-
- checkTables("shouldRemoveRootIndexIfResourceIsProject", new String[] {"build_date", "created_at", "authorization_updated_at"}, "projects", "snapshots");
- }
-
- @Test
- public void shouldGrantDefaultPermissionsIfNewProject() {
- setupData("shared");
-
- ResourcePermissions permissions = mock(ResourcePermissions.class);
- when(permissions.hasRoles(singleProject)).thenReturn(false);
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), permissions, resourceCache);
- persister.saveProject(singleProject, null);
-
- verify(permissions).grantDefaultRoles(singleProject);
- }
-
- @Test
- public void shouldNotGrantDefaultPermissionsIfExistingProject() {
- setupData("shared");
-
- ResourcePermissions permissions = mock(ResourcePermissions.class);
- when(permissions.hasRoles(singleProject)).thenReturn(true);
-
- ResourcePersister persister = new DefaultResourcePersister(getSession(), permissions, resourceCache);
- persister.saveProject(singleProject, null);
-
- verify(permissions, never()).grantDefaultRoles(singleProject);
- }
-
- private static Project newProject(String key, String language) {
- Settings settings = new Settings();
- settings.setProperty(CoreProperties.PROJECT_LANGUAGE_PROPERTY, language);
- return new Project(key).setSettings(settings).setAnalysisType(Project.AnalysisType.DYNAMIC);
- }
-
- private static Project newCopyProject(String key, String language, int copyResourceId) {
- Settings settings = new Settings();
- settings.setProperty(CoreProperties.PROJECT_LANGUAGE_PROPERTY, language);
- return new CopyProject(key, copyResourceId).setSettings(settings).setAnalysisType(Project.AnalysisType.DYNAMIC);
- }
-
- private static class CopyProject extends Project implements ResourceCopy {
-
- private int copyResourceId;
-
- public CopyProject(String key, int copyResourceId) {
- super(key);
- this.copyResourceId = copyResourceId;
- }
-
- public int getCopyResourceId() {
- return copyResourceId;
- }
-
- }
-
-}
Snapshot snapshot = new Snapshot();
snapshot.setId(100);
snapshot.setResourceId(200);
- resourceCache.add(new Project("myProject").setId(200), null, snapshot);
+ resourceCache.add(new Project("myProject").setId(200), null).setSnapshot(snapshot);
data = new ComponentDataCache(caches);
data.setStringData("myProject", SnapshotDataTypes.FILE_HASHES, "org/struts/Action.java=123ABC");
private static BatchResource batchResource(Resource resource, int id) {
Snapshot snapshot = mock(Snapshot.class);
when(snapshot.getId()).thenReturn(id);
- return new BatchResource(1, resource, snapshot, null);
+ return new BatchResource(1, resource, null).setSnapshot(snapshot);
}
private static Metric ncloc() {
package org.sonar.batch.index;
import org.junit.Test;
-import org.sonar.api.database.model.Snapshot;
import org.sonar.api.resources.File;
import org.sonar.api.resources.Resource;
ResourceCache cache = new ResourceCache();
String componentKey = "struts:src/org/struts/Action.java";
Resource resource = new File("org/struts/Action.java").setEffectiveKey(componentKey);
- cache.add(resource, null, new Snapshot());
+ cache.add(resource, null);
assertThat(cache.get(componentKey).resource()).isSameAs(resource);
assertThat(cache.get("other")).isNull();
ResourceCache cache = new ResourceCache();
Resource resource = new File("org/struts/Action.java").setEffectiveKey(null);
try {
- cache.add(resource, null, new Snapshot());
+ cache.add(resource, null);
fail();
} catch (IllegalStateException e) {
// success
--- /dev/null
+/*
+ * SonarQube, open source software quality management tool.
+ * Copyright (C) 2008-2014 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.batch.index;
+
+import org.apache.ibatis.session.SqlSession;
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+import org.junit.rules.TemporaryFolder;
+import org.sonar.api.CoreProperties;
+import org.sonar.api.batch.bootstrap.ProjectDefinition;
+import org.sonar.api.batch.measure.MetricFinder;
+import org.sonar.api.config.Settings;
+import org.sonar.api.database.model.Snapshot;
+import org.sonar.api.resources.Directory;
+import org.sonar.api.resources.File;
+import org.sonar.api.resources.Library;
+import org.sonar.api.resources.Project;
+import org.sonar.api.resources.Resource;
+import org.sonar.api.security.ResourcePermissions;
+import org.sonar.batch.ProjectTree;
+import org.sonar.batch.issue.DeprecatedViolations;
+import org.sonar.batch.scan.measure.MeasureCache;
+import org.sonar.core.component.ComponentDto;
+import org.sonar.core.component.ScanGraph;
+import org.sonar.core.component.db.ComponentMapper;
+import org.sonar.jpa.test.AbstractDbUnitTestCase;
+
+import javax.persistence.Query;
+
+import java.io.IOException;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.Arrays;
+
+import static org.fest.assertions.Assertions.assertThat;
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.never;
+import static org.mockito.Mockito.verify;
+import static org.mockito.Mockito.when;
+
+public class ResourcePersisterTest extends AbstractDbUnitTestCase {
+
+ @Rule
+ public ExpectedException thrown = ExpectedException.none();
+
+ @Rule
+ public TemporaryFolder temp = new TemporaryFolder();
+
+ private Project singleProject, singleCopyProject, multiModuleProject, moduleA, moduleB, moduleB1, existingProject;
+ private ResourceCache resourceCache;
+
+ private ResourcePersister persister;
+
+ private ProjectTree projectTree;
+
+ private ResourcePermissions permissions;
+
+ @Before
+ public void before() throws ParseException {
+ resourceCache = new ResourceCache();
+
+ SimpleDateFormat format = new SimpleDateFormat("dd/MM/yyyy");
+ singleProject = newProject("foo", "java");
+ singleProject.setName("Foo").setDescription("some description").setAnalysisDate(format.parse("25/12/2010"));
+
+ existingProject = newProject("my:key", "java");
+ existingProject.setName("Other project").setDescription("some description").setAnalysisDate(format.parse("25/12/2010"));
+
+ singleCopyProject = newCopyProject("foo", "java", 10);
+ singleCopyProject.setName("Foo").setDescription("some description").setAnalysisDate(format.parse("25/12/2010"));
+
+ multiModuleProject = newProject("root", "java");
+ multiModuleProject.setName("Root").setAnalysisDate(format.parse("25/12/2010"));
+
+ moduleA = newProject("a", "java");
+ moduleA.setName("A").setAnalysisDate(format.parse("25/12/2010"));
+ moduleA.setParent(multiModuleProject);
+ moduleA.setPath("/moduleA");
+
+ moduleB = newProject("b", "java");
+ moduleB.setName("B").setAnalysisDate(format.parse("25/12/2010"));
+ moduleB.setParent(multiModuleProject);
+ moduleB.setPath("/moduleB");
+
+ moduleB1 = newProject("b1", "java");
+ moduleB1.setName("B1").setAnalysisDate(format.parse("25/12/2010"));
+ moduleB1.setParent(moduleB);
+ moduleB1.setPath("/moduleB1");
+
+ projectTree = mock(ProjectTree.class);
+ permissions = mock(ResourcePermissions.class);
+ persister = new ResourcePersister(projectTree, getSession(), permissions, resourceCache, mock(ScanGraph.class));
+ }
+
+ @Test
+ public void shouldSaveNewProject() {
+ setupData("shared");
+
+ persister.persist(null, singleProject, null);
+
+ checkTables("shouldSaveNewProject", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
+ "projects", "snapshots");
+
+ // Need to enable snapshot to make resource visible using ComponentMapper
+ enableSnapshot(1001);
+ try (SqlSession session = getMyBatis().openSession(false)) {
+ ComponentDto newProject = session.getMapper(ComponentMapper.class).selectByKey("foo");
+ assertThat(newProject.uuid()).isNotNull();
+ assertThat(newProject.projectUuid()).isEqualTo(newProject.uuid());
+ assertThat(newProject.moduleUuid()).isNull();
+ assertThat(newProject.moduleUuidPath()).isEmpty();
+ // SONAR-3636 : created_at must be fed when inserting a new entry in the 'projects' table
+ assertThat(newProject.getCreatedAt()).isNotNull();
+ }
+ }
+
+ @Test
+ public void shouldSaveCopyProject() {
+ setupData("shared");
+
+ persister.persist(null, singleCopyProject, null);
+
+ checkTables("shouldSaveCopyProject", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
+ "projects", "snapshots");
+ // Need to enable snapshot to make resource visible using ComponentMapper
+ enableSnapshot(1001);
+ try (SqlSession session = getMyBatis().openSession(false)) {
+ ComponentDto newProject = session.getMapper(ComponentMapper.class).selectByKey("foo");
+ assertThat(newProject.uuid()).isNotNull();
+ assertThat(newProject.projectUuid()).isEqualTo(newProject.uuid());
+ assertThat(newProject.moduleUuid()).isNull();
+ assertThat(newProject.moduleUuidPath()).isEmpty();
+ }
+ }
+
+ @Test
+ public void shouldSaveNewMultiModulesProject() {
+ setupData("shared");
+
+ resourceCache.add(multiModuleProject, null).setSnapshot(persister.persist(null, multiModuleProject, null));
+ resourceCache.add(moduleA, multiModuleProject).setSnapshot(persister.persist(null, moduleA, multiModuleProject));
+ resourceCache.add(moduleB, multiModuleProject).setSnapshot(persister.persist(null, moduleB, multiModuleProject));
+ resourceCache.add(moduleB1, moduleB).setSnapshot(persister.persist(null, moduleB1, moduleB));
+ Resource file = File.create("src/main/java/org/Foo.java").setEffectiveKey("b1:src/main/java/org/Foo.java");
+ file.getParent().setEffectiveKey("b1:src/main/java/org");
+ resourceCache.add(file.getParent(), moduleB1).setSnapshot(persister.persist(moduleB1, file.getParent(), null));
+ persister.persist(moduleB1, file, file.getParent());
+
+ checkTables("shouldSaveNewMultiModulesProject",
+ new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"}, "projects", "snapshots");
+
+ // Need to enable snapshot to make resource visible using ComponentMapper
+ enableSnapshot(1001);
+ enableSnapshot(1002);
+ enableSnapshot(1003);
+ enableSnapshot(1004);
+ enableSnapshot(1005);
+ enableSnapshot(1006);
+ try (SqlSession session = getMyBatis().openSession(false)) {
+ ComponentDto root = session.getMapper(ComponentMapper.class).selectByKey("root");
+ assertThat(root.uuid()).isNotNull();
+ assertThat(root.projectUuid()).isEqualTo(root.uuid());
+ assertThat(root.moduleUuid()).isNull();
+ assertThat(root.moduleUuidPath()).isEmpty();
+ ComponentDto a = session.getMapper(ComponentMapper.class).selectByKey("a");
+ assertThat(a.uuid()).isNotNull();
+ assertThat(a.projectUuid()).isEqualTo(root.uuid());
+ assertThat(a.moduleUuid()).isEqualTo(root.uuid());
+ assertThat(a.moduleUuidPath()).isEqualTo(root.uuid());
+ ComponentDto b = session.getMapper(ComponentMapper.class).selectByKey("b");
+ assertThat(b.uuid()).isNotNull();
+ assertThat(b.projectUuid()).isEqualTo(root.uuid());
+ assertThat(b.moduleUuid()).isEqualTo(root.uuid());
+ assertThat(b.moduleUuidPath()).isEqualTo(root.uuid());
+ ComponentDto b1 = session.getMapper(ComponentMapper.class).selectByKey("b1");
+ assertThat(b1.uuid()).isNotNull();
+ assertThat(b1.projectUuid()).isEqualTo(root.uuid());
+ assertThat(b1.moduleUuid()).isEqualTo(b.uuid());
+ assertThat(b1.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid());
+ ComponentDto dir = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org");
+ assertThat(dir.uuid()).isNotNull();
+ assertThat(dir.projectUuid()).isEqualTo(root.uuid());
+ assertThat(dir.moduleUuid()).isEqualTo(b1.uuid());
+ assertThat(dir.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
+ ComponentDto fileComp = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org/Foo.java");
+ assertThat(fileComp.uuid()).isNotNull();
+ assertThat(fileComp.projectUuid()).isEqualTo(root.uuid());
+ assertThat(fileComp.moduleUuid()).isEqualTo(b1.uuid());
+ assertThat(fileComp.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
+ }
+ }
+
+ // FIXME this is a kind of medium test
+ @Test
+ public void shouldSaveNewMultiModulesProjectUsingIndex() throws IOException {
+ setupData("shared");
+
+ java.io.File baseDir = temp.newFolder();
+
+ when(projectTree.getRootProject()).thenReturn(multiModuleProject);
+ when(projectTree.getProjectDefinition(multiModuleProject)).thenReturn(ProjectDefinition.create().setBaseDir(baseDir));
+ when(projectTree.getProjectDefinition(moduleA)).thenReturn(ProjectDefinition.create().setBaseDir(new java.io.File(baseDir, "moduleA")));
+ when(projectTree.getProjectDefinition(moduleB)).thenReturn(ProjectDefinition.create().setBaseDir(new java.io.File(baseDir, "moduleB")));
+ when(projectTree.getProjectDefinition(moduleB1)).thenReturn(ProjectDefinition.create().setBaseDir(new java.io.File(baseDir, "moduleB/moduleB1")));
+
+ DefaultIndex index = new DefaultIndex(resourceCache, null, null, null, projectTree, mock(MetricFinder.class),
+ mock(DeprecatedViolations.class),
+ mock(ResourceKeyMigration.class),
+ mock(MeasureCache.class));
+
+ index.start();
+
+ Resource file = File.create("src/main/java/org/Foo.java");
+
+ index.setCurrentProject(moduleB1, null);
+ index.index(file);
+
+ // Emulate another project having library dependency on moduleA
+ index.addResource(new Library(moduleA.getKey(), "1.0"));
+
+ persister.persist();
+
+ checkTables("shouldSaveNewMultiModulesProjectAndLibrary",
+ new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"}, "projects", "snapshots");
+
+ // Need to enable snapshot to make resource visible using ComponentMapper
+ enableSnapshot(1001);
+ enableSnapshot(1002);
+ enableSnapshot(1003);
+ enableSnapshot(1004);
+ enableSnapshot(1005);
+ enableSnapshot(1006);
+ try (SqlSession session = getMyBatis().openSession(false)) {
+ ComponentDto root = session.getMapper(ComponentMapper.class).selectByKey("root");
+ System.out.println("Root: " + root.uuid());
+ assertThat(root.uuid()).isNotNull();
+ assertThat(root.projectUuid()).isEqualTo(root.uuid());
+ assertThat(root.moduleUuid()).isNull();
+ assertThat(root.moduleUuidPath()).isEmpty();
+ ComponentDto a = session.getMapper(ComponentMapper.class).selectByKey("a");
+ System.out.println("A: " + a.uuid());
+ assertThat(a.uuid()).isNotNull();
+ assertThat(a.projectUuid()).isEqualTo(root.uuid());
+ assertThat(a.moduleUuid()).isEqualTo(root.uuid());
+ assertThat(a.moduleUuidPath()).isEqualTo(root.uuid());
+ ComponentDto b = session.getMapper(ComponentMapper.class).selectByKey("b");
+ System.out.println("B: " + b.uuid());
+ assertThat(b.uuid()).isNotNull();
+ assertThat(b.projectUuid()).isEqualTo(root.uuid());
+ assertThat(b.moduleUuid()).isEqualTo(root.uuid());
+ assertThat(b.moduleUuidPath()).isEqualTo(root.uuid());
+ ComponentDto b1 = session.getMapper(ComponentMapper.class).selectByKey("b1");
+ System.out.println("B1: " + b1.uuid());
+ assertThat(b1.uuid()).isNotNull();
+ assertThat(b1.projectUuid()).isEqualTo(root.uuid());
+ assertThat(b1.moduleUuid()).isEqualTo(b.uuid());
+ assertThat(b1.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid());
+ ComponentDto dir = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org");
+ assertThat(dir.uuid()).isNotNull();
+ assertThat(dir.projectUuid()).isEqualTo(root.uuid());
+ assertThat(dir.moduleUuid()).isEqualTo(b1.uuid());
+ assertThat(dir.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
+ ComponentDto fileComp = session.getMapper(ComponentMapper.class).selectByKey("b1:src/main/java/org/Foo.java");
+ assertThat(fileComp.uuid()).isNotNull();
+ assertThat(fileComp.projectUuid()).isEqualTo(root.uuid());
+ assertThat(fileComp.moduleUuid()).isEqualTo(b1.uuid());
+ assertThat(fileComp.moduleUuidPath()).isEqualTo(root.uuid() + "." + b.uuid() + "." + b1.uuid());
+ }
+ }
+
+ @Test
+ public void shouldSaveNewDirectory() {
+ setupData("shared");
+
+ resourceCache.add(singleProject, null).setSnapshot(persister.persist(null, singleProject, null));
+ persister.persist(singleProject, Directory.create("src/main/java/org/foo", "org.foo").setEffectiveKey("foo:src/main/java/org/foo"), null);
+ // check that the directory is attached to the project
+ checkTables("shouldSaveNewDirectory", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
+ "projects", "snapshots");
+
+ // Need to enable snapshot to make resource visible using ComponentMapper
+ enableSnapshot(1001);
+ enableSnapshot(1002);
+ try (SqlSession session = getMyBatis().openSession(false)) {
+ ComponentDto newProject = session.getMapper(ComponentMapper.class).selectByKey("foo");
+ ComponentDto newDir = session.getMapper(ComponentMapper.class).selectByKey("foo:src/main/java/org/foo");
+ assertThat(newDir.uuid()).isNotNull();
+ assertThat(newDir.projectUuid()).isEqualTo(newProject.uuid());
+ assertThat(newDir.moduleUuid()).isEqualTo(newProject.uuid());
+ assertThat(newDir.moduleUuidPath()).isEqualTo(newProject.uuid());
+ }
+ }
+
+ private void enableSnapshot(int resourceId) {
+ String hql = "UPDATE " + Snapshot.class.getSimpleName() + " SET last=true";
+ hql += " WHERE project_id=:resourceId";
+ Query query = getSession().createQuery(hql);
+ query.setParameter("resourceId", resourceId);
+ query.executeUpdate();
+ getSession().commit();
+ }
+
+ @Test
+ public void shouldSaveNewLibrary() {
+ setupData("shared");
+
+ persister.persist(null, singleProject, null);
+ persister.persist(singleProject, new Library("junit:junit", "4.8.2").setEffectiveKey("junit:junit"), null);
+ persister.persist(singleProject, new Library("junit:junit", "4.8.2").setEffectiveKey("junit:junit"), null);// do nothing, already
+ // saved
+ persister.persist(singleProject, new Library("junit:junit", "3.2").setEffectiveKey("junit:junit"), null);
+
+ checkTables("shouldSaveNewLibrary", new String[] {"build_date", "created_at", "authorization_updated_at", "uuid", "project_uuid", "module_uuid", "module_uuid_path"},
+ "projects", "snapshots");
+
+ // Need to enable snapshot to make resource visible using ComponentMapper
+ enableSnapshot(1002);
+ try (SqlSession session = getMyBatis().openSession(false)) {
+ // FIXME selectByKey returns duplicates for libraries because of the join on snapshots table
+ ComponentDto newLib = session.getMapper(ComponentMapper.class).findByKeys(Arrays.asList("junit:junit")).get(0);
+ assertThat(newLib.uuid()).isNotNull();
+ assertThat(newLib.projectUuid()).isEqualTo(newLib.uuid());
+ assertThat(newLib.moduleUuid()).isNull();
+ assertThat(newLib.moduleUuidPath()).isEmpty();
+ }
+ }
+
+ @Test
+ public void shouldUpdateExistingResource() {
+ setupData("shouldUpdateExistingResource");
+
+ singleProject.setName("new name");
+ singleProject.setDescription("new description");
+ persister.persist(null, singleProject, null);
+
+ checkTables("shouldUpdateExistingResource", new String[] {"build_date", "created_at", "authorization_updated_at"}, "projects", "snapshots");
+ }
+
+ // SONAR-1700
+ @Test
+ public void shouldRemoveRootIndexIfResourceIsProject() {
+ setupData("shouldRemoveRootIndexIfResourceIsProject");
+
+ persister.persist(null, singleProject, null);
+
+ checkTables("shouldRemoveRootIndexIfResourceIsProject", new String[] {"build_date", "created_at", "authorization_updated_at"}, "projects", "snapshots");
+ }
+
+ @Test
+ public void shouldGrantDefaultPermissionsIfNewProject() {
+ setupData("shared");
+
+ when(permissions.hasRoles(singleProject)).thenReturn(false);
+
+ persister.persist(null, singleProject, null);
+
+ verify(permissions).grantDefaultRoles(singleProject);
+ }
+
+ @Test
+ public void shouldNotGrantDefaultPermissionsIfExistingProject() {
+ setupData("shared");
+
+ when(permissions.hasRoles(singleProject)).thenReturn(true);
+
+ persister.persist(null, singleProject, null);
+
+ verify(permissions, never()).grantDefaultRoles(singleProject);
+ }
+
+ private static Project newProject(String key, String language) {
+ Settings settings = new Settings();
+ settings.setProperty(CoreProperties.PROJECT_LANGUAGE_PROPERTY, language);
+ return new Project(key).setSettings(settings).setAnalysisType(Project.AnalysisType.DYNAMIC);
+ }
+
+ private static Project newCopyProject(String key, String language, int copyResourceId) {
+ Settings settings = new Settings();
+ settings.setProperty(CoreProperties.PROJECT_LANGUAGE_PROPERTY, language);
+ return new CopyProject(key, copyResourceId).setSettings(settings).setAnalysisType(Project.AnalysisType.DYNAMIC);
+ }
+
+ private static class CopyProject extends Project implements ResourceCopy {
+
+ private int copyResourceId;
+
+ public CopyProject(String key, int copyResourceId) {
+ super(key);
+ this.copyResourceId = copyResourceId;
+ }
+
+ public int getCopyResourceId() {
+ return copyResourceId;
+ }
+
+ }
+
+}
private void mockResourceCache(String relativePathEmpty, String projectKey, String uuid) {
File sonarFile = File.create(relativePathEmpty);
sonarFile.setUuid(uuid);
- when(resourceCache.get(projectKey + ":" + relativePathEmpty)).thenReturn(new BatchResource(1, sonarFile, new Snapshot(), null));
+ when(resourceCache.get(projectKey + ":" + relativePathEmpty)).thenReturn(new BatchResource(1, sonarFile, null));
}
private byte[] md5(String string) {
package org.sonar.batch.issue;
import org.junit.Test;
-import org.sonar.api.database.model.Snapshot;
import org.sonar.api.issue.internal.DefaultIssue;
import org.sonar.api.resources.Project;
import org.sonar.api.rule.RuleKey;
public void test_toViolation() throws Exception {
RuleKey ruleKey = RuleKey.of("squid", "AvoidCycles");
when(ruleFinder.findByKey(ruleKey)).thenReturn(new Rule("squid", "AvoidCycles"));
- when(resourceCache.get("org.apache:struts")).thenReturn(new BatchResource(1, new Project("org.apache:struts"), new Snapshot(), null));
+ when(resourceCache.get("org.apache:struts")).thenReturn(new BatchResource(1, new Project("org.apache:struts"), null));
DefaultIssue issue = newIssue(ruleKey);
public void test_get() throws Exception {
RuleKey ruleKey = RuleKey.of("squid", "AvoidCycles");
when(ruleFinder.findByKey(ruleKey)).thenReturn(new Rule("squid", "AvoidCycles"));
- when(resourceCache.get("org.apache:struts")).thenReturn(new BatchResource(1, new Project("org.apache:struts"), new Snapshot(), null));
+ when(resourceCache.get("org.apache:struts")).thenReturn(new BatchResource(1, new Project("org.apache:struts"), null));
when(issueCache.byComponent("org.apache:struts")).thenReturn(Arrays.asList(newIssue(ruleKey)));
List<Violation> violations = deprecatedViolations.get("org.apache:struts");
project = new Project("foo");
resourceCache = new ResourceCache();
- resourceCache.add(project, null, snapshot);
+ resourceCache.add(project, null).setSnapshot(snapshot);
verifier = new QualityGateVerifier(qualityGate, resourceCache, periods, i18n, durations);
}
import org.sonar.api.batch.bootstrap.ProjectDefinition;
import org.sonar.api.batch.bootstrap.ProjectReactor;
import org.sonar.api.database.model.Snapshot;
-import org.sonar.api.resources.*;
+import org.sonar.api.resources.Directory;
+import org.sonar.api.resources.Java;
+import org.sonar.api.resources.Language;
+import org.sonar.api.resources.Project;
+import org.sonar.api.resources.Qualifiers;
+import org.sonar.api.resources.Scopes;
import org.sonar.batch.index.ResourceCache;
import java.io.File;
Project root = new Project("foo").setName("Root project").setAnalysisDate(new SimpleDateFormat("dd/MM/yyyy").parse("12/12/2012"));
root.setId(1);
- resourceCache.add(root, null, new Snapshot().setId(11));
+ resourceCache.add(root, null).setSnapshot(new Snapshot().setId(11));
Project module1 = new Project("module1").setName("Module1");
module1.setParent(root);
module1.setId(2);
- resourceCache.add(module1, root, new Snapshot().setId(12));
+ resourceCache.add(module1, root).setSnapshot(new Snapshot().setId(12));
Directory dir1 = Directory.create("src");
dir1.setEffectiveKey("foo:src");
dir1.setId(3);
- resourceCache.add(dir1, module1, new Snapshot().setId(13));
+ resourceCache.add(dir1, module1).setSnapshot(new Snapshot().setId(13));
org.sonar.api.resources.File mainFile = org.sonar.api.resources.File.create("src/Foo.java", "Foo.java", Java.INSTANCE, false);
mainFile.setEffectiveKey("foo:src/Foo.java");
mainFile.setId(4);
- resourceCache.add(mainFile, dir1, new Snapshot().setId(14));
+ resourceCache.add(mainFile, dir1).setSnapshot(new Snapshot().setId(14));
Directory dir2 = Directory.create("test");
dir2.setEffectiveKey("foo:test");
dir2.setId(5);
- resourceCache.add(dir2, module1, new Snapshot().setId(15));
+ resourceCache.add(dir2, module1).setSnapshot(new Snapshot().setId(15));
org.sonar.api.resources.File testFile = org.sonar.api.resources.File.create("test/FooTest.java", "FooTest.java", Java.INSTANCE, true);
testFile.setEffectiveKey("foo:test/FooTest.java");
testFile.setId(6);
- resourceCache.add(testFile, dir2, new Snapshot().setId(16));
+ resourceCache.add(testFile, dir2).setSnapshot(new Snapshot().setId(16));
File exportDir = temp.newFolder();
publisher.export(exportDir);
View view = new View("ALL_PROJECT");
view.setId(1);
view.setAnalysisDate(new SimpleDateFormat("dd/MM/yyyy").parse("12/12/2012"));
- resourceCache.add(view, null, new Snapshot().setId(11));
+ resourceCache.add(view, null).setSnapshot(new Snapshot().setId(11));
org.sonar.api.resources.File mainFile = org.sonar.api.resources.File.create("ALL_PROJECTsample", "ALL_PROJECTsample", null, false);
mainFile.setEffectiveKey("ALL_PROJECTsample");
mainFile.setId(2);
- resourceCache.add(mainFile, view, new Snapshot().setId(12));
+ resourceCache.add(mainFile, view).setSnapshot(new Snapshot().setId(12));
File exportDir = temp.newFolder();
publisher.export(exportDir);
@Before
public void prepare() {
resourceCache = new ResourceCache();
- resourceCache.add(project, null, snapshot);
+ resourceCache.add(project, null).setSnapshot(snapshot);
loader = new PreviousFileHashLoader(project, resourceCache, snapshotDataDao, pastSnapshotFinder);
}
+++ /dev/null
-<dataset>
-
- <!-- other project -->
- <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
- name="Other project" long_name="Other" description="[null]"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" created_at="[null]" path="[null]" deprecated_kee="my:key"/>
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
- status="P" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path=""
- name="Foo" long_name="Foo" description="some description"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" created_at="[null]" path="[null]" deprecated_kee="foo"/>
-
- <!-- old snapshot -->
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
- <!-- new snapshot -->
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <!-- This project has a root_id which should be set to NULL (SONAR-1700) -->
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="12345" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path="[null]"
- name="name" long_name="long name" description="description"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" created_at="[null]" path="[null]" deprecated_kee="foo"/>
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <!-- other project -->
- <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
- name="Other project" long_name="Other" description="[null]"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
- status="P" islast="false" depth="0" />
-
-
- <!-- new project -->
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="Foo" long_name="Foo" description="some description"
- enabled="true" language="[null]" copy_resource_id="10" person_id="[null]" path="[null]" deprecated_kee="foo" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <!-- other project -->
- <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
- name="Other project" long_name="Other" description="[null]"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
- status="P" islast="false" depth="0"/>
-
-
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="Foo" long_name="Foo" description="some description"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
-
- <!-- new dir -->
- <projects id="1002" scope="DIR" qualifier="DIR" kee="foo:src/main/java/org/foo" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="src/main/java/org/foo" long_name="src/main/java/org/foo" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org/foo" deprecated_kee="[null]" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0"/>
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" parent_snapshot_id="3001" root_project_id="1001" root_snapshot_id="3001"
- scope="DIR" qualifier="DIR" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
- status="U" islast="false" depth="1"/>
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <!-- other project -->
- <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
- name="Other project" long_name="Other" description="[null]"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
- status="P" islast="false" depth="0" />
-
-
- <!-- new project -->
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="Foo" long_name="Foo" description="some description"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
-
- <projects id="1002" scope="PRJ" qualifier="LIB" kee="junit:junit" root_id="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="junit:junit" long_name="junit:junit" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" deprecated_kee="[null]" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" parent_snapshot_id="[null]" root_project_id="1002" root_snapshot_id="[null]"
- scope="PRJ" qualifier="LIB" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="4.8.2" path=""
- status="P" islast="false" depth="0" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3003" project_id="1002" parent_snapshot_id="[null]" root_project_id="1002" root_snapshot_id="[null]"
- scope="PRJ" qualifier="LIB" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="3.2" path=""
- status="P" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <!-- other project -->
- <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
- name="Other project" long_name="Other" description="[null]"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
- status="P" islast="false" depth="0" />
-
- <!-- new project -->
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="root" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="Root" long_name="Root" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="root" />
-
- <projects id="1002" scope="PRJ" qualifier="BRC" kee="a" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="A" long_name="A" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleA" deprecated_kee="a" />
-
- <projects id="1003" scope="PRJ" qualifier="BRC" kee="b" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="B" long_name="B" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB" deprecated_kee="b" />
-
- <projects id="1004" scope="PRJ" qualifier="BRC" kee="b1" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="B1" long_name="B1" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB1" deprecated_kee="b1" />
-
- <projects id="1005" scope="DIR" qualifier="DIR" kee="b1:src/main/java/org" root_id="1004"
- name="src/main/java/org" long_name="src/main/java/org" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org" deprecated_kee="[null]" />
-
- <projects id="1006" scope="FIL" qualifier="FIL" kee="b1:src/main/java/org/Foo.java" root_id="1004"
- name="src/main/java/org/Foo.java" long_name="src/main/java/org/Foo.java" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org/Foo.java" deprecated_kee="[null]" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" root_project_id="1001" parent_snapshot_id="[null]" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
- scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
- status="U" islast="false" depth="1" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3003" project_id="1003" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
- scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
- status="U" islast="false" depth="1" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3004" project_id="1004" root_project_id="1001" parent_snapshot_id="3003" root_snapshot_id="3001"
- scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003."
- status="U" islast="false" depth="2" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3005" project_id="1005" root_project_id="1001" parent_snapshot_id="3004" root_snapshot_id="3001"
- scope="DIR" qualifier="DIR" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004."
- status="U" islast="false" depth="3" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3006" project_id="1006" root_project_id="1001" parent_snapshot_id="3005" root_snapshot_id="3001"
- scope="FIL" qualifier="FIL" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004.3005."
- status="U" islast="false" depth="4" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <!-- other project -->
- <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
- name="Other project" long_name="Other" description="[null]"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
- status="P" islast="false" depth="0" />
-
- <!-- new project -->
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="root" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="Root" long_name="Root" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="root" />
-
- <projects id="1002" scope="PRJ" qualifier="BRC" kee="a" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="A" long_name="A" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleA" deprecated_kee="a" />
-
- <projects id="1003" scope="PRJ" qualifier="BRC" kee="b" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="B" long_name="B" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB" deprecated_kee="b" />
-
- <projects id="1004" scope="PRJ" qualifier="BRC" kee="b1" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="B1" long_name="B1" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB1" deprecated_kee="b1" />
-
- <projects id="1005" scope="DIR" qualifier="DIR" kee="b1:src/main/java/org" root_id="1004"
- name="src/main/java/org" long_name="src/main/java/org" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org" deprecated_kee="[null]" />
-
- <projects id="1006" scope="FIL" qualifier="FIL" kee="b1:src/main/java/org/Foo.java" root_id="1004"
- name="src/main/java/org/Foo.java" long_name="src/main/java/org/Foo.java" description="[null]"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org/Foo.java" deprecated_kee="[null]" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" root_project_id="1001" parent_snapshot_id="[null]" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
- scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
- status="U" islast="false" depth="1" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3003" project_id="1003" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
- scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
- status="U" islast="false" depth="1" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3004" project_id="1004" root_project_id="1001" parent_snapshot_id="3003" root_snapshot_id="3001"
- scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003."
- status="U" islast="false" depth="2" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3005" project_id="1005" root_project_id="1001" parent_snapshot_id="3004" root_snapshot_id="3001"
- scope="DIR" qualifier="DIR" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004."
- status="U" islast="false" depth="3" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3006" project_id="1006" root_project_id="1001" parent_snapshot_id="3005" root_snapshot_id="3001"
- scope="FIL" qualifier="FIL" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004.3005."
- status="U" islast="false" depth="4" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3007" project_id="1002" parent_snapshot_id="[null]" root_project_id="1002" root_snapshot_id="[null]"
- scope="PRJ" qualifier="LIB" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="1.0" path=""
- status="P" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <!-- other project -->
- <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
- name="Other project" long_name="Other" description="[null]"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key"/>
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
- status="P" islast="false" depth="0" />
-
-
- <!-- new project -->
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
- name="Foo" long_name="Foo" description="some description"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path=""
- name="new name" long_name="new name" description="new description"
- enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
-
- <!-- old snapshot -->
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
- <!-- new snapshot -->
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
-</dataset>
+++ /dev/null
-<dataset>
-
- <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path="[null]"
- name="old name" long_name="old name" description="old description"
- enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" />
-
- <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
- scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
- status="U" islast="false" depth="0" />
-
-</dataset>
--- /dev/null
+<dataset>
+
+ <!-- other project -->
+ <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
+ name="Other project" long_name="Other" description="[null]"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" created_at="[null]" path="[null]" deprecated_kee="my:key"/>
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
+ status="P" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path=""
+ name="Foo" long_name="Foo" description="some description"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" created_at="[null]" path="[null]" deprecated_kee="foo"/>
+
+ <!-- old snapshot -->
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+ <!-- new snapshot -->
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <!-- This project has a root_id which should be set to NULL (SONAR-1700) -->
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="12345" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path="[null]"
+ name="name" long_name="long name" description="description"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" created_at="[null]" path="[null]" deprecated_kee="foo"/>
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <!-- other project -->
+ <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
+ name="Other project" long_name="Other" description="[null]"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
+ status="P" islast="false" depth="0" />
+
+
+ <!-- new project -->
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="Foo" long_name="Foo" description="some description"
+ enabled="true" language="[null]" copy_resource_id="10" person_id="[null]" path="[null]" deprecated_kee="foo" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <!-- other project -->
+ <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
+ name="Other project" long_name="Other" description="[null]"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
+ status="P" islast="false" depth="0"/>
+
+
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="Foo" long_name="Foo" description="some description"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
+
+ <!-- new dir -->
+ <projects id="1002" scope="DIR" qualifier="DIR" kee="foo:src/main/java/org/foo" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="src/main/java/org/foo" long_name="src/main/java/org/foo" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org/foo" deprecated_kee="[null]" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0"/>
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" parent_snapshot_id="3001" root_project_id="1001" root_snapshot_id="3001"
+ scope="DIR" qualifier="DIR" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
+ status="U" islast="false" depth="1"/>
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <!-- other project -->
+ <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
+ name="Other project" long_name="Other" description="[null]"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
+ status="P" islast="false" depth="0" />
+
+
+ <!-- new project -->
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="Foo" long_name="Foo" description="some description"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
+
+ <projects id="1002" scope="PRJ" qualifier="LIB" kee="junit:junit" root_id="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="junit:junit" long_name="junit:junit" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" deprecated_kee="[null]" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" parent_snapshot_id="[null]" root_project_id="1002" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="LIB" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="4.8.2" path=""
+ status="P" islast="false" depth="0" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3003" project_id="1002" parent_snapshot_id="[null]" root_project_id="1002" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="LIB" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="3.2" path=""
+ status="P" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <!-- other project -->
+ <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
+ name="Other project" long_name="Other" description="[null]"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
+ status="P" islast="false" depth="0" />
+
+ <!-- new project -->
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="root" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="Root" long_name="Root" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="root" />
+
+ <projects id="1002" scope="PRJ" qualifier="BRC" kee="a" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="A" long_name="A" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleA" deprecated_kee="a" />
+
+ <projects id="1003" scope="PRJ" qualifier="BRC" kee="b" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="B" long_name="B" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB" deprecated_kee="b" />
+
+ <projects id="1004" scope="PRJ" qualifier="BRC" kee="b1" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="B1" long_name="B1" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB1" deprecated_kee="b1" />
+
+ <projects id="1005" scope="DIR" qualifier="DIR" kee="b1:src/main/java/org" root_id="1004"
+ name="src/main/java/org" long_name="src/main/java/org" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org" deprecated_kee="[null]" />
+
+ <projects id="1006" scope="FIL" qualifier="FIL" kee="b1:src/main/java/org/Foo.java" root_id="1004"
+ name="src/main/java/org/Foo.java" long_name="src/main/java/org/Foo.java" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org/Foo.java" deprecated_kee="[null]" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" root_project_id="1001" parent_snapshot_id="[null]" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
+ scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
+ status="U" islast="false" depth="1" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3003" project_id="1003" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
+ scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
+ status="U" islast="false" depth="1" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3004" project_id="1004" root_project_id="1001" parent_snapshot_id="3003" root_snapshot_id="3001"
+ scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003."
+ status="U" islast="false" depth="2" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3005" project_id="1005" root_project_id="1001" parent_snapshot_id="3004" root_snapshot_id="3001"
+ scope="DIR" qualifier="DIR" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004."
+ status="U" islast="false" depth="3" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3006" project_id="1006" root_project_id="1001" parent_snapshot_id="3005" root_snapshot_id="3001"
+ scope="FIL" qualifier="FIL" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004.3005."
+ status="U" islast="false" depth="4" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <!-- other project -->
+ <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
+ name="Other project" long_name="Other" description="[null]"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
+ status="P" islast="false" depth="0" />
+
+ <!-- new project -->
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="root" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="Root" long_name="Root" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="root" />
+
+ <projects id="1002" scope="PRJ" qualifier="BRC" kee="a" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="A" long_name="A" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleA" deprecated_kee="a" />
+
+ <projects id="1003" scope="PRJ" qualifier="BRC" kee="b" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="B" long_name="B" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB" deprecated_kee="b" />
+
+ <projects id="1004" scope="PRJ" qualifier="BRC" kee="b1" root_id="1001" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="B1" long_name="B1" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="moduleB1" deprecated_kee="b1" />
+
+ <projects id="1005" scope="DIR" qualifier="DIR" kee="b1:src/main/java/org" root_id="1004"
+ name="src/main/java/org" long_name="src/main/java/org" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org" deprecated_kee="[null]" />
+
+ <projects id="1006" scope="FIL" qualifier="FIL" kee="b1:src/main/java/org/Foo.java" root_id="1004"
+ name="src/main/java/org/Foo.java" long_name="src/main/java/org/Foo.java" description="[null]"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="src/main/java/org/Foo.java" deprecated_kee="[null]" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" root_project_id="1001" parent_snapshot_id="[null]" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1002" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
+ scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
+ status="U" islast="false" depth="1" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3003" project_id="1003" root_project_id="1001" parent_snapshot_id="3001" root_snapshot_id="3001"
+ scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001."
+ status="U" islast="false" depth="1" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3004" project_id="1004" root_project_id="1001" parent_snapshot_id="3003" root_snapshot_id="3001"
+ scope="PRJ" qualifier="BRC" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003."
+ status="U" islast="false" depth="2" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3005" project_id="1005" root_project_id="1001" parent_snapshot_id="3004" root_snapshot_id="3001"
+ scope="DIR" qualifier="DIR" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004."
+ status="U" islast="false" depth="3" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3006" project_id="1006" root_project_id="1001" parent_snapshot_id="3005" root_snapshot_id="3001"
+ scope="FIL" qualifier="FIL" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path="3001.3003.3004.3005."
+ status="U" islast="false" depth="4" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3007" project_id="1002" parent_snapshot_id="[null]" root_project_id="1002" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="LIB" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="1.0" path=""
+ status="P" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <!-- other project -->
+ <projects id="1000" scope="PRJ" qualifier="TRK" kee="my:key" root_id="[null]" uuid="ABCD" project_uuid="ABCD" module_uuid="[null]" module_uuid_path="[null]"
+ name="Other project" long_name="Other" description="[null]"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="my:key"/>
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3000" project_id="1000" parent_snapshot_id="[null]" root_project_id="1000" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2008-11-01 13:58:00.00" build_date="2008-11-01 13:58:00.00" version="[null]" path=""
+ status="P" islast="false" depth="0" />
+
+
+ <!-- new project -->
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="[null]" project_uuid="[null]" module_uuid="[null]" module_uuid_path="[null]"
+ name="Foo" long_name="Foo" description="some description"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path=""
+ name="new name" long_name="new name" description="new description"
+ enabled="true" language="[null]" copy_resource_id="[null]" person_id="[null]" path="[null]" deprecated_kee="foo" />
+
+ <!-- old snapshot -->
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+ <!-- new snapshot -->
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3002" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-25 00:00:00.00" build_date="2010-12-25 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+</dataset>
--- /dev/null
+<dataset>
+
+ <projects id="1001" scope="PRJ" qualifier="TRK" kee="foo" root_id="[null]" uuid="BCDE" project_uuid="BCDE" module_uuid="[null]" module_uuid_path="[null]"
+ name="old name" long_name="old name" description="old description"
+ enabled="true" language="java" copy_resource_id="[null]" person_id="[null]" path="[null]" />
+
+ <snapshots purge_status="[null]" period1_mode="[null]" period1_param="[null]" period1_date="[null]" period2_mode="[null]" period2_param="[null]" period2_date="[null]" period3_mode="[null]" period3_param="[null]" period3_date="[null]" period4_mode="[null]" period4_param="[null]" period4_date="[null]" period5_mode="[null]" period5_param="[null]" period5_date="[null]" id="3001" project_id="1001" parent_snapshot_id="[null]" root_project_id="1001" root_snapshot_id="[null]"
+ scope="PRJ" qualifier="TRK" created_at="2010-12-23 00:00:00.00" build_date="2010-12-23 00:00:00.00" version="[null]" path=""
+ status="U" islast="false" depth="0" />
+
+</dataset>