org.sonar.db.DbTester.java Source code

Java tutorial

Introduction

Here is the source code for org.sonar.db.DbTester.java

Source

/*
 * SonarQube
 * Copyright (C) 2009-2017 SonarSource SA
 * mailto:info AT sonarsource DOT com
 *
 * This program 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.
 *
 * This program 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.db;

import java.sql.Connection;
import java.sql.SQLException;
import java.util.List;
import java.util.Map;
import javax.annotation.Nullable;
import org.apache.commons.lang.StringUtils;
import org.picocontainer.containers.TransientPicoContainer;
import org.sonar.api.utils.System2;
import org.sonar.core.util.SequenceUuidFactory;
import org.sonar.db.component.ComponentDbTester;
import org.sonar.db.event.EventDbTester;
import org.sonar.db.favorite.FavoriteDbTester;
import org.sonar.db.issue.IssueDbTester;
import org.sonar.db.notification.NotificationDbTester;
import org.sonar.db.organization.OrganizationDbTester;
import org.sonar.db.organization.OrganizationDto;
import org.sonar.db.organization.OrganizationTesting;
import org.sonar.db.permission.template.PermissionTemplateDbTester;
import org.sonar.db.property.PropertyDbTester;
import org.sonar.db.qualitygate.QualityGateDbTester;
import org.sonar.db.qualityprofile.QualityProfileDbTester;
import org.sonar.db.rule.RuleDbTester;
import org.sonar.db.user.RootFlagAssertions;
import org.sonar.db.user.UserDbTester;

import static com.google.common.base.Preconditions.checkState;
import static org.apache.commons.lang.RandomStringUtils.randomAlphanumeric;

/**
 * This class should be called using @Rule.
 * Data is truncated between each tests. The schema is created between each test.
 */
public class DbTester extends AbstractDbTester<TestDb> {

    private final System2 system2;
    private DbClient client;
    private DbSession session = null;
    private boolean disableDefaultOrganization = false;
    private boolean started = false;
    private String defaultOrganizationUuid = randomAlphanumeric(40);
    private OrganizationDto defaultOrganization;

    private final UserDbTester userTester;
    private final ComponentDbTester componentTester;
    private final FavoriteDbTester favoriteTester;
    private final EventDbTester eventTester;
    private final OrganizationDbTester organizationTester;
    private final PermissionTemplateDbTester permissionTemplateTester;
    private final PropertyDbTester propertyTester;
    private final QualityGateDbTester qualityGateDbTester;
    private final IssueDbTester issueDbTester;
    private final RuleDbTester ruleDbTester;
    private final NotificationDbTester notificationDbTester;
    private final RootFlagAssertions rootFlagAssertions;
    private final QualityProfileDbTester qualityProfileDbTester;

    public DbTester(System2 system2, @Nullable String schemaPath) {
        super(TestDb.create(schemaPath));
        this.system2 = system2;

        initDbClient();
        this.userTester = new UserDbTester(this);
        this.componentTester = new ComponentDbTester(this);
        this.favoriteTester = new FavoriteDbTester(this);
        this.eventTester = new EventDbTester(this);
        this.organizationTester = new OrganizationDbTester(this);
        this.permissionTemplateTester = new PermissionTemplateDbTester(this);
        this.propertyTester = new PropertyDbTester(this);
        this.qualityGateDbTester = new QualityGateDbTester(this);
        this.issueDbTester = new IssueDbTester(this);
        this.ruleDbTester = new RuleDbTester(this);
        this.notificationDbTester = new NotificationDbTester(this);
        this.rootFlagAssertions = new RootFlagAssertions(this);
        this.qualityProfileDbTester = new QualityProfileDbTester(this);
    }

    public static DbTester create() {
        return new DbTester(System2.INSTANCE, null);
    }

    public static DbTester create(System2 system2) {
        return new DbTester(system2, null);
    }

    public static DbTester createForSchema(System2 system2, Class testClass, String filename) {
        String path = StringUtils.replaceChars(testClass.getCanonicalName(), '.', '/');
        String schemaPath = path + "/" + filename;
        return new DbTester(system2, schemaPath).setDisableDefaultOrganization(true);
    }

    private void initDbClient() {
        TransientPicoContainer ioc = new TransientPicoContainer();
        ioc.addComponent(db.getMyBatis());
        ioc.addComponent(system2);
        ioc.addComponent(new SequenceUuidFactory());
        for (Class daoClass : DaoModule.classes()) {
            ioc.addComponent(daoClass);
        }
        List<Dao> daos = ioc.getComponents(Dao.class);
        client = new DbClient(db.getDatabase(), db.getMyBatis(), daos.toArray(new Dao[daos.size()]));
    }

