I'm working on an Android app that needs to detect if other users of the app are close to each other (lets say within the same room or Bluetooth range). The app needs to be able to detect this without any user interaction.
Geolocation is not an option as this is too inaccurate indoors.
The app runs only on company owned phones that stay on company ground, privacy is not a concern.
All devices are always connected to the same wifi network and BT is always enabled.
My idea is to detect if users are within a close distance of eachother by periodically Bluetooth scanning and checking the results against a list of MAC adresses that contain all the devices that have the app installed.
The MAC adresses of all devices are send to a server, the devices then grab this list of mac adresses from the server to compare to the results of a BT scan.
Problem is, BT and Google's seem to use Advertisement / Discovery patterns where one device acts as the server and one device acts as the client. For this to work properly i feel like the devices need to always be discoverable.
Will an implementation based on Google's Nearby or BT work for my needs ?
Is it possible to detect the presence of a nearby device without it being discoverable ?
As battery life is a concern (need to be able to do this for atleast 8 hours a day) is BLE an option?
You can almost certainly handle 8 hours a day if the phones aren't really used for much else. There are a lot of variables, however.
Many older phones require a different type of scanning using infinite scanner restarts in order to properly report "seeing" a peripheral. This can dramatically decrease battery life.
If the phones are running Marshmallow or later, they have a doze mode which interrupts scanning. This can be circumvented using an AlarmManager, JobService/Dispatcher, or WorkManager. This can dramatically decrease battery life.
If the phones are running Oreo or later, they require a foreground service (persistent notification) in order to prevent the app from being automatically killed by the OS to save battery. The app should also be whitelisted from battery optimization because even with the foreground service, the app will still be killed off by the OS.
Finally, scanning and broadcasting and using location services is pretty expensive battery-wise. If you're attempting to cluster phones and guess their position based upon what other phones are nearby, at some level you'll still need the location data off of the phones to figure out where they're at.
You're much better off just scanning. You could carpet your company property with beacons, where each individual beacon's location is recorded. When the phone "enters a region" (comes within range of a beacon), it should send something to your api reporting which beacon it just found. This will tell you what room/area it's in.
Another less flashy (and potentially less accurate) way to track everything would be via the IP addresses of the wireless access points they're connected to. Use a WorkManager to periodically update an api with some unique ID for the phone and the IP address of the AP. Your IT department should know the locations of each of them. This way you get reasonably good tracking and virtually no battery drain.
Related
I have a security system where moving a Bluetooth LE device causes my android application to do some work. After some of the newer Android updates, I believe API 26, I could no longer get these updates if the Android device's screen was off. I was trying to think of a way around this and came up with an idea:
What if I paired the Android device and the Bluetooth device - would this allow for the message to be received when the Android screen is off?
Previously, all my BLE devices were part of a mesh, so I would regularly have the Android app check for changes in the mesh and turn the screen on to notify the user if needed. Now, because of the background execution limits introduced, I must require the Android device to have the screen on at all times, which leads to the death of display over time.
I'm not that great at programming in C, which is the language the BLE chips are programmed in, so I wanted to ask this first before spending hours just to see this NOT work. So, just to repeat the question: Will having a BLE device paired with the Android device allow a message through these restrictions when the Android screen is off?
If not - is there a way I can make this work?
Thank you for any info!
Use notifications instead of advertisements. This will deliver data instantly and works even if the screen is off. Newer versions of Android have introduced more restrictions for BLE scanning when the screen is off.
Use connectGatt with autoConnect set to true to automatically connect and reconnect in case the connection drops.
Use a Foreground Service in your app process to prevent the app process from being killed. If your app process exits, all Bluetooth connections are dropped as well.
You could use CompanionDeviceManager to gain some extra permissions.
You don't really need to be paired but it has some benefits such as faster connection setup and correctly remembering the address type (flaw in the API that this is missing).
I'm making an app that executes some actions after a device detects a beacon while monitoring for beacons after app is killed.
I am currently using altbeacon for detecting beacons on android. It works fine on stock android phones but on a few devices like OnePlus i need to run a foreground service to detect beacons which results in a notification which indeed looks a bad user experience.
In a few devices like xiaomi, I need to enable a few permissions, which differs from manufacturer to manufacturer, thus making it nearly impossible to redirect users to those settings to enable those permissions.
Could anyone please provide a workaround?
Currently I am monitoring beacons during app kill and once detected I range beacons in order to get the uuid, major and minor since I need to differentiate between a huge number of beacons.
What's the best way of detecting when an Android device is in a certain location? I'm creating a device admin app that enforces certain policies when the device is in a certain premise, e.g. a certain office building, and in order to enforce the policies, I need to know where the device is, and the Device Administrator API does not have any geo-location/geo-fence APIs.
I can think of a few methods, but none are foolproof:
Poll fine location (Wifi/GPS) - dependent on whether user has Wifi/GPS on. Impossible to enforce. Also, GPS doesn't work indoors and drains battery significantly.
Poll course location(cell tower) - more reliable, but inaccurate.
Place wifi routers around premises and detect when they are near - dependent of whether user has Wifi on.
What's the best way of detecting a device's location?
The only thing that meet your requirements are iBeacons or comparable devices.
That are blue tooth low energy beacons. Which are mounted on walls in the building.
They emit a beacon id and the distance to that device. You have to manage which beacon id is mounted at which place.
This technique was developed by Apple, so look how you can use that within android.
Outdoors GPS works best, you have to live with battery drain.
Cell Tower locationing you better forget, that has only about 1000m acuracy. Wlan locationing, too is of limited use.
This question follows on from Unity3D -- Send message to other mobile phones in the same vicinity
However, I made mistake of restricting to Unity3D.
So I would like to re-ask the question without that constraint.
Let us say we have 20 mobile phone users in a cave (so no Wi-Fi networks / isGPS)
One user hits a button, and every other user's screen flashes, (within a few milliseconds)
How to accomplish this?
What if everyone is using an iPhone?
What if there is a mix of iPhone and android users?
Finally, is there any solution that would cover a wider range of phones?
You should have some network so that mobiles can share some data. Bluetooth can have maximum of 10 m distance coverage (depends upon devices though). Since, all mobile are running same app they should be linked to a network and communicate. Please Check:
http://developer.android.com/samples/BluetoothLeGatt/index.html
You can create one device as server and communicate among other devices.
https://github.com/polyclef/BluetoothChatMulti
If you have installed the app on all of the devices then in all probability yes, if the device supports push (pretty much any smartphone) then you can use the push service to synchronize the devices based on geofencing (ie, 10m from my location), there are some other discovery routes you could try to (without using the B word) pinging other devices
the app would need to be able to provide some sort of server service if it was to create its own private network based on the IP addresses of the devices it found nearby, as those devices would have to connect to that phone acting as a server. the network interface shouldn't be important, but connecting the satellite devices to the server should be. You could try doing it based on which device can provide data services, aka hotspot. You can easily connect devices to networks programmatically.
at that point your faced with the classic client server problem. There is going to be a huge amount of work to get devices configured, network creation, client server infrastructure if it has to be done without data, packet optimization. Very expensive and very high risk depending on how many restrictions there are.
Search for How to make a html5 group chat and then build on that example.
Possibly send commands to the chat delimited by a / character where a javascript could then execute the command.
Good Luck with your design.
Danny117
i am programming for google android and i wonder if the scans for wireless 802.11 networks are done passively or actively? i mean: does the device actually emit a beacon request signal on WifiManager.startScan() or does it just listen for beacons sent periodically by the access points?
Android does passive scans, it listens for beacons. Doing an active scan can create a lot of congestion on the network by sending out probe requests and waiting for probe responses.
Even though this question is 11 years old, it still has relevance today and so I thought I'd give it an up-to-date answer:
Yes, Android devices do search for APs actively. Passive scanning requires for the device to listen for beacons for a longer time, which is energy consuming see this paper by Freudiger for more details
Active scanning only requires sending probe requests and then waiting for the reply on the corresponding channels. This takes less energy as it requires for the radio to be turned on for a much shorter time span. Unfortunately, active scans require for the device to identify itself somehow, and this makes it easily trackable. Mitigations in place are e.g. MAC address randomisation with every burst, randomised MACs during connection with an AP, randomised Sequence Numbers, omission of unnecessary fields and more. It all doesn't seem to be enough as people still find way to optimise their algorithms to improve tracking via Probe Requests. ;-)
Rain Ma replied that Probe Requests contain SSIDs, this is technically not true for all devices anymore. The only reason for SSIDs in Probe Requests is to find hidden networks. In Android devices, newer OS versions don't transmit SSIDs at all anymore, save for when scanning for hidden networks. Up until Android 8, all manually added networks were automatically assumed to be hidden networks. Starting with Android 9, one has to explicitly mark a network to be "hidden" for the device to probe with SSID.
iOS does automatic detection of hidden networks, and they say they don't probe with SSID at all unless they detect a network to be hidden.
The answer is YES
Actually, using omnipeek to capture packages from Android/iOS devices, we can get the result below:
Most Android devices always try to send Probe Request Frame every few minutes. They keep a list of SSID you used to connect, and always try to send probe request frame with SSID to see if they are available now. I guess one of the reason is 802.11 pre-authencation , and some other reason may be: enhance the wifi list display speed.
They are working in a active.
iOS devices seldom do active scan
If you wanna konw more about the rules, you'd better read "802.11 Wireless Networks The Guide"
You can refer to the pciture : Packages captured by omnipeek