bridgefy / bridgefy-react-native

The Bridgefy Software Development Kit (SDK) is a state-of-the-art, plug-and-play package that will let people use your mobile app when they don’t have access to the Internet, by using Bluetooth mesh networks.
MIT License
11 stars 4 forks source link

Bridgefy does not seem to send anything #33

Closed m4dh4t closed 2 months ago

m4dh4t commented 2 months ago

I am trying this library and wanted to try the data broadcasting feature using BLE on an iOS device and setup the permission granting based on the repository example project.

Unfortunately it seems like no data is being sent out and when trying to debug further, I saw that upon calling the Bridgefy.send method no call to bridgefyDidSendMessage was made either, although bridgefyDidStart was correctly called.

import React, { useState, useEffect } from 'react';
import { StyleSheet, TextInput, TouchableOpacity, NativeEventEmitter, NativeModules, EmitterSubscription, Platform, Alert } from 'react-native';
import { checkMultiple, openSettings, requestMultiple, PERMISSIONS, RESULTS } from 'react-native-permissions';
import Ionicons from '@expo/vector-icons/Ionicons';

import { Bridgefy, BridgefyPropagationProfile, BridgefyTransmissionModeType, BridgefyEvents } from 'bridgefy-react-native';

import ParallaxScrollView from '@/components/ParallaxScrollView';
import { ThemedText } from '@/components/ThemedText';
import { ThemedView } from '@/components/ThemedView';

const bridgefy = new Bridgefy();

const permissions = Platform.OS === 'android' ?
  [
    PERMISSIONS.ANDROID.ACCESS_FINE_LOCATION,
    PERMISSIONS.ANDROID.BLUETOOTH_ADVERTISE,
    PERMISSIONS.ANDROID.BLUETOOTH_CONNECT,
    PERMISSIONS.ANDROID.BLUETOOTH_SCAN,
  ] :
  [
    PERMISSIONS.IOS.LOCATION_ALWAYS,
    PERMISSIONS.IOS.BLUETOOTH,
  ];

export default function ExchangeScreen() {
  const [isStarted, setIsStarted] = useState(false);
  const [permissionsGranted, setPermissionsGranted] = useState(false);

  useEffect(() => {
    checkAndRequestPermissions();
  }, []);

  useEffect(() => {
    if (permissionsGranted) {
      initializeBridgefy();
    }
  }, [permissionsGranted]);

  const checkAndRequestPermissions = async () => {
    const statuses = await checkMultiple(permissions);
    const allGranted = Object.values(statuses).every(status => status === RESULTS.GRANTED);

    if (allGranted) {
      setPermissionsGranted(true);
    } else {
      const results = await requestMultiple(permissions);
      const allGrantedAfterRequest = Object.values(results).every(status => status === RESULTS.GRANTED);

      if (allGrantedAfterRequest) {
        setPermissionsGranted(true);
      } else {
        Alert.alert(
          'Permissions Required',
          'This app requires certain permissions to function properly. Please grant all requested permissions in the app settings.',
          [
            { text: 'Cancel', style: 'cancel' },
            { text: 'Open Settings', onPress: () => openSettings() }
          ]
        );
      }
    }
  };

  const initializeBridgefy = async () => {
    try {
      await bridgefy.initialize({
        apiKey: 'REDACTED',
        verboseLogging: true,
      });
      await bridgefy.start();
    } catch (error) {
      console.error('Failed to initialize Bridgefy:', error);
    }
  };

  useEffect(() => {
    const eventEmitter = new NativeEventEmitter(NativeModules.BridgefyReactNative);
    const subscriptions: EmitterSubscription[] = [];

    subscriptions.push(
      eventEmitter.addListener(BridgefyEvents.bridgefyDidStart, (event) => {
        console.log('Bridgefy started', event);
        setIsStarted(true);
      })
    );

    subscriptions.push(
      eventEmitter.addListener(BridgefyEvents.bridgefyDidFailToStart, (event) => {
        console.log('Bridgefy failed to start', event);
      })
    );

    subscriptions.push(
      eventEmitter.addListener(BridgefyEvents.bridgefyDidSendMessage, (event) => {
        console.log('Bridgefy sent message', event);
      })
    );

    subscriptions.push(
      eventEmitter.addListener(BridgefyEvents.bridgefyDidSendDataProgress, (event) => {
        console.log('Bridgefy sending data progress', event);
      })
    );

    subscriptions.push(
      eventEmitter.addListener(BridgefyEvents.bridgefyDidFailSendingMessage, (event) => {
        console.log('Bridgefy failed to send message', event);
      })
    );

    subscriptions.push(
      eventEmitter.addListener(BridgefyEvents.bridgefyDidReceiveData, (event) => {
        console.log('Bridgefy received data', event);
        setReceivedMessages((prevMessages) => [...prevMessages, event.data]);
      })
    );

    return () => {
      subscriptions.forEach((sub) => sub.remove());
      bridgefy.stop();
    };
  }, []);

  const sendMessage = async () => {
    try {
      const message = "Hello, world!";
      const lastMessageId = await bridgefy.se(
        message,
        {
          type: BridgefyTransmissionModeType.broadcast,
          uuid: await bridgefy.currentUserId(),
        }
      );
    } catch (error) {
      console.error('Failed to send message:', error);
    }
  };

  return (
    <ParallaxScrollView
      headerBackgroundColor={{ light: '#D0D0D0', dark: '#353636' }}
      headerImage={<Ionicons size={280} name="swap-horizontal-outline" style={styles.headerImage} />}>
      <ThemedView style={styles.titleContainer}>
        <ThemedText type="title">Exchange</ThemedText>
      </ThemedView>
      <ThemedView style={styles.stepContainer}>
        {!permissionsGranted && (
          <TouchableOpacity style={styles.button} onPress={checkAndRequestPermissions}>
            <ThemedText>Grant Permissions</ThemedText>
          </TouchableOpacity>
        )}
        {permissionsGranted && (
          <TouchableOpacity style={styles.button} onPress={sendMessage} disabled={!isStarted}>
            <ThemedText>Send Message</ThemedText>
          </TouchableOpacity>
        )}
      </ThemedView>
    </ParallaxScrollView>
  );
}

