1- import { GitRepository } from './types.js' ;
1+ import { GitRepository , AppContext } from './types.js' ;
22import { simpleGit , SimpleGitProgressEvent } from 'simple-git' ;
33import { existsSync } from 'fs' ;
44import { createLogger } from './logger.js' ;
5+ import { GitConfig } from './schemas/v2.js' ;
6+ import path from 'path' ;
57
68const logger = createLogger ( 'git' ) ;
79
@@ -48,4 +50,81 @@ export const fetchRepository = async (repo: GitRepository, onProgress?: (event:
4850 "--progress"
4951 ]
5052 ) ;
53+ }
54+
55+ const isValidGitRepo = async ( url : string ) : Promise < boolean > => {
56+ const git = simpleGit ( ) ;
57+ try {
58+ await git . listRemote ( [ url ] ) ;
59+ return true ;
60+ } catch ( error ) {
61+ logger . debug ( `Error checking if ${ url } is a valid git repo: ${ error } ` ) ;
62+ return false ;
63+ }
64+ }
65+
66+ const stripProtocolAndGitSuffix = ( url : string ) : string => {
67+ return url . replace ( / ^ [ a - z A - Z ] + : \/ \/ / , '' ) . replace ( / \. g i t $ / , '' ) ;
68+ }
69+
70+ const getRepoNameFromUrl = ( url : string ) : string => {
71+ const strippedUrl = stripProtocolAndGitSuffix ( url ) ;
72+ return strippedUrl . split ( '/' ) . slice ( - 2 ) . join ( '/' ) ;
73+ }
74+
75+ export const getGitRepoFromConfig = async ( config : GitConfig , ctx : AppContext ) => {
76+ const repoValid = await isValidGitRepo ( config . url ) ;
77+ if ( ! repoValid ) {
78+ logger . error ( `Git repo provided in config with url ${ config . url } is not valid` ) ;
79+ return null ;
80+ }
81+
82+ const cloneUrl = config . url ;
83+ const repoId = stripProtocolAndGitSuffix ( cloneUrl ) ;
84+ const repoName = getRepoNameFromUrl ( config . url ) ;
85+ const repoPath = path . resolve ( path . join ( ctx . reposPath , `${ repoId } .git` ) ) ;
86+ const repo : GitRepository = {
87+ vcs : 'git' ,
88+ id : repoId ,
89+ name : repoName ,
90+ path : repoPath ,
91+ isStale : false ,
92+ cloneUrl : cloneUrl ,
93+ branches : [ ] ,
94+ tags : [ ] ,
95+ }
96+
97+ if ( config . revisions ) {
98+ if ( config . revisions . branches ) {
99+ const branchGlobs = config . revisions . branches ;
100+ const git = simpleGit ( ) ;
101+ const branchList = await git . listRemote ( [ '--heads' , cloneUrl ] ) ;
102+ const branches = branchList
103+ . split ( '\n' )
104+ . map ( line => line . split ( '\t' ) [ 1 ] )
105+ . filter ( Boolean )
106+ . map ( branch => branch . replace ( 'refs/heads/' , '' ) ) ;
107+
108+ repo . branches = branches . filter ( branch =>
109+ branchGlobs . some ( glob => new RegExp ( glob ) . test ( branch ) )
110+ ) ;
111+ }
112+
113+ if ( config . revisions . tags ) {
114+ const tagGlobs = config . revisions . tags ;
115+ const git = simpleGit ( ) ;
116+ const tagList = await git . listRemote ( [ '--tags' , cloneUrl ] ) ;
117+ const tags = tagList
118+ . split ( '\n' )
119+ . map ( line => line . split ( '\t' ) [ 1 ] )
120+ . filter ( Boolean )
121+ . map ( tag => tag . replace ( 'refs/tags/' , '' ) ) ;
122+
123+ repo . tags = tags . filter ( tag =>
124+ tagGlobs . some ( glob => new RegExp ( glob ) . test ( tag ) )
125+ ) ;
126+ }
127+ }
128+
129+ return repo ;
51130}
0 commit comments