Zgodnie z zaleceniami w dokumencie, przeniosłem jakiś długi kod do pobierania danych do natywnego modułu, aby zwolnić wątek JS, ale zauważam, że to nadal blokuje interfejs użytkownika. Dlaczego tak jest i co mogę zrobić, aby tego uniknąć?Dlaczego to wywołanie reaguje na macierzysty moduł, blokując interfejs użytkownika?
Moduł rodzimy jest wywoływana z JS jak tak:
MyNativeModule.fetch(path).then(data => dispatchData(data))
Sposób rodzimy wygląda następująco (używa Androida Firebase SDK):
@ReactMethod
public void fetch(final String path, final Promise promise) {
root.child(path).addListenerForSingleValueEvent(new ValueEventListener() {
@Override
public void onDataChange(DataSnapshot snapshot) {
if (snapshot.exists()) {
promise.resolve(castSnapshot(snapshot));
} else {
promise.resolve(null);
}
}
@Override
public void onCancelled(FirebaseError firebaseError) {
promise.reject(firebaseError.getMessage());
}
}
}
Sposób castSnapshot
przekształca Firebase DataSnapshot
obiekt do WriteableMap
. Mogę udostępnić implementację, jeśli jest to przydatne.
Zauważyłem, że nawet jeśli zastąpię promise.resolve(castSnapshot(snapshot));
przez castSnapshot(snapshot); promise.resolve(null);
, połączenie blokuje interfejs użytkownika: więc nie wysyła danych przez most, który jest winowajcą. Jeśli ilość danych jest duża, może zająć trochę czasu, a to wyraźnie blokuje.
Nawet jeśli ten kod jest długotrwały, to czy przeniesienie go do natywnego modułu nie powinno go uwolnić? Czego nie rozumiem?
Wielkie dzięki.
mam ten sam problem. Myślałem, że rodzime moduły działają w innym wątku, ale wydaje się, że tak nie jest. –
@RomShiri tak .. myślę, że jeśli chcemy korzystać z natywnych modułów z powodów perf, musimy zarządzać nawlekaniem siebie. Z dokumentacji: "Moduły rodzime nie powinny mieć żadnych założeń dotyczących tego, do jakiego wątku są wywoływane [...] Jeśli wymagane jest wywołanie blokujące, ciężka praca powinna zostać wysłana do wewnętrznie zarządzanego wątku roboczego, a wszelkie wywołania zwrotne od tam." – VonD
Znalazłem to samo. Podejście Ryana było konieczne. – itinance