diff --git a/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WLBridgedProject.java b/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WLBridgedProject.java index b525b02a7a..f5ef52e2a3 100644 --- a/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WLBridgedProject.java +++ b/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WLBridgedProject.java @@ -27,11 +27,13 @@ public class WLBridgedProject { } public void buildRepository() throws RepositoryNotFoundException, ServiceNotEnabledException, FailedConnectionException { + writeLatexDataSource.lockForProject(name); if (repository.getObjectDatabase().exists()) { updateRepositoryFromSnapshots(repository); } else { buildRepositoryFromScratch(repository); } + writeLatexDataSource.unlockForProject(name); } private void updateRepositoryFromSnapshots(Repository repository) throws ServiceNotEnabledException, RepositoryNotFoundException, FailedConnectionException { diff --git a/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WriteLatexDataSource.java b/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WriteLatexDataSource.java index 64b89eed36..fe81647514 100644 --- a/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WriteLatexDataSource.java +++ b/services/git-bridge/src/uk/ac/ic/wlgitbridge/bridge/WriteLatexDataSource.java @@ -13,6 +13,10 @@ import java.util.List; */ public interface WriteLatexDataSource { + void lockForProject(String projectName); + + void unlockForProject(String projectName); + /* Called by request thread. */ public boolean repositoryExists(String projectName) throws FailedConnectionException; public List getWritableRepositories(String projectName) throws FailedConnectionException, InvalidProjectException; diff --git a/services/git-bridge/src/uk/ac/ic/wlgitbridge/writelatex/WriteLatexAPI.java b/services/git-bridge/src/uk/ac/ic/wlgitbridge/writelatex/WriteLatexAPI.java index 7557aa6a43..d782e83ea2 100644 --- a/services/git-bridge/src/uk/ac/ic/wlgitbridge/writelatex/WriteLatexAPI.java +++ b/services/git-bridge/src/uk/ac/ic/wlgitbridge/writelatex/WriteLatexAPI.java @@ -16,7 +16,11 @@ import uk.ac.ic.wlgitbridge.writelatex.api.request.push.exception.SnapshotPostEx import uk.ac.ic.wlgitbridge.writelatex.model.WLDataModel; import java.io.IOException; +import java.util.HashMap; import java.util.List; +import java.util.Map; +import java.util.concurrent.locks.Lock; +import java.util.concurrent.locks.ReentrantLock; /** * Created by Winston on 16/11/14. @@ -25,20 +29,48 @@ public class WriteLatexAPI implements WriteLatexDataSource { private final WLDataModel dataModel; private final PostbackManager postbackManager; + private final Map projectLocks; + private final Lock projectLocksLock; public WriteLatexAPI(WLDataModel dataModel) { this.dataModel = dataModel; postbackManager = new PostbackManager(); + projectLocks = new HashMap(); + projectLocksLock = new ReentrantLock(); + } + + private Lock getLockForProjectName(String projectName) { + projectLocksLock.lock(); + Lock lock = projectLocks.get(projectName); + if (lock == null) { + lock = new ReentrantLock(); + projectLocks.put(projectName, lock); + } + projectLocksLock.unlock(); + return lock; + } + + @Override + public void lockForProject(String projectName) { + getLockForProjectName(projectName).lock(); + } + + @Override + public void unlockForProject(String projectName) { + getLockForProjectName(projectName).unlock(); } @Override public boolean repositoryExists(String projectName) throws FailedConnectionException { + lockForProject(projectName); SnapshotGetDocRequest snapshotGetDocRequest = new SnapshotGetDocRequest(projectName); snapshotGetDocRequest.request(); try { snapshotGetDocRequest.getResult().getVersionID(); } catch (InvalidProjectException e) { return false; + } finally { + unlockForProject(projectName); } return true; } @@ -46,7 +78,8 @@ public class WriteLatexAPI implements WriteLatexDataSource { @Override public List getWritableRepositories(String projectName) throws FailedConnectionException, InvalidProjectException { System.out.println("Fetching project: " + projectName); - return dataModel.updateProjectWithName(projectName); + List writableRepositoryContents = dataModel.updateProjectWithName(projectName); + return writableRepositoryContents; } @Override