React native signed APK crash - react-native

Signed APK crash after launch, in logCat i got requiring unknown module 'React'
Debug application works fine, but in logCat i got >> Requiring module 'React' by name is only supported for debugging purposes and will BREAK IN PRODUCTION!
React v15.4.1, React native v0.39.2 ?
Sorry for my english

this is my index.android.js
import React from 'react';
import {AppRegistry} from 'react-native';
import myapp from './index_start.js';
AppRegistry.registerComponent('myapp', () => myapp);
and index_start.js
import React, { Component } from "react";
import {
StyleSheet,
AppRegistry,
Text,
Image,
View,
AsyncStorage,
NetInfo,
StatusBar,
Navigator,
Dimensions
} from 'react-native';
// Window dismensions
const { width, height } = Dimensions.get('window');
// Device infos
import DeviceInfo from 'react-native-device-info';
// Native SplashScreen
import SplashScreen from 'react-native-splash-screen';
// Spinner
import Spinner from 'react-native-spinkit';
// Models
import User from './model/UserModel';
// Json data for initial launch
var DB = require('./DB.json');
// Components
import Stage from './components/stage/stage.js'
import Player from './components/player/player.js'
import Settings from './components/settings/settings.js'
import House from './stages/house/house.js'
// LocalStorage key
var USER_KEY = 'user_key';
const routes = [
{name: 'loading'},
{name: 'stage', component: Stage},
{name: 'house', component: House},
{name: 'settings', component: Settings}
];
const _navigator = null;
export default class myapp extends Component {
constructor(props) {
super(props);
this.state = {
isConnected: false,
isLoading: true,
_navigator: null,
stages: null
}
}
componentWillMount() {
// check if connected
this._checkConnexionType();
}
componentDidMount() {
SplashScreen.hide();
this._loadInitialData();
}
componentDidUpdate() {
// console.log(this.state.stages)
if (!this.state.isLoading && this.state.stages !== null) {
_navigator.push({
name: 'stage',
passProps: {
data: this.state.stages
}
})
}
}
/**
* Load localStorage Data
*/
async _loadInitialData() {
// GET User LocalStorage
if (this.state.stages == null) {
var localData;
//AsyncStorage.removeItem(USER_KEY)
AsyncStorage.getItem(USER_KEY).then((data) => {
if (data !== null) {
var localData = JSON.parse(data);
// User.uuid = localData.uuid;
User.setStages(localData.stages)
this.setState({
'stages' : localData.stages
})
} else {
var storage = {};
storage.setUiid = DeviceInfo.getUniqueID();
storage.stages = DB.stages;
AsyncStorage.setItem(USER_KEY, JSON.stringify(storage));
this.setState({
'stages' : DB.stages
})
}
})
}
if (this.state.isConnected) {
// var rStages = this._loadRemoteStages();
// console.log(rStages);
}
// Change state
setTimeout((function() {
this.setState({
'isLoading': false
})
}).bind(this), 1500);
}
/**
* GET stages from remote DB
*/
async _loadRemoteStages() {
await fetch(API_URL)
.then((response) => response.json())
.then((responseJson) => {
console.log(responseJson)
return responseJson;
})
.catch((error) => {
console.error(error);
});
}
/**
* CHECK IF user is connected to Network
* SET bool to state isLoading
*/
_checkConnexionType() {
NetInfo.isConnected.fetch().then(response => {
this.setState({ isConnected: response})
})
}
_renderScene(route, navigator) {
_navigator = navigator;
if (route.name == 'loading') {
return (
<View style={styles.container}>
<StatusBar hidden={true} />
<Image
style={{width: width, height: height}}
source={require('./img/screen.jpg')}
/>
<View style={styles.loading}>
<Text style={styles.loadingText}>CHARGEMENT</Text>
<Spinner type="ThreeBounce" color={'#fff'}/>
</View>
</View>
)
} else if (route.name == 'stage') {
return (
<Stage navigator={_navigator} {...route.passProps}/>
)
} else if (route.name == 'player') {
return (
<House navigator={_navigator} {...route.passProps}}/>
)
} else if (route.name == 'settings') {
return (
<Settings navigator={_navigator} {...route.passProps}/>
)
}
}
render() {
return (
<Navigator
initialRoute={{name: 'loading'}}
configureScene={() => Navigator.SceneConfigs.FloatFromBottomAndroid}
renderScene={this._renderScene.bind(this)}
/>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
},
loading: {
flex: 1,
position: 'absolute',
bottom: 50,
left: 0,
right: 0,
alignItems: 'center',
},
loadingText:{
flex: 1,
fontFamily: 'CarterOne',
fontSize: 20,
color: '#fff'
}
});

