I need to access SecureRandom Java Object from Javascript. My ultimate goal is to grab 4 bytes from PRNG and convert it to Javascript integer variable. According to http://download.oracle.com/javase/1.4.2/docs/api/java/security/SecureRandom.html, the following two lines of Java code are supposed to do grab 4 random bytes:
byte bytes[] = new byte[4];
random.nextBytes(bytes);
My problems is that I don't know how to
1) allocate byte array suitable for passing to Java method
2) parse that array into integer afterwards
So far I have managed to getSeed() method which returns an array of random bytes. When I render HTML code provided below in Firefox it shows "[B#16f70a4", which appears to be a pointer or something.
<script>
var sprng = new java.security.SecureRandom();
random = sprng.getSeed(4);
document.write(random + "<br/>\n");
</script>
This makes me think that I succeed to instantiate and access Java class, but have a problem with type conversion.
Can anyone please help me to write allocateJavaByteArray(N) and convertJavaByteArrayToInt(N) to let the following code work:
var sprng = new java.security.SecureRandom();
var nextBytes = allocateJavaByteArray(4);
srng.nextBytes(nextBytes);
var nextInt = convertJavaByteArrayToInt(4);
Thank you in advance.
You could implement convertJavaByteArrayToInt like this:
function convertJavaByteArrayToInt(bytes) {
var r = 0;
for (var i = 0; i < bytes.length; i++) {
r += (bytes[i] & 0xff) << (8 * i);
}
return r;
}
allocateJavaByteArray is difficult to implement, because we cannot get the Class of byte. So it's not possible to use java.lang.reflect.Array.newInstance to create a byte[] instance. But here is a tricky implementation:
function allocateJavaByteArray(n) {
var r = "";
for (var i = 0; i < n; i++) {
r += "0";
}
return new java.lang.String(r).getBytes();
}
updated: It seems that above code not worked in FireFox 3.6. Here is another allocateJavaByteArray implementation, have a try:
function allocateJavaByteArray(n) {
var r = new java.io.ByteArrayOutputStream(4);
for (var i = 0; i < n; i++) {
r.write(0);
}
return r.toByteArray();
}
Normally you'd generate the random number on the server and pass it in the Request to the jsp.
You could simply generate a random integer in the first place, like this:
var nextInt = sprng.nextInt();
Java string is the only thing that will pass Java->JS or JS->Java without headache.
byte[] or any arry will be seen in JS as JSObject.
var sprng = new java.security.SecureRandom();
is
var foo= new java.package.SomeClass();
does work in Netscape/Mozilla/FF
It needs access to classes, so any java standard class or you need to load a jar and then access the class.
to orginal question:
create applet whith utility method:
public String someStringEncodedValue(){
return 1+"|"+2;
}
include applet into the page with unique id
JS find applet using unique id
call method
parse string ( split by | )
Related
Hi I currently have two arrays full of data sets, I'm trying to compare both by the address column to see if an address matches and if so pass along the data set to a new array to be used somewhere else.
So far I have this and its currently not comparing just passing along the IHMS array.
var rangeMaster = ssMaster.getRange('A2:G2000');
var rangeIhms = ssIhms.getRange('A2:K2000');
Master = rangeMaster.getValues();
IHMS = rangeIhms.getValues();
//Logger.log(Master);
var i = [6];
var j = [1];
for (var i in IHMS) {
var duplicate = false;
for (var j in Master) {
if(IHMS[i].join() == Master[j].join()) {
var matchedValFromArray2 = IHMS[i];
break;
}
}
}
//Logger.log(IHMS);
Logger.log(matchedValFromArray2);
finDes.getRange('A2:X1000').clearContent();
var h = IHMS.length; // get number of rows
var l = IHMS[0].length; // get number of columns
finDes.getRange(finDes.getLastRow() + 1, 1, h, l).setValues(IHMS);
PGSystemTester already provided a very good solution for sheets if that is an option for you, but if you really need script, then check this answer below:
function matchAddress() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var ssMaster = ss.getSheetByName("Master");
var ssIhms = ss.getSheetByName("IHMS");
var finDes = ss.getSheetByName("FinDes");
// Considering sheets' adresses are stored in different columns
// (1-indexing sheets vs 0-indexing arrays, so subtract 1)
var masterAddressCol = 2; // Column C
var ihmsAddressCol = 0; // Column A
// Range is filtered to exclude rows with no address column value
// (assumed empty rows)
var Master = ssMaster.getRange('A2:G2000').getValues().filter(row => row[masterAddressCol]);
var IHMS = ssIhms.getRange('A2:K2000').getValues().filter(row => row[ihmsAddressCol]);
// Get addresses from master sheet
var masterAddresses = Master.map(row => row[masterAddressCol]);
// Filter IHMS by only including rows that have address in master
var matchedValFromArray2 = IHMS.filter(row => masterAddresses.includes(row[ihmsAddressCol]));
finDes.getRange('A2:X1000').clearContent();
var h = matchedValFromArray2.length; // get number of rows
var l = matchedValFromArray2[0].length; // get number of columns
finDes.getRange(finDes.getLastRow() + 1, 1, h, l).setValues(matchedValFromArray2);
}
Master:
IHMS:
FinDes (Output):
Note:
I filtered the range to exclude blank rows (no 1st column value), feel free to remove it if needed.
It's not clear which or how the arrays are supposed to be output, but I am pretty sure you can accomplish what you need without using google app scripts. Basically create a filtered array and use the match function to include values where the addresses match.
You can see a sample in this file.
I used this formula to create the output array:
=Filter(A4:D,ISNUMBER(match(C4:C,H:H,0)))
Here's some sample results:
first we need to have look of how to use for loop.
for example you can consider.
var h={'hello','hi'};
for(int i=0;i<h.length;i++)
h[i];
if i=0 h[i] is hello
i=1 h[i] is hi
var h={'hello','hi'};
for(var j in h)
for first iteration value of i is hello so h[hello] may be undefined.
and you have defined var i,j in both local for loop scope and class level scope so by default it will take local for loop variable.
I'm trying to launch trained in Keras Tensorflow graph by means of Java Tensorflow API.
Aside from standard input image placeholder, this graph contains 'keras_learning_phase' placeholder that is needed to be fed with a boolean value.
The thing is, there is no method in TensorFlowInferenceInterface for boolean values - you can only feed it with float, double, int or byte values.
Obviously, when I try to pass int to this tensor by means of this code:
inferenceInterface.fillNodeInt("keras_learning_phase",
new int[]{1}, new int[]{0});
I get
tensorflow_inference_jni.cc:207 Error during inference: Internal:
Output 0 of type int32 does not match declared output type bool for
node _recv_keras_learning_phase_0 = _Recvclient_terminated=true,
recv_device="/job:localhost/replica:0/task:0/cpu:0",
send_device="/job:localhost/replica:0/task:0/cpu:0",
send_device_incarnation=4742451733276497694,
tensor_name="keras_learning_phase", tensor_type=DT_BOOL,
_device="/job:localhost/replica:0/task:0/cpu:0"
Is there a way to circumvent it?
Maybe it is possible somehow to explicitly convert Placeholder node in graph to Constant?
Or maybe it is possible to initially avoid creation of this Placeholder in the graph?
The TensorFlowInferenceInterface class essentially is a convenience wrapper over the full TensorFlow Java API, which does support boolean values.
You could perhaps add a method to TensorFlowInferenceInterface to do what you want. Similar to fillNodeInt, you could add the following (note the caveat that booleans in TensorFlow are represented as one byte):
public void fillNodeBool(String inputName, int[] dims, bool[] src) {
byte[] b = new byte[src.length];
for (int i = 0; i < src.length; ++i) {
b[i] = src[i] ? 1 : 0;
}
addFeed(inputName, Tensor.create(DatType.BOOL, mkDims(dims), ByteBuffer.wrap(b)));
}
Hope that helps. If it works, I'd encourage you to contribute back to the TensorFlow codebase.
This is in addition to the answer by ash, as the Tensorflow API has changed a little. Using this worked for me:
public void feed(String inputName, boolean[] src, long... dims) {
byte[] b = new byte[src.length];
for (int i = 0; i < src.length; i++) {
b[i] = src[i] ? (byte) 1 : (byte) 0;
}
addFeed(inputName, Tensor.create(Boolean.class, dims, ByteBuffer.wrap(b)));
}
I please bear with me, I have been using Java for 2 days and i've hit a bit of a hurdle.
I am using Talend to perform a count using the tMemorize and tJava components but this may be a question for a Java developer. I have previously posted an issue with using this method within a joblet by my new issue is more Java related which can be viewed here:
using Joblets in talend with tMemorize and tJavaFlex
I need to reference an array generated by the java code talend. I cannot reference this element directly because of an issue with using tJavaFlex within multiple joblets: Java renames joblets each time they are used.
It may be useful to understand how my code works in normal circumstances (excluding the use of joblets).
int counter = 1;
if (EnquiryID_mem_1_tMemorizeRows_1[0].equals(EnquiryID_mem_1_tMemorizeRows_1[1]))
{
counter++;
}
row3.counter = counter;
The EnquiryID_mem_1_tMemorizeRows_1[0] and EnquiryID_mem_1_tMemorizeRows_1[1] is what I need to reference.
To overcome this I have written the following code.
String string = currentComponent;
String[] parts = string.split("_");
String part1 = parts[0];
String part2 = parts[1];
String joblet = part1+'_'+part2;
String newrow = "EnquiryID_"+joblet+"_tMemorizeRows_1"
if (newrow[0].equals(newrow[1]))
{
counter++;
}
row3.counter = counter;
However I get the following error:
The type of the expression must be an array type but it resolved to String
I understand that the newrow variable is a string and I am using it to reference an array. I have searched far and wide online for a resolve but I cannot fine one. Can someone help me please?
Thank you
Here is the talend code that my code should reference. I have taken it from the currentComponent that I am using to when it changes to one not in use directly.
currentComponent = "mem_1_tMemorizeRows_1";
// row1
// row1
if (execStat) {
runStat.updateStatOnConnection("row1" + iterateId,
1, 1);
}
for (int i_mem_1_tMemorizeRows_1 = iRows_mem_1_tMemorizeRows_1 - 1; i_mem_1_tMemorizeRows_1 > 0; i_mem_1_tMemorizeRows_1--) {
EnquiryID_mem_1_tMemorizeRows_1[i_mem_1_tMemorizeRows_1] = EnquiryID_mem_1_tMemorizeRows_1[i_mem_1_tMemorizeRows_1 - 1];
}
EnquiryID_mem_1_tMemorizeRows_1[0] = row1.EnquiryID;
mem_1_row2 = row1;
tos_count_mem_1_tMemorizeRows_1++;
/**
* [mem_1_tMemorizeRows_1 main ] stop
*/
/**
* [mem_1_tJavaFlex_1 main ] start
*/
currentComponent = "mem_1_tJavaFlex_1";
// mem_1_row2
// mem_1_row2
if (execStat) {
runStat.updateStatOnConnection("mem_1_row2"
+ iterateId, 1, 1);
}
mem_1_row3.QuoteID = mem_1_row2.QuoteID;
mem_1_row3.EnquiryID = mem_1_row2.EnquiryID;
if (EnquiryID_mem_1_tMemorizeRows_1[0]
.equals(EnquiryID_mem_1_tMemorizeRows_1[1])) {
rower++;
}
mem_1_row3.rower = rower;
tos_count_mem_1_tJavaFlex_1++;
/**
* [mem_1_tJavaFlex_1 main ] stop
*/
/**
* [mem_1_tMap_1 main ] start
*/
currentComponent = "mem_1_tMap_1";
Thank you to everyone who has helped so far.
This
if (newrow[0].equals(newrow[1]))
Tries to pick the first and second element of the array newrow. Unfortunately you declare newrow as
String newrow = "EnquiryID_"+joblet+"_tMemorizeRows_1"
which is not an array but a String. That syntax in the if will not work with a String. I am not sure what you are trying to do but that if check will not work.
EDIT:
If you are trying to pick up char from a string you need to use charAt(index).
If you want to treat newrow as an array you have to declare it as such and pass appropriate elements to it.
EDIT 2: I think you are trying to pass the actual data in joblet to newrow in this:
String newrow = "EnquiryID_"+joblet+"_tMemorizeRows_1"
But what happens here is that everything is concatenated in one String so you need to figure out where the data you are looking for (part[0] and part[1] I assume) is present in that String so you can pull them out (basically what indices contain the values you are looking for).
An example of how newrow will look after that assignment:
"EnquiryID_part1_part2_tMemorizeRows_1"
So "part1" will start at index 10 and will end at index 14. I am just using "part1" here, but it would have whatever value is stored in part1 variable.
If you can show us what you expect it to look like that would help.
I'm not super familiar with talend (understand: not at all). But it sounds like you have some sort of attribute of a generated class (say myGeneratedObject) and you want to access it by name.
In that case, you could do something like:
String newrow = "EnquiryID_"+joblet+"_tMemorizeRows_1"
Field field = myGeneratedObject.getClass().getField(newrow);
if (field.getClass().isArray()) {
if(Array.get(field, 0).equals(Array.get(field, 1)) {
counter++;
}
}
It all depends how you access that field really and where it's declared. But if it's an attribute of an object, then the code above should work, +/- contextual adjustments due to my lack of knowledge of the exact problem.
I'm looking to be able to get the metadata from various mp3s and store them as strings. This is easy with ID3v1 as it's the last 128 bits, but for ID3v2 onwards all of the metadata is stored in variable sized frames, and I'm currently unable to extract this. Any help much appreciated, thanks
Current code is :
Path fromC = Paths.get("C:\\whatever.mp3");
byte[] data = Files.readAllBytes(fromC);
String[] bytesInString = new String[768];
//uses a loop 768 times as its up to 256mb in size, and 3 digit numbers
for (int i = 0; i < (768); i++) {
bytesInString [i] = Character.toString((char) (data[i]));
}
StringBuilder byteResult = new StringBuilder();
for (int i = 0; i < bytesInString .length; i++) {
byteResult.append(title[i]);
}
String allMeta= byteResult.toString();
System.out.println(allMeta);
which is to simply save the metadata as a string for use elsewhere, but currently prints it out to just check it.
This however gives results such as 'ID3 OTRCK 2TALB FeelTIT2 Here We GoPRIV ) WM/MediaClassSecondaryID PRIV 'WM/MediaClassPrimaryID # ̄¬KニᄀHᄂ PRIV ' - which shows that it is semi-able to get the metadata, but is currently unable to make it easy to read/useful. Could anyone explain or give any sample code as to how to make it more legible and with just the title, artist, etc, rather than the frame information.
I have the following function:
strNameValue = prefs.getString("NamePosition", "");
inNameValueConversion = Integer.parseInt(strNameValue);
if (inNameValueConversion == 0) {
DisplayInformation(inNameValueConversion, R.raw.audio01);
}
if (inNameValueConversion == 1) {
DisplayInformation(inNameValueConversion, R.raw.audio02);
}
if (inNameValueConversion == 2) {
DisplayInformation(inNameValueConversion, R.raw.audio03);
}
if (inNameValueConversion == 3) {
DisplayInformation(inNameValueConversion, R.raw.audio04);
}
Because all the audio file starts with audio and only the number changes at the end I wanted to create a function which allows me to use less code like this:
public void DisplayInformation(int inNum, final int inSoundResource) {
if (inSoundResource < 2) {
strIConv = String.valueOf("0" + inSoundResource);
inConv = Integer.parseInt(strIConv);
int k = R.raw.audio+"inConv";
}
}
I get the following error: audio cannot be resolved or is not a field
How do I edit the above code so I can just use one function instead of using so many IF statement, since it will be 90+ times.
You can use getIdentifier(), so your code would look like this:
public void displayInformation(int inNum) {
String id = "audio";
// for inNum < 9, we need to add 0, so for example when you pass 0
// id will be 01, not 1
if (inNum < 9) then id += "0";
//based on your code, 0 - audio01, 1 - audio02 etc, so add 1
id += (inNum + 1);
// call getIdentifier with string containing resource name, which are in your raw folder
// and in your package
int k = getResources().getIdentifier(id, "raw", "your.package.name.here");
//k now contains an id of your resource, so do whatever you want with it
}
and your code can then be reduced to this:
strNameValue = prefs.getString("NamePosition", "");
inNameValueConversion = Integer.parseInt(strNameValue);
displayInformation(inNameValueConversion);
Remember to use your package name in the call to getIdentifier().
Docs are here: http://developer.android.com/reference/android/content/res/Resources.html#getIdentifier(java.lang.String, java.lang.String, java.lang.String)
You could try to do it like it is mentioned in this post: https://stackoverflow.com/a/5626631/3178834
In your case, you have to create an array for all audio files as resources xml and then load it with res.getXml into java. Just follow the link from above.
Building R values that way won't work -- you'll need to use reflection instead.
For example:
import java.lang.reflect.Field;
/* ... */
int id = R.id.class.getField("video" + i).getInt(0);