class AbstractDatabaseDiffTask extends BaseLiquibaseTask {
    private DatabaseType referenceDatabaseType;
    @Getter
    @Setter
    private String diffTypes;

    protected DiffResult getDiffResult() {
        Liquibase liquibase = getLiquibase();
        Database targetDatabase = liquibase.getDatabase();
        Database referenceDatabase = createDatabaseFromType(referenceDatabaseType, getResourceAccessor());

        CatalogAndSchema targetCatalogAndSchema = buildCatalogAndSchema(targetDatabase);
        CatalogAndSchema referenceCatalogAndSchema = buildCatalogAndSchema(referenceDatabase);
        CompareControl.SchemaComparison[] schemaComparisons = {
                new CompareControl.SchemaComparison(referenceCatalogAndSchema, targetCatalogAndSchema)
        };

        SnapshotGeneratorFactory snapshotGeneratorFactory = SnapshotGeneratorFactory.getInstance();
        DatabaseSnapshot referenceSnapshot;
        try {
            referenceSnapshot = snapshotGeneratorFactory.createSnapshot(referenceDatabase.getDefaultSchema(),
                    referenceDatabase, new SnapshotControl(referenceDatabase, diffTypes));
        } catch (LiquibaseException e) {
            throw new BuildException("Unable to create a DatabaseSnapshot: " + e.getMessage(), e);
        }

        CompareControl compareControl = new CompareControl(schemaComparisons, referenceSnapshot.getSnapshotControl().getTypesToInclude());

        try {
            return liquibase.diff(referenceDatabase, targetDatabase, compareControl);
        } catch (LiquibaseException e) {
            throw new BuildException("Unable to diff databases: " + e.getMessage(), e);
        }
    }

    @Override
    protected void validateParameters() {<FILL_FUNCTION_BODY>}

    private CatalogAndSchema buildCatalogAndSchema(Database database) {
        return new CatalogAndSchema(database.getDefaultCatalogName(), database.getDefaultSchemaName());
    }

    public void addReferenceDatabase(DatabaseType referenceDatabase) {
        if(this.referenceDatabaseType != null) {
            throw new BuildException("Only one <referenceDatabase> element is allowed.");
        }
        this.referenceDatabaseType = referenceDatabase;
    }

    public void setReferenceDatabaseRef(Reference referenceDatabaseRef) {
        referenceDatabaseType = new DatabaseType(getProject());
        referenceDatabaseType.setRefid(referenceDatabaseRef);
    }
}

        super.validateParameters();

        if(referenceDatabaseType == null) {
            throw new BuildException("Reference database element or reference required.");
        }
    
<methods>public void <init>() ,public void addChangeLogParameters(liquibase.integration.ant.type.ChangeLogParametersType) ,public void addDatabase(liquibase.integration.ant.type.DatabaseType) ,public Path createClasspath() ,public final void execute() throws BuildException,public java.lang.String getChangeLogDirectory() ,public java.lang.String getSearchPath() ,public void init() throws BuildException,public boolean isPromptOnNonLocalDatabase() ,public void setChangeLogParametersRef(Reference) ,public void setClasspathRef(Reference) ,public void setDatabaseRef(Reference) ,public void setPromptOnNonLocalDatabase(boolean) <variables>private liquibase.integration.ant.type.ChangeLogParametersType changeLogParameters,private AntClassLoader classLoader,private Path classpath,private static final java.util.ResourceBundle coreBundle,private liquibase.integration.ant.type.DatabaseType databaseType,private liquibase.Liquibase liquibase,private liquibase.resource.ResourceAccessor resourceAccessor,private final Map<java.lang.String,java.lang.Object> scopeValues