diff --git a/src/scripting/smjs/Makefile b/src/scripting/smjs/Makefile index 1689f4789..4e8d5705f 100644 --- a/src/scripting/smjs/Makefile +++ b/src/scripting/smjs/Makefile @@ -4,6 +4,6 @@ include $(top_builddir)/Makefile.config INCLUDES += $(SPIDERMONKEY_CFLAGS) OBJS = smjs.o core.o global_object.o hooks.o elinks_object.o cache_object.o \ - view_state_object.o bookmarks.o keybinding.o + view_state_object.o bookmarks.o keybinding.o load_uri.o include $(top_srcdir)/Makefile.lib diff --git a/src/scripting/smjs/elinks_object.c b/src/scripting/smjs/elinks_object.c index c0ecb6b9b..b3ec84d98 100644 --- a/src/scripting/smjs/elinks_object.c +++ b/src/scripting/smjs/elinks_object.c @@ -17,6 +17,7 @@ #include "scripting/smjs/elinks_object.h" #include "scripting/smjs/global_object.h" #include "scripting/smjs/keybinding.h" +#include "scripting/smjs/load_uri.h" #include "session/location.h" #include "session/session.h" #include "session/task.h" @@ -130,6 +131,7 @@ smjs_init_elinks_object(void) smjs_init_bookmarks_interface(); smjs_init_keybinding_interface(); + smjs_init_load_uri_interface(); } /* If elinks. is defined, call it with the given arguments, diff --git a/src/scripting/smjs/load_uri.c b/src/scripting/smjs/load_uri.c new file mode 100644 index 000000000..a74f80b50 --- /dev/null +++ b/src/scripting/smjs/load_uri.c @@ -0,0 +1,105 @@ +/* ECMAScript browser scripting module */ + +#ifdef HAVE_CONFIG_H +#include "config.h" +#endif + +#include "elinks.h" + +#include "ecmascript/spidermonkey/util.h" +#include "network/connection.h" +#include "protocol/uri.h" +#include "scripting/smjs/core.h" +#include "scripting/smjs/cache_object.h" +#include "scripting/smjs/elinks_object.h" +#include "session/download.h" + + +struct smjs_load_uri_hop { + struct session *ses; + JSFunction *callback; +}; + +static void +smjs_loading_callback(struct download *download, void *data) +{ + struct session *saved_smjs_ses = smjs_ses; + struct smjs_load_uri_hop *hop = data; + jsval args[1], rval; + JSObject *cache_entry_object; + + if (is_in_progress_state(download->state)) return; + + if (!download->cached) goto end; + + assert(hop->callback); + + smjs_ses = hop->ses; + + cache_entry_object = smjs_get_cache_entry_object(download->cached); + if (!cache_entry_object) goto end; + + args[0] = OBJECT_TO_JSVAL(cache_entry_object); + + JS_CallFunction(smjs_ctx, NULL, hop->callback, 1, args, &rval); + +end: + mem_free(download->data); + mem_free(download); + + smjs_ses = saved_smjs_ses; +} + +static JSBool +smjs_load_uri(JSContext *ctx, JSObject *obj, uintN argc, jsval *argv, + jsval *rval) +{ + struct smjs_load_uri_hop *hop; + struct download *download; + JSString *jsstr; + unsigned char *uri_string; + struct uri *uri; + + if (argc < 2) return JS_FALSE; + + jsstr = JS_ValueToString(smjs_ctx, argv[0]); + uri_string = JS_GetStringBytes(jsstr); + + uri = get_uri(uri_string, 0); + if (!uri) return JS_FALSE; + + download = mem_alloc(sizeof(*download)); + if (!download) { + done_uri(uri); + return JS_FALSE; + } + + hop = mem_alloc(sizeof(*hop)); + if (!hop) { + done_uri(uri); + mem_free(download); + return JS_FALSE; + } + + hop->callback = JS_ValueToFunction(smjs_ctx, argv[1]); + hop->ses = smjs_ses; + + download->data = hop; + download->callback = (download_callback_T *) smjs_loading_callback; + + load_uri(uri, NULL, download, PRI_MAIN, CACHE_MODE_NORMAL, -1); + + done_uri(uri); + + return JS_TRUE; +} + +void +smjs_init_load_uri_interface(void) +{ + if (!smjs_ctx || !smjs_elinks_object) + return; + + JS_DefineFunction(smjs_ctx, smjs_elinks_object, "load_uri", + &smjs_load_uri, 2, 0); +} diff --git a/src/scripting/smjs/load_uri.h b/src/scripting/smjs/load_uri.h new file mode 100644 index 000000000..a62d33599 --- /dev/null +++ b/src/scripting/smjs/load_uri.h @@ -0,0 +1,6 @@ +#ifndef EL__SCRIPTING_SMJS_LOAD_URI_H +#define EL__SCRIPTING_SMJS_LOAD_URI_H + +void smjs_init_load_uri_interface(void); + +#endif