Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

Cook Up a Runtime with The New OSGi Resolver - Neil Bartlett

734 views

Published on

OSGi DevCon 2013

OSGi applications are assembled from loosely coupled bundles communicating via services. While this model provides huge flexibility and the ability to reuse components, it creates a challenge for the assembler of the application since it is unclear which bundles are needed, which are optional and which are unnecessary.

For example some dependencies are implicit, such as the provider of a service or an extender. We do not want to prematurely lock down these dependencies at build time, but at deployment time a specific provider must be found otherwise the application will fail to behave as expected. Furthermore when third-party libraries are used they often contain static dependencies on additional libraries, which in turn contain additional dependencies, and so on. Much time is wasted in finding a set of bundles that will actually resolve and run in the OSGi environment, and once such a set is found, developers tend to fear making changes to it.

The generic requirements and capabilities model introduced in OSGi Release 4.3, along with the standard Repository and Resolver specifications introduced in OSGi Release 5, provide answers for both of these problems. Using capabilities, we can describe dependencies in an abstract way without prematurely binding to specific providers. Using the resolver, we can narrow our focus to the very small set of bundles that describe our application at the top level, and allow all other dependencies to be computed and managed for us.

This talk begins with a brief technical overview of the new 4.3 and 5.0 specifications and how they can be used to assemble applications with ease. We then demonstrate both development tooling and a runtime platform that can be used to put these ideas into practice.

Published in: Technology
  • Be the first to comment

