/
123-tour-workspace.html
503 lines (226 loc) · 19.6 KB
/
123-tour-workspace.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
<!DOCTYPE html>
<html lang="en" ng-app="jpm">
<head>
<meta charset="utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<link href="/releases/6.3.0/css/style.css" rel="stylesheet" />
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css">
<script src="https://code.jquery.com/jquery-3.4.1.min.js"></script>
<script src="/js/releases.js"></script>
<!-- Begin Jekyll SEO tag v2.8.0 -->
<title>Guided Tour | bnd</title>
<meta name="generator" content="Jekyll v3.9.2" />
<meta property="og:title" content="Guided Tour" />
<meta property="og:locale" content="en_US" />
<meta name="description" content="The purpose of this com.acme.prime is to show build administrators how to setup workspaces and what features bndlib provides to automate common tasks. This section is not intended to be used by people wanting to learn OSGi, please use a bndtools tutorial for this." />
<meta property="og:description" content="The purpose of this com.acme.prime is to show build administrators how to setup workspaces and what features bndlib provides to automate common tasks. This section is not intended to be used by people wanting to learn OSGi, please use a bndtools tutorial for this." />
<meta property="og:site_name" content="bnd" />
<meta property="og:type" content="website" />
<meta name="twitter:card" content="summary" />
<meta property="twitter:title" content="Guided Tour" />
<script type="application/ld+json">
{"@context":"https://schema.org","@type":"WebPage","description":"The purpose of this com.acme.prime is to show build administrators how to setup workspaces and what features bndlib provides to automate common tasks. This section is not intended to be used by people wanting to learn OSGi, please use a bndtools tutorial for this.","headline":"Guided Tour","url":"/releases/6.3.0/chapters/123-tour-workspace.html"}</script>
<!-- End Jekyll SEO tag -->
<style>
body {
counter-reset: h1 3;
}
</style>
</head>
<body>
<ul class="container12 menu-bar" style="display:flex;align-items:center">
<li span=8><a class=menu-link href="/releases/6.3.0/"><img
class=menu-logo src="/releases/6.3.0/img/bnd-80x40-white.png"></a>
<a href="/releases/6.3.0/chapters/110-introduction.html">Intro
</a><a href="/releases/6.3.0/chapters/800-headers.html">Headers
</a><a href="/releases/6.3.0/chapters/825-instructions-ref.html">Instructions
</a><a href="/releases/6.3.0/chapters/855-macros-ref.html">Macros
</a><a href="/releases/6.3.0/chapters/400-commands.html">Commands
</a><div class="releases">
<button class="dropbtn"><span class="fa fa-bars"></span> 6.3.0</button>
<div class="dropdown-content"></div>
</div>
<li span=4>
<div class="search-container">
<form method="get" id="search" action="https://google.com/search" target="_blank">
<input type="hidden" name="as_q" value="site:bndtools.org OR site:bnd.discourse.group"/>
<input type="text" name="q" placeholder="Search…" aria-label="Search https://google.com for bnd specific"/>
<button type="submit" class="fa fa-search"></button>
</form>
</div>
</ul>
<div class=menu-link span=0><a href="https://github.com/bndtools/bnd" target="_"><img
style="position:absolute;top:0;right:0;margin:0;padding:0;z-index:100"
src="https://camo.githubusercontent.com/38ef81f8aca64bb9a64448d0d70f1308ef5341ab/68747470733a2f2f73332e616d617a6f6e6177732e636f6d2f6769746875622f726962626f6e732f666f726b6d655f72696768745f6461726b626c75655f3132313632312e706e67"
alt="Fork me on GitHub"
data-canonical-src="https://s3.amazonaws.com/github/ribbons/forkme_right_darkblue_121621.png"></a></div>
<ul class=container12>
<li span=3>
<div>
<ul class="side-nav">
<li><a href="/releases/6.3.0/chapters/110-introduction.html">Introduction</a>
<li><a href="/releases/6.3.0/chapters/120-install.html">How to install bnd</a>
<li class=selected>Guided Tour
<li><a href="/releases/6.3.0/chapters/125-tour-features.html">Guided Tour Workspace & Projects</a>
<li><a href="/releases/6.3.0/chapters/130-concepts.html">Concepts</a>
<li><a href="/releases/6.3.0/chapters/140-best-practices.html">Best practices</a>
<li><a href="/releases/6.3.0/chapters/150-build.html">Build</a>
<li><a href="/releases/6.3.0/chapters/155-project-setup.html">Project Setup</a>
<li><a href="/releases/6.3.0/chapters/160-jars.html">Generating JARs</a>
<li><a href="/releases/6.3.0/chapters/170-versioning.html">Versioning</a>
<li><a href="/releases/6.3.0/chapters/180-baselining.html">Baselining</a>
<li><a href="/releases/6.3.0/chapters/200-components.html">Service Components</a>
<li><a href="/releases/6.3.0/chapters/210-metatype.html">Metatype</a>
<li><a href="/releases/6.3.0/chapters/220-contracts.html">Contracts</a>
<li><a href="/releases/6.3.0/chapters/230-manifest-annotations.html">Bundle Annotations</a>
<li><a href="/releases/6.3.0/chapters/235-accessor-properties.html">Accessor Properties</a>
<li><a href="/releases/6.3.0/chapters/240-spi-annotations.html">SPI Annotations</a>
<li><a href="/releases/6.3.0/chapters/250-resolving.html">Resolving Dependencies</a>
<li><a href="/releases/6.3.0/chapters/300-launching.html">Launching</a>
<li><a href="/releases/6.3.0/chapters/305-startlevels.html">Startlevels</a>
<li><a href="/releases/6.3.0/chapters/310-testing.html">Testing</a>
<li><a href="/releases/6.3.0/chapters/315-launchpad-testing.html">Testing with Launchpad</a>
<li><a href="/releases/6.3.0/chapters/320-packaging.html">Packaging Applications</a>
<li><a href="/releases/6.3.0/chapters/330-jpms.html">JPMS Libraries</a>
<li><a href="/releases/6.3.0/chapters/390-wrapping.html">Wrapping Libraries to OSGi Bundles</a>
<li><a href="/releases/6.3.0/chapters/395-generating-documentation.html">Generating Documentation</a>
<li><a href="/releases/6.3.0/chapters/400-commands.html">Commands</a>
<li><a href="/releases/6.3.0/chapters/600-developer.html">For Developers</a>
<li><a href="/releases/6.3.0/chapters/650-windows.html">Tips for Windows users</a>
<li><a href="/releases/6.3.0/chapters/700-tools.html">Tools bound to bnd</a>
<li><a href="/releases/6.3.0/chapters/790-reference.html">Reference</a>
<li><a href="/releases/6.3.0/chapters/800-headers.html">Headers</a>
<li><a href="/releases/6.3.0/chapters/820-instructions.html">Instruction Reference</a>
<li><a href="/releases/6.3.0/chapters/825-instructions-ref.html">Instruction Index</a>
<li><a href="/releases/6.3.0/chapters/850-macros.html">Macro Reference</a>
<li><a href="/releases/6.3.0/chapters/855-macros-ref.html">Macro Index</a>
<li><a href="/releases/6.3.0/chapters/870-plugins.html">Plugins</a>
<li><a href="/releases/6.3.0/chapters/875-external-plugins.html">External Plugins</a>
<li><a href="/releases/6.3.0/chapters/880-settings.html">Settings</a>
<li><a href="/releases/6.3.0/chapters/900-errors.html">Errors</a>
<li><a href="/releases/6.3.0/chapters/910-warnings.html">Warnings</a>
<li><a href="/releases/6.3.0/chapters/920-faq.html">Frequently Asked Questions</a>
</ul>
</div>
<li span=9>
<div class=notes-margin>
<h1> Guided Tour
</h1>
<p>The purpose of this com.acme.prime is to show build administrators how to setup <em>workspaces</em> and what features bndlib provides to automate common tasks. This section is not intended to be used by people wanting to learn OSGi, please use a bndtools tutorial for this.</p>
<p>This section will go through the process of creating a workspace and a few projects while explaining what functions are useful in each phase. It will remain at a rather high level to keep the text flowing, details can be found in the different reference sections.</p>
<p>Since this section provides a tool independent view of bndlib, we use the <a href="120-install.html">bnd command line application</a> to demonstrate the features. Though this is an excellent way to show the low level functionality (the porcelain in git terms), it is not the normal way bndlib is used. In general, a build tool like gradle, ant, make, or maven drives this process from the command line an IDE like bndtools handles the user interaction. So please, please, do not take this com.acme.prime as a guide how to create a build. However handy bnd is, it falls far short of a real build tool like for example gradle.</p>
<h2 id="workspace">Workspace</h2>
<p>A workspace is a directory with the following mandatory files/directories:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>./
cnf/
build.bnd
ext/
</code></pre></div></div>
<p>That’s all! So let’s create one:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ bnd add workspace com.acme.prime
$ cd com.acme.prime
$ ls
cnf
</code></pre></div></div>
<p>The <code class="language-plaintext highlighter-rouge">cnf</code> directory is the ‘magic’ directory that makes a directory a workspace, just like the <code class="language-plaintext highlighter-rouge">.git</code> directory does for git.</p>
<p>In the <code class="language-plaintext highlighter-rouge">cnf</code> directory you find the following files:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ ls cnf
bnd.bnd build.bnd ext
</code></pre></div></div>
<p>The <code class="language-plaintext highlighter-rouge">build.bnd</code> is part of the magic to make something a workspace, it contains <em>your</em> workspace properties. The <code class="language-plaintext highlighter-rouge">ext</code> directory contains more properties. The <code class="language-plaintext highlighter-rouge">bnd.bnd</code> is the last piece of magic, it makes bndlib recognize the <code class="language-plaintext highlighter-rouge">cnf</code> directory as a project.</p>
<h3 id="naming">Naming</h3>
<p>Why such a long name for the workspace? Wouldn’t just <code class="language-plaintext highlighter-rouge">tour</code> suffice? Well, glad you asked. If you work with bnd(tools) for some time you will find that you will get many different workspaces since a workspace is another level of <em>modularity</em>. You can see a workspace as a <em>cohesive</em> set of bundles; just like any module it can import and export. Just like any other module, it imports and exports the thing it encapsulates. For example, a bundle imports and exports packages. In case of the workspace this is the <em>bundle</em>. A workspace imports and exports bundles through repositories.</p>
<p>A good module has cohesion; this means that its constituents have a rather strong relation. Since they also tend to come from the same organization they will have very similar bundle symbolic names. Since some of these bundles will escape in the wild it is always beneficial if you can quickly find the source of that bundle. Therefore naming the workspace with the shared prefix of the bundle symbolic names of its constituents is highly recommended.</p>
<p>That said, bndlib does not enforce this guideline in any way, unlike project names. You can name your workspace <code class="language-plaintext highlighter-rouge">foo</code> if you want to.</p>
<h3 id="properties">Properties</h3>
<p>A workspace so created is quite empty. However, if we look in the <code class="language-plaintext highlighter-rouge">cnf</code> directory then we can see the <code class="language-plaintext highlighter-rouge">build.bnd</code> file. This file is 100% for you … Any property, instruction, or header specified in here is available in anything you build in this workspace; all other bnd files will inherit everything from this properties file. In this file should add for example the headers Bundle-Vendor and Bundle-Copyright. However, using the macro language we can also add custom variables and macros that are useful across the workspace.</p>
<h2 id="plugins">Plugins</h2>
<p>An important aspect of the workspace is that it hosts <em>plugins</em>. A plugin is an extension to bndlib that gets loaded when the workspace is opened. Plugins provide a lot of different functions in bndlib. You can see the currently loaded plugins with bnd:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ bnd plugins
000 Workspace [com.acme.prime]
001 java.util.concurrent.ThreadPoolExecutor@a4102b8[Running, ...]
002 java.util.Random@11dc3715
003 Maven [m2=...]
004 Settings[/Users/aqute/.bnd/settings.json]
005 bnd-cache
006 ResourceRepositoryImpl [... ]
007 aQute.bnd.osgi.Processor
</code></pre></div></div>
<p>The plugins you see are the built-in plugins of bnd itself, they always are available. However, the purpose of plugins is to extend the base functionality. As almost everything, the set of external plugins is managed through an instruction, which is a property in the Workspace.</p>
<p>Before bndlib reads the <code class="language-plaintext highlighter-rouge">build.bnd</code> file to read the workspace properties, it first reads all the files with a <code class="language-plaintext highlighter-rouge">.bnd</code> extension in the <code class="language-plaintext highlighter-rouge">cnf/ext</code> folder. The purpose of this folder is to manage setups for plugins. We can add additional plugins by their name. You can see a list of built-in plugins with the add plugin command:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ bnd add plugin
Type Description
ant aQute.bnd.plugin.ant.AntPlugin
blueprint aQute.lib.spring.SpringXMLType
eclipse aQute.bnd.plugin.eclipse.EclipsePlugin
filerepo aQute.lib.deployer.FileRepo
git aQute.bnd.plugin.git.GitPlugin
gradle aQute.bnd.plugin.gradle.GradlePlugin
...
</code></pre></div></div>
<p>An interesting plugin is the Eclipse plugin that will prepare any projects for Eclipse. We could also add the git plugin that will make sure the proper .gitignore files are in place.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ bnd add plugin eclipse
$ bnd add plugin git
$ bnd plugins
...
007 aQute.bnd.osgi.Processor
008 EclipsePlugin
009 GitPlugin
</code></pre></div></div>
<p>Since you likely need to maintain this build it is good to know how this is stored. If you look in the <code class="language-plaintext highlighter-rouge">cnf/ext</code> directory you should see an <code class="language-plaintext highlighter-rouge">eclipse.bnd</code> and a <code class="language-plaintext highlighter-rouge">git.bnd</code> file:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ ls cnf/ext
eclipse.bnd git.bnd
</code></pre></div></div>
<p>The <code class="language-plaintext highlighter-rouge">eclipse.bnd</code> file contains the following:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ more cnf/ext/eclipse.bnd
#
# Plugin eclipse setup
#
-plugin.eclipse = aQute.bnd.plugin.eclipse.EclipsePlugin
</code></pre></div></div>
<p>So how does this work? When the workspace is opened bndlib will first read all the bnd files in the <code class="language-plaintext highlighter-rouge">cnf/ext</code> directory in alphabetical order. After that, it will read the <code class="language-plaintext highlighter-rouge">build.bnd</code> file. The idea of the <code class="language-plaintext highlighter-rouge">cnf/ext</code> files is that they should not be touched by you, the <code class="language-plaintext highlighter-rouge">build.bnd</code> file is, however, all yours. You can override any previous setting in the <code class="language-plaintext highlighter-rouge">build.bnd</code> file since it is read last.</p>
<p>As you can see, the <code class="language-plaintext highlighter-rouge">eclipse.bnd</code> file defines the property <code class="language-plaintext highlighter-rouge">-plugin.eclipse</code>. In most cases that a value should be settable in different places, bndlib uses <em>merged properties</em>. When bndlib loads the plugins, it actually gets the property <code class="language-plaintext highlighter-rouge">-plugin</code>, merged with any other property that has a key that starts with <code class="language-plaintext highlighter-rouge">-plugin.</code> (ordered alphabetically). This allows you to add to a merged property anywhere in the many places in bndlib where you can set properties.</p>
<p>So now we can try to build the workspace:</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ bnd build
No Projects
</code></pre></div></div>
<p>Which makes some sense …</p>
<h2 id="project">Project</h2>
<p>An empty workspace is not so useful, let’s add a project.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ bnd add project com.acme.prime.hello
$ ls -a com.acme.prime.hello/
. .gitignore bin_test src
.. .project bnd.bnd test
.classpath bin generated
</code></pre></div></div>
<p>This classic layout defines separate source folders for the main code and the test code. The <code class="language-plaintext highlighter-rouge">generated</code> directory is a temporary directory, it contains the artifacts produced by this build.</p>
<h2 id="setup">Setup</h2>
<h2 id="changing-the-layout">Changing the Layout</h2>
<p>This is a classical Eclipse layout, with a separate <code class="language-plaintext highlighter-rouge">src</code> and <code class="language-plaintext highlighter-rouge">test</code> folder. However, this is not baked into bndlib, it is possible to, for example, use the maven layout with the <code class="language-plaintext highlighter-rouge">src/main/java</code>, <code class="language-plaintext highlighter-rouge">src/test/java</code>, and <code class="language-plaintext highlighter-rouge">target</code> directories. We can try this out with the maven plugin.</p>
<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>$ bnd add plugin maven
$ more cnf/ext/maven.bnd
-plugin.maven = aQute.bnd.plugin.maven.MavenPlugin
-outputmask = ${@bsn}-${versionmask;===S;${@version}}.jar
src=src/main/java
bin=target/classes
testsrc=src/test/java
testbin=target/test-classes
target-dir=target
</code></pre></div></div>
<p>The maven plugin adds a number of properties that are recognized by bndlib and used appropriately.</p>
</div>
</ul>
<nav class=next-prev>
<a href='/releases/6.3.0/chapters/120-install.html'></a> <a href='/releases/6.3.0/chapters/125-tour-features.html'></a>
</nav>
<footer class="container12" style="border-top: 1px solid black;padding:10px 0">
<ul span=12 row>
<li span=12>
<ul>
<li><a href="/releases/6.3.0/">GitHub</a>
</ul>
</ul>
</footer>
</body>
</html>