2 * Copyright 2000-2009 JetBrains s.r.o.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package org
.jetbrains
.idea
.svn
.update
;
18 import com
.intellij
.openapi
.options
.Configurable
;
19 import com
.intellij
.openapi
.progress
.ProgressIndicator
;
20 import com
.intellij
.openapi
.ui
.DialogWrapper
;
21 import com
.intellij
.openapi
.ui
.Messages
;
22 import com
.intellij
.openapi
.vcs
.FilePath
;
23 import com
.intellij
.openapi
.vcs
.VcsException
;
24 import com
.intellij
.openapi
.vcs
.update
.UpdatedFiles
;
25 import org
.jetbrains
.idea
.svn
.SvnBundle
;
26 import org
.jetbrains
.idea
.svn
.SvnConfiguration
;
27 import org
.jetbrains
.idea
.svn
.SvnRevisionNumber
;
28 import org
.jetbrains
.idea
.svn
.SvnVcs
;
29 import org
.jetbrains
.annotations
.Nullable
;
30 import org
.tmatesoft
.svn
.core
.SVNException
;
31 import org
.tmatesoft
.svn
.core
.SVNURL
;
32 import org
.tmatesoft
.svn
.core
.io
.SVNRepository
;
33 import org
.tmatesoft
.svn
.core
.wc
.*;
36 import java
.util
.ArrayList
;
37 import java
.util
.Collection
;
40 public class SvnUpdateEnvironment
extends AbstractSvnUpdateIntegrateEnvironment
{
42 public SvnUpdateEnvironment(SvnVcs vcs
) {
46 protected AbstractUpdateIntegrateCrawler
createCrawler(final ISVNEventHandler eventHandler
,
47 final boolean totalUpdate
,
48 final ArrayList
<VcsException
> exceptions
, final UpdatedFiles updatedFiles
) {
49 return new UpdateCrawler(myVcs
, eventHandler
, totalUpdate
, exceptions
, updatedFiles
);
52 public Configurable
createConfigurable(final Collection
<FilePath
> collection
) {
53 if (collection
.isEmpty()) return null;
54 return new SvnUpdateConfigurable(myVcs
.getProject()){
56 public String
getDisplayName() {
57 return SvnBundle
.message("update.switch.configurable.name");
60 protected AbstractSvnUpdatePanel
createPanel() {
62 return new SvnUpdatePanel(myVcs
, collection
);
67 protected static class UpdateCrawler
extends AbstractUpdateIntegrateCrawler
{
68 public UpdateCrawler(SvnVcs vcs
, ISVNEventHandler handler
, boolean totalUpdate
,
69 Collection
<VcsException
> exceptions
, UpdatedFiles postUpdateFiles
) {
70 super(totalUpdate
, postUpdateFiles
, exceptions
, handler
, vcs
);
73 protected void showProgressMessage(final ProgressIndicator progress
, final File root
) {
74 progress
.setText(SvnBundle
.message("progress.text.updating", root
.getAbsolutePath()));
77 protected long doUpdate(
79 final SVNUpdateClient client
) throws
83 final SvnConfiguration configuration
= SvnConfiguration
.getInstanceChecked(myVcs
.getProject());
84 final UpdateRootInfo rootInfo
= configuration
.getUpdateRootInfo(root
, myVcs
);
86 final SVNUpdateClient updateClient
= myVcs
.createUpdateClient();
87 updateClient
.setEventHandler(myHandler
);
88 updateClient
.setUpdateLocksOnDemand(configuration
.UPDATE_LOCK_ON_DEMAND
);
89 if (rootInfo
!= null) {
90 final SVNURL url
= rootInfo
.getUrl();
91 if (url
!= null && url
.equals(getSourceUrl(myVcs
, root
))) {
92 if (rootInfo
.isUpdateToRevision()) {
93 rev
= updateClient
.doUpdate(root
, rootInfo
.getRevision(), configuration
.UPDATE_DEPTH
, false, false);
95 rev
= updateClient
.doUpdate(root
, SVNRevision
.HEAD
, configuration
.UPDATE_DEPTH
, false, false);
98 } else if (url
!= null) {
99 rev
= updateClient
.doSwitch(root
, url
, SVNRevision
.UNDEFINED
, rootInfo
.getRevision(), configuration
.UPDATE_DEPTH
, false, false);
101 rev
= updateClient
.doUpdate(root
, SVNRevision
.HEAD
, configuration
.UPDATE_DEPTH
, false, false);
104 rev
= updateClient
.doUpdate(root
, SVNRevision
.HEAD
, configuration
.UPDATE_DEPTH
, false, false);
107 myPostUpdateFiles
.setRevisions(root
.getAbsolutePath(), myVcs
, new SvnRevisionNumber(SVNRevision
.create(rev
)));
112 protected boolean isMerge() {
118 private static SVNURL
getSourceUrl(final SvnVcs vcs
, final File root
) {
120 SVNWCClient wcClient
= vcs
.createWCClient();
121 final SVNInfo svnInfo
= wcClient
.doInfo(root
, SVNRevision
.WORKING
);
122 if (svnInfo
!= null) {
123 return svnInfo
.getURL();
128 catch (SVNException e
) {
133 public boolean validateOptions(final Collection
<FilePath
> roots
) {
134 final SvnConfiguration configuration
= SvnConfiguration
.getInstanceChecked(myVcs
.getProject());
136 final Map
<File
,UpdateRootInfo
> map
= configuration
.getUpdateInfosMap();
138 for (FilePath root
: roots
) {
139 final File ioFile
= root
.getIOFile();
140 final UpdateRootInfo value
= map
.get(ioFile
);
144 final SVNURL url
= value
.getUrl();
145 if (url
!= null && (! url
.equals(getSourceUrl(myVcs
, root
.getIOFile())))) {
147 final SVNRevision updateRevision
= correctRevision(value
, url
, value
.getRevision());
149 // should be turned on after bugfix with copy url
150 //return checkAncestry(ioFile, url, updateRevision);
154 catch (SVNException e
) {
155 Messages
.showErrorDialog(myVcs
.getProject(), e
.getMessage(), SvnBundle
.message("switch.target.problem.title"));
162 private SVNRevision
correctRevision(final UpdateRootInfo value
, final SVNURL url
, final SVNRevision updateRevision
) throws SVNException
{
163 if (SVNRevision
.HEAD
.equals(value
.getRevision())) {
164 // find acual revision to update to (a bug if just say head in switch)
165 SVNRepository repository
= null;
167 repository
= myVcs
.createRepository(url
);
168 final long longRevision
= repository
.getLatestRevision();
169 final SVNRevision newRevision
= SVNRevision
.create(longRevision
);
170 value
.setRevision(newRevision
);
173 if (repository
!= null) {
174 repository
.closeSession();
178 return updateRevision
;
181 // false - do not do update
182 private boolean checkAncestry(final File sourceFile
, final SVNURL targetUrl
, final SVNRevision targetRevision
) throws SVNException
{
183 final SVNWCClient client
= myVcs
.createWCClient();
184 final SVNInfo sourceSvnInfo
= client
.doInfo(sourceFile
, SVNRevision
.WORKING
);
185 final SVNInfo targetSvnInfo
= client
.doInfo(targetUrl
, SVNRevision
.UNDEFINED
, targetRevision
);
187 if (sourceSvnInfo
== null || targetSvnInfo
== null) {
192 final SVNURL copyFromTarget
= targetSvnInfo
.getCopyFromURL();
193 final SVNURL copyFromSource
= sourceSvnInfo
.getCopyFromURL();
195 if ((copyFromSource
!= null) || (copyFromTarget
!= null)) {
196 if (sourceSvnInfo
.getURL().equals(copyFromTarget
) || targetUrl
.equals(copyFromSource
)) {
201 final int result
= Messages
.showYesNoDialog(myVcs
.getProject(), SvnBundle
.message("switch.target.not.copy.current"),
202 SvnBundle
.message("switch.target.problem.title"), Messages
.getWarningIcon());
203 return (DialogWrapper
.OK_EXIT_CODE
== result
);