Closed
Bug 202201
Opened 23 years ago
Closed 23 years ago
java.lang.String insances passed into Rhino have the "replace" function defined, different from NativeString's NativeRegExp
Categories
(Rhino Graveyard :: Core, defect)
Rhino Graveyard
Core
Tracking
(Not tracked)
VERIFIED
INVALID
1.5R5
People
(Reporter: mpg, Assigned: norrisboyd)
Details
User-Agent: Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 4.0)
Build Identifier: Rhino 1.5R4
In JavaScript implementation in IE if you pass a java.lang.String into the
scripting engine you can call "replace(<regexp>, <replaceString>)" on the
string and it is well-defined.
In Rhino 1.5R4 (and previous builds) the native String replace(char, char) will
be invoked, causing a crash. It attempts to convert the arguments to char(s)
which won't work.
org.mozilla.javascript.EvaluatorException: Cannot convert TSY to
java.lang.Character (jxmlbboard0; line 395)
at org.mozilla.javascript.DefaultErrorReporter.runtimeError
(DefaultErrorReporter.java:76)
at org.mozilla.javascript.Context.reportRuntimeError(Context.java:594)
at org.mozilla.javascript.Context.reportRuntimeError(Context.java:632)
at org.mozilla.javascript.Context.reportRuntimeError2(Context.java:614)
at org.mozilla.javascript.NativeJavaObject.reportConversionError
(NativeJavaObject.java:856)
at org.mozilla.javascript.NativeJavaObject.toInteger
(NativeJavaObject.java:830)
at org.mozilla.javascript.NativeJavaObject.coerceToNumber
(NativeJavaObject.java:671)
at org.mozilla.javascript.NativeJavaObject.coerceType
(NativeJavaObject.java:560)
at org.mozilla.javascript.NativeJavaMethod.call
(NativeJavaMethod.java:213)
at org.mozilla.javascript.Interpreter.interpret(Interpreter.java:2181)
at org.mozilla.javascript.Interpreter.interpret(Interpreter.java:2163)
at org.mozilla.javascript.InterpretedFunction.call
(InterpretedFunction.java:58)
Here is the call stack of a "healthy" call to replace defined on JavaScript
Strings (NativeString instances). Notice that the NativeJavaMethod does not
occur in the call stack:
Thread [JSInterpreter Worker:1] (Suspended)
Context.getRegExpProxy() line: 2077
NativeString.checkReProxy(Context) line: 258
NativeString.execMethod(int, IdFunction, Context, Scriptable,
Scriptable, Object[]) line: 244
IdFunction.call(Context, Scriptable, Scriptable, Object[]) line: 78 //
this is good, thinks it's a JavaScript String object
Interpreter.interpret(Context, Scriptable, Scriptable, Object[], double
[], int, int, NativeFunction, InterpreterData) line: 2169
InterpretedFunction.call(Context, Scriptable, Scriptable, Object[])
line: 58
JSInterpreter$4.run() line: 342
Worker.run() line: 221
Thread.run() line: 536 [local variables unavailable]
Reproducible: Always
Steps to Reproduce:
1. Call a javascript method by passing a java.lang.String instance obtained
from the Java VM (any instance of String will do).
2. In the JavaScript method, call replace(/blah/gi, "bluh") on the passed in
argument.
3. Watch the fireworks (detailed above).
Actual Results:
It failed as described above.
Expected Results:
I think that either I need some kind of hook to tell Mozilla to make all
strings into NativeStrings (somehow) or the Interpreter::interpret function
should catch the attempt to invoke replace(NativeRegExp, String) and perform
the NativeString replace function instead (which picks up the regular
expression). We need to be compatible with older versions of java so we can't
use the jdk1.4 and later regular expression aware versions of java.lang.String.
Comment 1•23 years ago
|
||
cc'ing Igor -
Comment 2•23 years ago
|
||
This is a feature, if you want to have the same behavior as MSIE does, in your
application after Context.enter call:
cx.getWrapFactory().setJavaPrimitiveWrap(false);
Status: NEW → RESOLVED
Closed: 23 years ago
Resolution: --- → INVALID
| Reporter | ||
Comment 3•23 years ago
|
||
Thanks, this does work. A couple of comments.
Firstly the comments to the method
org.mozilla.javascript.WrapFactory.isJavaPrimitiveWrap are a bit misleading.
It appears that "wrapping" means "make this object look like a JavaScript
object". In fact "wrapping" means "make this object look like what it is,
namely, a Java primitive instance". In otherwords, you need to "wrap" it to
keep it from appearing differently. In otherwords, in order to have Java
primitive instances appear as javaScript primitive instances (so "replace",
which is defined on java.lang.String, but has different param. types than the
JavaScript String.replace(<regular expression>, <replace expression>)) you need
to NOT wrap it. What you mean is "Set the javaPrimitiveWrap to false so it's
NOT wrapped to be made to appear like a Java primitive type". In other
words, "wrapping" a Java primitive type makes it continue to appear like a java
primitive type. Quite confusing I'd say.
So therefore, the default value should be:
javaPrimitiveWrap = false
But great job, guys! This is a great debugger and scripting engine.
Outstanding.
Comment 4•23 years ago
|
||
Patches for documentation are welcome, but note that in the method JavaDoc
"wrap" means:
put the object inside LiveConnect envelope so JavaScript can access the same
public fields and methods of the objects that a Java code can do.
Correspondingly "do not wrap" means that the object will be replaced by a
JavaScript primitive type.
Note that "wrapping" does not affects methods returning int, float etc. They are
always replaced by JavaScript primitive types. The issue is what to do when a
method returns an instance of String or Number.
You need to log in
before you can comment on or make changes to this bug.
Description
•