1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package io.earcam.instrumental.module.osgi;
20
21 import static io.earcam.instrumental.module.manifest.ManifestInfoBuilder.attribute;
22 import static io.earcam.instrumental.module.osgi.BundleManifestHeaders.BUNDLE_MANIFESTVERSION;
23 import static io.earcam.instrumental.module.osgi.ClauseParameters.EMPTY_PARAMETERS;
24 import static io.earcam.instrumental.module.osgi.OsgiManifestHeaderConstants.BUNDLE_ACTIVATOR;
25 import static io.earcam.instrumental.module.osgi.OsgiManifestHeaderConstants.BUNDLE_SYMBOLICNAME;
26 import static io.earcam.instrumental.module.osgi.OsgiManifestHeaderConstants.DYNAMICIMPORT_PACKAGE;
27 import static io.earcam.instrumental.module.osgi.OsgiManifestHeaderConstants.EXPORT_PACKAGE;
28 import static io.earcam.instrumental.module.osgi.OsgiManifestHeaderConstants.FRAGMENT_HOST;
29 import static io.earcam.instrumental.module.osgi.OsgiManifestHeaderConstants.IMPORT_PACKAGE;
30
31 import java.io.ByteArrayInputStream;
32 import java.io.ByteArrayOutputStream;
33 import java.io.InputStream;
34 import java.util.SortedSet;
35 import java.util.function.Predicate;
36 import java.util.jar.Attributes.Name;
37 import java.util.jar.Manifest;
38
39 import io.earcam.instrumental.fluent.Fluent;
40 import io.earcam.instrumental.module.manifest.ManifestInfoBuilder;
41 import io.earcam.instrumental.module.osgi.parser.BundleInfoParser;
42 import io.earcam.instrumental.reflect.Types;
43 import io.earcam.unexceptional.Exceptional;
44
45
46
47
48
49
50
51 public interface BundleInfoBuilder extends ManifestInfoBuilder<BundleInfoBuilder> {
52
53
54
55
56
57
58
59
60 @Fluent
61 public static BundleInfoBuilder bundle()
62 {
63 return new DefaultBundleInfo();
64 }
65
66
67
68
69
70
71
72
73
74
75 @Fluent
76 public static BundleInfoBuilder bundleFrom(String input)
77 {
78 return BundleInfoParser.parse(input);
79 }
80
81
82
83
84
85
86
87
88
89
90 @Fluent
91 public static BundleInfoBuilder bundleFrom(InputStream input)
92 {
93 return BundleInfoParser.parse(input);
94 }
95
96
97
98
99
100
101
102
103
104
105 public default BundleInfoBuilder bundleManifestVersion(String version)
106 {
107 return manifestMain(attribute(BUNDLE_MANIFESTVERSION.header(), version));
108 }
109
110
111
112
113
114
115
116
117
118
119 public default BundleInfoBuilder symbolicName(CharSequence name)
120 {
121 return symbolicName(name, EMPTY_PARAMETERS);
122 }
123
124
125
126
127
128
129
130
131
132
133
134 public default BundleInfoBuilder symbolicName(CharSequence name, ClauseParameters parameters)
135 {
136 return headerClause(BUNDLE_SYMBOLICNAME.value, new Clause(Clause.sortedSet(name.toString()), parameters));
137 }
138
139
140
141
142
143
144
145
146
147
148
149 public default BundleInfoBuilder fragmentHost(CharSequence name, ClauseParameters parameters)
150 {
151 return headerClause(FRAGMENT_HOST.value, new Clause(Clause.sortedSet(name.toString()), parameters));
152 }
153
154
155
156
157
158
159
160
161
162
163 public default BundleInfoBuilder exportPackages(String... packages)
164 {
165 return exportPackages(packages, EMPTY_PARAMETERS);
166 }
167
168
169
170
171
172
173
174
175
176
177
178 public default BundleInfoBuilder exportPackages(String paquet, ClauseParameters parameters)
179 {
180 return exportPackages(new String[] { paquet }, parameters);
181 }
182
183
184
185
186
187
188
189
190
191
192
193 public default BundleInfoBuilder exportPackages(String[] packages, ClauseParameters parameters)
194 {
195 return exportPackages(Clause.sortedSet(packages), parameters);
196 }
197
198
199
200
201
202
203
204
205
206
207 public default BundleInfoBuilder exportPackages(SortedSet<String> packages)
208 {
209 return exportPackages(packages, EMPTY_PARAMETERS);
210 }
211
212
213
214
215
216
217
218
219
220
221
222 public default BundleInfoBuilder exportPackages(SortedSet<String> packages, ClauseParameters parameters)
223 {
224 return headerClause(EXPORT_PACKAGE.value, new Clause(packages, parameters));
225 }
226
227
228
229
230
231
232
233
234
235
236 public default BundleInfoBuilder importPackages(String... packages)
237 {
238 return importPackages(packages, EMPTY_PARAMETERS);
239 }
240
241
242
243
244
245
246
247
248
249
250
251 public default BundleInfoBuilder importPackages(String paquet, ClauseParameters parameters)
252 {
253 return importPackages(Clause.sortedSet(paquet), parameters);
254 }
255
256
257
258
259
260
261
262
263
264
265
266 public default BundleInfoBuilder importPackages(String[] packages, ClauseParameters parameters)
267 {
268 return importPackages(Clause.sortedSet(packages), parameters);
269 }
270
271
272
273
274
275
276
277
278
279
280 public default BundleInfoBuilder importPackages(SortedSet<String> packages)
281 {
282 return importPackages(packages, EMPTY_PARAMETERS);
283 }
284
285
286
287
288
289
290
291
292
293
294
295 public default BundleInfoBuilder importPackages(SortedSet<String> packages, ClauseParameters parameters)
296 {
297 return importPackages(new Clause(packages, parameters));
298 }
299
300
301
302
303
304
305
306
307
308
309 public default BundleInfoBuilder importPackages(Clause clause)
310 {
311 return headerClause(IMPORT_PACKAGE.value, clause);
312 }
313
314
315
316
317
318
319
320
321
322
323
324 public default BundleInfoBuilder dynamicImportPackages(SortedSet<String> packages, ClauseParameters parameters)
325 {
326 return dynamicImportPackages(new Clause(packages, parameters));
327 }
328
329
330
331
332
333
334
335
336
337
338 public default BundleInfoBuilder dynamicImportPackages(Clause clause)
339 {
340 return headerClause(DYNAMICIMPORT_PACKAGE.value, clause);
341 }
342
343
344
345
346
347
348
349
350
351
352
353 public default BundleInfoBuilder headerClause(String header, Clause clause)
354 {
355 return headerClause(new Name(header), clause);
356 }
357
358
359
360
361
362
363
364
365
366
367
368 public abstract BundleInfoBuilder headerClause(Name header, Clause clause);
369
370
371
372
373
374
375
376
377
378
379 public default BundleInfoBuilder activator(Class<?> activator)
380 {
381 final String iface = "org.osgi.framework.BundleActivator";
382 boolean implementsActivator = Types.allInterfacesOf(activator)
383 .map(Class::getCanonicalName)
384 .anyMatch(Predicate.isEqual(iface));
385 if(!implementsActivator) {
386 throw new IllegalArgumentException(activator.getCanonicalName() + " does not implement " + iface);
387 }
388 return activator(activator.getCanonicalName());
389 }
390
391
392
393
394
395
396
397
398
399
400 public default BundleInfoBuilder activator(String className)
401 {
402 return headerClause(BUNDLE_ACTIVATOR.value, new Clause(className, EMPTY_PARAMETERS));
403 }
404
405
406
407
408
409
410
411
412
413 public abstract BundleInfo construct();
414
415
416 @Fluent
417 public static BundleInfoBuilder bundleFrom(Manifest manifest)
418 {
419 ByteArrayOutputStream baos = new ByteArrayOutputStream();
420 Exceptional.accept(manifest::write, baos);
421 ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray());
422 return BundleInfoBuilder.bundleFrom(bais);
423 }
424 }