Skip to content

Commit

Permalink
[#319] Added possibility to change default operation timeout. (#321)
Browse files Browse the repository at this point in the history
* Finished migration to gradle 3.0.

* Bumped version to 1.5.0
[#319] Added possibility to change default operation timeout.

* Replaced ConnectionSetup API with a overloaded method.

* Finished migration to gradle 3.0.

* Added missing method to a mock.

* Fixed test.

* Applied code review requests.
  • Loading branch information
uKL committed Nov 17, 2017
1 parent 7858ce8 commit 5f48dd9
Show file tree
Hide file tree
Showing 20 changed files with 145 additions and 36 deletions.
2 changes: 1 addition & 1 deletion gradle.properties
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
GROUP=com.polidea.rxandroidble
VERSION_NAME=1.4.3
VERSION_NAME=1.5.0-SNAPSHOT

POM_DESCRIPTION=RxJava backed support for Bluetooth Low Energy in Android

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
import com.polidea.rxandroidble.RxBleConnection;
import com.polidea.rxandroidble.RxBleDevice;
import com.polidea.rxandroidble.RxBleDeviceServices;
import com.polidea.rxandroidble.Timeout;
import com.polidea.rxandroidble.exceptions.BleAlreadyConnectedException;

import java.util.ArrayList;
Expand Down Expand Up @@ -96,6 +97,11 @@ public void call() {
});
}

@Override
public Observable<RxBleConnection> establishConnection(boolean autoConnect, Timeout operationTimeout) {
return establishConnection(autoConnect);
}