const styles = StyleSheet.create({
  titleContainer: {
    flexDirection: 'row',
    alignItems: 'center',
    gap: 8,
  },
  stepContainer: {
    gap: 8,
    marginBottom: 8,
  },
  headerImage: {
    color: '#808080',
    bottom: -60,
    left: -35,
    position: 'absolute',
  },
  input: {
    height: 40,
    borderColor: 'gray',
    borderWidth: 1,
    paddingHorizontal: 10,
  },
  button: {
    backgroundColor: '#007AFF',
    alignItems: 'center',
    borderRadius: 5,
    padding: 10,
  }
});

Would you have any guidance on how to debug this matter further ?

julian-bridgefy commented 2 months ago

Hi @m4dh4t, it appears that messaging functionality requires certain conditions to be met for proper operation.

SDK Initialization: Confirm that the SDK was properly initialized. The first time you use the SDK, an active internet connection is required to validate your API key and generate a license for offline use.

Permissions: Ensure that both Bluetooth and location permissions are granted for the app, as these are necessary for the SDK to function correctly.

Bluetooth Connection: Device connections rely on Bluetooth, so please verify that the Bluetooth on your device is enabled and functioning properly. Connectivity may also be limited by Bluetooth range and environment.

Offline Messaging: Bridgefy's messaging works offline, but it requires at least two devices with the same app and API key to communicate.


To help us troubleshoot further, please share the following details: The model and OS version of your device(s) The version of React Native you are using

I'll review the shared data and test on similar devices.

m4dh4t commented 2 months ago

Hi @julian-bridgefy, thank you very much for the quick answer. I can confirm you that:

Two test devices have been used, an iPhone 12 Pro running iOS 18 beta 7 and an iPad Air 5 running iPadOS 17.5.1, with React-Native 0.74.5.

Let me know if there is anything else I could do to help pinpoint the root cause and thank you again for your help.

julian-bridgefy commented 2 months ago

@m4dh4t Thanks for the update! I'll review it with similar devices. Could you please share with me the Bridgefy React Native version you're using? Yesterday, we released a new version (1.1.6) that solves communication problems.

m4dh4t commented 2 months ago

@julian-bridgefy thank you for reviewing this issue. I just tried using version 1.1.6 (I was running 1.1.5) and I'm still not seeing any feedback from the BridgefyEvents.bridgefyDidSendMessage method. Would you have any guidance on how to find the specific part at cause ?

Edit: I did not fully rebuild the app dependencies, it actually seems to respond correctly now ! I will keep you updated in case I find anything else but in the meantime thank you very much for your assistance.

julian-bridgefy commented 2 months ago

Thank you for reaching out!, I believe it's resolved now. I'll go ahead and close the issue for the time being. However, please feel free to reopen it or create a new issue if anything else comes up or if you need further assistance.