Ron Savage wrote:
Lincoln Stein says he's too busy at the moment (surprise!) and has asked me to whip up a can() method. I'll do that now.

Cool! Thanks for following up on this Ron.


If you have any suggestions, post them to this list (I'm subscribed).

Here is a first stab at a solution. I haven't really tested it thoroughly enough, but it should give you some ideas of how it can be implemented. Also, I'm sure Lincoln will want a .t test file as well.


First, a couple of notes... The reason I am compiling the function if it doesn't already exist is because UNIVERSAL::can returns a reference to the function on success, so the function will need to be compiled when 'can' is called... I was hoping there was a way to write 'can' so that the function wouldn't need to be compiled, but I can't come up with one...

Also, you have to check with UNIVERSAL::can first, since the function may already exist in the inheritance tree somewhere (in a subclass or superclass). The checks for existence need to be made in the same order that they would occur if the function was called directly (instead of through 'can'). Since AUTOLOAD gets called last, after the entire inheritance tree is searched, the copy in the inheritance tree takes presidence over any AUTOLOADed method. This situation could arise if someone wrote a class that inherited from CGI.pm and then overrode say the 'cookie' method. This subclass would inherit CGI::can as well, so it should return a reference to the overridden cookie method, and not compile the one in CGI.pm and return a reference to that.

Anyway, here is my attempt. Hope it helps:


# custom 'can' method for autoloaded subroutines sub can { my $class = shift; my $func_name = shift;

    # See if UNIVERSAL::can finds it
    if (my $func = $class->SUPER::can($func_name)) {
        return $func;
    }
    # Try to compile the function
    eval {
        # _compile looks at $AUTOLOAD for the function name
        local $AUTOLOAD = join "::",$class,$func_name;
        &_compile;
    };
    # now that the function is loaded (if it exists)
    #  just use UNIVERSAL::can again to do the work
    return $class->SUPER::can($func_name);
}


Cheers,


Cees

---------------------------------------------------------------------
Web Archive:  http://www.mail-archive.com/[EMAIL PROTECTED]/
             http://marc.theaimsgroup.com/?l=cgiapp&r=1&w=2
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Reply via email to