1
1
import { command , AbapFsCommands } from "../../commands"
2
2
import { Uri , QuickPickItem , window , commands , workspace , ProgressLocation } from "vscode"
3
- import { abapUri , uriRoot , getOrCreateRoot , getClient } from "../../adt/conections"
3
+ import { abapUri , uriRoot , getOrCreateRoot , getClient , ADTSCHEME , rootIsConnected } from "../../adt/conections"
4
4
import { AbapRevisionService , revLabel } from "./abaprevisionservice"
5
5
import { ADTClient , Revision } from "abap-adt-api"
6
6
import { AbapQuickDiff } from "./quickdiff"
@@ -9,11 +9,31 @@ import { RemoteManager, formatKey } from "../../config"
9
9
import { isAbapFile } from "abapfs"
10
10
import { AGroup , AState } from "./abapscm"
11
11
import { caughtToString } from "../../lib"
12
+ import * as t from "io-ts"
13
+ import { isRight } from "fp-ts/lib/Either"
14
+ import { vsCodeUri } from "../../langClient"
12
15
13
16
interface RevisionItem extends QuickPickItem {
14
17
label : string
15
18
revision : Revision
16
19
}
20
+
21
+ const revision = t . type ( {
22
+ uri : t . string ,
23
+ date : t . string ,
24
+ author : t . string ,
25
+ version : t . string ,
26
+ versionTitle : t . string
27
+ } )
28
+ const conflictDetails = t . type ( {
29
+ conflicting : t . string ,
30
+ transport : t . string ,
31
+ uri : t . string ,
32
+ incoming : revision ,
33
+ conflict : revision
34
+ } )
35
+
36
+ type ConflictDetails = t . TypeOf < typeof conflictDetails >
17
37
const revItems = ( revisions : Revision [ ] ) : RevisionItem [ ] =>
18
38
revisions . map ( ( r , i ) => ( {
19
39
label : revLabel ( r , `revision ${ i } ` ) ,
@@ -146,7 +166,20 @@ export class AbapRevisionCommands {
146
166
displayRevDiff ( rightRev , leftRev , uri )
147
167
}
148
168
149
- @command ( AbapFsCommands . mergeEditor )
169
+ private static async showMerge ( uri : Uri , incomingUri : Uri , incomings : Revision [ ] , locals : Revision [ ] , incoming : Revision , conflict : Revision ) {
170
+ const baseVer = await pickCommonAncestor ( locals , conflict , incomings , incoming )
171
+ if ( ! baseVer ) return
172
+ const base = revisionUri ( uri , baseVer )
173
+
174
+ const description = uri . path . replace ( / .* \/ / , "" )
175
+
176
+ const input1 = { uri : revisionUri ( incomingUri , incoming ) , title : `Incoming (${ incomingUri . authority } )` , description, detail : incoming . version }
177
+ const input2 = { uri : revisionUri ( uri , conflict ) , title : `Current (${ uri . authority } )` , description, detail : conflict . version }
178
+ const options = { base, input1, input2, output : uri }
179
+ return commands . executeCommand < void > ( "_open.mergeEditor" , options )
180
+
181
+ }
182
+
150
183
private static async mergeConflicts ( uri : Uri ) {
151
184
if ( ! abapUri ( uri ) ) return
152
185
try {
@@ -174,23 +207,35 @@ export class AbapRevisionCommands {
174
207
const locals = await loadRevisions ( uri , true )
175
208
const localVer = await pickRevision ( locals , "Local version" )
176
209
if ( ! localVer ) return
177
- const baseVer = await pickCommonAncestor ( locals , localVer , remotes , remoteVer )
178
- if ( ! baseVer ) return
179
- const base = revisionUri ( uri , baseVer )
180
-
181
- const description = uri . path . replace ( / .* \/ / , "" )
182
-
183
- const options = {
184
- base,
185
- input1 : { uri : revisionUri ( uri , localVer ) , title : uri . authority , description, detail : localVer . version } ,
186
- input2 : { uri : revisionUri ( remoteUri , remoteVer ) , title : remoteUri . authority , description, detail : remoteVer . version } ,
187
- output : uri
188
- }
189
- return commands . executeCommand < void > ( "_open.mergeEditor" , options )
210
+ return this . showMerge ( uri , remoteUri , remotes , locals , remoteVer , localVer )
190
211
} catch ( e ) {
191
212
window . showErrorMessage ( caughtToString ( e ) )
192
213
}
193
214
}
215
+ private static async mergeEditorByDetails ( details : ConflictDetails ) {
216
+ const remConnId = details . transport . substring ( 0 , 3 ) . toLowerCase ( )
217
+ const connId = details . conflicting . substring ( 0 , 3 ) . toLowerCase ( )
218
+ if ( ! rootIsConnected ( connId ) ) {
219
+ window . showErrorMessage ( `Unable to show merge, connection ${ connId } is not part of this workspace` )
220
+ return
221
+ }
222
+ await getOrCreateRoot ( remConnId )
223
+ await getOrCreateRoot ( connId )
224
+ const path = await vsCodeUri ( connId , details . uri , true , true )
225
+ const uri = Uri . parse ( path )
226
+ const incomingUri = uri . with ( { authority : remConnId } )
227
+ const locals = await loadRevisions ( uri , true )
228
+ const incoming = await loadRevisions ( incomingUri , true )
229
+ return this . showMerge ( uri , incomingUri , incoming , locals , details . incoming , details . conflict )
230
+ }
231
+
232
+ @command ( AbapFsCommands . mergeEditor )
233
+ private static async mergeEditor ( uri : Uri | ConflictDetails ) {
234
+ const details = conflictDetails . decode ( uri )
235
+ if ( isRight ( details ) ) this . mergeEditorByDetails ( details . right )
236
+ if ( uri instanceof Uri )
237
+ this . mergeConflicts ( uri )
238
+ }
194
239
@command ( AbapFsCommands . clearScmGroup )
195
240
private static clearGroup ( group : AGroup ) {
196
241
group . resourceStates = [ ]
0 commit comments