As some of you might have noticed I've been very busy for the past days working on GShell. I've been meaning to stop hacking and write some email about what I'm doing, but I always end up jumping into some feature or fixing some bug. But a lot has changed, so I really need to post some details... but rather than go all gooey on the details I am just going to point out the major changes. If anyone wants the gooey stuff, ping me back and I can explain in much more detail.

CONTAINER

Spring is used for 99% of the container needs. Still have some plexus stuff around to support maven-artifact-based resolution.

Dropped gshell-rapture, too much work to keep the plexus glue up to date with the spring glue (aka gshell-wisdom).

Layouts are gone, currently there is only a flat namespace for files... that is one of the major things left to be resolved. Originally I had though of the commands namespace like it was a filesystem, and you might even "cd" to change the path or whatever, but the VFS work (see below) really showed me that was not a good idea. I am planning on implementing a command namespace, just still trying to figure out how. More to come on this later I'm sure.

The gshell-remote && gshell-whisper stuff is now all spring happy, though it still needs to be re-implemented to move more of the configuration stuff into the spring context. There are still a lot of holes in this stuff, as I only have been making what was there before work again. So that is another major area which I plan to work on once the framework issues are sorted.

I18N

I've hooked up resource bundles for each and every command, and updated the CLP stuff to use them for messages related to --help content. Still need to hook up a really simple way to use i18n messages for all user output (except logging messages). But its getting closer. Related is that commands now have a "manual", so if you say "help help" it will show you the manual for the "help" command, this text is also externalized for i18n, though I've not had time to write a manual for anything so they are all todo's right now. Once things stabilize more we can write those.

VFS

Implemented a bunch more VFS commands to operate on files:

  cd              Changes the current directory.
  pwd             Displays the current directory.
  ls              List the contents of a file or directory.
  cp              Copies a file or directory.
  rm              Remove a file or directory.
  cat             Displays the contents of a file.
  edit            Edit a file with an external editor.
  touch           Sets the last-modified time of a file.
  dir             Link to: ls
  copy            Link to: cp
  del             Link to: rm

Changed all (well most, pending a commit for the script command to use this soon) commands to use VFS FileObjects instead of a File/URL, so they can take advantage of this flexibility.

I think this stuff is really cool, and will really be helpful for real- users down the line. For example, with the VFS SFTP provider configured you can do something like:

gshell> cd sftp://myusername:[EMAIL PROTECTED]/pub
gshell> ls
foo.txt bar.txt baz/
gshell> cat foo.txt

The cat will show whatever the contents are of foo.txt as you might expect.

You can also copy files between filesystems, this would copy from the cwd (which is still what is set from above) to your local /tmp directory:

gshell> cp foo.txt /tmp

And see that its there with:

gshell> ls /tmp/foo.txt

Or if you just want to *edit* the contents of the remote file:

gshell> edit foo.txt

This will open up an external editor with the contents of foo.txt, you can edit, save, close, then the changes are pushed to the remove. Same works for locals, minus the pull and push of content. Should work on windows, though I've not actually tried it to see what breaks.

Some features left to be done, are implementing a virtual VFS thingy, so you can mount/unmount filesystems to get an aggregate view which you can easily cd around without needing horrible long URIs.

COMPLETION

Finally implemented completion. Commands that take files, alias names, variables names, etc now support tab-completion. Can even complete VFS paths!

ALIASES & LINKS

Added support for command aliases (via "alias foo bar" and "unalias foo") as well as linked commands (sorta aliases, but with better completion support). Aliases don't show up in 'help' output, they show up under 'alias' output, like how it works on a unix shell. Though please note, that the definition syntax does not include a "=" as the syntax parser is still too stupid to handle that well.

Aliases don't have completer, as you can put any string as the value of the alias, so its really hard to figure out what command to resolve to and how to apply a completer for it. But I also wanted to provide some way to provide a different name for a command, so I implemented a _link_. Which simply defines a new command with a new name and delegates most of the work to a target command. This allows the _linked_ command to pick up the completer configuration from its target. For example, the 'source' command can complete any VFS path as its first argument... and the "." link (which is a unix shell thingy) performs exactly the same. Only difference is that when you ask for 'help', the help text shows up as "Link to: source". Right now links are not configurable at runtime, they have to be defined in a plugins components.xml.

