Data is stored in two different ways, temporarily in a buffer and permanently in the database.
Database
The database is using the Android SQLite implementation for saving data. The data stored in the database can be seen on Figure 5.17.
The tables contained in the database are LOCK_DATA, ACCELEROMETER_TABLE, WIFI-_TABLE, and BLUETOOTH_TABLE. Data tied to a specific lock is stored in the LOCK_DATA
Figure 5.17: Database design for stored decision data.
table, this data includes the MAC address, which is unique, that is used to tie the data to a specific physical lock. Along with this is the passphrase needed to unlock the lock.
The lock table also includes the location of the lock in form of longitude and latitude, as well as the inner and outer geofence size in meters. The location is the location of the lock as captured by the phone on the first unlock. Finally, there is a timestamp which includes the time of the most recent update to the row.
TheBLUETOOTH_TABLEandWIFI_TABLEincludes Bluetooth and Wifi devices. Both have a one-to-many relation with theLOCK_DATA, meaning that to each lock is tied multiple Wifi and Bluetooth devices. A Wifi device includes a SSID, MAC address, the minimum and maximum recorded RSSI where unlocking was approved, and a timestamp of the most recent change. A Bluetooth device consists of the same, but the SSID is called name, and the MAC is called source to adhere to the naming conventions of Bluetooth.
Finally there is a foreign key that ties each entry to a lock MAC address.
The primary key for both Bluetooth and Wifi is the combination of the MAC/Source address of the device along with the MAC address of the nearby lock. This allows a single Bluetooth or Wifi device to be tied to multiple different locks and still have independent data for each. The idea is that multiple locks can be near the same Bluetooth or Wifi device by being close to each other physically. The device can also follow the user around, this is true for fitness bands or smart watches that will often be near the user and continuously be announcing their presence with Bluetooth.
The ACCELEROMETER_TABLEis different from the Bluetooth and Wifi tables because the accelerometer data is a series of recorded events. The accelerometer data is still tied to a lock with a foreign key to the MAC address, however, the accelerometer data does not have any unique identifier that can be used. Therefore the ID is a randomly generated integer that identifies a series of captured accelerometer events. The ACCELEROMETER-_TABLE also includes data in the x,y, and z axis that have been rotated to geographic
coordinates along with the calculated speed at each event.
Data Buffer
The data buffer is a circular array that contains a list of four lists at each index. These four lists are the recorded accelerometer, Bluetooth, Wifi, and location data. The recorded data will be saved to the circular buffer every two seconds, and the lists of recorded data are cleared. In order to not put empty data into the data buffer, old data will be used if no new data has been found since the previous flush to the buffer.
Chapter 6
Implementation
6.1 Main Activity, UI, and Manifest
The basic building blocks of any Android application are the main activity, the user interface, and the Android manifest. The main activity is the class that is launched when the application is first opened. The user interface is defined in a number of XML files each corresponding to an activity, and the information about the application must be declared in theAndroidManifest.xml file.
Listing 6.1 shows the most important aspects of theAndroidManifest.xml file. Firstly, the permissions used in the application are defined. Following that, the application
details are defined, these include the name, icon, and theme. Lastly, the services that the application provides are defined, these have to be defined here for Android to allow them to run.
The User Interface
Most of the applications work is meant to happen seamlessly in the background, without the user seeing it. The user interface is thus quite minimal, most of the buttons in the main activity are used to start and stop individual services and would not be present in an end product.
Launching the Core Service
Besides the user interface, the main activity has the responsibility of launching the core service. The core service is different from the other services managed by the application as it is meant to be running at all times, rather than continuously starting and stopping.
1 protected void o n S t a r t ( ) {
Listing 6.2: onStart() method in the MainActivity class
Listing 6.2 shows the onStart() method of the MainActivity class. Here the core service is started if it is not already running, if the service is already running, the activity is simply bound to the service. The onStart() method also checks for the needed application permissions, if the necessary permissions have not been granted, the user will be notified and the application will not function properly.