I am new to React Native. I am developing an application that connects to AWS services and can send push notifications to the phone that occupies the application. The services I am using are AWS Amplify, PushNotification, AWS Pinpoint, AWS Kinesis.
First I start with that when I enter my application it will show me a login screen.
This login has no validation, the only thing valuable is the first input and the login button for now. When I write a client id it will send me to another screen where it will show me the push notification. To send this pushNotification I need to identify the token of the device I am occupying.
For that i am using the function:
let tokenDispositivo;
NativeModules.RNPushNotification.getToken(token =>
{ console.log(token);
tokenDispositivo = token;
}
But when I run the application for the first time, the Token variable is as undefined.
This happens the first time I run the application, when I reload the application in the same instance it finds the token. I have a suspicion that perhaps I am misusing the React components and not sending it correctly.
This is my code:
App.js:
/**
* Sample React Native App
* https://github.com/facebook/react-native
*
* @format
* @flow strict-local
*/
import 'react-native-gesture-handler';
import React from 'react';
import { NativeModules, Linking, Alert } from 'react-native';
//AWS
import Amplify, { Analytics } from 'aws-amplify';
import awsmobile from './aws-exports';
import PushNotification from '@aws-amplify/pushnotification';
//Navigation
import { NavigationContainer } from '@react-navigation/native';
import { createStackNavigator } from '@react-navigation/stack';
// Screens
import LoginScreen from './screens/loginScreen';
import LoginSuccessfulScreen from './screens/loginSuccessful';
//Configuraciones
Amplify.configure(awsmobile);
Analytics.configure(awsmobile);
PushNotification.configure(awsmobile);
Amplify.Logger.LOG_LEVEL = 'VERBOSE';
// Obtener datos de la notificación recibida
PushNotification.onNotification((notification) => {
if (notification.foreground) {
console.log('onNotification foreground', notification);
const data = JSON.parse(notification.data['pinpoint.jsonBody']);
console.log('onNotification data', data);
Alert.alert(
"Mensaje de oferta",
"Usted ha recibido una nueva oferta, si desea visualizarla, presione Ok",
[
{
text: "Cancel",
onPress: () => console.log("Cancel Pressed"),
style: "cancel"
},
{ text: "OK", onPress: () => OpenURLButton(data.Url) }
],
{ cancelable: false }
);
} else {
console.log('onNotification background or closed',
notification);
}
});
const OpenURLButton = async ( url ) => {
await Linking.openURL(url);
}
// Obtener token de registro
PushNotification.onRegister(async(token) => {
console.log('in app registration', token);
});
// Obtener datos de la notificación al momento de abrirla (background)
PushNotification.onNotificationOpened((notification) => {
console.log('the notification is opened', notification);
OpenURLButton("reservedNameOfUrl.html");
});
let tokenDispositivo;
NativeModules.RNPushNotification.getToken(token =>
{ console.log(token);
tokenDispositivo = token;
}
);
//Navigation
const Stack = createStackNavigator();
const App = () => {
return (
<NavigationContainer>
<Stack.Navigator>
<Stack.Screen name= "Login">
{props => <LoginScreen {...props} extraData={tokenDispositivo}/>}
</Stack.Screen>
<Stack.Screen name="Login exitoso" component = {LoginSuccessfulScreen}/>
</Stack.Navigator>
</NavigationContainer>
);
};
export default App;
LoginScreen.js:
import React, { useState } from 'react';
import { Text, View, StyleSheet, TextInput, Button, Alert, PermissionsAndroid } from 'react-native';
import Geolocation from '@react-native-community/geolocation';
import AWS from 'aws-sdk';
import config from '../config';
import moment from 'moment';
function sendRecord(event) {
// Update AWS Config
if (config.aws) {
AWS.config.update(config.aws);
}
if (event != null) {
console.log('event = ' + JSON.stringify(event));
}
else {
console.log('No event object');
}
var record = JSON.stringify(event);
var recordParams = {
Data: record,
PartitionKey: 'partitionkey',
StreamName: 'AnyStreamNameForEvent'
};
var kinesis = new AWS.Kinesis({ region: config.kinesis.region });
try {
kinesis.putRecord(recordParams, function (err, data) {
if (err) {
console.log(err);
}
else {
console.log('Successfully sent data to Kinesis.');
}
});
} catch (e) {
console.log(e);
}
};
//Obtener coordenadas de longitud y latitud
const handleData = (idCliente, token) => {
let now = moment().format('YYYY-MM-DD HH:mm:ss');
console.log('Tipo de variable now', typeof now);
Geolocation.getCurrentPosition(
(position) => {
// Obtener latitud y longitud
var latitud = position.coords.latitude;
var longitud = position.coords.longitude;
// Formato de los datos a enviar
var data = {
idCliente: idCliente,
longitud: longitud,
latitud: latitud,
tiempo: now,
token: token
}
console.log('Handle data: ', data);
sendRecord(data);
}
)
}
// Permisos para utilizar el GPS
let requestLocationPermission = async () => {
try {
const granted = await PermissionsAndroid.request(
PermissionsAndroid.PERMISSIONS.ACCESS_FINE_LOCATION,
{
title: "Permiso para utilizar el GPS",
message:
"La aplicación necesita permisos para utilizar el GPS",
buttonNeutral: "Preguntar más tarde",
buttonNegative: "Cancelar",
buttonPositive: "OK"
}
);
if (granted === PermissionsAndroid.RESULTS.GRANTED) {
console.log("Puede utilizar el GPS");
} else {
console.log("Acceso al GPS no permitido");
}
} catch (err) {
console.warn(err);
}
};
// Manejar el envio de los datos
const handleSendData = (idCliente,token) => {
requestLocationPermission();
handleData(idCliente,token);
}
export const LoginScreen = (props) => {
let [clientId, setClientId] = useState('');
let token = props.extraData;
console.log('Token LS:', token); // HERE IS UNDEFINED THE FIRST EXECUTION
return (
<View style={styles.container}>
<View>
<Text style={styles.title}>
App
</Text>
</View>
<TextInput
placeholder="Client ID ..."
style={styles.inputs}
onChangeText={text => setClientId(text)}
/>
<TextInput
placeholder="Password"
style={styles.inputs}
secureTextEntry={true} />
<Button title="Login"
onPress={() => {
handleSendData(clientId, token);
props.navigation.navigate('Login exitoso', { clientId: clientId });
}
}
/>
</View>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#fff',
alignItems: 'center',
justifyContent: 'center'
},
inputs: {
borderColor: 'black',
borderWidth: 1,
padding: 5,
textAlign: "center",
marginTop: 3,
marginBottom: 3,
width: '40%'
},
title: {
fontSize: 20
}
});
export default LoginScreen;
I would like to know what I must do so that this token has its corresponding value on the login screen. I appreciate your help in advance.

