Stories
Slash Boxes
Comments
NOTE: use Perl; is on undef hiatus. You can read content, but you can't post it. More info will be forthcoming forthcomingly.

All the Perl that's Practical to Extract and Report

use Perl Log In

Log In

[ Create a new account ]

grink (8549)

grink
  (email not shown publicly)

Journal of grink (8549)

Thursday October 09, 2008
06:38 PM

Config::JFDI 0.04 released

Config-JFDI 0.04 should be on CPAN shortly

Config::JFDI mimics Catalyst::Plugin::ConfigLoader (without the need to load Catalyst). The new features in this release are:

  • Value substitution, just like C::P::CL (__HOME__, __path_to(...)__, __literal(...)__, etc.)
  • Ability to accept a default hash for a baseline configuration

Config::JFDI 0.04 released

12:06 AM

POD-like documentation for JavaScript: Doc::Simply

I've just released Doc::Simply, a tool for generating documentation from JavaScript (or C, C++, etc.) comments.

I use it to for my b9j documentation

The idea came to me while developing some JavaScript: I was craving a way to drop in free-form documentation in a .js file as easily as I could in a .pm with perlpod.

The Doc::Simply format is modeled after Plain-Old-Documentation, but it is not an exact mimic. Body formatting, for example, is in Markdown (no C<>, L<>, ...)

However, if you are craving pure POD, then it shouldn't be too difficult to bolt a proper parser/generator on top of Doc::Simply

You can run it from the command-line as doc-simply

doc-simply < source.js > documentation.html

doc-simply --help

An example:
   /*
    * @head1 NAME
    *
    * Calculator - Add 2 + 2 and return the result
    *
    */

   // @head1 DESCRIPTION
   // @body Add 2 + 2 and return the result (which should be 4)

   /*
    * @head1 FUNCTIONS
    *
    * @head2 twoPlusTwo
    *
    * Add 2 and 2 **and** return 4
    *
    */

   function twoPlusTwo() {
       return 2 + 2; // Should return 4
   }

/*
 * @head1 AUTHOR
 *
 * Alice <alice@example.com>
 *
 * [http://example.com](http://example.com)
 *
 */

... which will generate this document

You can download it from http://search.cpan.org/CPAN/authors/id/R/RK/RKRIMEN/Doc-Simply-0.02.tar.gz

... or install it via cpan:

cpan -i Doc::Simply

POD-like documentation for JavaScript: Doc::Simply

Thursday September 11, 2008
06:21 PM

JavaScript URI/URL object

I've put together an interactive example of my JavaScript URI object:

b9j.uri.URI example

The example will also show the code necessary to perform the given operation (next to the result)

b9j.uri.URI overview:

  • Parses using Steven Levithan's parseUri 1.2
  • Easy path traversal (ascend to parent, descend to a child)
  • Set or add to the URI query (with proper encoding), get/interrogate the query (with proper decoding)
  • Add arbitrary data (unencoded) to the end of the query string, for extra flexibility
  • Manipulate/interrogate the scheme, user information (username & password), host, port, fragment, and more in a piecewise fashion
  • Add, change or strip the extension (html, js, css, ...) from a given URI

The code is available at http://appengine.bravo9.com/b9j/b9j.uri.js (19kb compressed / 5kb gzipped)

See also the documentation for b9j.uri

JavaScript URI object

Wednesday September 10, 2008
05:36 PM

Large Hadron Collider (LHC) webcam

Large Hadron Collider webcam, pretty interesting:

http://www.cyriak.co.uk/lhc/lhc-webcams.html

(thanks gcohen!)

Thursday September 04, 2008
01:47 PM

URI handling in JavaScript with b9j.uri

Following my b9j.path release, I just finished up work on URI object-class for javascript.

It uses Steven Levithan's parseUri 1.2 to do the parsing.

Some example usage:

var uri = new b9j.uri.URI( "http://example.com/a/b?a=1&b=2&c=3&c=4&c=5" )
var host = uri.host()

var child = uri.child("c.html")            // http://example.com/a/b/c.html?a=1& b=2& ...
child.query().add({ c: [ 6, 7 ], d: 8 })   // ... ?a=1&b=2&c=3&c=4&c=5&c=6&c=7&d =8
child.query().set("b", 9)                  // ... ?a=1&b=9&c ...

return child.toString()

Again, while CPAN has URI.pm for URI-handling, JavaScript didn't really have an equivalent (parsing yes -- modifying/generating no).

b9j.uri - URI parsing, manipulation, and generation

URI handling in JavaScript with b9j.uri: a URI/URI-query parser, manipulator, and generator

Wednesday August 27, 2008
09:10 PM

Path handling in JavaScript with b9j.path

b9j.path provides a way to parse, manipulate, and generate URI/UNIX-style paths.

CPAN provides lots of different options for path-handling and path-manipulation, but there didn't seem to be anything really available in JavaScript-land.

To fill the gap, I've released b9j.path:

 var path = new b9j.path.Path("/a/b/c")

 // /a/b/c/xyzzy
 var child = path.child("xyzzy")

 // /a/b
 var parent = path.parent()

 // ... and much, much, more...

It's part of my b9j javascript pack available at: http://appengine.bravo9.com/b9j/b9j-latest.zip

» Download

» Documentation

» Test

Path handling in JavaScript with b9j.path: a UNIX-style path parser, manipulator, and generator

Tuesday August 26, 2008
06:22 PM

