Skip to content

Commit

Permalink
Add Java JNI bindings
Browse files Browse the repository at this point in the history
Reviewed By: mhorowitz

Differential Revision: D4021520

fbshipit-source-id: dbaf2ebb7fa48f4efe6cf47a97c39bb079dda8d0
  • Loading branch information
lexs authored and Facebook Github Bot committed Nov 2, 2016
1 parent fbc8410 commit 788e277
Show file tree
Hide file tree
Showing 5 changed files with 241 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
// Copyright 2004-present Facebook. All Rights Reserved.

package com.facebook.react.bridge;

import java.util.Arrays;
import java.util.List;

import com.facebook.jni.HybridData;
import com.facebook.proguard.annotations.DoNotStrip;

@DoNotStrip
public class Inspector {
static {
ReactBridge.staticInit();
}

private final HybridData mHybridData;

public static List<Page> getPages() {
return Arrays.asList(instance().getPagesNative());
}

public static LocalConnection connect(int pageId, RemoteConnection remote) {
return instance().connectNative(pageId, remote);
}

private static native Inspector instance();

private native Page[] getPagesNative();

private native LocalConnection connectNative(int pageId, RemoteConnection remote);

private Inspector(HybridData hybridData) {
mHybridData = hybridData;
}

@DoNotStrip
public static class Page {
private final int mId;
private final String mTitle;

public int getId() {
return mId;
}

public String getTitle() {
return mTitle;
}

@Override
public String toString() {
return "Page{" +
"mId=" + mId +
", mTitle='" + mTitle + '\'' +
'}';
}

private Page(int id, String title) {
mId = id;
mTitle = title;
}
}

@DoNotStrip
public interface RemoteConnection {
void onMessage(String message);
void onDisconnect();
}

@DoNotStrip
public static class LocalConnection {
private final HybridData mHybridData;

public native void sendMessage(String message);
public native void disconnect();

private LocalConnection(HybridData hybridData) {
mHybridData = hybridData;
}
}
}
2 changes: 2 additions & 0 deletions ReactAndroid/src/main/jni/xreact/jni/BUCK
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ cxx_library(
'//xplat/fbsystrace:fbsystrace',
react_native_xplat_target('cxxreact:bridge'),
react_native_xplat_target('cxxreact:module'),
react_native_xplat_target('inspector:inspector'),
],
srcs = glob(['*.cpp']),
xcode_public_headers_symlinks = True,
Expand All @@ -35,6 +36,7 @@ cxx_library(
preprocessor_flags = [
'-DLOG_TAG="ReactNativeJNI"',
'-DWITH_FBSYSTRACE=1',
'-DWITH_INSPECTOR=1',
],
compiler_flags = [
'-Wall',
Expand Down
90 changes: 90 additions & 0 deletions ReactAndroid/src/main/jni/xreact/jni/JInspector.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
// Copyright 2004-present Facebook. All Rights Reserved.

#include "JInspector.h"

namespace facebook {
namespace react {

namespace {

class RemoteConnection : public Inspector::RemoteConnection {
public:
RemoteConnection(jni::alias_ref<JRemoteConnection::javaobject> connection)
: connection_(jni::make_global(connection)) {}

void onMessage(std::string message) override {
connection_->onMessage(message);
}

void onDisconnect() override {
connection_->onDisconnect();
}
private:
jni::global_ref<JRemoteConnection::javaobject> connection_;
};

}

jni::local_ref<JPage::javaobject> JPage::create(int id, const std::string& title) {
static auto constructor = javaClassStatic()->getConstructor<JPage::javaobject(jint, jni::local_ref<jni::JString>)>();
return javaClassStatic()->newObject(constructor, id, jni::make_jstring(title));
}

void JRemoteConnection::onMessage(const std::string& message) const {
static auto method = javaClassStatic()->getMethod<void(jni::local_ref<jstring>)>("onMessage");
method(self(), jni::make_jstring(message));
}

void JRemoteConnection::onDisconnect() const {
static auto method = javaClassStatic()->getMethod<void()>("onDisconnect");
method(self());
}

JLocalConnection::JLocalConnection(std::unique_ptr<Inspector::LocalConnection> connection)
: connection_(std::move(connection)) {}

void JLocalConnection::sendMessage(std::string message) {
connection_->sendMessage(std::move(message));
}

void JLocalConnection::disconnect() {
connection_->disconnect();
}

void JLocalConnection::registerNatives() {
javaClassStatic()->registerNatives({
makeNativeMethod("sendMessage", JLocalConnection::sendMessage),
makeNativeMethod("disconnect", JLocalConnection::disconnect),
});
}

jni::global_ref<JInspector::javaobject> JInspector::instance(jni::alias_ref<jclass>) {
static auto instance = jni::make_global(newObjectCxxArgs(&Inspector::instance()));
return instance;
}

jni::local_ref<jni::JArrayClass<JPage::javaobject>> JInspector::getPages() {
std::vector<Inspector::Page> pages = inspector_->getPages();
auto array = jni::JArrayClass<JPage::javaobject>::newArray(pages.size());
for (size_t i = 0; i < pages.size(); i++) {
(*array)[i] = JPage::create(pages[i].id, pages[i].title);
}
return array;
}

jni::local_ref<JLocalConnection::javaobject> JInspector::connect(int pageId, jni::alias_ref<JRemoteConnection::javaobject> remote) {
auto localConnection = inspector_->connect(pageId, folly::make_unique<RemoteConnection>(std::move(remote)));
return JLocalConnection::newObjectCxxArgs(std::move(localConnection));
}

void JInspector::registerNatives() {
JLocalConnection::registerNatives();
javaClassStatic()->registerNatives({
makeNativeMethod("instance", JInspector::instance),
makeNativeMethod("getPagesNative", JInspector::getPages),
makeNativeMethod("connectNative", JInspector::connect),
});
}

}
}
61 changes: 61 additions & 0 deletions ReactAndroid/src/main/jni/xreact/jni/JInspector.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
// Copyright 2004-present Facebook. All Rights Reserved.

#pragma once

#include <inspector/Inspector.h>

#include <fb/fbjni.h>
#include <folly/Memory.h>

namespace facebook {
namespace react {

class JPage : public jni::JavaClass<JPage> {
public:
static constexpr auto kJavaDescriptor = "Lcom/facebook/react/bridge/Inspector$Page;";

static jni::local_ref<JPage::javaobject> create(int id, const std::string& title);
};

class JRemoteConnection : public jni::JavaClass<JRemoteConnection> {
public:
static constexpr auto kJavaDescriptor = "Lcom/facebook/react/bridge/Inspector$RemoteConnection;";

void onMessage(const std::string& message) const;
void onDisconnect() const;
};

class JLocalConnection : public jni::HybridClass<JLocalConnection> {
public:
static constexpr auto kJavaDescriptor = "Lcom/facebook/react/bridge/Inspector$LocalConnection;";

JLocalConnection(std::unique_ptr<Inspector::LocalConnection> connection);

void sendMessage(std::string message);
void disconnect();

static void registerNatives();
private:
std::unique_ptr<Inspector::LocalConnection> connection_;
};

class JInspector : public jni::HybridClass<JInspector> {
public:
static constexpr auto kJavaDescriptor = "Lcom/facebook/react/bridge/Inspector;";

static jni::global_ref<JInspector::javaobject> instance(jni::alias_ref<jclass>);

jni::local_ref<jni::JArrayClass<JPage::javaobject>> getPages();
jni::local_ref<JLocalConnection::javaobject> connect(int pageId, jni::alias_ref<JRemoteConnection::javaobject> remote);

static void registerNatives();
private:
friend HybridBase;

JInspector(Inspector* inspector) : inspector_(inspector) {}

Inspector* inspector_;
};

}
}
7 changes: 7 additions & 0 deletions ReactAndroid/src/main/jni/xreact/jni/OnLoad.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,10 @@
#include "WebWorkers.h"
#include "JCallback.h"

#ifdef WITH_INSPECTOR
#include "JInspector.h"
#endif

#include "WritableNativeMap.h"
#include "WritableNativeArray.h"

Expand Down Expand Up @@ -181,6 +185,9 @@ extern "C" JNIEXPORT jint JNI_OnLoad(JavaVM* vm, void* reserved) {
ModuleRegistryHolder::registerNatives();
CxxModuleWrapper::registerNatives();
JCallbackImpl::registerNatives();
#ifdef WITH_INSPECTOR
JInspector::registerNatives();
#endif
registerJSLoaderNatives();

NativeArray::registerNatives();
Expand Down

0 comments on commit 788e277

Please sign in to comment.