    public DbTester setDisableDefaultOrganization(boolean b) {
        checkState(!started, "DbTester is already started");
        this.disableDefaultOrganization = b;
        return this;
    }

    public DbTester setDefaultOrganizationUuid(String uuid) {
        checkState(!started, "DbTester is already started");
        this.defaultOrganizationUuid = uuid;
        return this;
    }

    public DbTester enableOrganizations() {
        properties().insertInternal("organization.enabled", "true");
        return this;
    }

    @Override
    protected void before() throws Throwable {
        db.start();
        db.truncateTables();
        initDbClient();
        if (!disableDefaultOrganization) {
            insertDefaultOrganization();
        }
        started = true;
    }

    private void insertDefaultOrganization() {
        defaultOrganization = OrganizationTesting.newOrganizationDto().setUuid(defaultOrganizationUuid);
        try (DbSession dbSession = db.getMyBatis().openSession(false)) {
            client.organizationDao().insert(dbSession, defaultOrganization, false);
            client.internalPropertiesDao().save(dbSession, "organization.default", defaultOrganization.getUuid());
            dbSession.commit();
        }
    }

    public boolean hasDefaultOrganization() {
        return defaultOrganization != null;
    }

    public OrganizationDto getDefaultOrganization() {
        checkState(defaultOrganization != null, "Default organization has not been created");
        return defaultOrganization;
    }

    public UserDbTester users() {
        return userTester;
    }

    public ComponentDbTester components() {
        return componentTester;
    }

    public FavoriteDbTester favorites() {
        return favoriteTester;
    }

    public EventDbTester events() {
        return eventTester;
    }

    public OrganizationDbTester organizations() {
        return organizationTester;
    }

    public PermissionTemplateDbTester permissionTemplates() {
        return permissionTemplateTester;
    }

    public PropertyDbTester properties() {
        return propertyTester;
    }

    public QualityGateDbTester qualityGates() {
        return qualityGateDbTester;
    }

    public RootFlagAssertions rootFlag() {
        return rootFlagAssertions;
    }

    public IssueDbTester issues() {
        return issueDbTester;
    }

    public RuleDbTester rules() {
        return ruleDbTester;
    }

    public NotificationDbTester notifications() {
        return notificationDbTester;
    }

    public QualityProfileDbTester qualityProfiles() {
        return qualityProfileDbTester;
    }

    @Override
    protected void after() {
        if (session != null) {
            session.close();
        }
        db.stop();
        started = false;
    }

    public DbSession getSession() {
        if (session == null) {
            session = db.getMyBatis().openSession(false);
        }
        return session;
    }

    public void commit() {
        getSession().commit();
    }

    public DbClient getDbClient() {
        return client;
    }

    public int countRowsOfTable(DbSession dbSession, String tableName) {
        return super.countRowsOfTable(tableName, new DbSessionConnectionSupplier(dbSession));
    }

    public int countSql(DbSession dbSession, String sql) {
        return super.countSql(sql, new DbSessionConnectionSupplier(dbSession));
    }

    public List<Map<String, Object>> select(DbSession dbSession, String selectSql) {
        return super.select(selectSql, new DbSessionConnectionSupplier(dbSession));
    }

    public Map<String, Object> selectFirst(DbSession dbSession, String selectSql) {
        return super.selectFirst(selectSql, new DbSessionConnectionSupplier(dbSession));
    }

    @Deprecated
    public MyBatis myBatis() {
        return db.getMyBatis();
    }

    @Deprecated
    public Connection openConnection() throws SQLException {
        return getConnection();
    }

    private Connection getConnection() throws SQLException {
        return db.getDatabase().getDataSource().getConnection();
    }

    @Deprecated
    public Database database() {
        return db.getDatabase();
    }

    public DatabaseCommands getCommands() {
        return db.getCommands();
    }

    private static class DbSessionConnectionSupplier implements ConnectionSupplier {
        private final DbSession dbSession;

        public DbSessionConnectionSupplier(DbSession dbSession) {
            this.dbSession = dbSession;
        }

        @Override
        public Connection get() throws SQLException {
            return dbSession.getConnection();
        }

        @Override
        public void close() {
            // closing dbSession is not our responsability
        }
    }

}