Flyway可重复迁移-校验和不变,但Flyway仍执行脚本

时间:2018-10-27 00:01:16

标签: oracle flyway

我正在使用Flyway 4.2.0社区版。将来的版本中可能会解决此问题,但是我们的数据库升级项目仍然是一个出路,并且没有获得批准进入企业版的许可。

大约一年(11.2.0.4和11.2.0.2)已经使用Flyway成功地使用Flyway在Oracle数据库上进行了迁移,使用标准迁移,并且使用默认前缀(V)和后缀(.sql)。我们采用本地出产的方式来处理源代码,但我们希望转向“可重复迁移”以简化流程。

我们先前已使用针对不同对象类型(trigger = .trg,procedure = .prc等)的特定后缀将所有PL / SQL导出到git存储库中。我们希望保留这些后缀,但是我们使用的版本不支持较新的参数flyway.sqlMigrationSuffixes,因此在我们尝试使用带有后缀列表和for循环的解决方案。此解决方案主要在我的测试中有效,但有两个非常明显的例外:程序包规格和程序包主体(分别存储为.pks和.pkb)。

这是我们用来进行迁移的脚本(我知道它需要工作):

###Determine deployment environment for credential extraction
echo "Determining the deployment environment"
case "${bamboo_deploy_environment}" in 
    prod)
        path=prod
        dbs=( db1 db2 db3 )
        ;;
    stage)
        path=stage
        dbs=( db1 db2 db3 )
        ;;
    *)
        path=dev
        dbs=( db1 db2 db3 )
        ;;
esac
echo "Environment for credentials unlock is ${path}"

packages=( .sql .trg .pks .pkb .fnc .typ .java .class .properties .config .txt .dat )
echo "Packages to loop through when deploying flyway are ${packages[*]}"

echo "Databases to run against in this environment are ${dbs[*]}"
###Flyway execution stuff
for db in "${dbs[@]}"
do
    if [ -z ${db} ]; then 
    echo "No db specified"
    exit 2
    else
    echo "Working on db ${db}"
    case "${db}" in 
            db1)
                sid=db1
                host=db1.fqdn
                port=$portnm
                ;;
            db2)
                sid=db2
                host=db2.fqdn
                port=$portnm
                ;;
            db3)
                sid=db3
                host=db3.fqdn
                port=$portnm
                ;;
        esac
    fi

    echo "Current directory is `pwd`" && echo "\n Contents of current directory as `ls -l`"

    echo "Executing Flyway against ${db} for package ${pkg}"
    for pkg in "${packages[@]}"
    ###Target the specific migrations starting folder (it goes recursively)
    do
        case "${pkg}" in 
            .sql)
                loc=filesystem:${db}/migrations
                ;;
            *)
                loc=filesystem:${db}
                migrateParams="-repeatableSqlMigrationPrefix=RM -table=REPEATABLE_MIGRATIONS_HISTORY"
                ;;
        esac
        echo "Running flyway for package type ${pkg} against ${db} db with location set to ${loc}"

        baseParams="-configFile=${db}/migrations/base.conf -locations=${loc} -url=jdbc:oracle:thin:@${host}:${port}:${sid}"
        migrateParams="${migrateParams} -sqlMigrationSuffix=${pkg} ${baseParams}"
        addParams=" -ignoreMissingMigrations=True"
        flyway "repair" "${migrateParams}"
        flyway "migrate" "${migrateParams}${addParams}"
        echo "Finished with ${pkg} against ${db} db"
        unset baseParams
        unset migrateParams
        unset addParams
    done
done

echo "Finished with the migration runs"

我的方法是在环境中运行部署,将REPEATABLE_MIGRATIONS_HISTORY表(可重复迁移的自定义表)中的数据导出为insert语句,然后截断该表,执行插入,然后使用相同的部署工件。对于每个文件类型,Flyway都会正确评估校验和没有更改,并跳过文件。但是,对于程序包规范(.pks)和程序包主体(.pkb)文件,Flyway每次都会执行可重复的迁移。我已经运行查询来进行验证,并且我在所有.pks和.pkb文件上的执行量都得到了增加,但对于其他后缀却保持一次执行。

select "description", "script", "checksum", count(1) 
    from FLYWAY.repeatable_migrations_history 
    group by "description", "script", "checksum"
    order by count(1) desc, "script";

外面的其他人有什么想法吗?我知道这些源文件应该是幂等的,并且在很大程度上应该是幂等的,但是其中一些PL / SQL已经存在了20多年。我们已经看到了几个对象,它们在编译后的第一次执行时会引发错误,然后才能完美地工作,而且我们永远无法找到原因或解决方案。为了将其推广到生产,我们将需要防止不必要的行为。

0 个答案:

没有答案