Related

Apollo cache query fields policy offsetLimitPagination() doesnt work with subscriptions

I use apollo client for react native.
When I use offsetLimitPagination() for pagination my subscriptions doesn't update cache.
Subscriptions works correctly but doesn't update flatlist data.
When i remove offsetLimitPagination function it works. I can't use together subscriptions and offsetLimitPagination function on cache.
Is there any solution for that?`
Thanks.
Cache
const cache = new InMemoryCache({
typePolicies: {
Query: {
fields: {
chatDetail: offsetLimitPagination(),
}
}
},
});
ChatDetailPage
import React, { useState, useCallback } from 'react'
import { StyleSheet, Text, View, FlatList } from 'react-native'
import { ActivityIndicator } from 'react-native-paper';
import { useQuery } from '#apollo/client'
import { useSelector } from 'react-redux'
import { CHAT_DETAIL } from '../../../Graphql/Queries/Message'
import { MESSAGE_SUB } from '../../../Graphql/Subscriptions/Message'
import MainFlow from './Components/Flow/MainFlow'
const ChatDetailMain = () => {
const user = useSelector(state => state.auth.user)
const currentRoom = useSelector(state => state.room.currentRoom)
const [hasNext, setHasNext] = useState(true)
const limit = 15
const { error, loading, data, refetch, fetchMore, subscribeToMore } = useQuery(CHAT_DETAIL, {
variables: { userId: user._id, roomId: currentRoom._id, limit }, fetchPolicy: "cache-and-
network",
nextFetchPolicy: "cache-first" })
// render item
const renderItem = (
({item} ) => {
return <MainFlow item={item} />
}
)
if (error) {
console.warn('CHAT_DETAIL QUERY ERROR: ', error)
console.log(error.message);
return (
<View>
<Text>
An Error Occured: {error.message}
</Text>
</View>
)
}
if (loading || data == undefined || data == null) {
return (
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
<ActivityIndicator size={50} color="gray" />
</View>
)
}
// fetchMore
const fetchMoreData=()=>{
// console.log("fetchMore runnig hasnext limit, data.chatDetail.length >= limit ", hasNext, limit, data.chatDetail.length >= limit);
if(hasNext && data.chatDetail.length >= limit){
fetchMore({
variables:{
offset: data.chatDetail.length,
limit: data.chatDetail.length+limit
}
}).then((flowMoredata)=>{
if(flowMoredata.data.chatDetail.length==0 || flowMoredata.data.chatDetail.length === data.chatDetail.length){
setHasNext(false)
}
})
}
}
// subscription area
const subscribeQ = () => subscribeToMore({
document: MESSAGE_SUB,
variables: {
userId: user._id
},
updateQuery: (prev, { subscriptionData }) => {
if (!subscriptionData.data) return prev;
const { messageSub } = subscriptionData.data
let current = {}
let others = []
switch(messageSub.type){
case 'update':
prev.chatDetail.map(message => {
if (message._id != messageSub.message._id) others.push(message)
if (message._id == messageSub.message._id) current = messageSub.message
})
return { chatDetail: [ current, ...others ]}
case 'remove':
prev.chatDetail.map(message => {
if (message._id != messageSub.message._id) others.push(message)
if (message._id == messageSub.message._id) current = messageSub.message
})
return { chatDetail: [ ...others ]}
case 'create':
return { chatDetail: { ...prev, chatDetail: [ messageSub.message, ...prev.chatDetail] }}
default: return { ...prev }
}
}
})
if (subscribeToMore != undefined && subscribeToMore) {
subscribeQ()
}
return (
<View>
<FlatList
data={data.chatDetail}
renderItem={renderItem}
keyExtractor={(item, index) => String(index)}
onEndReached={fetchMoreData}
onEndReachedThreshold={0.2}
contentContainerStyle={{ paddingTop: 80 }}
inverted={true}
/>
</View>
)
}
export default ChatDetailMain
const styles = StyleSheet.create({})
It was about cache merge issue. If you want to cache data, you shoul give a key to apollo client "Cache according to the what, for each room has an id or roomName for keyArgs param it should uniqe value like that
const cache = new InMemoryCache({
typePolicies: {
Query: {
fields: {
chatDetail: {
keyArgs:['roomId'],
merge(incoming=[], existing=[]){
.
.
.
return offsetLimitPagination()
}}
}
}
},
});

react native setInterval cannot read property apply

I am new in react native I am trying to render the count of unread notification for that I called my API in HOC it is working fine for initial few seconds but after that, I started to get the below error
func.apply is not a function
below is my code
import React, { Component } from "react";
import PropTypes from "prop-types";
import { Modal, View } from "react-native";
import { themes } from "./constants";
import { AsyncStorage } from "react-native";
export default (OriginalComponent, animationType) =>
class extends Component {
static propTypes = {
handleFail: PropTypes.func,
theme: PropTypes.string,
visible: PropTypes.bool
};
state = {
modalVisible: true
};
static getDerivedStateFromProps({ visible }) {
if (typeof visible === "undefined") {
setInterval(
AsyncStorage.getItem("loginJWT").then(result => {
if (result !== null) {
result = JSON.parse(result);
fetch(serverUrl + "/api/getUnreadNotificationsCount", {
method: "GET",
headers: {
Authorization: "Bearer " + result.data.jwt
}
})
.then(e => e.json())
.then(function(response) {
if (response.status === "1") {
if (response.msg > 0) {
AsyncStorage.setItem(
"unreadNotification",
JSON.stringify(response.msg)
);
} else {
AsyncStorage.setItem("unreadNotification", 0);
}
}
})
.catch(error => {
alert(error);
// console.error(error, "ERRRRRORRR");
});
} else {
AsyncStorage.setItem("unreadNotification", 0);
}
}),
5000
);
return null;
}
return { modalVisible: visible };
}
handleOpenModal = () => {
this.setState({ modalVisible: true });
};
handleCloseModal = () => {
const { handleFail } = this.props;
this.setState({ modalVisible: false }, handleFail);
};
render() {
const { modalVisible } = this.state;
const { theme } = this.props;
return (
<View>
<Modal
animationType={animationType ? animationType : "fade"}
transparent={true}
visible={modalVisible}
onRequestClose={this.handleCloseModal}
>
<View style={themes[theme] ? themes[theme] : themes.transparent}>
<OriginalComponent
handleCloseModal={this.handleCloseModal}
{...this.props}
/>
</View>
</Modal>
</View>
);
}
};
I have not used getDerivedStateFromProps but, according to the docs, it is called on initial component mount and before each render update.
Thus your code is creating a new interval timer on each update without clearing any of the earlier timers, which could be causing a race condition of some sort.
You may want to consider using the simpler alternatives listed in the docs, or at a minimum, insure that you cancel an interval before creating a new one.

Get user location on app running as well as if app is in background

I'm beginner in React Native, I'm using expo I want to ask user for permission to access location if user granted the permission it will check if phone location from setting is on or not if it is on then it will give it's current location and if the app is close or running in background it will still give location
I have tried but it's not working
import React, { Component } from "react";
import {
Platform,
Text,
View,
StyleSheet,
Linking,
Button,
AppState
} from "react-native";
import Constants from "expo-constants";
import * as TaskManager from "expo-task-manager";
import * as Location from "expo-location";
import * as Permissions from "expo-permissions";
import * as IntentLauncher from "expo-intent-launcher";
import { Alert, NavigationActions } from "react-native";
import Modal from "react-native-modal";
const LOCATION_TASK_NAME = "background-location-task";
export default class LocationScreen extends Component {
state = {
location: null,
errorMessage: null,
};
componentDidMount = async () => {
await Location.startLocationUpdatesAsync(LOCATION_TASK_NAME, {
accuracy: Location.Accuracy.Balanced
});
render() {
let text = "Waiting..";
if (this.state.errorMessage) {
text = this.state.errorMessage;
} else if (this.state.location) {
text = JSON.stringify(this.state.location);
}
return (
<View style={styles.container}>
<Text style={styles.paragraph}>{text}</Text>
</View>
);
}
}
TaskManager.defineTask(LOCATION_TASK_NAME, handel);
export async function handel({ data, error }) {
try {
let { status } = await Permissions.askAsync(Permissions.LOCATION);
if (status !== "granted") {
this.setState({
errorMessage: "Permission to access location was denied"
});
return;
} else {
if (data) {
const { locations } = data;
const location = locations.map(location => {
let newLocation = Location.reverseGeocodeAsync(location.coords).then(
data => {
let maplocation = data.map(location => {
console.log(location);
console.log(location.city);
});
}
);
});
}
}
} catch (error) {
let status = Location.getProviderStatusAsync();
if (!status.locationServiceEnabled) {
const { navigation } = this.props;
navigation.navigate("Login");
}
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
alignItems: "center",
justifyContent: "center",
paddingTop: Constants.statusBarHeight,
backgroundColor: "#ecf0f1"
},
paragraph: {
margin: 24,
fontSize: 18,
textAlign: "center"
}
});
This is only working if location is on. It's not asking for permission if location is off or not granted

bundling failed: SyntaxError in D:\RN\AtmosphericMeshing-\src\router.js: D:/RN/AtmosphericMeshing-/src/router.js: Unexpected token (16:0)

everyone, I have been reporting wrong when I used the react-native compilation project, I don't know how to solve it, I can't find the error, please give me some Suggestions, thank you very much.
import React, { PureComponent } from 'react';
import { BackHandler, Platform, View, StatusBar, Text,Modal } from 'react-native';
import {
addNavigationHelpers
} from 'react-navigation';
import { connect } from 'react-redux';
import moment from 'moment';
import SplashScreen from 'react-native-splash-screen';
import { loadToken, getNetConfig, saveNetConfig, loadNetConfig } from './dvapack/storage';
import { createAction, NavigationActions, getCurrentScreen } from './utils';
import NetConfig from './config/NetConfig.json';
import api from './config/globalapi';
import AppNavigator from './containers/';
*I don't know if this is the correct way of writing the router, and it has led to this problem.*
#connect(({ router }) => ({ router }))***//一直报这里的错误=I've been making mistakes here.***
class Router extends PureComponent {
constructor(props) {
super(props);
this.state = {
configload: true
};
}
async componentWillMount() {
let netconfig =await loadNetConfig();
if (!netconfig && !netconfig != null) {
if (NetConfig.isAutoLoad) {
const newconfig = [];
NetConfig.Config.map((item, key) => {
const netitem = {};
// netitem.neturl = `http://${item.configIp}:${item.configPort}`+api.appurl;
netitem.neturl = `http://${item.configIp}:${item.configPort}`;
if (key === 0) {
netitem.isuse = true;
} else {
netitem.isuse = false;
}
newconfig.push(netitem);
});
saveNetConfig(newconfig);
} else {
this.setState({ configload: false });
SplashScreen.hide();
}
}
BackHandler.addEventListener('hardwareBackPress', this.backHandle);
}
async componentDidMount() {
const user = await loadToken();
this.props.dispatch(createAction('app/loadglobalvariable')({ user }));
}
componentWillUnmount() {
if (Platform.OS === 'android') {
BackHandler.removeEventListener('hardwareBackPress', this.backHandle);
JPushModule.removeReceiveCustomMsgListener(receiveCustomMsgEvent);
JPushModule.removeReceiveNotificationListener(receiveNotificationEvent);
JPushModule.removeReceiveOpenNotificationListener(openNotificationEvent);
JPushModule.removeGetRegistrationIdListener(getRegistrationIdEvent);
JPushModule.clearAllNotifications();
} else {
DeviceEventEmitter.removeAllListeners();
NativeAppEventEmitter.removeAllListeners();
}
}
backHandle = () => {
const currentScreen = getCurrentScreen(this.props.router);
//登录
if (currentScreen === 'Login') {
return true;
}
if (currentScreen !== 'Home') {
this.props.dispatch(NavigationActions.back());
return true;
}
return false;
}
render() {
if (!this.state.configload) {
return (
<View style={{ flex: 1 }}>
<StatusBar
barStyle="light-content"
/>
{/* <ScanNetConfig ScanSuccess={() => {
this.setState({ configload: true });
}}
/> */}
<Text>ScanNetConfig</Text>
</View>
);
}
const { dispatch, router } = this.props;
const navigation = addNavigationHelpers({ dispatch, state: router });
return (
<View style={{ flex: 1 }}>
<AppNavigator navigation={navigation} />
</View>
);
}
}
export function routerReducer(state, action = {}) {
return AppNavigator.router.getStateForAction(action, state);
}
export default Router;
Need More Detail?
this is the error.
bundling failed: SyntaxError in D:\RN\AtmosphericMeshing-\src\router.js: D:/RN/AtmosphericMeshing-/src/router.js: Unexpected token (16:0)
I find the Solution
.babelrc needs to be changed:
{
"presets": ["react-native"],
"plugins": [
"syntax-decorators",
"transform-decorators-legacy",
["import", { "libraryName": "antd-mobile" }]
]
}