PLUGINS

GShell plugins are now loaded, using configuration in the application.xml descriptor to load at boot, or the 'install-plugin' command to dynamically install. For example, right now the gshell-bsf (which supports scripting) is not enabled by default, but you can run the shell and install it simply by running:

gshell> install-plugin -g org.apache.geronimo.gshell.commands -a gshell-bsf -v 1.0-alpha-2-SNAPSHOT

Plugins are configured via META-INF/spring/components.xml so you can define any required muck there. But I added some sugar to simplify the wiring of the command muck. Have a peek, this is the components.xml for the gshell-bsf (script command) plugin:

----8<----
<beans xmlns="http://www.springframework.org/schema/beans";
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance";
       xmlns:gshell="http://gshell.org/schema/wisdom-gshell";
       xsi:schemaLocation="
            http://www.springframework.org/schema/beans 
http://www.springframework.org/schema/beans/spring-beans.xsd
http://gshell.org/schema/wisdom-gshell http://gshell.org/schema/wisdom-gshell/wisdom-gshell.xsd ">

    <gshell:plugin name="gshell-bsf">
        <gshell:command-bundle name="default">
            <gshell:command name="script">
<gshell:action class="org.apache.geronimo.gshell.commands.bsf.ScriptAction"/>
                <gshell:completers>
                    <ref bean="fileObjectNameCompleter"/>
                    <null/>
                </gshell:completers>
            </gshell:command>
        </gshell:command-bundle>
    </gshell:plugin>

<bean id="bsfManager" class="org.apache.geronimo.gshell.commands.bsf.BSFManagerFactoryBean"/>

</beans>
---->8----

I won't show you what this generates under the covers though... its quite a lot of noisy spring beans muck.

You can also see what plugins are installed with:

gshell> list-plugins

I'm still working on the plugin system, so I leave it at that for now. But I plan to add more management commands, make install-plugin be persistable (so you can dynamically add a plugin and then on next boot it will automatically enable w/o running install-plugin again.

Plugins are also made up of "bundles", that is so a plugin can define smaller chunks of stuff (commands, classpath extentions, whatever) which can be enabled/disabled. For example, a plugin might define a default command bundle with user commands, and another command bundle for admin stuff, which would require an administrator to enable the bundle before the commands could be used.

Also plugins are intended to have some "activation" muck, which could conditionally enable bundles based on some rules, like only enable bundle "windowsmuck" when the OS is windows, etc. Still working all this stuff out, but just to give ya an idea of what that stuff is doing.

SIZE

So as you might expect, as more features get added, the size of the dist gets bigger, and right now its 4.1m (for the bootstrap lib/* stuff). That does not include the gshell-wisdom core and related bits, or plugin bits, which get downloaded from a remoteRepository dynamically. About 1/4 of that is to support that artifact resolution, as it requires a lot of Maven internal muck to process poms. I am thinking about ways to reduce that. Also the gshell- wisdom impl uses the spring-context stuff ATM, which adds another ~500k and I'm not sure that we really need it.

Anyways, my point is that its gotten bigger :-( But I'm looking into sliming her down again... w/o loosing any functionality.

SPEED

Another thing you might notice if you play with the new shell, is that it boots up a lot slower the first time due to all that artifact resolution stuff, plugin container construction, etc. I plan on doing a few rounds of optimization of things once some of the other functional issues are wrapped up, or close to be wrapped. So, don't panic ;-)

 * * *

Um, I guess I could go on and on, as I keep thinking of stuff I've done recently and not included in an update, but this mail is already longer than I'd hopped... though covered less than I'd like. If you are feeling bored, give the latest bits a try, its usually in a compilable state. Though you must build maven-2.0.x first because the Maven team never seems to update its snapshots. So if you want to build gshell, then:

svn co https://svn.apache.org/repos/asf/maven/components/branches/maven-2.0.x
cd maven-2.0.x
mvn install

and then:

svn co https://svn.apache.org/repos/asf/geronimo/gshell/trunk gshell
cd gshell
mvn

Cheers,

--jason




Reply via email to