private Observable<RxBleConnection> emitConnectionWithoutCompleting() {
return Observable.<RxBleConnection>never().startWith(rxBleConnection);
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,13 +1,18 @@
package com.polidea.rxandroidble.internal;
package com.polidea.rxandroidble;

import android.bluetooth.BluetoothGattCallback;
import android.content.Context;
import com.polidea.rxandroidble.RxBleDevice;

import com.polidea.rxandroidble.internal.BleIllegalOperationException;

import java.util.concurrent.TimeUnit;

/**
* Container for various connection parameters.
*/
public class ConnectionSetup {

public static final int DEFAULT_OPERATION_TIMEOUT = 30;
/**
* Flag related with
* {@link android.bluetooth.BluetoothDevice#connectGatt(Context, boolean, BluetoothGattCallback)} autoConnect flag.
Expand All @@ -22,16 +27,23 @@ public class ConnectionSetup {
* don't match those required by the operation. If set to true, an event will be logged without interrupting the execution.
*/
public final boolean suppressOperationCheck;
/**
* Timeout in seconds after which the operation will be considered as broken. Eventually the operation will be
* canceled and removed from queue.
*/
public final Timeout operationTimeout;

private ConnectionSetup(boolean autoConnect, boolean suppressOperationCheck) {
private ConnectionSetup(boolean autoConnect, boolean suppressOperationCheck, Timeout operationTimeout) {
this.autoConnect = autoConnect;
this.suppressOperationCheck = suppressOperationCheck;
this.operationTimeout = operationTimeout;
}

public static class Builder {

private boolean autoConnect = false;
private boolean suppressOperationCheck = false;
private Timeout operationTimeout = new Timeout(DEFAULT_OPERATION_TIMEOUT, TimeUnit.SECONDS);


/**
Expand Down Expand Up @@ -64,8 +76,19 @@ public Builder setSuppressIllegalOperationCheck(boolean suppressOperationCheck)
return this;
}

/**
* @param operationTimeout Timeout after which the operation will be considered as broken. Eventually the operation
* will be canceled and removed from queue. Keep in mind that it will cancel the library's operation
* only and may leave Android's BLE stack in an inconsistent state.
* @return this builder instance
*/
public Builder setOperationTimeout(Timeout operationTimeout) {
this.operationTimeout = operationTimeout;
return this;
}

public ConnectionSetup build() {
return new ConnectionSetup(autoConnect, suppressOperationCheck);
return new ConnectionSetup(autoConnect, suppressOperationCheck, operationTimeout);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothGattCallback;
import android.content.Context;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;

import com.polidea.rxandroidble.exceptions.BleDisconnectedException;
Expand Down Expand Up @@ -86,6 +87,42 @@ public interface RxBleDevice {
*/
Observable<RxBleConnection> establishConnection(boolean autoConnect);

/**
* Establishes connection with a given BLE device. {@link RxBleConnection} is a handle, used to process BLE operations with a connected
* device.
* <p>
* The connection is automatically disconnected (and released) when resulting Observable is unsubscribed.
* On the other hand when the connections is interrupted by the device or the system, the Observable will be unsubscribed as well
* following BleDisconnectedException or BleGattException emission.
* <p>
* During the disconnect process the library automatically handles order and requirement of device disconnect and gatt close operations.
* <p>
* Autoconnect concept may be misleading at first glance. In cases when the BLE device is available and it is advertising constantly you
* won't need to use autoconnect. Use autoconnect for connections where the BLE device is not advertising at
* the moment of #establishConnection call.
*
* @param autoConnect Flag related to
* {@link android.bluetooth.BluetoothDevice#connectGatt(Context, boolean, BluetoothGattCallback)}
* autoConnect flag. In case of auto connect is enabled the observable will wait with the emission
* of RxBleConnection. Without auto connect flag set to true the connection will fail
* with {@link com.polidea.rxandroidble.exceptions.BleGattException} if the device is not
* in range after a 30 seconds timeout.
* @param operationTimeout Timeout configuration after which the operation will be considered as broken. Eventually the operation
* will be canceled and removed from queue. Keep in mind that it will cancel the library's operation
* only and may leave Android's BLE stack in an inconsistent state.
* @return Observable emitting the connection.
* @throws BleDisconnectedException emitted when the BLE link has been disconnected either when the connection
* was already established or was in pending connection state. This occurs when the
* connection was released as a part of expected behavior
* (with {@link android.bluetooth.BluetoothGatt#GATT_SUCCESS} state).
* @throws BleGattException emitted when the BLE link has been interrupted as a result of an error.
* The exception contains detailed explanation of the error source (type of operation) and
* the code proxied from the Android system.
* @throws BleGattCallbackTimeoutException emitted when an internal timeout for connection has been reached. The operation will
* timeout in direct mode (autoConnect = false) after 35 seconds.
*/
Observable<RxBleConnection> establishConnection(boolean autoConnect, @NonNull Timeout operationTimeout);

/**
* Name of the device. Name is optional and it's up to the device vendor if will be provided.
*
Expand Down
14 changes: 14 additions & 0 deletions rxandroidble/src/main/java/com/polidea/rxandroidble/Timeout.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
package com.polidea.rxandroidble;

import java.util.concurrent.TimeUnit;

public class Timeout {

public final TimeUnit timeUnit;
public final long timeout;

public Timeout(long timeout, TimeUnit timeUnit) {
this.timeUnit = timeUnit;
this.timeout = timeout;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -47,12 +47,6 @@ String provideMacAddress() {
return macAddress;
}

@Provides
@Named(OPERATION_TIMEOUT)
static TimeoutConfiguration providesOperationTimeoutConf(@Named(NamedSchedulers.TIMEOUT) Scheduler timeoutScheduler) {
return new TimeoutConfiguration(DEFAULT_OPERATION_TIMEOUT, TimeUnit.SECONDS, timeoutScheduler);
}

@Provides
@Named(CONNECT_TIMEOUT)
static TimeoutConfiguration providesConnectTimeoutConf(@Named(ClientComponent.NamedSchedulers.TIMEOUT) Scheduler timeoutScheduler) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,10 @@
import android.support.annotation.Nullable;

import com.jakewharton.rxrelay.BehaviorRelay;
import com.polidea.rxandroidble.ConnectionSetup;
import com.polidea.rxandroidble.RxBleConnection;
import com.polidea.rxandroidble.RxBleDevice;
import com.polidea.rxandroidble.Timeout;
import com.polidea.rxandroidble.exceptions.BleAlreadyConnectedException;
import com.polidea.rxandroidble.internal.connection.Connector;

Expand Down Expand Up @@ -62,7 +64,16 @@ public Observable<RxBleConnection> establishConnection(final boolean autoConnect
return establishConnection(options);
}

// @Override
@Override
public Observable<RxBleConnection> establishConnection(final boolean autoConnect, final Timeout timeout) {
ConnectionSetup options = new ConnectionSetup.Builder()
.setAutoConnect(autoConnect)
.setOperationTimeout(timeout)
.setSuppressIllegalOperationCheck(true)
.build();
return establishConnection(options);
}

public Observable<RxBleConnection> establishConnection(final ConnectionSetup options) {
return Observable.defer(new Func0<Observable<RxBleConnection>>() {
@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -1,31 +1,48 @@
package com.polidea.rxandroidble.internal.connection;

import static com.polidea.rxandroidble.internal.connection.ConnectionComponent.NamedBooleans.AUTO_CONNECT;

import android.bluetooth.BluetoothGattCharacteristic;
import com.polidea.rxandroidble.internal.ConnectionSetup;

import com.polidea.rxandroidble.ClientComponent;
import com.polidea.rxandroidble.ConnectionSetup;
import com.polidea.rxandroidble.Timeout;
import com.polidea.rxandroidble.internal.operations.TimeoutConfiguration;
import com.polidea.rxandroidble.internal.util.CharacteristicPropertiesParser;
import dagger.Module;
import dagger.Provides;

import javax.inject.Named;
import javax.inject.Provider;

import dagger.Module;
import dagger.Provides;
import rx.Scheduler;

import static com.polidea.rxandroidble.internal.connection.ConnectionComponent.NamedBooleans.AUTO_CONNECT;

@Module
public class ConnectionModule {

public static final String OPERATION_TIMEOUT = "operation-timeout";
final boolean autoConnect;
final boolean suppressOperationCheck;
private final Timeout operationTimeout;

ConnectionModule(ConnectionSetup connectionSetup) {
this.autoConnect = connectionSetup.autoConnect;
this.suppressOperationCheck = connectionSetup.suppressOperationCheck;
this.operationTimeout = connectionSetup.operationTimeout;
}

@ConnectionScope
@Provides @Named(AUTO_CONNECT) boolean provideAutoConnect() {
return autoConnect;
}


@Provides
@Named(OPERATION_TIMEOUT)
TimeoutConfiguration providesOperationTimeoutConf(@Named(ClientComponent.NamedSchedulers.TIMEOUT) Scheduler timeoutScheduler) {
return new TimeoutConfiguration(operationTimeout.timeout, operationTimeout.timeUnit, timeoutScheduler);
}

@Provides
IllegalOperationHandler provideIllegalOperationHandler(
Provider<LoggingIllegalOperationHandler> loggingIllegalOperationHandlerProvider,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package com.polidea.rxandroidble.internal.connection;


import com.polidea.rxandroidble.internal.ConnectionSetup;
import com.polidea.rxandroidble.ConnectionSetup;
import com.polidea.rxandroidble.RxBleConnection;
import rx.Observable;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

import com.polidea.rxandroidble.ClientComponent;
import com.polidea.rxandroidble.RxBleConnection;
import com.polidea.rxandroidble.internal.ConnectionSetup;
import com.polidea.rxandroidble.ConnectionSetup;
import com.polidea.rxandroidble.internal.serialization.ClientOperationQueue;

import java.util.Set;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,14 +13,14 @@
import com.polidea.rxandroidble.exceptions.BleGattCallbackTimeoutException;
import com.polidea.rxandroidble.exceptions.BleGattCannotStartException;
import com.polidea.rxandroidble.exceptions.BleGattOperationType;
import com.polidea.rxandroidble.internal.DeviceModule;
import com.polidea.rxandroidble.internal.serialization.QueueReleaseInterface;
import com.polidea.rxandroidble.internal.QueueOperation;
import com.polidea.rxandroidble.internal.connection.ConnectionModule;
import com.polidea.rxandroidble.internal.connection.PayloadSizeLimitProvider;
import com.polidea.rxandroidble.internal.connection.RxBleGattCallback;
import com.polidea.rxandroidble.internal.serialization.QueueReleaseInterface;
import com.polidea.rxandroidble.internal.util.ByteAssociation;

import com.polidea.rxandroidble.internal.util.QueueReleasingEmitterWrapper;

import java.nio.ByteBuffer;
import java.util.UUID;

Expand Down Expand Up @@ -50,7 +50,7 @@ public class CharacteristicLongWriteOperation extends QueueOperation<byte[]> {
BluetoothGatt bluetoothGatt,
RxBleGattCallback rxBleGattCallback,
@Named(ClientComponent.NamedSchedulers.BLUETOOTH_INTERACTION) Scheduler bluetoothInteractionScheduler,
@Named(DeviceModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
@Named(ConnectionModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
BluetoothGattCharacteristic bluetoothGattCharacteristic,
PayloadSizeLimitProvider batchSizeProvider,
WriteOperationAckStrategy writeOperationAckStrategy,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,8 @@
import android.bluetooth.BluetoothGattCharacteristic;

import com.polidea.rxandroidble.exceptions.BleGattOperationType;
import com.polidea.rxandroidble.internal.DeviceModule;
import com.polidea.rxandroidble.internal.SingleResponseOperation;
import com.polidea.rxandroidble.internal.connection.ConnectionModule;
import com.polidea.rxandroidble.internal.connection.RxBleGattCallback;
import com.polidea.rxandroidble.internal.util.ByteAssociation;

Expand All @@ -21,7 +21,7 @@ public class CharacteristicReadOperation extends SingleResponseOperation<byte[]>
private final BluetoothGattCharacteristic bluetoothGattCharacteristic;

CharacteristicReadOperation(RxBleGattCallback rxBleGattCallback, BluetoothGatt bluetoothGatt,
@Named(DeviceModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
@Named(ConnectionModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
BluetoothGattCharacteristic bluetoothGattCharacteristic) {
super(bluetoothGatt, rxBleGattCallback, BleGattOperationType.CHARACTERISTIC_READ, timeoutConfiguration);
this.bluetoothGattCharacteristic = bluetoothGattCharacteristic;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,8 @@
import android.bluetooth.BluetoothGattCharacteristic;

import com.polidea.rxandroidble.exceptions.BleGattOperationType;
import com.polidea.rxandroidble.internal.DeviceModule;
import com.polidea.rxandroidble.internal.SingleResponseOperation;
import com.polidea.rxandroidble.internal.connection.ConnectionModule;
import com.polidea.rxandroidble.internal.connection.RxBleGattCallback;
import com.polidea.rxandroidble.internal.util.ByteAssociation;

Expand All @@ -22,7 +22,7 @@ public class CharacteristicWriteOperation extends SingleResponseOperation<byte[]
private final byte[] data;

CharacteristicWriteOperation(RxBleGattCallback rxBleGattCallback, BluetoothGatt bluetoothGatt,
@Named(DeviceModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
@Named(ConnectionModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
BluetoothGattCharacteristic bluetoothGattCharacteristic,
byte[] data) {
super(bluetoothGatt, rxBleGattCallback, BleGattOperationType.CHARACTERISTIC_WRITE, timeoutConfiguration);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,8 @@
import android.bluetooth.BluetoothGattDescriptor;

import com.polidea.rxandroidble.exceptions.BleGattOperationType;
import com.polidea.rxandroidble.internal.DeviceModule;
import com.polidea.rxandroidble.internal.SingleResponseOperation;
import com.polidea.rxandroidble.internal.connection.ConnectionModule;
import com.polidea.rxandroidble.internal.connection.RxBleGattCallback;
import com.polidea.rxandroidble.internal.util.ByteAssociation;

Expand All @@ -21,7 +21,7 @@ public class DescriptorReadOperation extends SingleResponseOperation<ByteAssocia

@Inject
DescriptorReadOperation(RxBleGattCallback rxBleGattCallback, BluetoothGatt bluetoothGatt,
@Named(DeviceModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
@Named(ConnectionModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
BluetoothGattDescriptor descriptor) {
super(bluetoothGatt, rxBleGattCallback, BleGattOperationType.DESCRIPTOR_READ, timeoutConfiguration);
bluetoothGattDescriptor = descriptor;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@
import android.bluetooth.BluetoothGattDescriptor;

import com.polidea.rxandroidble.exceptions.BleGattOperationType;
import com.polidea.rxandroidble.internal.DeviceModule;
import com.polidea.rxandroidble.internal.SingleResponseOperation;
import com.polidea.rxandroidble.internal.connection.ConnectionModule;
import com.polidea.rxandroidble.internal.connection.RxBleGattCallback;
import com.polidea.rxandroidble.internal.util.ByteAssociation;

Expand All @@ -23,7 +23,7 @@ public class DescriptorWriteOperation extends SingleResponseOperation<byte[]> {

DescriptorWriteOperation(RxBleGattCallback rxBleGattCallback,
BluetoothGatt bluetoothGatt,
@Named(DeviceModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
@Named(ConnectionModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
int bluetoothGattCharacteristicDefaultWriteType,
BluetoothGattDescriptor bluetoothGattDescriptor,
byte[] data) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

import com.polidea.rxandroidble.ClientComponent;
import com.polidea.rxandroidble.RxBleConnection;
import com.polidea.rxandroidble.internal.DeviceModule;
import com.polidea.rxandroidble.internal.connection.ConnectionModule;
import com.polidea.rxandroidble.internal.connection.PayloadSizeLimitProvider;
import com.polidea.rxandroidble.internal.connection.RxBleGattCallback;

Expand All @@ -33,7 +33,7 @@ public class OperationsProviderImpl implements OperationsProvider {
OperationsProviderImpl(
RxBleGattCallback rxBleGattCallback,
BluetoothGatt bluetoothGatt,
@Named(DeviceModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
@Named(ConnectionModule.OPERATION_TIMEOUT) TimeoutConfiguration timeoutConfiguration,
@Named(ClientComponent.NamedSchedulers.BLUETOOTH_INTERACTION) Scheduler bluetoothInteractionScheduler,
@Named(ClientComponent.NamedSchedulers.TIMEOUT) Scheduler timeoutScheduler,
Provider<ReadRssiOperation> rssiReadOperationProvider) {
Expand Down
Loading

0 comments on commit 5f48dd9

Please sign in to comment.