Пример #1
0
v8::Handle<v8::Value> javaToV8(Java* java, JNIEnv* env, jobject obj) {
  v8::HandleScope scope;

  if(obj == NULL) {
    return v8::Null();
  }

  jclass objClazz = env->GetObjectClass(obj);
  jvalueType resultType = javaGetType(env, objClazz);

  //printf("javaToV8: %d %s\n", resultType, javaObjectToString(env, obj).c_str());

  switch(resultType) {
    case TYPE_ARRAY:
      {
        v8::Handle<v8::Value> result = javaArrayToV8(java, env, (jobjectArray)obj);
        return scope.Close(result);
      }
    case TYPE_VOID:
      return v8::Undefined();
    case TYPE_BOOLEAN:
      {
        jclass booleanClazz = env->FindClass("java/lang/Boolean");
        jmethodID boolean_booleanValue = env->GetMethodID(booleanClazz, "booleanValue", "()Z");
        bool result = env->CallBooleanMethod(obj, boolean_booleanValue);
        return scope.Close(v8::Boolean::New(result));
      }
    case TYPE_BYTE:
      {
        jclass byteClazz = env->FindClass("java/lang/Byte");
        jmethodID byte_byteValue = env->GetMethodID(byteClazz, "byteValue", "()B");
        jbyte result = env->CallByteMethod(obj, byte_byteValue);
        return scope.Close(v8::Number::New(result));
      }
    case TYPE_LONG:
      {
        jclass longClazz = env->FindClass("java/lang/Long");
        jmethodID long_longValue = env->GetMethodID(longClazz, "longValue", "()J");
        jlong result = env->CallLongMethod(obj, long_longValue);
        return scope.Close(v8::Number::New(result));
      }
    case TYPE_INT:
      {
        jclass integerClazz = env->FindClass("java/lang/Integer");
        jmethodID integer_intValue = env->GetMethodID(integerClazz, "intValue", "()I");
        jint result = env->CallIntMethod(obj, integer_intValue);
        return scope.Close(v8::Integer::New(result));
      }
    case TYPE_DOUBLE:
      {
        jclass doubleClazz = env->FindClass("java/lang/Double");
        jmethodID double_doubleValue = env->GetMethodID(doubleClazz, "doubleValue", "()D");
        jdouble result = env->CallDoubleMethod(obj, double_doubleValue);
        return scope.Close(v8::Number::New(result));
      }
    case TYPE_STRING:
      return scope.Close(v8::String::New(javaObjectToString(env, obj).c_str()));
    case TYPE_OBJECT:
      return scope.Close(JavaObject::New(java, obj));
    default:
      printf("unhandled type: 0x%03x\n", resultType);
      return scope.Close(JavaObject::New(java, obj));
  }

  return v8::Undefined();
}
Пример #2
0
v8::Handle<v8::Value> javaToV8(Java* java, JNIEnv* env, jobject obj) {
  v8::HandleScope scope;

  if(obj == NULL) {
    return v8::Null();
  }

  jclass objClazz = env->GetObjectClass(obj);
  jvalueType resultType = javaGetType(env, objClazz);

  //printf("javaToV8: %d %s\n", resultType, javaObjectToString(env, obj).c_str());

  switch(resultType) {
    case TYPE_ARRAY:
      {
        v8::Handle<v8::Value> result = javaArrayToV8(java, env, (jobjectArray)obj);
        return scope.Close(result);
      }
    case TYPE_VOID:
      return v8::Undefined();
    case TYPE_BOOLEAN:
      {
        jclass booleanClazz = env->FindClass("java/lang/Boolean");
        jmethodID boolean_booleanValue = env->GetMethodID(booleanClazz, "booleanValue", "()Z");
        bool result = env->CallBooleanMethod(obj, boolean_booleanValue);
        return scope.Close(v8::Boolean::New(result));
      }
    case TYPE_BYTE:
      {
        jclass byteClazz = env->FindClass("java/lang/Byte");
        jmethodID byte_byteValue = env->GetMethodID(byteClazz, "byteValue", "()B");
        jbyte result = env->CallByteMethod(obj, byte_byteValue);
        return scope.Close(v8::Number::New(result));
      }
    case TYPE_LONG:
      {
        jclass longClazz = env->FindClass("java/lang/Long");
        jmethodID long_longValue = env->GetMethodID(longClazz, "longValue", "()J");
        jlong result = env->CallLongMethod(obj, long_longValue);
        std::string strValue = javaObjectToString(env, obj);
        v8::Local<v8::Value> v8Result = v8::NumberObject::New(result);
        v8::NumberObject* v8ResultNumberObject = v8::NumberObject::Cast(*v8Result);
        v8ResultNumberObject->Set(v8::String::New("longValue"), v8::String::New(strValue.c_str()));
        v8ResultNumberObject->SetHiddenValue(v8::String::New(V8_HIDDEN_MARKER_JAVA_LONG), v8::Boolean::New(true));
        return scope.Close(v8Result);
      }
    case TYPE_INT:
      {
        jclass integerClazz = env->FindClass("java/lang/Integer");
        jmethodID integer_intValue = env->GetMethodID(integerClazz, "intValue", "()I");
        jint result = env->CallIntMethod(obj, integer_intValue);
        return scope.Close(v8::Integer::New(result));
      }
    case TYPE_SHORT:
      {
        jclass shortClazz = env->FindClass("java/lang/Short");
        jmethodID short_shortValue = env->GetMethodID(shortClazz, "shortValue", "()S");
        jshort result = env->CallShortMethod(obj, short_shortValue);
        return scope.Close(v8::Integer::New(result));
      }
    case TYPE_DOUBLE:
      {
        jclass doubleClazz = env->FindClass("java/lang/Double");
        jmethodID double_doubleValue = env->GetMethodID(doubleClazz, "doubleValue", "()D");
        jdouble result = env->CallDoubleMethod(obj, double_doubleValue);
        return scope.Close(v8::Number::New(result));
      }
    case TYPE_FLOAT:
      {
        jclass floatClazz = env->FindClass("java/lang/Float");
        jmethodID float_floatValue = env->GetMethodID(floatClazz, "floatValue", "()F");
        jfloat result = env->CallFloatMethod(obj, float_floatValue);
        return scope.Close(v8::Number::New(result));
      }
    case TYPE_STRING:
      return scope.Close(v8::String::New(javaObjectToString(env, obj).c_str()));
    case TYPE_OBJECT:
      return scope.Close(JavaObject::New(java, obj));
    default:
      printf("javaToV8: unhandled type: 0x%03x\n", resultType);
      return scope.Close(JavaObject::New(java, obj));
  }

  return v8::Undefined();
}
Пример #3
0
void EIO_AfterCallJs(uv_work_t* req, int status) {
#else
void EIO_AfterCallJs(uv_work_t* req) {
#endif
  DynamicProxyData* dynamicProxyData = static_cast<DynamicProxyData*>(req->data);
  if(!dynamicProxyDataVerify(dynamicProxyData)) {
    return;
  }
  dynamicProxyData->result = NULL;

  JNIEnv* env;
  int ret = dynamicProxyData->java->getJvm()->GetEnv((void**)&env, JNI_BEST_VERSION);
  if (ret != JNI_OK) {
    dynamicProxyData->throwableClass = "java/lang/IllegalStateException";
    dynamicProxyData->throwableMessage = "Could not retrieve JNIEnv: jvm->GetEnv returned " + to_string<int>(ret);
    dynamicProxyData->done = DYNAMIC_PROXY_JS_ERROR;
    return;
  }

  Nan::HandleScope scope;
  v8::Array* v8Args;
  v8::Function* fn;
  v8::Handle<v8::Value>* argv;
  int argc;
  int i;
  v8::Local<v8::Value> v8Result;
  jobject javaResult;

  v8::Local<v8::Object> dynamicProxyDataFunctions = Nan::New(dynamicProxyData->functions);
  v8::Local<v8::Value> fnObj = dynamicProxyDataFunctions->Get(Nan::New<v8::String>(dynamicProxyData->methodName.c_str()).ToLocalChecked());
  if(fnObj->IsUndefined() || fnObj->IsNull()) {
    dynamicProxyData->throwableClass = "java/lang/NoSuchMethodError";
    dynamicProxyData->throwableMessage = "Could not find js function " + dynamicProxyData->methodName;
    dynamicProxyData->done = DYNAMIC_PROXY_JS_ERROR;
    return;
  }
  if(!fnObj->IsFunction()) {
    dynamicProxyData->throwableClass = "java/lang/IllegalStateException";
    dynamicProxyData->throwableMessage = dynamicProxyData->methodName + " is not a function";
    dynamicProxyData->done = DYNAMIC_PROXY_JS_ERROR;
    return;
  }

  fn = v8::Function::Cast(*fnObj);

  if(dynamicProxyData->args) {
    v8Args = v8::Array::Cast(*javaArrayToV8(dynamicProxyData->java, env, dynamicProxyData->args));
    argc = v8Args->Length();
  } else {
    argc = 0;
  }
  argv = new v8::Handle<v8::Value>[argc];
  for(i=0; i<argc; i++) {
    argv[i] = v8Args->Get(i);
  }

  Nan::TryCatch tryCatch;
  tryCatch.SetCaptureMessage(true);
  v8Result = fn->Call(dynamicProxyDataFunctions, argc, argv);
  delete[] argv;
  if (tryCatch.HasCaught()) {
    dynamicProxyData->throwableClass = "node/NodeJsException";
    v8::String::Utf8Value message(tryCatch.Message()->Get());
    dynamicProxyData->throwableMessage = std::string(*message);
    tryCatch.Reset();
    dynamicProxyData->done = DYNAMIC_PROXY_JS_ERROR;
    return;
  }

  if(!dynamicProxyDataVerify(dynamicProxyData)) {
    return;
  }

  javaResult = v8ToJava(env, v8Result);
  if(javaResult == NULL) {
    dynamicProxyData->result = NULL;
  } else {
    dynamicProxyData->result = env->NewGlobalRef(javaResult);
  }

  dynamicProxyData->done = true;
}