b9jTest: Simplifying and enhancing YUI Test

YUI Test is a great tool for javascript testing, but it has a couple of small issues:

  • Setting up the HTML document requires many different .js and .css assets
  • The actual javascript code to set up the test environment is not trivial (setting up the TestRunner, setting up the TestLogger, etc.)
  • A failed assertion will abort the test function immediately, preventing later tests from running

b9jTest addresses the problems above by:

  • Bundling all the required .js and .css assets into just two separate files
  • Providing some boilerplate javascript so you can jump right into testing without a lot of setup

An example b9jTest document:

<html>
<head>
    <meta http-equiv="content-type" content="text/html; charset=utf-8">
<title>b9jTest example</title>
<link rel="stylesheet" type="text/css"
    href="http://appengine.bravo9.com/b9j/b9jTest.css">
<script type="text/javascript"
    src="http://appengine.bravo9.com/b9j/b9jTest.js"></script>
</head>
<body class="yui-skin-sam">
<div id="testLogger"></div>
<script type="text/javascript">

    b9jTest(function(test) {
        test.areEqual("xyzzy", "xyzzy");
        test.areEqual("apple", "apple");
        test.areEqual("banana", "banana");
    });  

</script>
</body>

b9jTest() is a global function that accepts a function that is called with a testing object. The testing object provides access to the standard YUI assertions and more.

Documentation:

Download:

b9jTest: Simplifying and enhancing YUI Test

Saturday August 23, 2008
08:30 PM

Copying text into the clipboard with javascript

Example of copying text into the clipboard

Firefox won't allow copying text into the clipboard via javascript for a variety of reasons.

For better or worse, you can get around this problem with a little .swf (Flash):

    function copyIntoClipboard(text) {

        var flashId = 'flashId-HKxmj5';

        /* Replace this with your clipboard.swf location */
        var clipboardSWF = 'http://appengine.bravo9.com/copy-into-clipboard/clip board.swf';

        if(!document.getElementById(flashId)) {
            var div = document.createElement('div');
            div.id = flashId;
            document.body.appendChild(div);
        }
        document.getElementById(flashId).innerHTML = '';
        var content = '<embed src="' + 
            clipboardSWF +
            '" FlashVars="clipboard=' + encodeURIComponent(text) +
            '" width="0" height="0" type="application/x-shockwave-flash"></embed >';
        document.getElementById(flashId).innerHTML = content;
    }

The above trick will also work in Safari, IE, and Opera.

Download clipboard.swf

Alternatively, you can use the Google App Engine hosted version at
http://appengine.bravo9.com/copy-into-clipboard/clipboard.swf

(Originally adapted from http://www.jeffothy.com/weblog/clipboard-copy/)

Copying text into the clipboard with javascript in Firefox, Safari, IE, Opera, ...

Sunday August 17, 2008
03:30 PM

Getopt::Chain released: git(1) style command-line processing

Getopt::Chain

Option and subcommand processing in the style svn(1) and git(1)

Getopt::Chain will help you make your command-line scripts work like this:

    ./script --opt --opt=<value> cmd --opt ...
    ./script cmd ...

NOTE: Any option specification covered by Getopt::Long is fair game.

Here is some example usage:

    #!/usr/bin/perl -w

    use strict;
    use Getopt::Chain;

    # A partial, pseudo-reimplementation of git(1):

    Getopt::Chain->process(

        options => [qw/ version bare git-dir=s /]

        run => sub {
            my $context = shift;
            my @arguments = @_; # Remaining, unparsed arguments

            # ... do stuff before any subcommand ...

        }

        commands => {

            init => {
                options => [qw/ quiet|q --template=s /]
                run => sub {
                    my $context = shift;
                    my @arguments = @_; # Again, remaining unparsed arguments 

                    # ... do init stuff ...
                }
            }

            commit => {
                options => [qw/ all|a message|m=s /]
                run => sub {
                    my $context = shift;

                    # ... do commit stuff ..
                }
            }

            add => ...

            help => ...

            ...
        }
    )

    # The above will allow the following (example) usage:
    #
    # ./script --version
    # ./script --git-dir path/to/repository init
    # ./script --git-dir path/to/repository commit -a --message '...'
    # ./script commit -m '~'

The source repository is on GitHub: http://github.com/robertkrimen/getopt-chain/tree/master

Getopt::Chain released: git(1) and svn(1) style command-line processing

Saturday August 16, 2008
11:20 AM

Hash::Param released

Hash::Param

A CGI/Catalyst::Request-like parameter-hash accessor/mutator

    my $params = Hash::Param->new(parameters => {
        qw/a 1 b 2 c 3/,
        d => [qw/4 5 6 7/],
    })

    $result = $params->param( a )           # Returns 1
    $result = $params->param( d )           # Returns 4
    @result = $params->param( d )           # Returns 4, 5, 6, 7
    @result = $params->params               # Returns a, b, c, d
    $result = $params->params               # Returns { a => , b => 2,
                                                        c => 3, d => [ 4, 5, 6,  7 ] }
    @result = $params->params( a, b, d )    # Returns 1, 2, [ 4, 5, 6, 7 ]
    %result = $params->slice( a, b )        # Returns a => 1, b => 2

              $params->param( a => 8 )      # Sets a to 8
              $params->param( a => 8, 9 )   # Sets a to [ 8, 9 ]

The source repository is on GitHub: http://github.com/robertkrimen/hash-param/tree/master

Hash::Param released