OfflineODataParameters
public class OfflineODataParameters
OfflineODataParameters contains the configuration details for
an OfflineODataProvider
.
-
A key to use to encrypt the local data store. This is an optional property.
WARNING: If this property is omitted the store will be created without encrypting the data on the device.
Declaration
Swift
public var storeEncryptionKey: String?
-
An arbitrary name to identify this store. This is an optional property. If omitted a default name of “localstore” will be used.
Declaration
Swift
public var storeName: String?
-
The file system path to store the local data store. This is an optional property. If omitted, the default location will be the application’s Document directory.
Declaration
Swift
public var storePath: URL?
-
The URL suffix path to the server. Specify the suffix to add to the URL of each HTTP request sent to the server. When connecting through a proxy or web server, the urlSuffix may be necessary to find the server. This is an optional property.
Declaration
Swift
public var urlSuffix: String?
-
Additional advanced stream parameters. This is an optional property.
Declaration
Swift
public var extraStreamParameters: String?
-
Additional database connection parameters for store database. This is an optional property, the available parameters for ultralite database are listed on https://help.sap.com/docs/SAP_SQL_Anywhere/7eca48cee41b418bbd54feff83d57803/826ae5ab6ce2101491829fece129fbaf.html (Only cache related parameters can be changed)
Declaration
Swift
public var extraDatabaseConnectionParameters: String?
-
Custom headers to add to all HTTP communications. These are added to HTTP requests between the
OfflineODataProvider
and server and to HTTP requests between the server and the OData backend. The keys are header names. The values are header values.Declaration
Swift
public var customHeaders: [String : String]
-
Custom cookies to add to all HTTP communications. These are added to HTTP requests between the
OfflineODataProvider
and server and to HTTP requests between the server and the OData backend. The keys are cookie names. The values are cookie values.Declaration
Swift
public var customCookies: [String : String]
-
Specifies whether the OData backend or mobile services supports repeatable requests.
Repeatable requests (or idempotent requests) is a feature of some OData backends that ensures OData modification requests are applied exactly once even if the request is received multiple times. This is useful in cases where OData responses may be lost due to intermittent network connectivity and is required by the
OfflineODataProvider
in order to guarantee that requests are applied exactly once to the OData backend.If repeatable requests are supported by either the OData backend or mobile services, this parameter should be set to
true
, so that Offline OData will generate the repeatable request headers (RequestID and RepeatabilityCreation) for each modification request. The RequestID and RepeatabilityCreation headers are required for the server’s repeatable request implementation so that it can determine whether or not the request has already been applied.If both the OData backend and mobiles services do not support repeatable requests, set this parameter to
false
so that the repeatable request headers are not generated or sent.By default, enableRepeatableRequests is
true
.Declaration
Swift
public var enableRepeatableRequests: Bool
-
A constant used to indicate that by default, server-driven paging should not be used.
Declaration
Swift
public static let noPaging: Int?
-
Specifies the maximum number of entities that can be returned in a single local read request; i.e. the maximum page size to use for server-driven paging. In this case, “server” refers to the local provider, not the OData backend.
Reading an entity set will return at most this many entities in its response payload. If the response is a partial set of entities then a “next link” to the next page of the response will be provided.
By default, pageSize is
noPaging
.Declaration
Swift
public var pageSize: Int?
-
WARNING: If the timeout set too low ( less than 30 seconds ), it would increase network traffic for checking the liveness of the connection within each timeout period to ensure that the connection is still active.
Declaration
Swift
public var timeout: Int32?
-
Specifies whether or not to enable request queue optimization.
Request queue optimization is an algorithm that runs prior to an upload to reduce the number of requests that get sent to the backend while still maintaining the final state of the data as if all the requests the application made were sent as is.
Consider a simple example. Say the application creates a new entity and then updates that entity before uploading. With
enableRequestQueueOptimization
set tofalse
, both the create and update requests will be sent to the backend in the next upload. However, withenableRequestQueueOptimization
set totrue
, the create and update requests will be combined and only a create request will be sent in the next upload.Consider another simple example. Say the application creates a new entity and then deletes that entity before doing the next upload. With
enableRequestQueueOptimization
set tofalse
, both the create and delete requests will be sent to the backend. However, withenableRequestQueueOptimization
set totrue
, neither request will be sent.Additional Notes:
enableRequestQueueOptimization
isfalse
by default.The request queue optimization algorithm will maintain transaction (OData change set) boundaries. That is requests within a transaction can be combined, and requests between the end and start of the next transaction that reference the the same entity can be combined, but the algorithm will not remove a request from within a transaction to combine with a request outside a transaction nor move a request from outside a transaction to combine with a request inside a transaction. In this context the transaction could have been created manually by creating a local change set or built as a result of enabling transaction builder (see
enableTransactionBuilder
).For example, consider the following sequence of requests:
1. Create Customer 1 with Name="John" 2. Batch #1: 1. Change Set #1: 1. Create Customer 2 with Name="Jan" 2. Update Customer 2 with Name="Jane" 3. Update Customer 1 with Name="John Doe" 4. Update Customer 2 with Name="Jane Do" 5. Update Customer 2 with Name="Jane Doe"
After the request queue optimization algorithm is run, the requests will be:
1. Create Customer 1 with Name="John Doe" 2. Batch #1: 1. Change Set #1: 1. Create Customer 2 with Name="Jane" 3. Update Customer 2 with Name="Jane Doe"
Certain requests may need to be sent as is. For example, imagine an entity which needs to move from one explicit state to another such as NEW, IN PROCESS, SOLUTION PROVIDED, CONFIRMED. For such requests, use
OfflineODataRequestOptions
when executing the request and setOfflineODataRequestOptions.unmodifiableRequest
totrue
. Such requests will be left as is (not combined with other requests) when the request queue optimization algorithm is run.
See also
enableUndoLocalCreation
Declaration
Swift
public var enableRequestQueueOptimization: Bool
-
Specifies whether or not to enable an optimization such that deleting an entity that was created locally but not yet uploaded undoes the creation. More specifically, the optimization will remove requests from the request queue so that the backend never sees them.
Additional Notes:
enableUndoLocalCreation
isfalse
by default.enableUndoLocalCreation
is different thanenableRequestQueueOptimization
. The algorithm thatenableRequestQueueOptimization
controls respects transaction boundaries and unmodifiable requests (seeOfflineODataRequestOptions.unmodifiableRequest
). IfenableUndoLocalCreation
is set totrue
, it does not matter whether the creates, updates and deletes are in different transactions or are unmodifiable; they will all be removed.The optimization will respect cascading deletes. That is, if a parent in a parent-child relationship that is “on delete cascade” is deleted and this optimization is enabled, the algorithm will also ensure that requests for children that were also created and not yet uploaded will also be removed from the request queue. However, if deleting a locally created but not yet uploaded entity will cause an entity downloaded from the backend to be deleted (for example, if a cascading delete of the local entity causes a server entity to be deleted), the requests referencing the locally deleted entity will be sent to the backend to ensure the correct entities are deleted from the backend. If the application needs to guarantee requests creating and modifying a locally created entity are not sent to the backend, the application should use
OfflineODataProvider.undoPendingChanges(for:)
.
Consider the following examples:
Say you have created a new entity customer101 locally, updated it once and then deleted it. After performing these operations, you invoke upload(). Below is the operation sequence:
1. Request #1: Create customer101 locally 2. Request #2: Update customer101 3. Request #3: Delete customer101 4. Invoke upload()
Note that before invoking upload(), customer101 is not available (since it has been deleted) but requests #1 to #3 are kept in the request queue.
If
enableUndoLocalCreation
isfalse
(the default value), when calling upload(), requests #1 to #3 will be sent to the backend. The entity customer101 will be created, updated then deleted in the backend.If
enableUndoLocalCreation
istrue
, when calling upload, the optimization will happen by removing requests #1 to #3, therefore they would not be sent to the backend.Say you have created a new entity customer101 locally, and then also created a related order101 where the relationship between customers and orders is “on delete cascade”. Then customer101 is deleted before any operations are uploaded. Then upload() is invoked. Below is the operation sequence:
1. Request #1: Create customer101 locally 2. Request #2: Create order101 related to customer101 locally 3. Request #3: Delete customer101 4. Invoke upload()
If
enableUndoLocalCreation
isfalse
(the default value), when calling upload(), requests #1 to #3 will be sent to the backend.If
enableUndoLocalCreation
istrue
, when calling upload, the optimization will happen by removing requests #1 to #3, therefore they would not be sent to the backend.Say a pre-manufactured CPU101 (represented by an existing entity) was installed to a new motherboard101 (represented by a new entity created locally), but during testing the motherboard and CPU were found damaged. The motherboard as well as the CPU should be destroyed as they cannot be reused, indicating an “on delete cascade” relationship. Below is the operation sequence:
1. Request #1: Create motherboard101 locally associating to CPU101 2. Request #2: Delete motherboard101 3. Invoke upload()
If
enableUndoLocalCreation
isfalse
(the default value), when calling upload(), requests #1 and #2 will be sent to the backend. As a result, CPU101 will be deleted.If
enableUndoLocalCreation
istrue
, when calling upload(), the optimization will NOT remove requests #1 and #2. Instead, the requests will be sent to the backend because enabling the optimization should not change the end result.
Declaration
Swift
public var enableUndoLocalCreation: Bool
-
Specifies whether or not to enable the transaction builder.
Enabling transaction builder allows grouping requests into transactions (OData change sets) to be sent in the next upload that were not necessarily executed in a single change set initially. In other words, enabling this allows building large transactions for the next upload where all requests that need to go into the transactions are not known at one time.
Which requests go in which transactions is controlled by specifying
OfflineODataRequestOptions.transactionID
when performing the requests. Requests that contain the same transaction ID will be put into the same transaction (see additional notes).For example, consider the following sequence of requests:
1. Create Customer 1 with a transaction ID "1" 2. Create Order 1 with a transaction ID "1" 3. Create Product 1 with NO transaction ID 4. Create Customer 2 with a transaction ID "2" 5. Update Customer 1 with a transaction ID "1" 6. Update Customer 2 with a transaction ID "2"
Just prior to executing the upload, the transaction builder algorithm will run and these requests will result in the following requests being sent to the backend (in this example assume
enableRequestQueueOptimization
isfalse
):1. Batch #1 1. Change Set #1 1. Create Customer 1 2. Create Order 1 3. Update Customer 1 2. Create Product 1 3. Batch #2 1. Change Set #1 1. Create Customer 2 2. Update Customer 2
Additional Notes:
enableTransactionBuilder
isfalse
by default.enableTransactionBuilder
can be used in combination withenableRequestQueueOptimization
.To ensure referential integrity of related entities and to ensure all requests are valid OData requests, it is not always possible to group all requests with the same transaction ID into a single change set. Therefore, the transaction builder will group requests with the same transaction ID into as few change sets as possible.
In addition to referential integrity,
OfflineODataRequestOptions.unmodifiableRequest
can affect the transaction builder. Only one unmodifiable request per entity will be put into a single change set.
Declaration
Swift
public var enableTransactionBuilder: Bool
-
Specifies whether or not to enable deletion of individual entities from the ErrorArchive, the entity set which contains information about failed requests during the last upload.
The value is
false
by default.By default, when one failed request is deleted from the ErrorArchive, the whole entity set is cleared along with the associated requests in the request queue. By setting this option to
true
, the app can choose exactly which failed requests to delete. Deleting an individual failed request from the ErrorArchive will cause that request and any following requests in the request queue (sent or unsent) that depend on the failed request to be deleted as well.For example, imagine the following requests are made by the app, some of which will fail when they are executed on the backend:
// Request 1: Update customer101 which will fail in the backend service.updateEntity( customer101 ) // Request 2: Update customer102 which will fail in the backend service.updateEntity( customer102 ) // Request 3: Update customer101 again service.updateEntity( customer101 ) // Upload requests 1 - 3 service.upload( completionHandler: uploadHandler ) // Request 4: Update customer102 again service.updateEntity( customer102 )
During the upload, the first two requests fail due to issues in the backend. The third request (the second customer101 update) will not be sent to the backend at all because a request it depends on (the first customer101 update) failed. At the end of the upload, the ErrorArchive will have three error requests, one for each failed request in the upload.
With enableIndividualErrorArchiveDeletion set to
false
, deleting any entity from the ErrorArchive will result in requests 1, 2, and 3 being removed but will leave request 4 in the request queue unchanged.With enableIndividualErrorArchiveDeletion set to
true
, the app decides which failed requests to delete explicitly. If the app chooses to delete failed request 3, request 3 is the only request that will be deleted because no other requests after it in the request queue depend on it. If the app chooses to delete failed request 1, both request 1 and request 3 will be removed from the request queue because request 3 depends on request 1. If failed request 2 is deleted, both request 2 and request 4 will be deleted because even though request 4 has not yet been uploaded, it depends on request 2.Declaration
Swift
public var enableIndividualErrorArchiveDeletion: Bool
-
Specifies whether or not to allow data transfer for open, upload, and download operations when the current process switches to the background.
The value is ‘true’ by default.
By default, it will continue the data transfer of upload, download and open, but it is not guaranteed to finish the action while current process in the background. By setting to this option to ‘false’, the data transfer of upload, download and open can be interpreted when the current process switches to the background.
Declaration
Swift
public var enableBackgroundDataTransfer: Bool
-
Specifies whether or not to force uploading previous user’s pending change when a second user is opening local store that was used by the previous user. This is generally useful when multiple users share devices and the previous user forgot to upload his\her work at the end of the shift.
There is a SAP Mobile Services flag named ‘Allow Upload of Pending Changes from Previous User’ to specify whether server allows uploading pending changes of another user.
The upload function will be called automatically inside the open function when the second user opens the local store. After the pending changes from the previous user are uploaded to SAP Mobile Services, SAP Mobile Services will send them to the OData back end in the previous user’s context. If all changes are successfully executed by the back end, the pending state will be cleared in the local store. If some changes fail at the back end, open will be terminated. The application should use
OfflineProvider.getPreviousUser()
to notify the previous user and ask them to take over the device and fix the issue. This typically requires the previous user’s manual involvement. Or, the application can choose to open the store withoutforceUploadOnUserSwitch
and rollback the changes from the previous user. This should be done with care and is generally not recommended, because the previous user’sun-uploaded
work will be lost. Instead of rollback, the application can also upload the previous user’s work in the current user context. Careful consideration should be used before implementing this process, because it means the back end will receive the previous user’s request in the current user’s context, which may be a security concern.By default, forceUploadOnUserSwitch is ‘false’.
See also
currentUser
.See also
OfflineODataProvider.getPreviousUser
.Declaration
Swift
public var forceUploadOnUserSwitch: Bool
-
Specifies whether or not SAP Mobile Services will execute defining query in the order of addition. The execute order could also be specified through refresh_in_order in application configuration file at server side. If refreshInOrderOfAddition is set to true, the setting of refresh_in_order in server side will be ignored.
The addition order of defining query was not recorded in old SDK that doesn’t support refreshInOrderOfAddition. To make sure defining queries added with old SDK are executed in the order of addition, local store should be removed and downloaded again, or removed and added again in order.
By default, refreshInOrderOfAddition is ‘false’.
Declaration
Swift
public var refreshInOrderOfAddition: Bool
-
Specifies whether or not to enable Client Registrations.
Currently, only Mobile Back-End Tools is supported.
The value is
false
by default.Declaration
Swift
public var autoRegisterClient: Bool
-
Specifies the user who is opening store. Only applicable when forceUploadOnUserSwitch is enabled, otherwise the parameter will be ignored.
See also
forceUploadOnUserSwitch
.See also
OfflineODataProvider.getPreviousUser
.Declaration
Swift
public var currentUser: String?
-
Specifies whether or not to enable client-only schema creation based on the provied client-only metadata. If
enableClientOnlyMetadata
is false, no client only schema will be created. IfenableClientOnlyMetadata
is changed from true to false, all existing client-only data will be purged.By default, enableClientOnlyMetadata is false
Declaration
Swift
public var enableClientOnlyMetadata: Bool
-
Sepcifies whether or not to purge client-only data before switch user. If
forcePurgeClientOnlyDataOnUserSwitch
is true, all existing client-only data will be purged before switch to another user.forcePurgeClientOnlyDataOnUserSwitch
is true by default.If
forcePurgeClientOnlyDataOnUserSwitch
is false and there is existing client-only data created by previous users, the client-only data will be shared between different users.Optionally, user may manually purge the client only data through the
OfflineODataProvider.purgeClientOnlyData
APISee also
forceUploadOnUserSwitch
.Declaration
Swift
public var forcePurgeClientOnlyDataOnUserSwitch: Bool
-
Specifies whether or not to purge client-only data if the provided metadata has some incompatible change with previous metadata version when the client-only schema was built.
- If
forcePurgeClientOnlyDataOnMetadataChange
is false and the new version of client metadata is compatible with previous version, the client-only schema will be upgraded to reflect the change in the new metadata, existing client-only data will be preserved during the upgrade. - If
forcePurgeClientOnlyDataOnMetadataChange
is false and there is incompatible metadata change in the new version of client metadata, open store will fail. - If
forcePurgeClientOnlyDataOnMetadataChange
is true and the new version of client metadata is compatible with previous version, the client-only schema will be upgraded to reflect the change in the new metadata, existing client-only data will be preserved during the upgrade. If
forcePurgeClientOnlyDataOnMetadataChange
is true and there is incompatible metadata change in the new version of client metadata, Offline OData will try to forcibly purge all existing client-only data and recreate the database structure for the client-only metadata.See also
DataService.refreshMetadata By default, forcePurgeClientOnlyDataOnMetadataChange is false
Declaration
Swift
public var forcePurgeClientOnlyDataOnMetadataChange: Bool
- If
-
Initializes offline parameters.
Declaration
Swift
public init()
Return Value
Instance of OfflineODataParameters.