• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

moosetechnology / GitProjectHealth / 17852906108

19 Sep 2025 08:25AM UTC coverage: 74.019% (+0.7%) from 73.342%
17852906108

Pull #232

github

web-flow
Merge e5fac281b into dd8ffa1f6
Pull Request #232: add constructor in class since of GitModelImporter for quality of life setup

49 of 147 new or added lines in 8 files covered. (33.33%)

45 existing lines in 3 files now uncovered.

18909 of 25546 relevant lines covered (74.02%)

0.74 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

63.6
/src/GitProjectHealth-Model-Importer/GitModelImporter.class.st
1
"
2
I am a superclass for Model importer.
3
I am a try of normalization for the different importer.
4

5
I also define some contract so it is easier to switch from one importer to another
6
"
7
Class {
8
        #name : #GitModelImporter,
9
        #superclass : #Object,
10
        #instVars : [
11
                'withCommitsSince',
12
                'withFiles',
13
                'glhModel',
14
                'userCatalogue',
15
                'repoApi',
16
                'withCommitDiffs'
17
        ],
18
        #classVars : [
19
                'currentImporter'
20
        ],
21
        #category : #'GitProjectHealth-Model-Importer'
22
}
23

24
{ #category : #github }
NEW
25
GitModelImporter class >> forGithubWithToken: anApiToken [
×
NEW
26
        ^ self forGithubWithToken: anApiToken andModel: GLHModel new
×
NEW
27
]
×
28

29
{ #category : #github }
NEW
30
GitModelImporter class >> forGithubWithToken: anApiToken andModel: aGitModel [
×
NEW
31
        |githubImport|
×
NEW
32
        githubImport := GithubModelImporter new
×
NEW
33
          glhModel: aGitModel;
×
NEW
34
         privateToken: anApiToken;
×
NEW
35
         withCommitsSince: (Date today - 10 day) asDateAndTime ;
×
NEW
36
 yourself.
×
NEW
37
        ^ githubImport 
×
NEW
38
]
×
39

40
{ #category : #gitlab }
NEW
41
GitModelImporter class >> forGitlabHostOn: anHostURL withToken: anApiToken [ 
×
NEW
42
        ^ self forGitlabHostOn: anHostURL withToken: anApiToken andModel: GLHModel new. 
×
NEW
43
]
×
44

45
{ #category : #gitlab }
NEW
46
GitModelImporter class >> forGitlabHostOn: anHostURL withToken: anApiToken andModel: aGitModel [
×
NEW
47
        "use it when accessing onpremise or custom gitlab platform"
×
NEW
48
        | glphApi gitlabImporter |
×
NEW
49
        
×
NEW
50
        glphApi := GitlabApi new
×
NEW
51
    privateToken: anApiToken;
×
NEW
52
    hostUrl: anHostURL;
×
NEW
53
         output: 'json';
×
NEW
54
    yourself.
×
NEW
55

×
NEW
56
        gitlabImporter := GitlabModelImporter new
×
NEW
57
    repoApi: glphApi;
×
NEW
58
    glhModel: aGitModel;
×
NEW
59
         withFiles: false;
×
NEW
60
         withCommitsSince: 3 day;
×
NEW
61
         withCommitDiffs: false.
×
NEW
62
        
×
NEW
63
        ^ gitlabImporter 
×
NEW
64
]
×
65

66
{ #category : #gitlab }
NEW
67
GitModelImporter class >> forGitlabWithToken: anApiToken [
×
NEW
68
        ^ self forGitlabHostOn: 'https://gitlab.com/api/v4' withToken: anApiToken andModel: GLHModel new. 
×
NEW
69
]
×
70

71
{ #category : #gitlab }
NEW
72
GitModelImporter class >> forGitlabWithToken: anApiToken andModel: aGitModel [
×
NEW
73
        ^ self forGitlabHostOn: 'https://gitlab.com/api/v4' withToken: anApiToken andModel: aGitModel
×
NEW
74
]
×
75

76
{ #category : #'accessing - global variables' }
77
GitModelImporter class >> importers [
×
78
        ^ currentImporter 
×
79
]
×
80

81
{ #category : #initialization }
82
GitModelImporter class >> reset [
×
83
        currentImporter := OrderedDictionary new.
×
84
]
×
85

86
{ #category : #accessing }
87
GitModelImporter >> beWithFiles [
×
88

×
89
        withFiles := true
×
90
]
×
91

92
{ #category : #accessing }
93
GitModelImporter >> beWithoutFiles [
×
94

×
95
        withFiles := false
×
96
]
×
97

98
{ #category : #'as yet unclassified' }
99
GitModelImporter >> blockEqualityOn: aSymbol [
1✔
100
        ^ [ :existing :new |
1✔
101
          (existing perform: aSymbol) = (new perform: aSymbol) ]
1✔
102
]
1✔
103

104
{ #category : #'as yet unclassified' }
105
GitModelImporter >> blockEqualityOn: aSymbol andOn: aSecondSymbol [
×
106
        ^ (self blockEqualityOn: aSymbol) and: [ self blockEqualityOn: aSecondSymbol ]
×
107
]
×
108

109
{ #category : #equality }
110
GitModelImporter >> blockForBranchEquality [
1✔
111
        ^ [ :existing :new |
1✔
112
          (existing name = new name) and: [ existing repository project id = new repository project id ] ]
1✔
113
        
1✔
114
]
1✔
115

116
{ #category : #equality }
117
GitModelImporter >> blockForDiffEquality [
1✔
118
        ^ [ :existing :new |
1✔
119
                        existing diffString size = new diffString size and: [
1✔
120
                                existing diffString = new diffString ] ]
1✔
121
]
1✔
122

123
{ #category : #'as yet unclassified' }
124
GitModelImporter >> blockForDiffRangeEquality [
1✔
125

1✔
126
        ^ [ :existing :new |
1✔
127
          existing diff mooseID = new diff mooseID and: [
1✔
128
                  existing originalLineRange = new originalLineRange and: [
1✔
129
                          existing newLineRange = new newLineRange ] ] ]
1✔
130
]
1✔
131

132
{ #category : #equality }
133
GitModelImporter >> blockOnIdEquality [
1✔
134

1✔
135
        ^ [ :existing :new |
1✔
136
          existing id = new id ]
1✔
137
]
1✔
138

139
{ #category : #equality }
140
GitModelImporter >> blockOnNameEquality [
1✔
141

1✔
142
        ^ self blockEqualityOn: #name
1✔
143
]
1✔
144

145
{ #category : #commit }
146
GitModelImporter >> chainsCommitsFrom: commitsCollection [
1✔
147

1✔
148
        | dic |
1✔
149
        ('Chains ' , commitsCollection size printString , ' commits')
1✔
150
                recordInfo.
1✔
151

1✔
152
        dic := ((self glhModel allWithType: GLHCommit) collect: [ :commit |
1✔
153
                        commit id -> commit ]) asSet asDictionary.
1✔
154

1✔
155
        commitsCollection do: [ :commit |
1✔
156
                commit parent_ids do: [ :parentId |
1✔
157
                        dic
1✔
158
                                at: parentId
1✔
159
                                ifPresent: [ :parentCommit |
1✔
160
                                        parentCommit childCommits
1✔
161
                                                add: commit
1✔
162
                                                unless: [ :existing :new | existing id = new id ] ]
1✔
163
                                ifAbsent: [  ] ] ].
1✔
164
        ^ commitsCollection
1✔
165
]
1✔
166

167
{ #category : #commit }
168
GitModelImporter >> completeImportedCommit: aGLHCommit [ 
×
169
        
×
170
        
×
171
        ('completing commit: ' , aGLHCommit short_id printString) recordInfo.
×
172
        self importCreatorOfCommit: aGLHCommit.
×
173

×
174
        self withCommitDiffs ifTrue: [
×
175
                | diffs |
×
176
                aGLHCommit diffs ifEmpty: [
×
177
                        diffs := self importDiffOfCommit: aGLHCommit.
×
178
                        self glhModel addAll: diffs unless: self blockForDiffEquality ] ].
×
179

×
180
        ^ aGLHCommit
×
181
]
×
182

183
{ #category : #'as yet unclassified' }
184
GitModelImporter >> filterCommitChanges: aCollection [
1✔
185

1✔
186
        ^ aCollection reject: [ :line |
1✔
187
                  | trimmedLine |
1✔
188
                  trimmedLine := line trimLeft.
1✔
189
                  (trimmedLine beginsWith: '---') or: [
1✔
190
                          (trimmedLine beginsWith: '+++') or: [
1✔
191
                                  trimmedLine beginsWith: '\ No newline at end of file' ] ] ]
1✔
192
]
1✔
193

194
{ #category : #accessing }
195
GitModelImporter >> glhModel [
1✔
196

1✔
197
        ^ glhModel
1✔
198
]
1✔
199

200
{ #category : #accessing }
201
GitModelImporter >> glhModel: anObject [
1✔
202

1✔
203
        glhModel := anObject
1✔
204
]
1✔
205

206
{ #category : #'import - repositories' }
207
GitModelImporter >> importBranchesOf: aGLHProject [
208

209
        ^ self subclassResponsibility
210
]
211

212
{ #category : #import }
213
GitModelImporter >> importDiffRangesForDiff: aGLHDiff [
1✔
214

1✔
215
        | diffRanges |
1✔
216
        aGLHDiff diffRanges ifNotEmpty: [
1✔
217
                ('Diffs already imported for ' , aGLHDiff printString) recordInfo.
1✔
218
                ^ aGLHDiff diffRanges ].
1✔
219

1✔
220
        ('Import changes of diff ' , aGLHDiff printString) recordInfo.
1✔
221
        "the import of 'diffRanges' entites is technically done inside the parseDiffString"
1✔
222

1✔
223
        diffRanges := self glhModel
1✔
224
                              addAll: (self parseDiffString: aGLHDiff)
1✔
225
                              unless: self blockForDiffRangeEquality.
1✔
226
        ^ aGLHDiff diffRanges
1✔
227
                  addAll: diffRanges
1✔
228
                  unless: self blockForDiffRangeEquality
1✔
229
]
1✔
230

231
{ #category : #'import - groups' }
232
GitModelImporter >> importGroup: aGroupID [
233

234
        self subclassResponsibility
235
]
236

237
{ #category : #pipelines }
238
GitModelImporter >> importLatestPipelinesOfProject: aGLHProject [ 
×
239
        (self pipelinesOf: aGLHProject id withLimit:30) do: [ :pipeline |
×
240
                self glhModel add: pipeline unless: self blockOnIdEquality .
×
241
                aGLHProject pipelines add: pipeline unless: self blockOnIdEquality]
×
242
]
×
243

244
{ #category : #'import - notes' }
245
GitModelImporter >> importNotesfromMergeRequest: mergeRequest [
246

247
        self subclassResponsibility
248
]
249

250
{ #category : #'import - projects' }
251
GitModelImporter >> importProject: id [
252
        "id can be a string or an integer depending on the APi implementation"
253

254
        "return the project created or retrieved"
255

256
        ^ self subclassResponsibility
257
]
258

259
{ #category : #'import - projects' }
260
GitModelImporter >> importProjects: aCollectionOfProjectID [
×
261

×
262

×
263
        ^ aCollectionOfProjectID collect: [ :id | self importProject: id ]
×
264
]
×
265

266
{ #category : #initialization }
267
GitModelImporter >> initialize [
1✔
268

1✔
269
        super initialize.
1✔
270
        self withCommitsSince: (Date today - 1 week) asDateAndTime.
1✔
271
        userCatalogue := GLHUserCatalogueV2 new
1✔
272
                                 anImporter: self;
1✔
273
                                 yourself.
1✔
274
]
1✔
275

276
{ #category : #'as yet unclassified' }
277
GitModelImporter >> makeGlobal [
×
278
        ^ self makeGlobal: DateAndTime now printString.
×
279
]
×
280

281
{ #category : #'as yet unclassified' }
282
GitModelImporter >> makeGlobal: aLabel [ 
×
283

×
284
        currentImporter := GithubModelImporter importers ifNil: [ OrderedDictionary new ].
×
285
        currentImporter at: aLabel put: self. 
×
286
        ^ currentImporter 
×
287
]
×
288

289
{ #category : #parsing }
290
GitModelImporter >> parseDiffString: aDiff [
1✔
291
        "parse diff string to create entities for each lines"
1✔
292

1✔
293
        | lines range index firstChangeRange |
1✔
294
        lines := aDiff diffString lines.
1✔
295
        index := 0.
1✔
296
        range := nil.
1✔
297

1✔
298
        lines ifEmpty: [ ^ aDiff diffRanges ].
1✔
299
        lines := self filterCommitChanges: lines.
1✔
300
        lines ifEmpty: [ ^ aDiff diffRanges ].
1✔
301
        (lines first beginsWith: '@@') ifFalse: [ ^ aDiff diffRanges ].
1✔
302

1✔
303
        lines do: [ :line |
1✔
304
                | aChange |
1✔
305
                firstChangeRange := false.
1✔
306
                (line trim beginsWith: #'@@') ifTrue: [
1✔
307
                        range := GLHDiffRange newFrom: line.
1✔
308
                        firstChangeRange := true.
1✔
309
                        range := aDiff diffRanges add: range unless: [ :existing :new |
1✔
310
                                         existing originalLineRange = new originalLineRange and: [
1✔
311
                                                 existing newLineRange = new newLineRange ] ] ].
1✔
312

1✔
313
                self withCommitDiffs ifTrue: [
1✔
314
                        firstChangeRange ifFalse: [
1✔
315
                                aChange := GLHChange newFrom: line.
1✔
316
                                aChange relativeIndex: index.
1✔
317
                                aChange := range changes add: aChange unless: [ :existing :new |
1✔
318
                                                   existing sourceCode = new sourceCode and: [
1✔
319
                                                           existing index = new index ] ].
1✔
320
                                index := index + 1 ] ] ].
1✔
321

1✔
322
        "add changes to the diff range"
1✔
323
        aDiff diffRanges do: [ :diffRange |
1✔
324
                self glhModel addAll: diffRange changes unless: [ :existing :new |
1✔
325
                        existing diffRange mooseID = new diffRange mooseID and: [
1✔
326
                                existing sourceCode = new sourceCode and: [
1✔
327
                                        existing index = new index ] ] ] ].
1✔
328

1✔
329
        ^ aDiff diffRanges
1✔
330
]
1✔
331

332
{ #category : #accessing }
333
GitModelImporter >> repoApi [
1✔
334

1✔
335
        ^ repoApi
1✔
336
]
1✔
337

338
{ #category : #accessing }
339
GitModelImporter >> repoApi: anObject [
1✔
340

1✔
341
        repoApi := anObject
1✔
342
]
1✔
343

344
{ #category : #accessing }
345
GitModelImporter >> userCatalogue [
1✔
346
        ^ userCatalogue 
1✔
347
]
1✔
348

349
{ #category : #accessing }
350
GitModelImporter >> userCatalogue: aGLHUserCatalogue [
×
351

×
352
        userCatalogue := aGLHUserCatalogue.
×
353
        aGLHUserCatalogue anImporter: self. 
×
354
]
×
355

356
{ #category : #accessing }
357
GitModelImporter >> withCommitDiffs [
1✔
358

1✔
359
        ^ withCommitDiffs
1✔
360
]
1✔
361

362
{ #category : #accessing }
363
GitModelImporter >> withCommitDiffs: anObject [
1✔
364

1✔
365
        withCommitDiffs := anObject
1✔
366
]
1✔
367

368
{ #category : #accessing }
369
GitModelImporter >> withCommitsSince [
×
370

×
371
        ^ withCommitsSince
×
372
]
×
373

374
{ #category : #accessing }
375
GitModelImporter >> withCommitsSince: someDays [
1✔
376
        "substract the current date with a given number of days. Use to retrieve the commits submit in the last giving days"
1✔
377

1✔
378
        "(GitlabModelImporter new withCommitsSince: 1 week ) >>> (Date today - 1 week) asDateAndTime"
1✔
379

1✔
380
        "(GitlabModelImporter new withCommitsSince: 30 day ) >>> (Date today - 30 day) asDateAndTime"
1✔
381

1✔
382
        (someDays isKindOf: DateAndTime)
1✔
383
                ifTrue: [ withCommitsSince := someDays ]
1✔
384
                ifFalse: [
1✔
385
                withCommitsSince := (DateAndTime today - someDays) ].
1✔
386
        ^ withCommitsSince
1✔
387
]
1✔
388

389
{ #category : #accessing }
390
GitModelImporter >> withFiles [
1✔
391

1✔
392
        ^ withFiles
1✔
393
]
1✔
394

395
{ #category : #accessing }
396
GitModelImporter >> withFiles: anObject [
1✔
397

1✔
398
        withFiles := anObject
1✔
399
]
1✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc