20
20
from readthedocs .config import LATEST_CONFIGURATION_VERSION
21
21
from readthedocs .core .utils import broadcast
22
22
from readthedocs .projects .constants import (
23
+ BITBUCKET_COMMIT_URL ,
23
24
BITBUCKET_URL ,
25
+ GITHUB_COMMIT_URL ,
24
26
GITHUB_URL ,
27
+ GITHUB_PULL_REQUEST_URL ,
28
+ GITHUB_PULL_REQUEST_COMMIT_URL ,
29
+ GITLAB_COMMIT_URL ,
25
30
GITLAB_URL ,
26
31
PRIVACY_CHOICES ,
27
32
PRIVATE ,
36
41
BUILD_STATE_FINISHED ,
37
42
BUILD_STATE_TRIGGERED ,
38
43
BUILD_TYPES ,
44
+ GENERIC_EXTERNAL_VERSION_NAME ,
45
+ GITHUB_EXTERNAL_VERSION_NAME ,
39
46
INTERNAL ,
40
47
LATEST ,
41
48
NON_REPOSITORY_VERSIONS ,
63
70
get_gitlab_username_repo ,
64
71
)
65
72
from readthedocs .builds .version_slug import VersionSlugField
73
+ from readthedocs .oauth .models import RemoteRepository
66
74
67
75
68
76
log = logging .getLogger (__name__ )
@@ -158,9 +166,20 @@ def vcs_url(self):
158
166
"""
159
167
Generate VCS (github, gitlab, bitbucket) URL for this version.
160
168
161
- Branch/Tag Example: https://github.com/rtfd/readthedocs.org/tree/3.4.2/.
162
- Pull/merge Request Example: https://github.com/rtfd/readthedocs.org/pull/9999 /.
169
+ Example: https://github.com/rtfd/readthedocs.org/tree/3.4.2/.
170
+ External Version Example: https://github.com/rtfd/readthedocs.org/pull/99 /.
163
171
"""
172
+ if self .type == EXTERNAL :
173
+ if 'github' in self .project .repo :
174
+ user , repo = get_github_username_repo (self .project .repo )
175
+ return GITHUB_PULL_REQUEST_URL .format (
176
+ user = user ,
177
+ repo = repo ,
178
+ number = self .verbose_name ,
179
+ )
180
+ # TODO: Add VCS URL for other Git Providers
181
+ return ''
182
+
164
183
url = ''
165
184
if self .slug == STABLE :
166
185
slug_url = self .ref
@@ -169,25 +188,12 @@ def vcs_url(self):
169
188
else :
170
189
slug_url = self .slug
171
190
172
- if self .type == EXTERNAL :
173
- if 'github' in self .project .repo :
174
- slug_url = self .verbose_name
175
- url = f'/pull/{ slug_url } /'
191
+ if ('github' in self .project .repo ) or ('gitlab' in self .project .repo ):
192
+ url = f'/tree/{ slug_url } /'
176
193
177
- if 'gitlab' in self .project .repo :
178
- slug_url = self .identifier
179
- url = f'/merge_requests/{ slug_url } /'
180
-
181
- if 'bitbucket' in self .project .repo :
182
- slug_url = self .identifier
183
- url = f'/pull-requests/{ slug_url } '
184
- else :
185
- if ('github' in self .project .repo ) or ('gitlab' in self .project .repo ):
186
- url = f'/tree/{ slug_url } /'
187
-
188
- if 'bitbucket' in self .project .repo :
189
- slug_url = self .identifier
190
- url = f'/src/{ slug_url } '
194
+ if 'bitbucket' in self .project .repo :
195
+ slug_url = self .identifier
196
+ url = f'/src/{ slug_url } '
191
197
192
198
# TODO: improve this replacing
193
199
return self .project .repo .replace ('git://' , 'https://' ).replace ('.git' , '' ) + url
@@ -745,6 +751,60 @@ def get_full_url(self):
745
751
)
746
752
return full_url
747
753
754
+ def get_commit_url (self ):
755
+ """Return the commit URL."""
756
+ repo_url = self .project .repo
757
+ if self .is_external :
758
+ if 'github' in repo_url :
759
+ user , repo = get_github_username_repo (repo_url )
760
+ if not user and not repo :
761
+ return ''
762
+
763
+ repo = repo .rstrip ('/' )
764
+ return GITHUB_PULL_REQUEST_COMMIT_URL .format (
765
+ user = user ,
766
+ repo = repo ,
767
+ number = self .version .verbose_name ,
768
+ commit = self .commit
769
+ )
770
+ # TODO: Add External Version Commit URL for other Git Providers
771
+ else :
772
+ if 'github' in repo_url :
773
+ user , repo = get_github_username_repo (repo_url )
774
+ if not user and not repo :
775
+ return ''
776
+
777
+ repo = repo .rstrip ('/' )
778
+ return GITHUB_COMMIT_URL .format (
779
+ user = user ,
780
+ repo = repo ,
781
+ commit = self .commit
782
+ )
783
+ if 'gitlab' in repo_url :
784
+ user , repo = get_gitlab_username_repo (repo_url )
785
+ if not user and not repo :
786
+ return ''
787
+
788
+ repo = repo .rstrip ('/' )
789
+ return GITLAB_COMMIT_URL .format (
790
+ user = user ,
791
+ repo = repo ,
792
+ commit = self .commit
793
+ )
794
+ if 'bitbucket' in repo_url :
795
+ user , repo = get_bitbucket_username_repo (repo_url )
796
+ if not user and not repo :
797
+ return ''
798
+
799
+ repo = repo .rstrip ('/' )
800
+ return BITBUCKET_COMMIT_URL .format (
801
+ user = user ,
802
+ repo = repo ,
803
+ commit = self .commit
804
+ )
805
+
806
+ return ''
807
+
748
808
@property
749
809
def finished (self ):
750
810
"""Return if build has a finished state."""
@@ -756,6 +816,28 @@ def is_stale(self):
756
816
mins_ago = timezone .now () - datetime .timedelta (minutes = 5 )
757
817
return self .state == BUILD_STATE_TRIGGERED and self .date < mins_ago
758
818
819
+ @property
820
+ def is_external (self ):
821
+ return self .version .type == EXTERNAL
822
+
823
+ @property
824
+ def external_version_name (self ):
825
+ if self .is_external :
826
+ try :
827
+ if self .project .remote_repository .account .provider == 'github' :
828
+ return GITHUB_EXTERNAL_VERSION_NAME
829
+ # TODO: Add External Version Name for other Git Providers
830
+ except RemoteRepository .DoesNotExist :
831
+ log .info ('Remote repository does not exist for %s' , self .project )
832
+ return GENERIC_EXTERNAL_VERSION_NAME
833
+ except Exception :
834
+ log .exception (
835
+ 'Unhandled exception raised for %s while getting external_version_name' ,
836
+ self .project
837
+ )
838
+ return GENERIC_EXTERNAL_VERSION_NAME
839
+ return None
840
+
759
841
def using_latest_config (self ):
760
842
return int (self .config .get ('version' , '1' )) == LATEST_CONFIGURATION_VERSION
761
843
0 commit comments