Last active
September 12, 2019 17:30
-
-
Save 2lazy2debug/789b5c70ae95cacbd27e55b8f6a10735 to your computer and use it in GitHub Desktop.
Use ScriptEngineManager to load JavaScript on Android
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
* Add the following to your build.gradle file : | |
* implementation 'io.apisense:rhino-android:1.0' | |
*/ | |
package vergecurrency.vergewallet.helpers; | |
import android.content.Context; | |
import org.mozilla.javascript.NativeArray; | |
import org.mozilla.javascript.NativeObject; | |
import java.io.InputStream; | |
import javax.script.Invocable; | |
import javax.script.ScriptEngine; | |
import javax.script.ScriptEngineManager; | |
import javax.script.ScriptException; | |
import vergecurrency.vergewallet.Constants; | |
import vergecurrency.vergewallet.helpers.utils.FileUtils; | |
public class SJCL { | |
private ScriptEngine engine; | |
private org.mozilla.javascript.Context jsContext; | |
public SJCL(Context c) { | |
init(c); | |
} | |
public void init(Context c) { | |
ScriptEngineManager manager = new ScriptEngineManager(); | |
engine = manager.getEngineByName("rhino"); | |
try { | |
//this is just my way to access a script, which is SJCL for the purpose | |
InputStream is = c.getAssets().open(Constants.SJCL_FILE_PATH); | |
String sjcl = FileUtils.convertStreamToString(is); | |
// read script file | |
engine.eval(sjcl); | |
} catch (Exception e) { | |
e.printStackTrace(); | |
//don't be like me kids, do proper error management | |
System.err.println("Can't do something.................................................."); | |
} | |
} | |
/** | |
* This method might look confusing. So here a detailed explanation. | |
* The SJCL Library has nested objects, sorry if it's not the correct phrasing, I'm no JS expert. | |
* So, while in JS (and in Swift too) you could call the "toBits" method by just typing "sjcl.codec.base64.toBits", | |
* well, you can't in Java because we are Java devs and don't give a flying fuck about doing things easily (Just Kidding!) | |
* So, we have to use the ScriptEngine to get the SJCL object as a NativeObject, which is basically a key-value pair | |
* that will have as a key the object name and as values the sub-objects/methods. | |
* So I had to cast the returned objects as NativeObjects and retrieve the correct keys according to the file structure. | |
* | |
* The result will come as a native array whereas the 0 index contains the result, which is turned to a String. | |
* | |
* @param encryptingKey the key in a string form | |
* @return the string represantation of a bit array. | |
*/ | |
public String base64ToBits(String encryptingKey) { | |
try { | |
Invocable invocable = (Invocable) engine; | |
Object o = ((NativeObject) ((NativeObject) engine.get("sjcl")).get("codec")).get("base64"); | |
NativeArray o2 = (NativeArray) invocable.invokeMethod(o, "toBits", encryptingKey); | |
String result = o2.get(0).toString(); | |
return result; | |
} catch (ScriptException | NoSuchMethodException e) { | |
e.printStackTrace(); | |
return null; | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment