| <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> |
| <html lang="en"> |
| <head> |
| <meta name="copyright" |
| content="Copyright (c) IBM Corporation and others 2009. This page is made available under license. For full details see the LEGAL in the documentation book that contains this page."> |
| <meta http-equiv="Content-Type" |
| content="text/html; charset=ISO-8859-1"> |
| <meta http-equiv="Content-Style-Type" content="text/css"> |
| <link REL="STYLESHEET" HREF="../book.css" CHARSET="ISO-8859-1" TYPE="text/css"> |
| <title>Customizing p2 metadata</title> |
| </head> |
| <body> |
| <h1>Customizing p2 metadata</h1> |
| <p> |
| <i> Disclaimer: Authoring p2 metadata is something we expect to support with better tooling in a future release. |
| The support for customizing metadata with a p2.inf file is provisional although we expect to maintain a basic level |
| of compatibility for common tasks.</i> |
| </p> |
| <p> |
| On occasion the metadata that is automatically generated by p2 for bundles, features and products |
| does not provide everything required to successfully provision an installable unit. |
| For those cases p2 supports the use of an advice file (a p2.inf file) that can be used to augment the metadata for an installable unit. |
| In this release the p2.inf file will allow an author to customize capabilities, properties, and instructions. |
| In addition support is provided for defining additional installable units that are related to the container IU. |
| </p> |
| |
| The touchpoint advice file is a <b>java properties</b> file and can be placed: |
| <ul> |
| <li>In bundles (META-INF/p2.inf): The instructions are added to the installable unit for the bundle.</li> |
| <li>In features (a p2.inf file co-located with the feature.xml): The instructions are added to the installable unit for the feature group.</li> |
| <li>In products (a p2.inf file co-located with the .product file): The instructions are added to the root installable unit for that product.</li> |
| </ul> |
| |
| <p> |
| Version substitution is a common practice and two special version parameters are supported: |
| </p> |
| <ul> |
| <li><b>$version$</b> - returns the string form of the containing IU's version</li> |
| <li><b>$qualifier$</b> - returns just the string form of the qualifier of the containing IU's version</li> |
| </ul> |
| |
| <p>One common use for advice files is to allow more fine grained control of the |
| <a href="#categoryGen">generation of categories</a> used by the UI to group installable features</p> |
| |
| <hr> |
| <h3>Capability Advice</h3> |
| <p>Note: Capability advice will "replace" an existing capability of the same type on the IU if the name and namespace match.</p> |
| <p>There are three different type of capability advice:</p> |
| <ol> |
| <li><b>provides</b> - these are capabilities that an IU will offer to satisfy the needs of other IUs.</li> |
| <li><b>requires</b> - these are the capabilities that an IU requires from other IUs in order to resolve correctly.</li> |
| <li><b>metaRequirements</b> - these are capabilities that the IU puts on the profile that must already be installed before this IU can be installed.</li> |
| </ol> |
| |
| <pre> |
| provides.{#}.namespace = {namespace} |
| provides.{#}.name = {name} |
| provides.{#}.version = {version} (optional / default: 1.0.0) |
| |
| requires.{#}.namespace = {namespace} |
| requires.{#}.name = {name} |
| requires.{#}.range = {range} (optional / default: 0.0.0)] |
| requires.{#}.matchExp = {p2QL expression} (note that in this case the namespace, name and range attributes are not used) |
| requires.{#}.greedy = {true|false} (optional / default: true) |
| requires.{#}.optional = {true|false} (optional / default: false) |
| requires.{#}.multiple = {true|false} (optional / default: false) |
| requires.{#}.min = {integer} |
| requires.{#}.max = {integer} (when min and max are specified the optional flag is ignored) |
| |
| metaRequirements.{#}.namespace = {namespace} |
| metaRequirements.{#}.name = {name} |
| metaRequirements.{#}.range = {range} (optional / default: 0.0.0) |
| metaRequirements.{#}.matchExp = {p2QL expression} (note that in this case the namespace, name and range attributes are not used) |
| metaRequirements.{#}.greedy = {true|false} (optional / default: true) |
| metaRequirements.{#}.optional = {true|false} (optional / default: false) |
| metaRequirements.{#}.multiple = {true|false} (optional / default: false) |
| metaRequirements.{#}.min = {integer} |
| metaRequirements.{#}.max = {integer} (when min and max are specified the optional flag is ignored) |
| |
| </pre> |
| |
| Where {#} is an index for the property, {namespace}, and {name} are the associated named strings, {version} and {range} are version and version range strings respectively. |
| <br> |
| For example: |
| <pre> |
| provides.0.namespace = testNamespace1 |
| provides.0.name = testName1 |
| provides.0.version = 1.2.3.$qualifier$ |
| provides.1.namespace = testNamespace2 |
| provides.1.name = testName2 |
| provides.1.version = $version$ |
| |
| requires.0.namespace = testNamespace1 |
| requires.0.name = testName1 |
| requires.0.range = [1.2.3.$qualifier$, 2) |
| requires.0.greedy = true |
| requires.0.optional = true |
| requires.0.multiple = true |
| requires.1.namespace = testNamespace2 |
| requires.1.name = testName2 |
| requires.1.range = [$version$, $version$] |
| requires.1.greedy = false |
| |
| metaRequirements.0.namespace = testNamespace1 |
| metaRequirements.0.name = testName1 |
| metaRequirements.0.range = [1.2.3, 2) |
| metaRequirements.0.greedy = true |
| metaRequirements.0.optional = true |
| metaRequirements.0.multiple = true |
| metaRequirements.1.namespace = testNamespace2 |
| metaRequirements.1.name = testName2 |
| metaRequirements.1.range = $version$ |
| metaRequirements.1.greedy = false |
| </pre> |
| <hr> |
| <h3>Property Advice</h3> |
| <pre> |
| properties.{#}.name = {propertyName} |
| properties.{#}.value = {propertyValue} |
| </pre> |
| <p>Where {#} is an index for the property, {propertyName}, and {propertyValue} hold the name and value strings for the property. |
| <br>For example: |
| </p> |
| <pre> |
| properties.0.name = testName1 |
| properties.0.value = testValue1 |
| properties.1.name = testName2 |
| properties.1.value = testValue2 |
| </pre> |
| <hr> |
| |
| <h3>Update descriptor advice</h3> |
| <p>The update descriptor advice allows to override the default update descriptor generated by p2. |
| Typically this is useful if an IU has been renamed and automatic update detection is still desired.</p> |
| <pre> |
| update.id = {id of IU} |
| update.range = {range of the IU being updated} |
| update.matchExp = {a match expression identifying the IU being updated}. (When this is specified the values of id and range are ignored) |
| update.severity = {0|1} |
| </pre> |
| <hr> |
| |
| <h3>Touchpoint Instruction Advice</h3> |
| <pre> |
| instructions.{phase} = {raw actions} |
| instructions.{phase}.import = {qualified action name} [,{qualified action name}]* (optional) |
| </pre> |
| Where {phase} is a p2 installation phase (collect, configure, install, uninstall, unconfigure, etc). |
| |
| Note: |
| <ul> |
| <li>The {raw actions} will be "appended" to the end of any instructions already being generated.</li> |
| <li>The qualified action names for the IU's touchpoint type are implicitly imported. All other actions need to be imported.</li> |
| </ul> |
| |
| For example: |
| <pre> |
| instructions.install = \ |
| ln(targetDir:@artifact,linkTarget:foo/lib.1.so,linkName:lib.so);\ |
| chmod(targetDir:@artifact,targetFile:lib/lib.so,permissions:755); |
| instructions.install.import= \ |
| org.eclipse.equinox.p2.touchpoint.natives.ln,\ |
| org.eclipse.equinox.p2.touchpoint.natives.chmod |
| </pre> |
| Additional information on touchpoint instructions and action syntax can be found <a href="http://wiki.eclipse.org/Equinox/p2/Engine/Touchpoint_Instructions_35">here.</a> |
| <hr> |
| <h3>Additional Installable Unit Advice</h3> |
| <p>In addition to customizing attributes of the containing IU one can also author additional installable units that work |
| with the container IU. Typically this mechanism is used to author an IU fragment that customizes the containing IU or one of its dependencies.</p> |
| |
| <pre> |
| iu.{#}.id = {identifier} |
| iu.{#}.version = {version} (optional) |
| </pre> |
| <p>Where {#} is an index for the installable unit, so multiple installable units can be declared. A full range of IU customizations are supported including:</p> |
| |
| <pre> |
| id |
| version |
| singleton |
| copyright |
| licenses |
| filter |
| touchpoint |
| update |
| artifacts |
| properties |
| provides |
| requires |
| metaRequirements |
| hostRequirements |
| instructions |
| </pre> |
| <p>To illustrate all the various settings for these customizations here's a more complete example of: (unit.0) a minimal IU and (unit.1) a full featured IU:</p> |
| |
| <pre> |
| units.0.id = testid0 |
| units.0.version = 1.2.3 |
| units.1.id = testid1 |
| units.1.version = 1.2.4 |
| units.1.singleton = true |
| units.1.copyright = testCopyright |
| units.1.copyright.location = http://localhost/test |
| units.1.filter = test=testFilter |
| units.1.touchpoint.id = testTouchpointId |
| units.1.touchpoint.version = 1.2.5 |
| units.1.update.id = testid1 |
| units.1.update.range = (1,2) |
| units.1.update.severity = 1 |
| units.1.update.description = some description |
| units.1.artifacts.0.id = testArtifact1 |
| units.1.artifacts.0.version = 1.2.6 |
| units.1.artifacts.0.classifier = testClassifier1 |
| units.1.artifacts.1.id = testArtifact2 |
| units.1.artifacts.1.version = 1.2.7 |
| units.1.artifacts.1.classifier = testClassifier2 |
| units.1.licenses.0 = testLicense |
| units.1.licenses.0.location = http://localhost/license |
| units.1.properties.0.name = testName1 |
| units.1.properties.0.value = testValue1 |
| units.1.properties.1.name = testName2 |
| units.1.properties.1.value = testValue2 |
| units.1.requires.0.namespace = testNamespace1 |
| units.1.requires.0.name = testName1 |
| units.1.requires.0.range = [1.2.3.$qualifier$, 2) |
| units.1.requires.0.greedy = true |
| units.1.requires.0.optional = true |
| units.1.requires.0.multiple = true |
| units.1.requires.1.namespace = testNamespace2 |
| units.1.requires.1.name = testName2 |
| units.1.requires.1.range = $version$ |
| units.1.requires.1.greedy = false |
| units.1.requires.1.optional = false |
| units.1.metaRequirements.0.namespace = testNamespace1 |
| units.1.metaRequirements.0.name = testName1 |
| units.1.metaRequirements.0.range = [1.2.3.$qualifier$, 2) |
| units.1.metaRequirements.0.greedy = true |
| units.1.metaRequirements.0.optional = true |
| units.1.metaRequirements.0.multiple = true |
| units.1.metaRequirements.1.namespace = testNamespace2 |
| units.1.metaRequirements.1.name = testName2 |
| units.1.metaRequirements.1.range = $version$ |
| units.1.metaRequirements.1.greedy = false |
| units.1.metaRequirements.1.optional = false |
| units.1.provides.0.namespace = testNamespace1 |
| units.1.provides.0.name = testName1 |
| units.1.provides.0.version = 1.2.3.$qualifier$ |
| units.1.provides.1.namespace = testNamespace2 |
| units.1.provides.1.name = testName2 |
| units.1.provides.1.version = $version$ |
| units.1.instructions.configure = addProgramArg(programArg:-startup); addProgramArg(programArg:@artifact); |
| units.1.instructions.unconfigure = removeProgramArg(programArg:-startup); removeProgramArg(programArg:@artifact);) |
| units.1.instructions.unconfigure.import = some.removeProgramArg |
| units.1.hostRequirements.0.namespace = testNamespace1 |
| units.1.hostRequirements.0.name = testName1 |
| units.1.hostRequirements.0.range = [1.2.3.$qualifier$, 2) |
| units.1.hostRequirements.0.greedy = true |
| units.1.hostRequirements.0.optional = true |
| units.1.hostRequirements.0.multiple = true |
| </pre> |
| |
| <hr> |
| |
| <a name="categoryGen"></a> |
| <h2>Category Generation Using p2.inf</h2> |
| |
| <p>The p2 UI allows for hierarchical organization of installable units based on the concept of "categories" where the children |
| of categories are what's installable. On occasion we might want to take finer grained control of the contents of a category and |
| what it contains. For example we might want to support further categorization of a feature's contents to allow individual plug-ins |
| to be installed instead of the more typical features.</p> |
| |
| <p>To support this we can tag a feature as a category as follows:</p> |
| <pre> |
| properties.1.name=org.eclipse.equinox.p2.type.category |
| properties.1.value=true |
| </pre> |
| |
| <p>Another possibility is to use "additional IU advice" to create a specialized category IU like this:</p> |
| <pre> |
| units.1.id=my.product.category |
| units.1.version=1.0.0 |
| units.1.provides.1.namespace=org.eclipse.equinox.p2.iu |
| units.1.provides.1.name=my.product.category |
| units.1.provides.1.version=1.0.0 |
| units.1.properties.1.name=org.eclipse.equinox.p2.type.category |
| units.1.properties.1.value=true |
| units.1.properties.2.name=org.eclipse.equinox.p2.name |
| units.1.properties.2.value=My Category Name |
| requires.1.namespace=org.eclipse.equinox.p2.iu |
| requires.1.name=my.product |
| requires.1.range=[1.0.0,1.0.0] |
| requires.1.greedy=true |
| </pre> |
| |
| </body> |
| </html> |