aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/library_browser.js50
-rw-r--r--system/include/emscripten/emscripten.h2
-rw-r--r--tests/http.cpp284
-rw-r--r--tests/http.h151
4 files changed, 487 insertions, 0 deletions
diff --git a/src/library_browser.js b/src/library_browser.js
index 00ee158c..c18edf4a 100644
--- a/src/library_browser.js
+++ b/src/library_browser.js
@@ -385,6 +385,56 @@ mergeInto(LibraryManager.library, {
);
},
+ emscripten_async_wget2: function(url, file, request, param, arg, onload, onerror, onprogress) {
+ var _url = Pointer_stringify(url);
+ var _file = Pointer_stringify(file);
+ var _request = Pointer_stringify(request);
+ var _param = Pointer_stringify(param);
+ var index = _file.lastIndexOf('/');
+
+ var http = new XMLHttpRequest();
+ http.open(_request, _url, true);
+ http.responseType = 'arraybuffer';
+
+ // LOAD
+ http.onload = function(e) {
+ if (http.status == 200) {
+ FS.createDataFile( _file.substr(0, index), _file.substr(index +1), new Uint8Array(http.response), true, true);
+ if (onload) FUNCTION_TABLE[onload](arg,file);
+ } else {
+ if (onerror) FUNCTION_TABLE[onerror](arg,http.status);
+ }
+ };
+
+ // ERROR
+ http.onerror = function(e) {
+ if (onerror) FUNCTION_TABLE[onerror](arg,http.status);
+ };
+
+ // PROGRESS
+ http.onprogress = function(e) {
+ var percentComplete = (e.position / e.totalSize)*100;
+ if (onprogress) FUNCTION_TABLE[onprogress](arg,percentComplete);
+ };
+
+ try {
+ if (http.channel instanceof Ci.nsIHttpChannel)
+ http.channel.redirectionLimit = 0;
+ } catch (ex) { /* whatever */ }
+
+ if (_request == "POST") {
+ //Send the proper header information along with the request
+ http.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
+ http.setRequestHeader("Content-length", _param.length);
+ http.setRequestHeader("Connection", "close");
+
+ http.send(_param);
+ } else {
+ http.send(null);
+ }
+
+ },
+
emscripten_async_prepare: function(file, onload, onerror) {
var _file = Pointer_stringify(file);
var data = FS.analyzePath(_file);
diff --git a/system/include/emscripten/emscripten.h b/system/include/emscripten/emscripten.h
index 3eefe0b8..fb63384b 100644
--- a/system/include/emscripten/emscripten.h
+++ b/system/include/emscripten/emscripten.h
@@ -186,6 +186,8 @@ float emscripten_random();
*/
void emscripten_async_wget(const char* url, const char* file, void (*onload)(const char*), void (*onerror)(const char*));
+void emscripten_async_wget2(const char* url, const char* file, const char* requesttype, const char* param, void *arg, void (*onload)(void*, const char*), void (*onerror)(void*, int), void (*onprogress)(void*, int));
+
/*
* Prepare a file in asynchronous way. This does just the
* preparation part of emscripten_async_wget, that is, it
diff --git a/tests/http.cpp b/tests/http.cpp
new file mode 100644
index 00000000..623709bf
--- /dev/null
+++ b/tests/http.cpp
@@ -0,0 +1,284 @@
+//
+// http.cpp
+// Player Javascript
+//
+// Created by Anthony Liot on 23/11/12.
+//
+
+#include "http.h"
+#include <emscripten/emscripten.h>
+#include <stdio.h>
+#include <stdlib.h>
+
+int http::uid = 0;
+
+/*
+- Useful for download an url on other domain
+<?php
+header("Access-Control-Allow-Origin: *");
+// verifie si on a les bons parametres
+if( isset($_GET['url']) ) {
+
+ $fileName = $_GET['url'];
+ if($f = fopen($fileName,'rb') ){
+ $fSize = 0;
+ while(!feof($f)){
+ ++$fSize;
+ $data = fread($f,1);
+ }
+ fclose($f);
+ if( $fSize < 1 ) {
+ header($_SERVER['SERVER_PROTOCOL'] . ' 404 Not Found');
+ echo 'For empty file ' . $fileName;
+ die();
+ } else {
+ header("POST ".$fileName." HTTP/1.1\r\n");
+ header('Content-Description: File Transfer');
+ header('Content-Transfer-Encoding: binary');
+ header('Content-Disposition: attachment; filename="' . basename($fileName) . "\";");
+ header('Content-Type: application/octet-stream');
+ header('Content-Length: '.$fSize);
+
+ header('Expires: 0');
+ header('Cache-Control: must-revalidate');
+ header('Pragma: public');
+ ob_clean();
+ flush();
+ readfile($fileName);
+ exit;
+ }
+ } else {
+ header($_SERVER['SERVER_PROTOCOL'] . ' 404 Not Found');
+ echo 'For filename ' . $fileName;
+ }
+} else {
+ header($_SERVER['SERVER_PROTOCOL'] . ' 403 Forbidden');
+}
+?>
+*/
+// http://..../download.php?url=
+std::string http::cross_domain = "";
+
+
+//----------------------------------------------------------------------------------------
+// HTTP CLASS
+//----------------------------------------------------------------------------------------
+
+void http::onLoaded(void* parent, const char * file) {
+ http* req = reinterpret_cast<http*>(parent);
+ req->onLoaded(file);
+}
+
+void http::onError(void* parent, int statuserror) {
+ http* req = reinterpret_cast<http*>(parent);
+ req->onError(statuserror);
+}
+
+void http::onProgress(void* parent, int progress) {
+ http* req = reinterpret_cast<http*>(parent);
+ req->onProgress(progress);
+}
+
+/**
+* Constructeur
+*/
+http::http(const char* hostname, int requestType, const char* targetFilename) : _hostname(hostname), _page(""), _targetFileName(targetFilename), _param(""), _content(""), _error(""), _request((RequestType)requestType), _status(ST_PENDING), _assync(ASSYNC_THREAD) {
+ _progressValue = -1;
+ _uid = uid++;
+}
+
+
+/**
+* Destructeur
+*/
+http::~http() {
+}
+
+/**
+* Effectue la requete
+*/
+void http::runRequest(const char* page, int assync) {
+ _page = page;
+ _status = ST_PENDING;
+ _assync = (AssyncMode)assync;
+ _progressValue = 0;
+
+ std::string url = cross_domain;
+ url += _hostname + _page;
+
+ if (_hostname.size() > 0 && _page.size() > 0) {
+
+ printf("URL : %s\n",url.c_str());
+ printf("REQUEST : %s\n",(_request==REQUEST_GET) ? "GET":"POST");
+ printf("PARAMS : %s\n",_param.c_str());
+
+ if (_targetFileName.size() == 0 ) {
+ _targetFileName = format("prepare%d",_uid);
+ }
+
+ emscripten_async_wget2(url.c_str(), _targetFileName.c_str(), (_request==REQUEST_GET) ? "GET":"POST", _param.c_str(), this, http::onLoaded, http::onError, http::onProgress);
+
+ } else {
+ _error = format("malformed url : %s\n",url.c_str());
+ _content = "";
+ _status = ST_FAILED;
+ _progressValue = -1;
+ }
+}
+
+/**
+* Accede a la reponse
+*/
+const char* http::getContent() {
+ return _content.c_str();
+}
+
+/**
+* Accede a l'erreur
+*/
+const char* http::getError() {
+ return _error.c_str();
+}
+
+/**
+* Accede au status
+*/
+int http::getStatus() {
+ return _status;
+}
+
+/**
+* Accede a la progression between 0 & 100
+*/
+float http::getProgress() {
+ return (float)_progressValue;
+}
+
+/**
+* Accede a la progression between 0 & 100
+*/
+int http::getId() {
+ return _uid;
+}
+
+/**
+* Post
+*/
+void http::addValue(const char* key, const char* value) {
+ if (_param.size() > 0) {
+ _param += "&";
+ _param += key;
+ _param += "=";
+ _param += value;
+ } else {
+ _param += key;
+ _param += "=";
+ _param += value;
+ }
+}
+
+void http::onProgress(int progress) {
+ _progressValue = progress;
+}
+
+void http::onLoaded(const char* file) {
+
+ if (strstr(file,"prepare")) {
+ FILE* f = fopen(file,"rb");
+ if (f) {
+ fseek (f, 0, SEEK_END);
+ int size=ftell (f);
+ fseek (f, 0, SEEK_SET);
+
+ char* data = new char[size];
+ fread(data,size,1,f);
+ _content = data;
+ delete data;
+ fclose(f);
+ } else {
+ _content = file;
+ }
+
+ } else {
+ _content = file;
+ }
+
+ _progressValue = 100;
+ _status = ST_OK;
+}
+
+void http::onError(int error) {
+
+ printf("Error status : %d\n",error);
+
+ _error = "";
+ _content = "";
+ _status = ST_FAILED;
+ _progressValue = -1;
+}
+
+/// TEST
+int num_request = 0;
+float time_elapsed = 0.0f;
+
+void wait_https() {
+ if (num_request == 0) {
+ printf("End of all download ... %fs\n",(emscripten_get_now() - time_elapsed) / 1000.f);
+ emscripten_cancel_main_loop();
+ }
+}
+
+void wait_http(void* request) {
+ http* req = reinterpret_cast<http*>(request);
+ if (req != 0) {
+ if (req->getStatus() == http::ST_PENDING) {
+ if ((int)req->getProgress()>0) {
+ printf("Progress Request n°%d : %d\n",req->getId(),(int)req->getProgress());
+ }
+ emscripten_async_call(wait_http,request,500);
+
+ } else {
+ if (req->getStatus() == http::ST_OK) {
+ printf("Success Request n°%d : %s\n",req->getId(),req->getContent());
+
+ } else {
+ printf("Error Request n°%d : %s\n",req->getId(), req->getError());
+ }
+
+ num_request --;
+ }
+ } else {
+ num_request --;
+ }
+}
+
+
+int main() {
+ time_elapsed = emscripten_get_now();
+
+ http* http1 = new http("https://github.com",http::REQUEST_GET,"emscripten_master.zip");
+ http1->runRequest("/kripken/emscripten/archive/master.zip",http::ASSYNC_THREAD);
+
+ http* http2 = new http("https://github.com",http::REQUEST_GET,"wolfviking_master.zip");
+ http2->runRequest("/wolfviking0/image.js/archive/master.zip",http::ASSYNC_THREAD);
+
+ http* http3 = new http("https://raw.github.com",http::REQUEST_GET);
+ http3->runRequest("/kripken/emscripten/master/LICENSE",http::ASSYNC_THREAD);
+
+ num_request ++;
+ emscripten_async_call(wait_http,http1,500);
+ num_request ++;
+ emscripten_async_call(wait_http,http2,500);
+ num_request ++;
+ emscripten_async_call(wait_http,http3,500);
+
+ /*
+ Http* http4 = new Http("http://www.---.com",Http::REQUEST_POST);
+ http4->addValue("app","123");
+ http4->runRequest("/test.php",Http::ASSYNC_THREAD);
+ num_request ++;
+ emscripten_async_call(wait_http,http4,500);
+ */
+
+ emscripten_set_main_loop(wait_https, 0, 0);
+} \ No newline at end of file
diff --git a/tests/http.h b/tests/http.h
new file mode 100644
index 00000000..7eff7013
--- /dev/null
+++ b/tests/http.h
@@ -0,0 +1,151 @@
+//
+// Http.h
+// Player Javascript
+//
+// Created by Anthony Liot on 23/11/12.
+//
+
+#ifndef __HTTP_H__
+#define __HTTP_H__
+
+#include <string>
+
+
+/*
+ */
+class http {
+
+ public:
+
+ enum Status {
+ ST_PENDING = 0,
+ ST_FAILED,
+ ST_OK
+ };
+
+ enum RequestType {
+ REQUEST_GET = 0,
+ REQUEST_POST ,
+ };
+
+ enum AssyncMode {
+ ASSYNC_THREAD
+ };
+
+ // enregistrement sur unigine
+ static void RegisterAsExtension(bool regis);
+
+ // Callback
+ static void onLoaded(void* parent, const char * file);
+ static void onError(void* parent, int statuserror);
+ static void onProgress(void* parent, int progress);
+
+ // Constructeur
+ http(const char* hostname, int requestType, const char* targetFileName = "");
+
+ //Destructeur
+ virtual ~http();
+
+ /**
+ * Effectue la requete
+ */
+ void runRequest(const char* page, int assync);
+
+ /**
+ * Accede a la reponse
+ */
+ const char* getContent();
+
+ /**
+ * Accede a l'erreur
+ */
+ const char* getError();
+
+ /**
+ * Accede au status
+ */
+ int getStatus();
+
+ /**
+ * Accede a la progression
+ */
+ float getProgress();
+
+ /**
+ * Get Id of http Class
+ */
+ int getId();
+
+ /**
+ *
+ */
+ void addValue(const char* key, const char* value);
+
+ /**
+ * Callback
+ */
+ void onProgress(int progress);
+ void onLoaded(const char* file);
+ void onError(int error);
+
+ // Static parameter
+ static int uid;
+ static std::string cross_domain ;
+
+ private:
+
+ // Id of request
+ int _uid;
+
+ // nom de l'hote
+ std::string _hostname;
+
+ // nom de la page
+ std::string _page;
+
+ // target filename
+ std::string _targetFileName;
+
+ // param
+ std::string _param;
+
+ // resultat
+ std::string _content;
+
+ // probleme
+ std::string _error;
+
+ // request type
+ RequestType _request;
+
+ // status
+ int _status;
+
+ // progress value
+ int _progressValue;
+
+ // mode assyncrone courant
+ AssyncMode _assync;
+
+};
+
+//this is safe and convenient but not exactly efficient
+inline std::string format(const char* fmt, ...){
+ int size = 512;
+ char* buffer = 0;
+ buffer = new char[size];
+ va_list vl;
+ va_start(vl,fmt);
+ int nsize = vsnprintf(buffer,size,fmt,vl);
+ if(size<=nsize){//fail delete buffer and try again
+ delete buffer; buffer = 0;
+ buffer = new char[nsize+1];//+1 for /0
+ nsize = vsnprintf(buffer,size,fmt,vl);
+ }
+ std::string ret(buffer);
+ va_end(vl);
+ delete buffer;
+ return ret;
+}
+
+#endif /* __HTTP_H__ */