{"comment":{"created_at":"2011-10-10T11:25:15Z","body":"Scope of Change\n====\nModule support will be added to the XP Framework. Modules are a groups\nof types and resources with added metadata: Versions, dependencies, main\nclass, initialization code.\n\n\nRationale\n====\nTake for example an application that someone has written using the XP\nFramework and wants to make it available for the public to use. This\napplication uses a certain version of the framework (or a range, such\nas \"5.7-SERIES\"), but also depends on a certain library which is not\npart of the framework but the app's author himself has written and made \navailable as a separate download. The following questions arise: \n* Where is the software installed to?\n* How is the dependency on the library tracked?\n* How is the framework version verified?\n\n\nFunctionality\n====\nAt the moment, the procedure would probably be as follows:\n* Bundle the library into the application's lib directory\n  and add that to the class path via path files.\n* Zip that all up into a file, posting that for download.\n* Tell the users to unzip that to an arbitrary directory.\n* Add startup code to the main class verifying the framework version.\n\n<summary>\nDirectory layout:\n\n```\n  ~/apps/\n  ^- sloccount-2.0.1\n     |- lib/lang-parsers-1.0.0.xar\n     |- src/\n     |  ^- de/\n     |     ^- thekid/\n     |        ^- sloccount/\n     |           ^- SlocCount.class.php\n     |- app.pth\n     ^- README\n\n```\nThe app.pth file contains the lines `src` and `lib/lang-parsers-1.0.0.xar`.\n\nTo use the application, the following is necessary:\n\n```\n  $ cd ~/apps/sloccount-2.0.1\n  $ xpcli de.thekid.sloccount.SlocCount ~/devel/xp/trunk\n\n```\n</summary>\n\nThis approach has the following downsides:\n* The user has to \"cd\" to the application's directory to use the app.\n* The user has to know the fully qualified (and thus: long) classname\n  to execute the app.\n* The dependency needs to be bundled by the app's author manually.\n* The app has to be re-released if the bundled library is updated.\n* The version verifications have to be performed manually.\n\nWhat we would want to do would be something along the lines of:\n<summary>\nUsage:\n\n```\n  # Use a certain version: Long version, -m shorthand\n  $ xpcli -cp sloccount@2.0.1 de.thekid.sloccount.SlocCount ~/devel/xp/trunk\n  $ xpcli -m sloccount@2.0.1 ~/devel/xp/trunk\n  \n  # Use a certain version: Long version, -m shorthand\n  $ xpcli -cp sloccount@ de.thekid.sloccount.SlocCount ~/devel/xp/trunk\n  $ xpcli -m sloccount ~/devel/xp/trunk\n\n```\n\nThe app would still be installed in a certain place (but this would\nhave to be known to the xp runners), and would somehow indicate it\nrequired the `lang-parsers` library in a certain version as\nwell as the XP Framework's 5.7-SERIES to run.\n\nSo the directory layout would be something like this:\n\n```\n  /???/\n  |- sloccount -> sloccount-2.0.1\n  ^- sloccount-2.0.1\n     |- src/\n     |  |- ???\n     |  ^- de/\n     |     ^- thekid/\n     |        ^- sloccount/\n     |           ^- SlocCount.class.php\n     |- app.pth\n     ^- README\n\n```\nThe app.pth file contains the lines `src` and `lang-parsers@1.0.0`\nso that the dependencies are loaded.\n</summary>\n\nmodule-info.xp\n----\nMost simple version:\n\n```php\n<?php\n  module parallels(0.1.1) {\n  }\n?>\n```\n\nAn application with a main class:\n\n```php\n<?php\n  #[@main('de.thekid.dialog.cmd.AddAlbum')]\n  module dialog.addalbum(2.5.0) {\n  }\n?>\n```\n\nA library:\n\n```php\n<?php\n  uses('rdbms.DriverManager');\n  \n  module mysqlx(1.0.0) {\n    static function __static() {\n      $driver= XPClass::forName('rdbms.mysqlx.MySqlxConnection');\n      $instance= DriverManager::getInstance();\n      $instance->register('mysqlx', $driver);\n      \n      // Snap-in replacement if no MySQL support loaded\n      if (!isset($instance->drivers['mysql'])) {\n        $instance->register('mysql', $driver);\n      }\n    }\n  }\n?>\n```\n\nExecution\n----\nA module with a main class can be executed as follows:\n\n```\n  $ xp -m dialog.addalbum [arg1 [arg2 [...]]]\n\n```\n\nInclusion\n----\nCommand line:\n\n```\n  $ xp -cp mysqlx@0.1.1 [class.Name]\n\n```\n\nPath file:\n\n```\n  src/              # A directory\n  lib/utils.xar     # An archive\n  mysqlx@0.1.1      # A module reference\n\n```\n\nConfiguration\n----\nIn xp.ini:\n\n```\n  use=~/.xp/5.9.0\n  repository=local(~/.xp/modules,/opt/xp/modules/)\n  repository=ivy(~/.ivy)\n\n```\n\nBootstrapping\n----\nHere's a directory listing for an XP release:\n\n```\n  $ ls 5.9.0/*\n  5.9.0/boot.pth  5.9.0/bootstrap.xar\n\n  5.9.0/tools:\n  class.php  web.php    xar.php  lang.base.php\n\n```\nThe bootstrap.xar file contains all the classes in the `lang` package\nand its subpackages and the `VERSION` file. The `boot.pth` file\ncontains the lines `bootstrap.xar` and `xp-rt@5.9.0`.\n\nModule layout\n----\nA typical module directory consists of a class path and a `module-info.xp`\nfile as well as the sources, either inside a file system structure or inside\nan archive.\n\n```\n  $ ls xp-rt/*/*\n  xp-rt/5.9.0/class.pth  xp-rt/5.9.0/module-info.xp\n\n  xp-rt/5.9.0/lib:\n  xp-rt-5.9.0.xar  xp-tools-5.9.0.xar\n\n```\n\nReflection\n----\n\n```php\n<?php\n  $modules= Repository::findAll('dialog');\n  \n  // Core information\n  $modules[0]->getName();             // 'dialog'\n  $modules[0]->getVersion();          // '2.5.0'\n  \n  // Requirements\n  $requirements= $modules[0]->getRequirements();\n  $requirements[0]->getModule();      // 'parallels'\n  $requirements[0]->getConstraint();  // '0.1.1'\n  $requirements[1]->getModule();      // 'xp'\n  $requirements[1]->getConstraint();  // '5.7+'\n  \n  // Annotations\n  $modules[0]->getAnnotations();      // main => 'de.thekid.dialog.cmd.AddAlbum'\n  $modules[0]->getAnnotation('main'); // 'de.thekid.dialog.cmd.AddAlbum'\n  $modules[0]->hasAnnotation('main'); // TRUEs\n?>\n```\n\nRepository\n----\n\n```\n  /opt/xp/modules/\n  |- parallels-0.1.1.xar\n  |  |- module-info.xp\n  |  ^- de/\n  |     ^- thekid/\n  |        ^- parallels/\n  |           |- package-info.xp\n  |           ^- Process.class.php\n  |\n  |- dialog.addalbum -> dialog.addalbum-2.5.0/\n  |\n  |- dialog.addalbum-2.5.0/\n  |  |- module-info.xp\n  |  ^- de/\n  |     ^- thekid/\n  |        ^- dialog/\n  |           ^- cmd\n  |              |- AddAlbum.class.php\n  |              ^- ...\n  |  \n  |- dialog-2.5.0.xar\n  |  |- module-info.xp\n  |  ^- de/\n  |     ^- thekid/\n  |        ^- dialog/\n  |           |- Album.class.php\n  |           |- IEntry.class.php\n  |           ^- ...\n  |\n  ^- dialog-2.4.2.xar\n     |- module-info.xp\n     ^- ...\n\n```\n\nSecurity considerations\n====\n\nSpeed impact\n====\n\nDependencies\n====\n\nRelated documents\n====\n* http://xp-framework.net/rfc/contrib/rfc0204-modules.diff\n  Alternative implementation\n* http://openjdk.java.net/projects/modules/\n  Java Modules @ OpenJDK\n* http://openjdk.java.net/projects/modules/samplerepo/\n  Online repository\n* http://www.javabeat.net/articles/print.php?article_id=101  \n  Introduction to Java Module System in Java 7.0\n* http://mediacast.sun.com/users/sundelabassee/media/J1Ag_Modularity.pdf\n  Modularity in Java OSGi and/or JSR 277\n* http://blogs.sun.com/abuckley/resource/Devoxx2008-ModularityInJava.pdf\n  Modularity in Java - Devoxx 2008\n\n\n\n* friebe, Sat, 14 Aug 2010 14:23:30 +0200","updated_at":"2011-10-10T11:25:15Z","url":"https://api.github.com/repos/thekid/rfc/issues/comments/2346348","id":2346348,"user":{"avatar_url":"https://secure.gravatar.com/avatar/26f07e3b262e9a80436f368cb11bd0c2?d=https://a248.e.akamai.net/assets.github.com%2Fimages%2Fgravatars%2Fgravatar-140.png","url":"https://api.github.com/users/thekid","id":696742,"login":"thekid"}},"action":"created","issue":{"number":204,"created_at":"2011-10-09T16:12:35Z","pull_request":{"diff_url":null,"patch_url":null,"html_url":null},"body":"Scope of Change\n====\nModule support will be added to the XP Framework. Modules are a groups\nof types and resources with added metadata: Versions, dependencies, main\nclass, initialization code.\n\n\nRationale\n====\nTake for example an application that someone has written using the XP\nFramework and wants to make it available for the public to use. This\napplication uses a certain version of the framework (or a range, such\nas \"5.7-SERIES\"), but also depends on a certain library which is not\npart of the framework but the app's author himself has written and made \navailable as a separate download. The following questions arise: \n* Where is the software installed to?\n* How is the dependency on the library tracked?\n* How is the framework version verified?\n\n\nFunctionality\n====\nAt the moment, the procedure would probably be as follows:\n* Bundle the library into the application's lib directory\n  and add that to the class path via path files.\n* Zip that all up into a file, posting that for download.\n* Tell the users to unzip that to an arbitrary directory.\n* Add startup code to the main class verifying the framework version.\n\n<summary>\nDirectory layout:\n\n```\n  ~/apps/\n  ^- sloccount-2.0.1\n     |- lib/lang-parsers-1.0.0.xar\n     |- src/\n     |  ^- de/\n     |     ^- thekid/\n     |        ^- sloccount/\n     |           ^- SlocCount.class.php\n     |- app.pth\n     ^- README\n\n```\nThe app.pth file contains the lines `src` and `lib/lang-parsers-1.0.0.xar`.\n\nTo use the application, the following is necessary:\n\n```\n  $ cd ~/apps/sloccount-2.0.1\n  $ xpcli de.thekid.sloccount.SlocCount ~/devel/xp/trunk\n\n```\n</summary>\n\nThis approach has the following downsides:\n* The user has to \"cd\" to the application's directory to use the app.\n* The user has to know the fully qualified (and thus: long) classname\n  to execute the app.\n* The dependency needs to be bundled by the app's author manually.\n* The app has to be re-released if the bundled library is updated.\n* The version verifications have to be performed manually.\n\nWhat we would want to do would be something along the lines of:\n<summary>\nUsage:\n\n```\n  # Use a certain version: Long version, -m shorthand\n  $ xpcli -cp sloccount@2.0.1 de.thekid.sloccount.SlocCount ~/devel/xp/trunk\n  $ xpcli -m sloccount@2.0.1 ~/devel/xp/trunk\n  \n  # Use a certain version: Long version, -m shorthand\n  $ xpcli -cp sloccount@ de.thekid.sloccount.SlocCount ~/devel/xp/trunk\n  $ xpcli -m sloccount ~/devel/xp/trunk\n\n```\n\nThe app would still be installed in a certain place (but this would\nhave to be known to the xp runners), and would somehow indicate it\nrequired the `lang-parsers` library in a certain version as\nwell as the XP Framework's 5.7-SERIES to run.\n\nSo the directory layout would be something like this:\n\n```\n  /???/\n  |- sloccount -> sloccount-2.0.1\n  ^- sloccount-2.0.1\n     |- src/\n     |  |- ???\n     |  ^- de/\n     |     ^- thekid/\n     |        ^- sloccount/\n     |           ^- SlocCount.class.php\n     |- app.pth\n     ^- README\n\n```\nThe app.pth file contains the lines `src` and `lang-parsers@1.0.0`\nso that the dependencies are loaded.\n</summary>\n\nmodule-info.xp\n----\nMost simple version:\n\n```php\n<?php\n  module parallels(0.1.1) {\n  }\n?>\n```\n\nAn application with a main class:\n\n```php\n<?php\n  #[@main('de.thekid.dialog.cmd.AddAlbum')]\n  module dialog.addalbum(2.5.0) {\n  }\n?>\n```\n\nA library:\n\n```php\n<?php\n  uses('rdbms.DriverManager');\n  \n  module mysqlx(1.0.0) {\n    static function __static() {\n      $driver= XPClass::forName('rdbms.mysqlx.MySqlxConnection');\n      $instance= DriverManager::getInstance();\n      $instance->register('mysqlx', $driver);\n      \n      // Snap-in replacement if no MySQL support loaded\n      if (!isset($instance->drivers['mysql'])) {\n        $instance->register('mysql', $driver);\n      }\n    }\n  }\n?>\n```\n\nExecution\n----\nA module with a main class can be executed as follows:\n\n```\n  $ xp -m dialog.addalbum [arg1 [arg2 [...]]]\n\n```\n\nInclusion\n----\nCommand line:\n\n```\n  $ xp -cp mysqlx@0.1.1 [class.Name]\n\n```\n\nPath file:\n\n```\n  src/              # A directory\n  lib/utils.xar     # An archive\n  mysqlx@0.1.1      # A module reference\n\n```\n\nConfiguration\n----\nIn xp.ini:\n\n```\n  use=~/.xp/5.9.0\n  repository=local(~/.xp/modules,/opt/xp/modules/)\n  repository=ivy(~/.ivy)\n\n```\n\nBootstrapping\n----\nHere's a directory listing for an XP release:\n\n```\n  $ ls 5.9.0/*\n  5.9.0/boot.pth  5.9.0/bootstrap.xar\n\n  5.9.0/tools:\n  class.php  web.php    xar.php  lang.base.php\n\n```\nThe bootstrap.xar file contains all the classes in the `lang` package\nand its subpackages and the `VERSION` file. The `boot.pth` file\ncontains the lines `bootstrap.xar` and `xp-rt@5.9.0`.\n\nModule layout\n----\nA typical module directory consists of a class path and a `module-info.xp`\nfile as well as the sources, either inside a file system structure or inside\nan archive.\n\n```\n  $ ls xp-rt/*/*\n  xp-rt/5.9.0/class.pth  xp-rt/5.9.0/module-info.xp\n\n  xp-rt/5.9.0/lib:\n  xp-rt-5.9.0.xar  xp-tools-5.9.0.xar\n\n```\n\nReflection\n----\n\n```php\n<?php\n  $modules= Repository::findAll('dialog');\n  \n  // Core information\n  $modules[0]->getName();             // 'dialog'\n  $modules[0]->getVersion();          // '2.5.0'\n  \n  // Requirements\n  $requirements= $modules[0]->getRequirements();\n  $requirements[0]->getModule();      // 'parallels'\n  $requirements[0]->getConstraint();  // '0.1.1'\n  $requirements[1]->getModule();      // 'xp'\n  $requirements[1]->getConstraint();  // '5.7+'\n  \n  // Annotations\n  $modules[0]->getAnnotations();      // main => 'de.thekid.dialog.cmd.AddAlbum'\n  $modules[0]->getAnnotation('main'); // 'de.thekid.dialog.cmd.AddAlbum'\n  $modules[0]->hasAnnotation('main'); // TRUEs\n?>\n```\n\nRepository\n----\n\n```\n  /opt/xp/modules/\n  |- parallels-0.1.1.xar\n  |  |- module-info.xp\n  |  ^- de/\n  |     ^- thekid/\n  |        ^- parallels/\n  |           |- package-info.xp\n  |           ^- Process.class.php\n  |\n  |- dialog.addalbum -> dialog.addalbum-2.5.0/\n  |\n  |- dialog.addalbum-2.5.0/\n  |  |- module-info.xp\n  |  ^- de/\n  |     ^- thekid/\n  |        ^- dialog/\n  |           ^- cmd\n  |              |- AddAlbum.class.php\n  |              ^- ...\n  |  \n  |- dialog-2.5.0.xar\n  |  |- module-info.xp\n  |  ^- de/\n  |     ^- thekid/\n  |        ^- dialog/\n  |           |- Album.class.php\n  |           |- IEntry.class.php\n  |           ^- ...\n  |\n  ^- dialog-2.4.2.xar\n     |- module-info.xp\n     ^- ...\n\n```\n\nSecurity considerations\n====\n\nSpeed impact\n====\n\nDependencies\n====\n\nRelated documents\n====\n* http://xp-framework.net/rfc/contrib/rfc0204-modules.diff\n  Alternative implementation\n* http://openjdk.java.net/projects/modules/\n  Java Modules @ OpenJDK\n* http://openjdk.java.net/projects/modules/samplerepo/\n  Online repository\n* http://www.javabeat.net/articles/print.php?article_id=101  \n  Introduction to Java Module System in Java 7.0\n* http://mediacast.sun.com/users/sundelabassee/media/J1Ag_Modularity.pdf\n  Modularity in Java OSGi and/or JSR 277\n* http://blogs.sun.com/abuckley/resource/Devoxx2008-ModularityInJava.pdf\n  Modularity in Java - Devoxx 2008\n\n\n","comments":3,"title":"RFC 0204: Modules","updated_at":"2011-10-10T11:25:15Z","url":"https://api.github.com/repos/thekid/rfc/issues/204","id":1856819,"assignee":null,"milestone":null,"closed_at":null,"user":{"avatar_url":"https://secure.gravatar.com/avatar/26f07e3b262e9a80436f368cb11bd0c2?d=https://a248.e.akamai.net/assets.github.com%2Fimages%2Fgravatars%2Fgravatar-140.png","url":"https://api.github.com/users/thekid","id":696742,"login":"thekid"},"html_url":"https://github.com/thekid/rfc/issues/204","labels":[{"name":"draft","url":"https://api.github.com/repos/thekid/rfc/labels/draft","color":"02d7e1"}],"state":"open"},"legacy":{"issue_id":1856819,"comment_id":2346348}}