Fix status table race condition (#1835)
This commit is contained in:
		
							parent
							
								
									0f5b399e35
								
							
						
					
					
						commit
						bfb44f8854
					
				
					 5 changed files with 26 additions and 10 deletions
				
			
		| 
						 | 
					@ -1881,10 +1881,9 @@ func DeleteRepositoryArchives() error {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// DeleteOldRepositoryArchives deletes old repository archives.
 | 
					// DeleteOldRepositoryArchives deletes old repository archives.
 | 
				
			||||||
func DeleteOldRepositoryArchives() {
 | 
					func DeleteOldRepositoryArchives() {
 | 
				
			||||||
	if taskStatusTable.IsRunning(archiveCleanup) {
 | 
						if !taskStatusTable.StartIfNotRunning(archiveCleanup) {
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	taskStatusTable.Start(archiveCleanup)
 | 
					 | 
				
			||||||
	defer taskStatusTable.Stop(archiveCleanup)
 | 
						defer taskStatusTable.Stop(archiveCleanup)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	log.Trace("Doing: ArchiveCleanup")
 | 
						log.Trace("Doing: ArchiveCleanup")
 | 
				
			||||||
| 
						 | 
					@ -2025,10 +2024,9 @@ const (
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// GitFsck calls 'git fsck' to check repository health.
 | 
					// GitFsck calls 'git fsck' to check repository health.
 | 
				
			||||||
func GitFsck() {
 | 
					func GitFsck() {
 | 
				
			||||||
	if taskStatusTable.IsRunning(gitFsck) {
 | 
						if !taskStatusTable.StartIfNotRunning(gitFsck) {
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	taskStatusTable.Start(gitFsck)
 | 
					 | 
				
			||||||
	defer taskStatusTable.Stop(gitFsck)
 | 
						defer taskStatusTable.Stop(gitFsck)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	log.Trace("Doing: GitFsck")
 | 
						log.Trace("Doing: GitFsck")
 | 
				
			||||||
| 
						 | 
					@ -2097,10 +2095,9 @@ func repoStatsCheck(checker *repoChecker) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// CheckRepoStats checks the repository stats
 | 
					// CheckRepoStats checks the repository stats
 | 
				
			||||||
func CheckRepoStats() {
 | 
					func CheckRepoStats() {
 | 
				
			||||||
	if taskStatusTable.IsRunning(checkRepos) {
 | 
						if !taskStatusTable.StartIfNotRunning(checkRepos) {
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	taskStatusTable.Start(checkRepos)
 | 
					 | 
				
			||||||
	defer taskStatusTable.Stop(checkRepos)
 | 
						defer taskStatusTable.Stop(checkRepos)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	log.Trace("Doing: CheckRepoStats")
 | 
						log.Trace("Doing: CheckRepoStats")
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -202,10 +202,9 @@ func DeleteMirrorByRepoID(repoID int64) error {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// MirrorUpdate checks and updates mirror repositories.
 | 
					// MirrorUpdate checks and updates mirror repositories.
 | 
				
			||||||
func MirrorUpdate() {
 | 
					func MirrorUpdate() {
 | 
				
			||||||
	if taskStatusTable.IsRunning(mirrorUpdate) {
 | 
						if !taskStatusTable.StartIfNotRunning(mirrorUpdate) {
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	taskStatusTable.Start(mirrorUpdate)
 | 
					 | 
				
			||||||
	defer taskStatusTable.Stop(mirrorUpdate)
 | 
						defer taskStatusTable.Stop(mirrorUpdate)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	log.Trace("Doing: MirrorUpdate")
 | 
						log.Trace("Doing: MirrorUpdate")
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -1334,10 +1334,9 @@ func GetWatchedRepos(userID int64, private bool) ([]*Repository, error) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// SyncExternalUsers is used to synchronize users with external authorization source
 | 
					// SyncExternalUsers is used to synchronize users with external authorization source
 | 
				
			||||||
func SyncExternalUsers() {
 | 
					func SyncExternalUsers() {
 | 
				
			||||||
	if taskStatusTable.IsRunning(syncExternalUsers) {
 | 
						if !taskStatusTable.StartIfNotRunning(syncExternalUsers) {
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	taskStatusTable.Start(syncExternalUsers)
 | 
					 | 
				
			||||||
	defer taskStatusTable.Stop(syncExternalUsers)
 | 
						defer taskStatusTable.Stop(syncExternalUsers)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	log.Trace("Doing: SyncExternalUsers")
 | 
						log.Trace("Doing: SyncExternalUsers")
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -24,6 +24,18 @@ func NewStatusTable() *StatusTable {
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// StartIfNotRunning sets value of given name to true if not already in pool.
 | 
				
			||||||
 | 
					// Returns whether set value was set to true
 | 
				
			||||||
 | 
					func (p *StatusTable) StartIfNotRunning(name string) bool {
 | 
				
			||||||
 | 
						p.lock.Lock()
 | 
				
			||||||
 | 
						_, ok := p.pool[name]
 | 
				
			||||||
 | 
						if !ok {
 | 
				
			||||||
 | 
							p.pool[name] = struct{}{}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						p.lock.Unlock()
 | 
				
			||||||
 | 
						return !ok
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// Start sets value of given name to true in the pool.
 | 
					// Start sets value of given name to true in the pool.
 | 
				
			||||||
func (p *StatusTable) Start(name string) {
 | 
					func (p *StatusTable) Start(name string) {
 | 
				
			||||||
	p.lock.Lock()
 | 
						p.lock.Lock()
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -18,6 +18,15 @@ func Test_StatusTable(t *testing.T) {
 | 
				
			||||||
	table.Start("xyz")
 | 
						table.Start("xyz")
 | 
				
			||||||
	assert.True(t, table.IsRunning("xyz"))
 | 
						assert.True(t, table.IsRunning("xyz"))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						assert.False(t, table.StartIfNotRunning("xyz"))
 | 
				
			||||||
 | 
						assert.True(t, table.IsRunning("xyz"))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						table.Stop("xyz")
 | 
				
			||||||
 | 
						assert.False(t, table.IsRunning("xyz"))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						assert.True(t, table.StartIfNotRunning("xyz"))
 | 
				
			||||||
 | 
						assert.True(t, table.IsRunning("xyz"))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	table.Stop("xyz")
 | 
						table.Stop("xyz")
 | 
				
			||||||
	assert.False(t, table.IsRunning("xyz"))
 | 
						assert.False(t, table.IsRunning("xyz"))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue