@@ -158,6 +158,75 @@ public boolean changesSince(@CheckForNull SCMRevision revision, @NonNull OutputS
158
158
throw new UnsupportedOperationException ();
159
159
}
160
160
161
+ /**
162
+ * Given a {@link SCM} this method will try to retrieve a corresponding {@link SCMFileSystem} instance.
163
+ *
164
+ * @param build the build of the {@link SCM}
165
+ * @param scm the {@link SCM}.
166
+ * @return the corresponding {@link SCMFileSystem} or {@code null} if there is none.
167
+ * @throws IOException if the attempt to create a {@link SCMFileSystem} failed due to an IO error
168
+ * (such as the remote system being unavailable)
169
+ * @throws InterruptedException if the attempt to create a {@link SCMFileSystem} was interrupted.
170
+ */
171
+ @ CheckForNull
172
+ public static SCMFileSystem of (@ NonNull Run build , @ NonNull SCM scm ) throws IOException , InterruptedException {
173
+ return of (build , scm , null );
174
+ }
175
+
176
+ /**
177
+ * Given a {@link SCM} this method will try to retrieve a corresponding {@link SCMFileSystem} instance that
178
+ * reflects the content at the specified {@link SCMRevision}.
179
+ *
180
+ * @param build the build of the {@link SCM}
181
+ * @param scm the {@link SCM}.
182
+ * @param rev the specified {@link SCMRevision}.
183
+ * @return the corresponding {@link SCMFileSystem} or {@code null} if there is none.
184
+ * @throws IOException if the attempt to create a {@link SCMFileSystem} failed due to an IO error
185
+ * (such as the remote system being unavailable)
186
+ * @throws InterruptedException if the attempt to create a {@link SCMFileSystem} was interrupted.
187
+ */
188
+ @ CheckForNull
189
+ public static SCMFileSystem of (@ NonNull Run build , @ NonNull SCM scm , @ CheckForNull SCMRevision rev )
190
+ throws IOException , InterruptedException {
191
+ Objects .requireNonNull (scm );
192
+ SCMFileSystem fallBack = null ;
193
+ Throwable failure = null ;
194
+ for (Builder b : ExtensionList .lookup (Builder .class )) {
195
+ if (b .supports (scm )) {
196
+ try {
197
+ SCMFileSystem inspector = b .build (build , scm , rev );
198
+ if (inspector != null ) {
199
+ if (inspector .isFixedRevision ()) {
200
+ return inspector ;
201
+ }
202
+ if (fallBack == null ) {
203
+ fallBack = inspector ;
204
+ }
205
+ }
206
+ } catch (IOException | InterruptedException | RuntimeException e ) {
207
+ if (failure == null ) {
208
+ failure = e ;
209
+ } else {
210
+ failure .addSuppressed (e );
211
+ }
212
+ }
213
+ }
214
+ }
215
+ if (fallBack == null ) {
216
+ if (failure instanceof IOException ) {
217
+ throw (IOException ) failure ;
218
+ }
219
+ if (failure instanceof InterruptedException ) {
220
+ throw (InterruptedException ) failure ;
221
+ }
222
+ //noinspection ConstantConditions
223
+ if (failure instanceof RuntimeException ) {
224
+ throw (RuntimeException ) failure ;
225
+ }
226
+ }
227
+ return fallBack ;
228
+ }
229
+
161
230
/**
162
231
* Given a {@link SCM} this method will try to retrieve a corresponding {@link SCMFileSystem} instance.
163
232
*
@@ -483,6 +552,25 @@ public final boolean supports(SCMSourceDescriptor descriptor) {
483
552
*/
484
553
protected abstract boolean supportsDescriptor (SCMSourceDescriptor descriptor );
485
554
555
+ /**
556
+ * Given a {@link SCM} this should try to build a corresponding {@link SCMFileSystem} instance that
557
+ * reflects the content at the specified {@link SCMRevision}. If the {@link SCM} is supported but not
558
+ * for a fixed revision, best effort is acceptable as the most capable {@link SCMFileSystem} will be returned
559
+ * to the caller.
560
+ *
561
+ * @param build the build of the {@link SCM}
562
+ * @param scm the {@link SCM}.
563
+ * @param rev the specified {@link SCMRevision}.
564
+ * @return the corresponding {@link SCMFileSystem} or {@code null} if this builder cannot create a {@link
565
+ * SCMFileSystem} for the specified {@link SCM}.
566
+ * @throws IOException if the attempt to create a {@link SCMFileSystem} failed due to an IO error
567
+ * (such as the remote system being unavailable)
568
+ * @throws InterruptedException if the attempt to create a {@link SCMFileSystem} was interrupted.
569
+ */
570
+ @ CheckForNull
571
+ public abstract SCMFileSystem build (@ NonNull Run build , @ NonNull SCM scm , @ CheckForNull SCMRevision rev )
572
+ throws IOException , InterruptedException ;
573
+
486
574
/**
487
575
* Given a {@link SCM} this should try to build a corresponding {@link SCMFileSystem} instance that
488
576
* reflects the content at the specified {@link SCMRevision}. If the {@link SCM} is supported but not
0 commit comments