mirror of
https://github.com/gitbucket/gitbucket.git
synced 2025-11-08 14:35:52 +01:00
(refs #578)Add migration for repositories which have removed parent or origin repository.
This commit is contained in:
@@ -137,7 +137,7 @@ trait RepositoryService { self: AccountService =>
|
|||||||
WebHooks .filter(_.byRepository(userName, repositoryName)).delete
|
WebHooks .filter(_.byRepository(userName, repositoryName)).delete
|
||||||
Repositories .filter(_.byRepository(userName, repositoryName)).delete
|
Repositories .filter(_.byRepository(userName, repositoryName)).delete
|
||||||
|
|
||||||
// Update ORIGINAL_USER_NAME and ORIGINAL_REPOSITORY_NAME
|
// Update ORIGIN_USER_NAME and ORIGIN_REPOSITORY_NAME
|
||||||
Repositories
|
Repositories
|
||||||
.filter { x => (x.originUserName === userName.bind) && (x.originRepositoryName === repositoryName.bind) }
|
.filter { x => (x.originUserName === userName.bind) && (x.originRepositoryName === repositoryName.bind) }
|
||||||
.map { x => (x.userName, x.repositoryName) }
|
.map { x => (x.userName, x.repositoryName) }
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ import org.apache.commons.io.IOUtils
|
|||||||
import org.slf4j.LoggerFactory
|
import org.slf4j.LoggerFactory
|
||||||
import util.Directory._
|
import util.Directory._
|
||||||
import util.ControlUtil._
|
import util.ControlUtil._
|
||||||
|
import util.JDBCUtil._
|
||||||
import org.eclipse.jgit.api.Git
|
import org.eclipse.jgit.api.Git
|
||||||
import util.Directory
|
import util.Directory
|
||||||
import plugin.PluginUpdateJob
|
import plugin.PluginUpdateJob
|
||||||
@@ -56,14 +57,35 @@ object AutoUpdate {
|
|||||||
new Version(2, 7) {
|
new Version(2, 7) {
|
||||||
override def update(conn: Connection): Unit = {
|
override def update(conn: Connection): Unit = {
|
||||||
super.update(conn)
|
super.update(conn)
|
||||||
using(conn.createStatement.executeQuery("SELECT USER_NAME, REPOSITORY_NAME FROM REPOSITORY")){ rs =>
|
conn.select("SELECT * FROM REPOSITORY"){ rs =>
|
||||||
while(rs.next){
|
// Rename attached files directory from /issues to /comments
|
||||||
defining(Directory.getAttachedDir(rs.getString("USER_NAME"), rs.getString("REPOSITORY_NAME"))){ newDir =>
|
val userName = rs.getString("USER_NAME")
|
||||||
|
val repoName = rs.getString("REPOSITORY_NAME")
|
||||||
|
defining(Directory.getAttachedDir(userName, repoName)){ newDir =>
|
||||||
val oldDir = new File(newDir.getParentFile, "issues")
|
val oldDir = new File(newDir.getParentFile, "issues")
|
||||||
if(oldDir.exists && oldDir.isDirectory){
|
if(oldDir.exists && oldDir.isDirectory){
|
||||||
oldDir.renameTo(newDir)
|
oldDir.renameTo(newDir)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// Update ORIGIN_USER_NAME and ORIGIN_REPOSITORY_NAME if it does not exist
|
||||||
|
val originalUserName = rs.getString("ORIGIN_USER_NAME")
|
||||||
|
val originalRepoName = rs.getString("ORIGIN_REPOSITORY_NAME")
|
||||||
|
if(originalUserName != null && originalRepoName != null){
|
||||||
|
if(conn.selectInt("SELECT COUNT(*) FROM REPOSITORY WHERE USER_NAME = ? AND REPOSITORY_NAME = ?",
|
||||||
|
originalUserName, originalRepoName) == 0){
|
||||||
|
conn.update("UPDATE REPOSITORY SET ORIGIN_USER_NAME = NULL, ORIGIN_REPOSITORY_NAME = NULL " +
|
||||||
|
"WHERE USER_NAME = ? AND REPOSITORY_NAME = ?", userName, repoName)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Update PARENT_USER_NAME and PARENT_REPOSITORY_NAME if it does not exist
|
||||||
|
val parentUserName = rs.getString("PARENT_USER_NAME")
|
||||||
|
val parentRepoName = rs.getString("PARENT_REPOSITORY_NAME")
|
||||||
|
if(parentUserName != null && parentRepoName != null){
|
||||||
|
if(conn.selectInt("SELECT COUNT(*) FROM REPOSITORY WHERE USER_NAME = ? AND REPOSITORY_NAME = ?",
|
||||||
|
parentUserName, parentRepoName) == 0){
|
||||||
|
conn.update("UPDATE REPOSITORY SET PARENT_USER_NAME = NULL, PARENT_REPOSITORY_NAME = NULL " +
|
||||||
|
"WHERE USER_NAME = ? AND REPOSITORY_NAME = ?", userName, repoName)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -74,18 +96,11 @@ object AutoUpdate {
|
|||||||
new Version(2, 3) {
|
new Version(2, 3) {
|
||||||
override def update(conn: Connection): Unit = {
|
override def update(conn: Connection): Unit = {
|
||||||
super.update(conn)
|
super.update(conn)
|
||||||
using(conn.createStatement.executeQuery("SELECT ACTIVITY_ID, ADDITIONAL_INFO FROM ACTIVITY WHERE ACTIVITY_TYPE='push'")){ rs =>
|
conn.select("SELECT ACTIVITY_ID, ADDITIONAL_INFO FROM ACTIVITY WHERE ACTIVITY_TYPE='push'"){ rs =>
|
||||||
while(rs.next) {
|
val curInfo = rs.getString("ADDITIONAL_INFO")
|
||||||
val info = rs.getString("ADDITIONAL_INFO")
|
val newInfo = curInfo.split("\n").filter(_ matches "^[0-9a-z]{40}:.*").mkString("\n")
|
||||||
val newInfo = info.split("\n").filter(_ matches "^[0-9a-z]{40}:.*").mkString("\n")
|
if (curInfo != newInfo) {
|
||||||
if (info != newInfo) {
|
conn.update("UPDATE ACTIVITY SET ADDITIONAL_INFO = ? WHERE ACTIVITY_ID = ?", newInfo, rs.getInt("ACTIVITY_ID"))
|
||||||
val id = rs.getString("ACTIVITY_ID")
|
|
||||||
using(conn.prepareStatement("UPDATE ACTIVITY SET ADDITIONAL_INFO=? WHERE ACTIVITY_ID=?")) { sql =>
|
|
||||||
sql.setString(1, newInfo)
|
|
||||||
sql.setLong(2, id.toLong)
|
|
||||||
sql.executeUpdate
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
FileUtils.deleteDirectory(Directory.getPluginCacheDir())
|
FileUtils.deleteDirectory(Directory.getPluginCacheDir())
|
||||||
@@ -102,8 +117,7 @@ object AutoUpdate {
|
|||||||
mimeUtil.registerMimeDetector("eu.medsea.mimeutil.detector.MagicMimeMimeDetector")
|
mimeUtil.registerMimeDetector("eu.medsea.mimeutil.detector.MagicMimeMimeDetector")
|
||||||
|
|
||||||
super.update(conn)
|
super.update(conn)
|
||||||
using(conn.createStatement.executeQuery("SELECT USER_NAME, REPOSITORY_NAME FROM REPOSITORY")){ rs =>
|
conn.select("SELECT USER_NAME, REPOSITORY_NAME FROM REPOSITORY"){ rs =>
|
||||||
while(rs.next){
|
|
||||||
defining(Directory.getAttachedDir(rs.getString("USER_NAME"), rs.getString("REPOSITORY_NAME"))){ dir =>
|
defining(Directory.getAttachedDir(rs.getString("USER_NAME"), rs.getString("REPOSITORY_NAME"))){ dir =>
|
||||||
if(dir.exists && dir.isDirectory){
|
if(dir.exists && dir.isDirectory){
|
||||||
dir.listFiles.foreach { file =>
|
dir.listFiles.foreach { file =>
|
||||||
@@ -118,7 +132,6 @@ object AutoUpdate {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
},
|
},
|
||||||
Version(1, 13),
|
Version(1, 13),
|
||||||
Version(1, 12),
|
Version(1, 12),
|
||||||
@@ -134,8 +147,7 @@ object AutoUpdate {
|
|||||||
override def update(conn: Connection): Unit = {
|
override def update(conn: Connection): Unit = {
|
||||||
super.update(conn)
|
super.update(conn)
|
||||||
// Fix wiki repository configuration
|
// Fix wiki repository configuration
|
||||||
using(conn.createStatement.executeQuery("SELECT USER_NAME, REPOSITORY_NAME FROM REPOSITORY")){ rs =>
|
conn.select("SELECT USER_NAME, REPOSITORY_NAME FROM REPOSITORY"){ rs =>
|
||||||
while(rs.next){
|
|
||||||
using(Git.open(getWikiRepositoryDir(rs.getString("USER_NAME"), rs.getString("REPOSITORY_NAME")))){ git =>
|
using(Git.open(getWikiRepositoryDir(rs.getString("USER_NAME"), rs.getString("REPOSITORY_NAME")))){ git =>
|
||||||
defining(git.getRepository.getConfig){ config =>
|
defining(git.getRepository.getConfig){ config =>
|
||||||
if(!config.getBoolean("http", "receivepack", false)){
|
if(!config.getBoolean("http", "receivepack", false)){
|
||||||
@@ -146,7 +158,6 @@ object AutoUpdate {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
},
|
},
|
||||||
Version(1, 2),
|
Version(1, 2),
|
||||||
Version(1, 1),
|
Version(1, 1),
|
||||||
|
|||||||
55
src/main/scala/util/JDBCUtil.scala
Normal file
55
src/main/scala/util/JDBCUtil.scala
Normal file
@@ -0,0 +1,55 @@
|
|||||||
|
package util
|
||||||
|
|
||||||
|
import java.sql._
|
||||||
|
import util.ControlUtil._
|
||||||
|
import scala.collection.mutable.ListBuffer
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Provides implicit class which extends java.sql.Connection.
|
||||||
|
* This is used in automatic migration in [[servlet.AutoUpdateListener]].
|
||||||
|
*/
|
||||||
|
object JDBCUtil {
|
||||||
|
|
||||||
|
implicit class RichConnection(conn: Connection){
|
||||||
|
|
||||||
|
def update(sql: String, params: Any*): Int = {
|
||||||
|
execute(sql, params: _*){ stmt =>
|
||||||
|
stmt.executeUpdate()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
def select[T](sql: String, params: Any*)(f: ResultSet => T): Seq[T] = {
|
||||||
|
execute(sql, params: _*){ stmt =>
|
||||||
|
using(stmt.executeQuery()){ rs =>
|
||||||
|
val list = new ListBuffer[T]
|
||||||
|
while(rs.next){
|
||||||
|
list += f(rs)
|
||||||
|
}
|
||||||
|
list.toSeq
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
def selectInt(sql: String, params: Any*): Int = {
|
||||||
|
execute(sql, params: _*){ stmt =>
|
||||||
|
using(stmt.executeQuery()){ rs =>
|
||||||
|
if(rs.next) rs.getInt(1) else 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private def execute[T](sql: String, params: Any*)(f: (PreparedStatement) => T): T = {
|
||||||
|
using(conn.prepareStatement(sql)){ stmt =>
|
||||||
|
params.zipWithIndex.foreach { case (p, i) =>
|
||||||
|
p match {
|
||||||
|
case x: Int => stmt.setInt(i + 1, x)
|
||||||
|
case x: String => stmt.setString(i + 1, x)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
f(stmt)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user