Cook Up a Runtime with The New OSGi Resolver - Neil Bartlett

  1. 1. Copyright © 2005 - 2013 Paremus Ltd. May not be reproduced by any means without express permission. All rights reserved. Paremus Packager March 2013 Cook Up a Runtime with the OSGi Resolver Neil Bartlett - Paremus neil.bartlett@paremus.com Friday, 29 March 13
  2. 2. Problem Statement (1) Friday, 29 March 13
  3. 3. OSGi “The Framework that Likes to Say...” Friday, 29 March 13
  4. 4. NOYOU CAN’T Friday, 29 March 13
  5. 5. NO YOU CAN’T • Example: missing import: org.wtf. • Google for org.wtf, find that it’s part of bundle com.acme.fml • Download and install com.acme.fml, now you have more missing imports: org.thingummy, javax.whatever (version 3.0.2.SNAPSHOT). • Go round again... and again... and again... Friday, 29 March 13
  6. 6. THIS IS NOT A JOB FOR HUMAN BEANS Friday, 29 March 13
  7. 7. Problem Statement (2) Friday, 29 March 13
  8. 8. NOTHING’S HAPPENING! Friday, 29 March 13
  9. 9. Nothing’s Happening • Oh you’re using Declarative Services! Did you remember to include org.apache.felix.scr? • Oh you’re using Blueprint. Did you remember to include org.apache.aries.blueprint? • Oh you’re using JPA. Did you remember to include org.eclipse.gemini.jpa? Friday, 29 March 13
  10. 10. Extender/Whiteboard • NO direct/static dependency • Dependency is implicit: without the extender, nothing happens. • NO diagnostic error messages Friday, 29 March 13
  11. 11. Not Really Solutions • Deployment Admin Packages • Eclipse Features • Virgo Plans/PARs • Karaf KARs/Features • etc... Friday, 29 March 13
  12. 12. OSGi Release 5 Friday, 29 March 13
  13. 13. OSGi Release 5 • Released April 2012 • New Specification: Resolver and Repository Friday, 29 March 13
  14. 14. Repositories Friday, 29 March 13
  15. 15. Simple API! public interface Repository { Map<Requirement, Collection<Capability>> findProviders( Collection<? extends Requirement> requirements); } Friday, 29 March 13
  16. 16. Repository • Can return Resources from anywhere • Should have knowledge of capabilities and requirements of the resources it manages • Database? XML file? Just an implementation detail. Friday, 29 March 13
  17. 17. XML Index Format <repository name='Local' xmlns='http://www.osgi.org/xmlns/repository/v1.0.0'> <resource> <capability namespace='osgi.identity'> <attribute name='osgi.identity' value='org.apache.felix.gogo.runtime'/> <attribute name='type' value='osgi.bundle'/> <attribute name='version' type='Version' value='0.10.0'/> </capability> <capability namespace='osgi.content'> <attribute name='osgi.content' value='15e94961ae2d0046278686965fe6a34ad43d8d18719f5bc2304e725cdb57a379'/> <attribute name='url' value='org.apache.felix.gogo.runtime/ org.apache.felix.gogo.runtime-0.10.0.jar'/> <attribute name='size' type='Long' value='66965'/> <attribute name='mime' value='application/vnd.osgi.bundle'/> </capability> <capability namespace='osgi.wiring.package'> <attribute name='osgi.wiring.package' value='org.apache.felix.service.command'/> <attribute name='version' type='Version' value='0.10.0'/> <attribute name='status' value='provisional'/> <attribute name='bundle-symbolic-name' value='org.apache.felix.gogo.runtime'/> <attribute name='bundle-version' type='Version' value='0.10.0'/> <directive name='mandatory' value='status'/> </capability> ... Friday, 29 March 13
  18. 18. Generating an Index • RepoIndex: https://github.com/osgi/bindex • Standalone library, also command line,ANT, OSGi service, etc. Friday, 29 March 13
  19. 19. Repository Implementations • RI from Red Hat: github.com/jbosgi/jbosgi-repository • bnd “Fixed Indexed Repo” • Just needs a URI to an index • bnd “Local Indexed Repo” • Mutable, based on local file-system folder • Automatically reindexes on deploy Friday, 29 March 13
  20. 20. Resolver Friday, 29 March 13
  21. 21. Simple API! public interface Resolver { Map<Resource, List<Wire>> resolve(ResolveContext context) throws ResolutionException; } Friday, 29 March 13
  22. 22. Resolver Result • Returns a Delta: new Resources, new Wires • Can be used by OSGi Framework • Use outside OSGi to discover resources Friday, 29 March 13
  23. 23. DO NOT IMPLEMENT • Implementing a Resolver is HARD • Resolver is very generic.You almost certainly don’t NEED to implement your own Friday, 29 March 13
  24. 24. Resolver Implementation • Just One: The RI from Apache Felix • Used in Felix Framework • Soon to be used in Equinox Framework • Used by Subsystems Specification • Used by Bnd(tools) • Soon to be used in Paremus Nimble Friday, 29 March 13
  25. 25. So the Resolver talks to the Repository, right? Friday, 29 March 13
  26. 26. WRONG • Resolver has no knowledge of any Repository. Friday, 29 March 13
  27. 27. At least it knows about current Bundles and Wires, right? Friday, 29 March 13
  28. 28. WRONG • Resolver has no knowledge of existing state. Friday, 29 March 13
  29. 29. Resolver is Clueless! • Resolver just finds a solution to a puzzle • The inputs to the puzzle depend on us: the Resolve Context Friday, 29 March 13
  30. 30. Resolve Context Friday, 29 March 13
  31. 31. Resolve Context • Implemented by Resolver clients. I.e., us! • Guides the resolver. Friday, 29 March 13
  32. 32. Not So Simple API! public abstract class ResolveContext { public Collection<Resource> getMandatoryResources() { return emptyCollection(); } public Collection<Resource> getOptionalResources() { return emptyCollection(); } public abstract Map<Resource, Wiring> getWirings(); public abstract List<Capability> findProviders(Requirement requirement); public abstract boolean isEffective(Requirement requirement); public abstract int insertHostedCapability(List<Capability> capabilities, HostedCapability hostedCapability); } Friday, 29 March 13
  33. 33. getMandatoryResources() • This is our starting point • List of resources that must be present in the result • Bndtools creates a single dummy Resource containing the input Requirements Friday, 29 March 13
  34. 34. getOptionalResources() • List of resources we hope will be present in the result • Failure to resolve one of these doesn’t break the whole resolution Friday, 29 March 13
  35. 35. getWirings() • Map of existing resolved resources and their wires • Inside OSGi, this is the already resolved bundles • In Bndtools this is empty Friday, 29 March 13
  36. 36. findProviders() • Here’s the meat! • The Resolver wants to resolve a requirement... • ... asks us to find the candidate Capabilities to satisfy it • We return a ranked collection of Capabilities • Typically we talk to our Repositories • Resolver tries to use the highest ranked candidate, but no promises. Friday, 29 March 13
  37. 37. GOTCHA • Don’t go to Repositories for JRE packages etc. • Always check system bundle capabilities first. • Some Resources have “self-requirements”, e.g. importing package exported by same bundle. • Always check first if the resource’s own capabilities satisfy the requirement Friday, 29 March 13
  38. 38. isEffective() • Decide whether to ignore the Requirement Friday, 29 March 13
  39. 39. insertHostedCapability() • Oh Mummy... • Insert fragment capabilities into the list returned by findProviders(), at the correct position • More proof that fragments are horrible. Friday, 29 March 13
  40. 40. Implementations • Felix and Equinox Frameworks • BndrunResolveContext in bnd project takes a .bndrun file as input Friday, 29 March 13
  41. 41. DEMO Friday, 29 March 13
  42. 42. Requirement “Effectiveness” Friday, 29 March 13
  43. 43. Effective • Some requirements are “effective” at different times • E.g.: Require-Capability: osgi.service;filter:=... • Should Not block resolution by the OSGi Framework •Should guide OBR/Nimble/Bndtools to add a provider to the result Friday, 29 March 13
  44. 44. Effective Require-Capability: osgi.service; filter:="(objectClass=org.example.exchange.api.Exchange)"; effective:=active Friday, 29 March 13
  45. 45. Effective • Requirements are only effective in OSGi Framework resolution if effective == “resolve” • ... but “resolve” is the default, so omitting the “effective:” directive also works. • Other Resolve Contexts (e.g. Bndtools) can decide by implementing isEffective(Requirement). Friday, 29 March 13
  46. 46. effective:=active • No value for “effective:” is defined by OSGi other than “resolve” • “active” is a convention for requirements that apply to active bundles. • E.g.: extenders, whiteboard, services, etc Friday, 29 March 13
  47. 47. Open Questions Friday, 29 March 13
  48. 48. Choice • Your app requires a Web container, e.g. osgi.extender;filter:=“(osgi.extender =osgi.wab)” • Tomcat and Jetty are both available. • It only makes sense to have one! How do we decide? Friday, 29 March 13
  49. 49. Choice • It’s all down to ResolveContext.findProviders() • Ranked preference, Resolver tries to pick highest. • Or we return just one. Friday, 29 March 13
  50. 50. Current State-of-the-Art • “Repository Path” • Resources from earlier repos are preferred over later repos. • Forces us to have many, granular repos. • Probably won’t scale. Friday, 29 March 13
  51. 51. Future? • Interactive Resolve. • Ask the user, but cache the answer (...for how long?) • Policies • “Prefer Jetty over Tomcat” • Repository Filters Friday, 29 March 13
  52. 52. Conclusion Friday, 29 March 13
  53. 53. What is an Application?? • A small number of bundles defining the high-level functionality. • All of the dependencies of the above. • Curate your top-level bundles. •Generate your dependency lists. Friday, 29 March 13
  54. 54. Caution • When should we resolve? • The result can change if repo contents change! • Resolve => Test => Resolve => Deploy to Prod... bang! • WYTIWYR • Persist your resolution result. Friday, 29 March 13
  55. 55. Thank YouThank You Friday, 29 March 13

×