NAME
JavaScript::Duktape - Perl interface to Duktape embeddable javascript engine
SYNOPSIS
use JavaScript::Duktape;
##create new js context
my $js = JavaScript::Duktape->new();
#set function to be used from javascript land
$js->set('write' => sub {
my $duk = shift;
print $_[0], "\n";
});
$js->eval(qq~
(function(){
for (var i = 0; i < 100; i++){
write(i);
}
})();
~);
DESCRIPTION
JavaScript::Duktape implements almost all duktape javascript engine api, the c code is just a thin layer that maps duktape api to perl, and all other functions implemented in perl it self, so maintaing and contributing to the base code should be easy.
methods
- set('name', data);
-
Creates properity 'name' and sets it's value to the given perl data
- get('name');
-
Gets properity 'name' value from javascript and return it as perl data
- eval('javascript');
-
Evaluates javascript string and return the results or croak if error
VM API
vm api corresponds to Duktape Engine API see http://duktape.org/api.html To access vm create new context then call vm
my $js = JavaScript::Duktape->new();
my $duk = $js->vm;
#now you can call Duktape API from perl
$duk->push_string('print');
$duk->eval();
$duk->push_string('hi');
$duk->call(1);
$duk->pop();
Also you may find it useful to use dump
function regularly to get a better idea where you're in the stack, the following code is the same example above but with using dump
function to get a glance of stack top
my $js = JavaScript::Duktape->new();
my $duk = $js->duk;
#push "print" string
$duk->push_string('print');
$duk->dump(); #-> [ Duktape (top=1): print ]
#since print is a native function we need to evaluate it
$duk->eval();
$duk->dump(); #-> [ Duktape (top=1): function print() {/* native */} ]
#push one argument to print function
$duk->push_string('hi');
$duk->dump(); #-> [ Duktape (top=2): function print() {/* native */} hi ]
#now call print function and pass "hi" as one argument
$duk->call(1);
#since print function doesn't return any value, it will push undefined to the stack
$duk->dump(); #-> [ Duktape (top=1): undefined ]
#pop to remove undefined from stack top
$duk->pop();
#Bingo
$duk->dump(); #-> [ Duktape (top=0): ]
VM methods
As a general rule all duktape api supported, but I haven't had the chance to test them all, so please report any missing or failure api call and I'll try to fix
For the list of duktape engine API please see http://duktape.org/api.html, and here is how you can translate duktape api to perl
my $js = JavaScript::Duktape->new();
my $duk = $js->duk;
# -- C example
# duk_push_c_function(func, 2);
# duk_push_int(ctx, 2);
# duk_push_int(ctx, 3);
# duk_call(ctx, 2); /* [ ... func 2 3 ] -> [ 5 ] */
# printf("2+3=%ld\n", (long) duk_get_int(ctx, -1));
# duk_pop(ctx);
#and here is how we can implement it in JavaScript::Duktape
$duk->push_c_function(sub {
my $duk = shift;
my $num1 = shift;
my $num2 = shift;
my $total = $num1+$num2;
$duk->push_number($total);
return 1;
}, 2);
$duk->push_int(2);
$duk->push_int(3);
$duk->call(2); # [ ... func 2 3 ] -> [ 5 ]
printf("2+3=%ld\n", $duk->get_int(-1));
$duk->pop();
As you can see all you need to do is replacing duk_
with $duk-
> and remove ctx
from the function call, this may sounds crazy but api tests have been generated by copying duktape tests and using search and replace tool :)
Besides duktape api, JavaScript::Duktape::Vm
implements the following methods
- push_function ( code_ref, num_of_args );
-
an alias to push_c_function
- push_perl( ... );
-
Push given perl data into the duktape stack.
- to_perl(index);
-
Get the value at index and return it as perl data
- reset_top
-
resets duktape stack top
AUTHOR
Mamod Mehyar <mamod.mehyar@gmail.com>
LICENSE
This library is free software; you can redistribute it and/or modify it under the same terms as Perl itself.