React native - Can't dispatch action in component because state gets undefined

In my react native android app, when I try to dispatch an action in BoardsScreen or in the root of the app, the following error pops up:
However, when I remove it, the app doesn't crashes.
BoardsScreen.js
import React from 'react';
import { connect } from 'react-redux';
import { Container, Content, Text, List, Button, Icon, ListItem } from 'native-base';
import { ListView, StatusBar } from 'react-native';
import { ConfirmDialog } from 'react-native-simple-dialogs';
import ActionButton from 'react-native-action-button';
import { removeBoard } from '../actions/configurationActions';
class BoardsScreen extends React.PureComponent {
constructor(props) {
super(props);
this.state = {
boardDeleteDialog: false,
secId: null,
rowId: null,
rowMap: null,
};
}
deleteRow(secId, rowId, rowMap) {
rowMap[`${secId}${rowId}`].props.closeRow();
const newData = [...this.props.boards];
newData.splice(rowId, 1);
this.props.removeBoard(newData);
this.setState({
rowId: null,
secId: null,
rowMap: null,
boardDeleteDialog: false,
});
}
dataSource = new ListView.DataSource({ rowHasChanged: (r1, r2) => r1 !== r2 });
render() {
console.log(this.props.boards);
return (
<Container>
<StatusBar backgroundColor="#00C853" />
<ConfirmDialog
title="Delete board?"
animationType="fade"
visible={this.state.boardDeleteDialog}
positiveButton={{
title: 'Delete',
titleStyle: {
color: '#2ecc71',
},
onPress: () => this.deleteRow(this.state.secId, this.state.rowId, this.state.rowMap),
}}
negativeButton={{
titleStyle: {
color: '#2ecc71',
},
title: 'Cancel',
onPress: () =>
this.setState({
boardDeleteDialog: false,
secId: null,
rowId: null,
rowMap: null,
}),
}}
/>
<Content>
{this.props.boards.length >= 1 ? (
<List
style={{ backgroundColor: '#D9534F' }}
dataSource={this.dataSource.cloneWithRows(this.props.boards)}
renderRow={data => (
<ListItem
style={{ paddingLeft: 14, backgroundColor: 'transparent' }}
button
onPress={() =>
this.props.navigation.navigate('Board', {
board: data.board,
boardName: data.boardName,
})
}
>
<Text>{data.boardName}</Text>
</ListItem>
)}
renderRightHiddenRow={(data, secId, rowId, rowMap) => (
<Button
full
danger
onPress={() =>
this.setState({
boardDeleteDialog: true,
secId,
rowId,
rowMap,
})
}
>
<Icon active name="trash" />
</Button>
)}
disableRightSwipe
rightOpenValue={-75}
/>
) : (
<Text>No boards added.</Text>
)}
</Content>
<ActionButton
buttonColor="#2ecc71"
fixNativeFeedbackRadius
onPress={() => this.props.navigation.navigate('AddBoard')}
/>
</Container>
);
}
}
const mapStateToProps = state => ({
boards: state.configurationReducer.boards,
});
const mapDispatchToProps = dispatch => ({
removeBoard: (board) => {
dispatch(removeBoard(board));
},
});
export default connect(mapStateToProps, mapDispatchToProps)(BoardsScreen);
App.js
import React from 'react';
import { connect } from 'react-redux';
import MainNavigator from './src/config/Router';
import { addBoardToList } from './src/actions/configurationActions';
import { Board } from './src/API';
class App extends React.PureComponent {
componentDidMount() {
Board.getList(true).then(response => this.parseDataFromJSONResponse(response));
}
parseDataFromJSONResponse(response) {
for (let i = 0; i < response.length; i += 1) {
this.props.addBoardToList(response[1]);
}
}
render() {
return <MainNavigator />;
}
}
const mapStateToProps = state => ({
boards: state.configurationReducer.boards,
});
const mapDispatchToProps = dispatch => ({
addBoardToList: (board) => {
dispatch(addBoardToList(board));
},
});
export default connect(mapStateToProps, mapDispatchToProps)(App);
configurationReducer.js
const initialState = {
theme: 1,
obscure: false,
boards: [],
boardsList: [],
};
const configurationReducer = (state = initialState, action) => {
let newState = { ...state };
switch (action.type) {
case 'ADD_BOARD':
newState = {
boards: [...state.boards, action.payload],
};
return newState;
case 'REMOVE_BOARD':
newState = {
boards: action.payload,
};
return newState;
case 'ADD_BOARD_TO_LIST':
newState = {
boardsList: [...state.boardsList, action.payload],
};
return newState;
default:
return state;
}
};
export default configurationReducer;
configurationActions.js
function addBoard(board) {
return {
type: 'ADD_BOARD',
payload: board,
};
}
function removeBoard(board) {
return {
type: 'REMOVE_BOARD',
payload: board,
};
}
function addBoardToList(board) {
return {
type: 'ADD_BOARD_TO_LIST',
payload: board,
};
}
export { addBoard, removeBoard, addBoardToList };
I really don't have a clue what is causing this, maybe it's a bug but I don't know if is react-redux fault or react native itself.
When you remove the board, it looks like in you reducer, you return a strange new state:
case 'REMOVE_BOARD':
newState = {
boards: action.payload,
};
return newState;
Should the boards to be an array always? I think you missed something, for example:
boards: state.boards.filter ((it) => it.id !== action.payload.id),