diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CacheItem.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CacheItem.cs
index b3be547f5..b6d87b66f 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CacheItem.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CacheItem.cs
@@ -13,7 +13,7 @@ public class CacheItem
public long AddedToCacheTicksUtc;
/// ETag value of API response. https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/ETag
public string ETag;
- /// Can be 'null' as not all APIs populated this value. Last-Modified value of API response in GMT: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Last-Modified
- public DateTime? LastModified;
+
+ public DateTime ExpirationDate;
}
}
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CachingWebFileSource.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CachingWebFileSource.cs
index b881516ff..1ec5fa613 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CachingWebFileSource.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/CachingWebFileSource.cs
@@ -5,14 +5,10 @@
using System.Collections.Generic;
using Mapbox.Unity.Utilities;
using Mapbox.Map;
- using System.Collections;
- using System.Linq;
public class CachingWebFileSource : IFileSource, IDisposable
{
-
-
#if MAPBOX_DEBUG_CACHE
private string _className;
#endif
@@ -22,6 +18,8 @@ public class CachingWebFileSource : IFileSource, IDisposable
private Func _getMapsSkuToken;
private bool _autoRefreshCache;
+ private const string EtagHeaderName = "ETag";
+ private const string CacheControlHeaderName = "Cache-Control";
public CachingWebFileSource(string accessToken, Func getMapsSkuToken, bool autoRefreshCache)
{
@@ -34,8 +32,7 @@ public CachingWebFileSource(string accessToken, Func getMapsSkuToken, bo
}
-#region idisposable
-
+ #region idisposable
~CachingWebFileSource()
{
@@ -64,12 +61,12 @@ protected virtual void Dispose(bool disposeManagedResources)
}
}
}
+
_disposed = true;
}
}
-
-#endregion
+ #endregion
///
@@ -102,7 +99,8 @@ public void Clear()
}
- public void ReInit() {
+ public void ReInit()
+ {
foreach (var cache in _caches)
{
cache.ReInit();
@@ -118,7 +116,6 @@ string uri
, string tilesetId = null
)
{
-
if (string.IsNullOrEmpty(tilesetId))
{
throw new Exception("Cannot cache without a tileset id");
@@ -150,6 +147,7 @@ string uri
uriBuilder.Query = accessTokenQuery + "&" + mapsSkuToken;
}
}
+
string finalUrl = uriBuilder.ToString();
#if MAPBOX_DEBUG_CACHE
@@ -166,58 +164,49 @@ string uri
callback(Response.FromCache(cachedItem.Data));
// check for updated tiles online if this is enabled in the settings
- if (_autoRefreshCache)
+ if (cachedItem.ExpirationDate < DateTime.Now)
{
// check if tile on the web is newer than the one we already have locally
IAsyncRequestFactory.CreateRequest(
finalUrl,
- (Response headerOnly) =>
+ timeout,
+ "If-None-Match", cachedItem.ETag,
+ (Response response) =>
{
// on error getting information from API just return. tile we have locally has already been returned above
- if (headerOnly.HasError)
+ if (response.HasError || response.StatusCode == null)
{
return;
}
- // TODO: remove Debug.Log before PR
- //UnityEngine.Debug.LogFormat(
- // "{1}{0}cached:{2}{0}header:{3}"
- // , Environment.NewLine
- // , finalUrl
- // , cachedItem.ETag
- // , headerOnly.Headers["ETag"]
- //);
-
// data from cache is the same as on the web:
// * tile has already been returned above
// * make sure all all other caches have it too, but don't force insert via cache.add(false)
// additional ETag empty check: for backwards compability with old caches
- if (!string.IsNullOrEmpty(cachedItem.ETag) && cachedItem.ETag.Equals(headerOnly.Headers["ETag"]))
+ if (response.StatusCode == 304) // 304 NOT MODIFIED
{
- foreach (var cache in _caches)
- {
- cache.Add(tilesetId, tileId, cachedItem, false);
- }
+ cachedItem.ExpirationDate = response.GetExpirationDate();
+ }
+ else if (response.StatusCode == 200) // 200 OK, it means etag&data has changed so need to update cache
+ {
+ string eTag = response.GetETag();
+
+ // not all APIs populate 'Last-Modified' header
+ // don't log error if it's missing
+ DateTime expirationDate = response.GetExpirationDate();
+
+ cachedItem.Data = response.Data;
+ cachedItem.ETag = eTag;
+ cachedItem.ExpirationDate = expirationDate;
}
- else
+
+ foreach (var cache in _caches)
{
- // TODO: remove Debug.Log before PR
- UnityEngine.Debug.LogWarningFormat(
- "updating cached tile {1} tilesetId:{2}{0}cached etag:{3}{0}remote etag:{4}{0}{5}"
- , Environment.NewLine
- , tileId
- , tilesetId
- , cachedItem.ETag
- , headerOnly.Headers["ETag"]
- , finalUrl
- );
-
- // request updated tile and pass callback to return new data to subscribers
- requestTileAndCache(finalUrl, tilesetId, tileId, timeout, callback);
+ cache.Add(tilesetId, tileId, cachedItem, true);
}
+
+ callback(Response.FromCache(cachedItem.Data));
}
- , timeout
- , HttpRequestType.Head
);
}
@@ -233,34 +222,18 @@ string uri
}
}
-
private IAsyncRequest requestTileAndCache(string url, string tilesetId, CanonicalTileId tileId, int timeout, Action callback)
{
return IAsyncRequestFactory.CreateRequest(
url,
- (Response r) =>
+ (Response response) =>
{
// if the request was successful add tile to all caches
- if (!r.HasError && null != r.Data)
+ if (!response.HasError && null != response.Data)
{
- string eTag = string.Empty;
- DateTime? lastModified = null;
-
- if (!r.Headers.ContainsKey("ETag"))
- {
- UnityEngine.Debug.LogWarningFormat("no 'ETag' header present in response for {0}", url);
- }
- else
- {
- eTag = r.Headers["ETag"];
- }
+ string eTag = response.GetETag();
- // not all APIs populate 'Last-Modified' header
- // don't log error if it's missing
- if (r.Headers.ContainsKey("Last-Modified"))
- {
- lastModified = DateTime.ParseExact(r.Headers["Last-Modified"], "r", null);
- }
+ DateTime expirationDate = response.GetExpirationDate();
// propagate to all caches forcing update
foreach (var cache in _caches)
@@ -270,27 +243,25 @@ private IAsyncRequest requestTileAndCache(string url, string tilesetId, Canonica
, tileId
, new CacheItem()
{
- Data = r.Data,
+ Data = response.Data,
ETag = eTag,
- LastModified = lastModified
+ ExpirationDate = expirationDate
}
, true // force insert/update
);
}
}
+
if (null != callback)
{
- r.IsUpdate = true;
- callback(r);
+ response.IsUpdate = true;
+ callback(response);
}
}, timeout);
}
-
class MemoryCacheAsyncRequest : IAsyncRequest
{
-
-
public string RequestUrl { get; private set; }
@@ -302,14 +273,14 @@ public MemoryCacheAsyncRequest(string requestUrl)
public bool IsCompleted
{
- get
- {
- return true;
- }
+ get { return true; }
}
- public HttpRequestType RequestType { get { return HttpRequestType.Get; } }
+ public HttpRequestType RequestType
+ {
+ get { return HttpRequestType.Get; }
+ }
public void Cancel()
@@ -318,4 +289,4 @@ public void Cancel()
}
}
}
-}
+}
\ No newline at end of file
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/ResponseStatic.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/ResponseStatic.cs
new file mode 100644
index 000000000..53e2ca6ed
--- /dev/null
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/ResponseStatic.cs
@@ -0,0 +1,48 @@
+using System;
+using Mapbox.Platform;
+using UnityEngine;
+
+public static class ResponseStatic
+{
+ private static string EtagHeaderName = "ETag";
+ private static string CacheControlHeaderName = "Cache-Control";
+
+ public static DateTime GetExpirationDate(this Response response)
+ {
+ DateTime expirationDate = DateTime.Now;
+ if (response.Headers.ContainsKey(CacheControlHeaderName))
+ {
+ var cacheEntries = response.Headers[CacheControlHeaderName].Split(',');
+ if (cacheEntries.Length > 0)
+ {
+ foreach (var entry in cacheEntries)
+ {
+ var value = entry.Split('=');
+ if (value[0] == "max-age")
+ {
+ expirationDate = expirationDate + TimeSpan.FromSeconds(int.Parse(value[1]));
+ return expirationDate;
+ }
+ }
+ }
+ }
+
+ return expirationDate;
+ }
+
+ public static string GetETag(this Response response)
+ {
+ string eTag = String.Empty;
+ if (!response.Headers.ContainsKey(EtagHeaderName))
+ {
+ Debug.LogWarning("no 'ETag' header present in response");
+ }
+ else
+ {
+ eTag = response.Headers[EtagHeaderName];
+ }
+
+ return eTag;
+ }
+
+}
\ No newline at end of file
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/ResponseStatic.cs.meta b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/ResponseStatic.cs.meta
new file mode 100644
index 000000000..90a027a53
--- /dev/null
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/ResponseStatic.cs.meta
@@ -0,0 +1,3 @@
+fileFormatVersion: 2
+guid: 4413348b85554bea88efd493b7dd4d4c
+timeCreated: 1601304948
\ No newline at end of file
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/SQLiteCache.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/SQLiteCache.cs
index a221ce117..fd24d472b 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/SQLiteCache.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/SQLiteCache.cs
@@ -1,6 +1,7 @@
-namespace Mapbox.Platform.Cache
-{
+using UnityEngine.PlayerLoop;
+namespace Mapbox.Platform.Cache
+{
using Mapbox.Map;
using Mapbox.Utils;
using SQLite4Unity3d;
@@ -12,18 +13,22 @@
public class SQLiteCache : ICache, IDisposable
{
-
-
///
/// maximum number tiles that get cached
///
- public uint MaxCacheSize { get { return _maxTileCount; } }
+ public uint MaxCacheSize
+ {
+ get { return _maxTileCount; }
+ }
///
/// Check cache size every n inserts
///
- public uint PruneCacheDelta { get { return _pruneCacheDelta; } }
+ public uint PruneCacheDelta
+ {
+ get { return _pruneCacheDelta; }
+ }
#if MAPBOX_DEBUG_CACHE
@@ -34,10 +39,13 @@ public class SQLiteCache : ICache, IDisposable
private string _dbPath;
private SQLiteConnection _sqlite;
private readonly uint _maxTileCount;
+
/// check cache size only every '_pruneCacheDelta' calls to 'Add()' to avoid being too chatty with the database
private const int _pruneCacheDelta = 20;
+
/// counter to keep track of calls to `Add()`
private int _pruneCacheCounter = 0;
+
private object _lock = new object();
@@ -48,10 +56,8 @@ public SQLiteCache(uint? maxTileCount = null, string dbName = "cache.db")
init();
}
-
#region idisposable
-
~SQLiteCache()
{
Dispose(false);
@@ -77,104 +83,28 @@ protected virtual void Dispose(bool disposeManagedResources)
_sqlite = null;
}
}
+
_disposed = true;
}
}
-
#endregion
-
private void init()
{
-
#if MAPBOX_DEBUG_CACHE
_className = this.GetType().Name;
#endif
- openOrCreateDb(_dbName);
+ OpenOrCreateDatabase(_dbName);
//hrmpf: multiple PKs not supported by sqlite.net
//https://github.com/praeclarum/sqlite-net/issues/282
//do it via plain SQL
- List colInfoTileset = _sqlite.GetTableInfo(typeof(tilesets).Name);
- if (0 == colInfoTileset.Count)
- {
- string cmdCreateTableTilesets = @"CREATE TABLE tilesets(
-id INTEGER PRIMARY KEY ASC AUTOINCREMENT NOT NULL UNIQUE,
-name STRING NOT NULL
-);";
- _sqlite.Execute(cmdCreateTableTilesets);
- string cmdCreateIdxNames = @"CREATE UNIQUE INDEX idx_names ON tilesets (name ASC);";
- _sqlite.Execute(cmdCreateIdxNames);
- }
-
- List colInfoTiles = _sqlite.GetTableInfo(typeof(tiles).Name);
- if (0 == colInfoTiles.Count)
- {
-
- string cmdCreateTableTiles = @"CREATE TABLE tiles(
-tile_set INTEGER REFERENCES tilesets (id) ON DELETE CASCADE ON UPDATE CASCADE,
-zoom_level INTEGER NOT NULL,
-tile_column BIGINT NOT NULL,
-tile_row BIGINT NOT NULL,
-tile_data BLOB NOT NULL,
-timestamp INTEGER NOT NULL,
-etag TEXT,
-lastmodified INTEGER,
- PRIMARY KEY(
- tile_set ASC,
- zoom_level ASC,
- tile_column ASC,
- tile_row ASC
- )
-);";
- _sqlite.Execute(cmdCreateTableTiles);
-
- string cmdIdxTileset = "CREATE INDEX idx_tileset ON tiles (tile_set ASC);";
- _sqlite.Execute(cmdIdxTileset);
- string cmdIdxTimestamp = "CREATE INDEX idx_timestamp ON tiles (timestamp ASC);";
- _sqlite.Execute(cmdIdxTimestamp);
- }
-
-
- // some pragmas to speed things up a bit :-)
- // inserting 1,000 tiles takes 1-2 sec as opposed to ~20 sec
- string[] cmds = new string[]
- {
- "PRAGMA synchronous=OFF",
- "PRAGMA count_changes=OFF",
- "PRAGMA journal_mode=MEMORY",
- "PRAGMA temp_store=MEMORY"
- };
- foreach (var cmd in cmds)
- {
- try
- {
- _sqlite.Execute(cmd);
- }
- catch (SQLiteException ex)
- {
- // workaround for sqlite.net's exeception:
- // https://stackoverflow.com/a/23839503
- if (ex.Result != SQLite3.Result.Row)
- {
- UnityEngine.Debug.LogErrorFormat("{0}: {1}", cmd, ex);
- // TODO: when mapbox-sdk-cs gets backported to its own repo -> throw
- //throw; // to throw or not to throw???
- }
- }
- }
- }
-
-
- private void openOrCreateDb(string dbName)
- {
- _dbPath = GetFullDbPath(dbName);
- _sqlite = new SQLiteConnection(_dbPath, SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.Create);
+ CreateTables();
+ PragmaCommands();
}
-
///
/// Reinitialize cache.
/// This is needed after 'Clear()' to recreate the cache database.
@@ -191,6 +121,11 @@ public void ReInit()
init();
}
+ private void OpenOrCreateDatabase(string dbName)
+ {
+ _dbPath = GetFullDbPath(dbName);
+ _sqlite = new SQLiteConnection(_dbPath, SQLiteOpenFlags.ReadWrite | SQLiteOpenFlags.Create);
+ }
public static string GetFullDbPath(string dbName)
{
@@ -198,17 +133,18 @@ public static string GetFullDbPath(string dbName)
#if UNITY_EDITOR_WIN || UNITY_STANDALONE_WIN || UNITY_WSA
dbPath = Path.GetFullPath(dbPath);
#endif
- if (!Directory.Exists(dbPath)) { Directory.CreateDirectory(dbPath); }
+ if (!Directory.Exists(dbPath))
+ {
+ Directory.CreateDirectory(dbPath);
+ }
+
dbPath = Path.Combine(dbPath, dbName);
return dbPath;
}
-
-
public void Add(string tilesetName, CanonicalTileId tileId, CacheItem item, bool forceInsert = false)
{
-
#if MAPBOX_DEBUG_CACHE
string methodName = _className + "." + new System.Diagnostics.StackFrame().GetMethod().Name;
UnityEngine.Debug.LogFormat("{0} {1} {2} forceInsert:{3}", methodName, tileset, tileId, forceInsert);
@@ -224,15 +160,7 @@ public void Add(string tilesetName, CanonicalTileId tileId, CacheItem item, bool
return;
}
- int? tilesetId = null;
- lock (_lock)
- {
- tilesetId = getTilesetId(tilesetName);
- if (!tilesetId.HasValue)
- {
- tilesetId = insertTileset(tilesetName);
- }
- }
+ int? tilesetId = GetOrCraeteTileset(tilesetName);
if (tilesetId < 0)
{
@@ -240,17 +168,27 @@ public void Add(string tilesetName, CanonicalTileId tileId, CacheItem item, bool
return;
}
- int rowsAffected = _sqlite.InsertOrReplace(new tiles
+ var newTile = new tiles
{
tile_set = tilesetId.Value,
zoom_level = tileId.Z,
tile_column = tileId.X,
tile_row = tileId.Y,
tile_data = item.Data,
- timestamp = (int)UnixTimestampUtils.To(DateTime.Now),
- etag = item.ETag
- });
- if (1 != rowsAffected)
+ expirationdate = (int) UnixTimestampUtils.To(item.ExpirationDate),
+ etag = item.ETag,
+ accessed = (int) UnixTimestampUtils.To(DateTime.Now)
+ };
+ int rowsAffected = UpdateTile(newTile);
+ if (rowsAffected == 0)
+ {
+ rowsAffected = (int) InsertTile(newTile);
+ if (rowsAffected > 0)
+ {
+ _pruneCacheCounter++;
+ }
+ }
+ if (rowsAffected < 1)
{
throw new Exception(string.Format("tile [{0} / {1}] was not inserted, rows affected:{2}", tilesetName, tileId, rowsAffected));
}
@@ -260,49 +198,92 @@ public void Add(string tilesetName, CanonicalTileId tileId, CacheItem item, bool
Debug.LogErrorFormat("Error inserting {0} {1} {2} ", tilesetName, tileId, ex);
}
- // update counter only when new tile gets inserted
- if (!forceInsert)
- {
- _pruneCacheCounter++;
- }
if (0 == _pruneCacheCounter % _pruneCacheDelta)
{
_pruneCacheCounter = 0;
- prune();
+ //prune();
+ pruneNonOfflineTiles();
}
}
-
- private void prune()
+ private int? GetOrCraeteTileset(string tilesetName)
{
+ int? tilesetId;
+ lock (_lock)
+ {
+ tilesetId = getTilesetId(tilesetName);
+ if (!tilesetId.HasValue)
+ {
+ tilesetId = insertTileset(tilesetName);
+ }
+ }
- long tileCnt = _sqlite.ExecuteScalar("SELECT COUNT(zoom_level) FROM tiles");
-
- if (tileCnt < _maxTileCount) { return; }
-
- long toDelete = tileCnt - _maxTileCount;
+ return tilesetId;
+ }
-#if MAPBOX_DEBUG_CACHE
- string methodName = _className + "." + new System.Diagnostics.StackFrame().GetMethod().Name;
- Debug.LogFormat("{0} {1} about to prune()", methodName, _tileset);
-#endif
+ private void pruneNonOfflineTiles()
+ {
+ long tileCnt = _sqlite.ExecuteScalar("SELECT COUNT(id) FROM (SELECT id FROM tiles LEFT JOIN tile2offline ON id = tileId WHERE tileId IS NULL)");
- try
+ if (tileCnt > MaxCacheSize)
{
- // no 'ORDER BY' or 'LIMIT' possible if sqlite hasn't been compiled with 'SQLITE_ENABLE_UPDATE_DELETE_LIMIT'
- // https://sqlite.org/compile.html#enable_update_delete_limit
- _sqlite.Execute("DELETE FROM tiles WHERE rowid IN ( SELECT rowid FROM tiles ORDER BY timestamp ASC LIMIT ? );", toDelete);
+ var query = "SELECT max(accessed) " +
+ "FROM ( " +
+ " SELECT accessed " +
+ " FROM tiles " +
+ " LEFT JOIN tile2offline " +
+ " ON tileId = tiles.id " +
+ " WHERE tileId IS NULL " +
+ " ORDER BY accessed ASC LIMIT ?1 " +
+ ") ";
+
+ var command = _sqlite.CreateCommand(query, 5);
+ var accessed = command.ExecuteScalar();
+
+ var tileQuery = "DELETE FROM tiles " +
+ "WHERE id IN ( " +
+ " SELECT id FROM tiles " +
+ " LEFT JOIN tile2offline " +
+ " ON tileId = tiles.id " +
+ " WHERE tileId IS NULL " +
+ " AND accessed <= ?1 " +
+ ") ";
+ var tileCommand = _sqlite.CreateCommand(tileQuery, accessed);
+ var rowChanged = tileCommand.ExecuteNonQuery();
}
- catch (Exception ex)
- {
- Debug.LogErrorFormat("error pruning: {0}", ex);
- }
- }
+//
+//
+// long tileCnt = _sqlite.ExecuteScalar("SELECT COUNT(zoom_level) FROM tiles");
+//
+// if (tileCnt < _maxTileCount)
+// {
+// return;
+// }
+//
+// long toDelete = tileCnt - _maxTileCount;
+//
+// #if MAPBOX_DEBUG_CACHE
+// string methodName = _className + "." + new System.Diagnostics.StackFrame().GetMethod().Name;
+// Debug.LogFormat("{0} {1} about to prune()", methodName, _tileset);
+// #endif
+//
+// try
+// {
+// // no 'ORDER BY' or 'LIMIT' possible if sqlite hasn't been compiled with 'SQLITE_ENABLE_UPDATE_DELETE_LIMIT'
+// // https://sqlite.org/compile.html#enable_update_delete_limit
+// _sqlite.Execute("DELETE FROM tiles WHERE rowid IN ( SELECT rowid FROM tiles ORDER BY timestamp ASC LIMIT ? );", toDelete);
+// }
+// catch (Exception ex)
+// {
+// Debug.LogErrorFormat("error pruning: {0}", ex);
+// }
+ }
///
/// Returns the tile data, otherwise null
///
+ /// Name of the tileset/style requested
/// Canonical tile id to identify the tile
/// tile data as byte[], if tile is not cached returns null
public CacheItem Get(string tilesetName, CanonicalTileId tileId)
@@ -328,7 +309,7 @@ public CacheItem Get(string tilesetName, CanonicalTileId tileId)
&& t.zoom_level == tileId.Z
&& t.tile_column == tileId.X
&& t.tile_row == tileId.Y
- )
+ )
.FirstOrDefault();
}
catch (Exception ex)
@@ -336,60 +317,220 @@ public CacheItem Get(string tilesetName, CanonicalTileId tileId)
Debug.LogErrorFormat("error getting tile {1} {2} from cache{0}{3}", Environment.NewLine, tilesetName, tileId, ex);
return null;
}
+
if (null == tile)
{
return null;
}
- DateTime? lastModified = null;
- if (tile.lastmodified.HasValue) { lastModified = UnixTimestampUtils.From((double)tile.lastmodified.Value); }
-
return new CacheItem()
{
Data = tile.tile_data,
AddedToCacheTicksUtc = tile.timestamp,
- ETag = tile.etag,
- LastModified = lastModified
+ ETag = tile.etag
};
}
-
///
/// Check if tile exists
///
+ /// Name of the tileset/style requested
/// Canonical tile id
/// True if tile exists
public bool TileExists(string tilesetName, CanonicalTileId tileId)
+ {
+ var query = "SELECT length(tile_data) " +
+ "FROM tiles " +
+ "WHERE tile_set = ?1 " +
+ " AND zoom_level = ?2 " +
+ " AND tile_column = ?3 " +
+ " AND tile_row = ?4 " +
+ "LIMIT 1";
+ var countCommand = _sqlite.CreateCommand(query,
+ tilesetName,
+ tileId.Z,
+ tileId.X,
+ tileId.Y);
+ var count = countCommand.ExecuteScalar();
+
+ return count > 0;
+ }
+
+ ///
+ /// FOR INTERNAL DEBUGGING ONLY - DON'T RELY ON IN PRODUCTION
+ ///
+ ///
+ ///
+ public long TileCount(string tilesetName)
{
int? tilesetId = getTilesetId(tilesetName);
if (!tilesetId.HasValue)
{
- return false;
+ return 0;
}
- return null != _sqlite
+ return _sqlite
.Table()
- .Where(t =>
- t.tile_set == tilesetId.Value
- && t.zoom_level == tileId.Z
- && t.tile_column == tileId.X
- && t.tile_row == tileId.Y
- )
- .FirstOrDefault();
+ .Where(t => t.tile_set == tilesetId.Value)
+ .LongCount();
+ }
+
+ public int GetAmbientTileCount()
+ {
+ return _sqlite.ExecuteScalar("SELECT COUNT(id) FROM (SELECT id FROM tiles LEFT JOIN tile2offline ON id = tileId WHERE tileId IS NULL)");
}
+ public int GetOfflineTileCount()
+ {
+ return _sqlite.ExecuteScalar("SELECT COUNT(id) FROM (SELECT id FROM tiles LEFT JOIN tile2offline ON id = tileId WHERE tileId IS NOT NULL)");
+ }
+
+ public int GetOfflineTileCount(string offlineMapName)
+ {
+ var query = "SELECT COUNT(tileId) FROM tile2offline WHERE mapId = (SELECT id FROM offlinemaps WHERE name = ?1)";
+ var command = _sqlite.CreateCommand(query, offlineMapName);
+ return command.ExecuteScalar();
+ }
+
+ public int GetOfflineDataSize(int offlineMapId)
+ {
+ var query = "SELECT SUM(LENGTH(tile_data)) " +
+ "FROM tile2offline, tiles " +
+ "WHERE mapId = ?1 " +
+ "AND tileId = tiles.id ";
+ var command = _sqlite.CreateCommand(query, offlineMapId);
+ return command.ExecuteScalar();
+ }
+
+ public int GetOfflineDataSize(string offlineMapName)
+ {
+ var query = "SELECT SUM(LENGTH(tile_data)) " +
+ "FROM tile2offline, tiles " +
+ "WHERE mapId = (SELECT id FROM offlinemaps WHERE name = ?1) " +
+ "AND tileId = tiles.id ";
+ var command = _sqlite.CreateCommand(query, offlineMapName);
+ return command.ExecuteScalar();
+ }
+
+ public void ClearAmbientCache()
+ {
+ var query = "DELETE FROM tiles WHERE id NOT IN ( SELECT tileId FROM tile2offline)";
+ var clearAmbientCommand = _sqlite.CreateCommand(query);
+ clearAmbientCommand.ExecuteNonQuery();
+ }
+
+ public void Clear(string tilesetName)
+ {
+
+ }
+
+ ///
+ /// Delete the database file.
+ /// Call 'ReInit()' if you intend to continue using the cache after 'Clear()!
+ ///
+ public void Clear()
+ {
+ //already disposed
+ if (null == _sqlite)
+ {
+ return;
+ }
+
+ _sqlite.Close();
+ _sqlite.Dispose();
+ _sqlite = null;
+
+ Debug.LogFormat("deleting {0}", _dbPath);
+
+ // try several times in case SQLite needs a bit more time to dispose
+ for (int i = 0; i < 5; i++)
+ {
+ try
+ {
+ File.Delete(_dbPath);
+ return;
+ }
+ catch
+ {
+#if !WINDOWS_UWP
+ System.Threading.Thread.Sleep(100);
+#else
+ System.Threading.Tasks.Task.Delay(100).Wait();
+#endif
+ }
+ }
+
+ // if we got till here, throw on last try
+ File.Delete(_dbPath);
+ }
+
+ public void MarkOffline(int offlineMapId, string tilesetName, CanonicalTileId tileId)
+ {
+ try
+ {
+ var query = "INSERT OR IGNORE INTO tile2offline (mapId, tileId)" +
+ "SELECT ?1, tiles.id " +
+ "FROM tiles " +
+ "WHERE tile_set = (SELECT id FROM tilesets WHERE name = ?2) " +
+ " AND zoom_level = ?3 " +
+ " AND tile_column = ?4 " +
+ " AND tile_row = ?5";
+ var command = _sqlite.CreateCommand(query,
+ offlineMapId,
+ tilesetName,
+ tileId.Z,
+ tileId.X,
+ tileId.Y);
+ command.ExecuteNonQuery();
+ }
+ catch (Exception ex)
+ {
+ Debug.LogErrorFormat("Error inserting {0} {1} {2} ", offlineMapId, tileId, ex);
+ }
+ }
+
+ public void DeleteOfflineMap(int offlineMapId)
+ {
+ var query = "DELETE FROM offlinemaps WHERE id = ?";
+ var command = _sqlite.CreateCommand(query, offlineMapId);
+ command.ExecuteNonQuery();
+ }
+
+ public void DeleteOfflineMap(string offlineMapName)
+ {
+ var query = "DELETE FROM offlinemaps WHERE name = ?";
+ var command = _sqlite.CreateCommand(query, offlineMapName);
+ command.ExecuteNonQuery();
+ }
+
+
+
+ public Dictionary GetOfflineMapList()
+ {
+ var mapList = new Dictionary();
+
+ var maps = _sqlite.Table().ToList();
+
+ foreach (var offlineMap in maps)
+ {
+ mapList.Add(offlineMap.name, _sqlite.Table().Where(x => x.mapId == offlineMap.id).Count());
+ }
+
+ return mapList;
+ }
private int insertTileset(string tilesetName)
{
try
{
_sqlite.BeginTransaction(true);
- tilesets newTileset = new tilesets { name = tilesetName };
+ tilesets newTileset = new tilesets {name = tilesetName};
int rowsAffected = _sqlite.Insert(newTileset);
if (1 != rowsAffected)
{
throw new Exception(string.Format("tileset [{0}] was not inserted, rows affected:{1}", tilesetName, rowsAffected));
}
+
return newTileset.id;
}
catch (Exception ex)
@@ -403,83 +544,201 @@ private int insertTileset(string tilesetName)
}
}
-
private int? getTilesetId(string tilesetName)
{
tilesets tileset = _sqlite
.Table()
.Where(ts => ts.name.Equals(tilesetName))
.FirstOrDefault();
- return null == tileset ? (int?)null : tileset.id;
+ return null == tileset ? (int?) null : tileset.id;
}
+ private int insertOfflineMap(string offlineMapName)
+ {
+ try
+ {
+ _sqlite.BeginTransaction(true);
+ var newOfflineMap = new offlineMaps() {name = offlineMapName};
+ int rowsAffected = _sqlite.Insert(newOfflineMap);
+ if (1 != rowsAffected)
+ {
+ throw new Exception(string.Format("tileset [{0}] was not inserted, rows affected:{1}", offlineMapName, rowsAffected));
+ }
- ///
- /// FOR INTERNAL DEBUGGING ONLY - DON'T RELY ON IN PRODUCTION
- ///
- ///
- ///
- public long TileCount(string tilesetName)
+ return newOfflineMap.id;
+ }
+ catch (Exception ex)
+ {
+ Debug.LogErrorFormat("could not insert offlinemaps [{0}]: {1}", offlineMapName, ex);
+ return -1;
+ }
+ finally
+ {
+ _sqlite.Commit();
+ }
+ }
+
+ private int? getOfflineMapId(string offlineMapName)
{
- int? tilesetId = getTilesetId(tilesetName);
- if (!tilesetId.HasValue) { return 0; }
+ var offlineMap = _sqlite
+ .Table()
+ .Where(ts => ts.name.Equals(offlineMapName))
+ .FirstOrDefault();
+ return null == offlineMap ? (int?) null : offlineMap.id;
+ }
- return _sqlite
- .Table()
- .Where(t => t.tile_set == tilesetId.Value)
- .LongCount();
+ public int GetOrAddOfflineMapId(string offlineMapName)
+ {
+ int? offlineMapId;
+ offlineMapId = getOfflineMapId(offlineMapName);
+ if (!offlineMapId.HasValue)
+ {
+ offlineMapId = insertOfflineMap(offlineMapName);
+ }
+
+ return offlineMapId.Value;
}
+ public int UpdateTile(tiles newTile)
+ {
+ var query = "UPDATE tiles " +
+ "SET tile_data = ?1, timestamp = ?2, expirationdate = ?3, etag = ?4, accessed = ?5 " +
+ "WHERE tile_set = ?6 AND zoom_level = ?7 AND tile_column = ?8 AND tile_row = ?9 ";
+ var command = _sqlite.CreateCommand(query,
+ newTile.tile_data,
+ newTile.timestamp,
+ newTile.expirationdate,
+ newTile.etag,
+ newTile.accessed,
+ newTile.tile_set,
+ newTile.zoom_level,
+ newTile.tile_column,
+ newTile.tile_row);
+ return command.ExecuteNonQuery();
+ }
- ///
- /// Clear cache for one tile set
- ///
- ///
- public void Clear(string tilesetName)
+ public long InsertTile(tiles newTile)
{
- int? tilesetId = getTilesetId(tilesetName);
- if (!tilesetId.HasValue) { return; }
- //just delete on table 'tilesets', we've setup cascading which should take care of tabls 'tiles'
- _sqlite.Delete(tilesetId.Value);
+ var query = "INSERT INTO tiles " +
+ "(tile_set, zoom_level, tile_column, tile_row, tile_data, timestamp, expirationdate, etag, accessed)" +
+ "VALUES (?1, ?2, ?3, ?4, ?5, ?6, ?7, ?8, ?9)";
+
+ var command = _sqlite.CreateCommand(query,
+ newTile.tile_set,
+ newTile.zoom_level,
+ newTile.tile_column,
+ newTile.tile_row,
+ newTile.tile_data,
+ newTile.timestamp,
+ newTile.expirationdate,
+ newTile.etag,
+ newTile.accessed);
+ var rowsChanged = command.ExecuteNonQuery();
+ if (rowsChanged > 0)
+ {
+ newTile.id = (int) SQLite3.LastInsertRowid(_sqlite.Handle);
+ }
+
+ return rowsChanged;
}
- ///
- /// Delete the database file.
- /// Call 'ReInit()' if you intend to continue using the cache after 'Clear()!
- ///
- public void Clear()
+
+ private void CreateTables()
{
- //already disposed
- if (null == _sqlite) { return; }
+ List colInfoTileset = _sqlite.GetTableInfo(typeof(tilesets).Name);
+ if (0 == colInfoTileset.Count)
+ {
+ string cmdCreateTableTilesets = @"CREATE TABLE tilesets(
+id INTEGER PRIMARY KEY ASC AUTOINCREMENT NOT NULL UNIQUE,
+name STRING NOT NULL
+);";
+ _sqlite.Execute(cmdCreateTableTilesets);
+ string cmdCreateIdxNames = @"CREATE UNIQUE INDEX idx_names ON tilesets (name ASC);";
+ _sqlite.Execute(cmdCreateIdxNames);
+ }
- _sqlite.Close();
- _sqlite.Dispose();
- _sqlite = null;
+ List colInfoTiles = _sqlite.GetTableInfo(typeof(tiles).Name);
+ if (0 == colInfoTiles.Count)
+ {
+ string cmdCreateTableTiles = @"CREATE TABLE tiles(
+id INTEGER PRIMARY KEY ASC AUTOINCREMENT NOT NULL UNIQUE,
+tile_set INTEGER REFERENCES tilesets (id) ON DELETE CASCADE ON UPDATE CASCADE,
+zoom_level INTEGER NOT NULL,
+tile_column BIGINT NOT NULL,
+tile_row BIGINT NOT NULL,
+tile_data BLOB NOT NULL,
+timestamp INTEGER NOT NULL,
+expirationdate INTEGER NOT NULL,
+etag TEXT,
+accessed INTEGER NOT NULL,
+CONSTRAINT tileConstraint UNIQUE (tile_set, zoom_level, tile_column, tile_row)
+);";
+ _sqlite.Execute(cmdCreateTableTiles);
- Debug.LogFormat("deleting {0}", _dbPath);
+ string cmdIdxTileset = "CREATE INDEX idx_tileset ON tiles (tile_set ASC);";
+ _sqlite.Execute(cmdIdxTileset);
+ string cmdIdxTimestamp = "CREATE INDEX idx_timestamp ON tiles (timestamp ASC);";
+ _sqlite.Execute(cmdIdxTimestamp);
+ }
- // try several times in case SQLite needs a bit more time to dispose
- for (int i = 0; i < 5; i++)
+
+ List colInfoOfflineMaps = _sqlite.GetTableInfo(typeof(offlineMaps).Name);
+ if (0 == colInfoOfflineMaps.Count)
+ {
+ string cmdCreateTableOfflineMaps = @"CREATE TABLE offlinemaps(
+id INTEGER PRIMARY KEY ASC AUTOINCREMENT NOT NULL UNIQUE,
+name STRING NOT NULL
+);";
+ _sqlite.Execute(cmdCreateTableOfflineMaps);
+ string cmdCreateIdxOfflineMapNames = @"CREATE UNIQUE INDEX idx_offlineMapNames ON offlinemaps (name ASC);";
+ _sqlite.Execute(cmdCreateIdxOfflineMapNames);
+ }
+
+ List colInfoTileToOffline = _sqlite.GetTableInfo(typeof(tile2offline).Name);
+ if (0 == colInfoTileToOffline.Count)
+ {
+ string cmdCreateTableTile2Offline = @"CREATE TABLE tile2offline(
+tileId INTEGER NOT NULL,
+mapId INTEGER NOT NULL,
+CONSTRAINT tileAssignmentConstraint UNIQUE (tileId, mapId)
+);";
+ _sqlite.Execute(cmdCreateTableTile2Offline);
+ string cmdCreateIdxOfflineMap2Tiles = @"CREATE UNIQUE INDEX idx_offlineMapToTiles ON tile2offline (tileId, mapId ASC);";
+ _sqlite.Execute(cmdCreateIdxOfflineMap2Tiles);
+ }
+ }
+
+ private void PragmaCommands()
+ {
+ // some pragmas to speed things up a bit :-)
+ // inserting 1,000 tiles takes 1-2 sec as opposed to ~20 sec
+ string[] cmds = new string[]
+ {
+ "PRAGMA synchronous=OFF",
+ "PRAGMA count_changes=OFF",
+ "PRAGMA journal_mode=MEMORY",
+ "PRAGMA temp_store=MEMORY"
+ };
+ foreach (var cmd in cmds)
{
try
{
- File.Delete(_dbPath);
- return;
+ _sqlite.Execute(cmd);
}
- catch
+ catch (SQLiteException ex)
{
-#if !WINDOWS_UWP
- System.Threading.Thread.Sleep(100);
-#else
- System.Threading.Tasks.Task.Delay(100).Wait();
-#endif
+ // workaround for sqlite.net's exeception:
+ // https://stackoverflow.com/a/23839503
+ if (ex.Result != SQLite3.Result.Row)
+ {
+ UnityEngine.Debug.LogErrorFormat("{0}: {1}", cmd, ex);
+ // TODO: when mapbox-sdk-cs gets backported to its own repo -> throw
+ //throw; // to throw or not to throw???
+ }
}
}
-
- // if we got till here, throw on last try
- File.Delete(_dbPath);
}
}
-}
+}
\ No newline at end of file
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tiles.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tiles.cs
index 18629526b..30d50aa6f 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tiles.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tiles.cs
@@ -1,4 +1,5 @@
-using System.Collections;
+using System;
+using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using SQLite4Unity3d;
@@ -11,6 +12,8 @@ namespace Mapbox.Platform.Cache
///
public class tiles
{
+ [PrimaryKey, AutoIncrement]
+ public int id { get; set; }
public int tile_set { get; set; }
@@ -34,7 +37,23 @@ public class tiles
/// ETag Header value of the reponse for auto updating cache
public string etag { get; set; }
- /// Last-Modified header value of API response. Not all APIs populate it, will be -1 in that case.
- public int? lastmodified { get; set; }
+ /// Last time entry accessed
+ public int accessed { get; set; }
+
+ /// datetime when tile forced to update
+ public int expirationdate { get; set; }
+ }
+
+ public class offlineMaps
+ {
+ [PrimaryKey, AutoIncrement]
+ public int id { get; set; }
+ public string name { get; set; }
+ }
+
+ public class tile2offline
+ {
+ public int tileId { get; set; }
+ public int mapId { get; set; }
}
}
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tilesets.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tilesets.cs
index ebd47aa28..9c809b739 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tilesets.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Cache/SQLiteCache/Tilesets.cs
@@ -20,4 +20,10 @@ public class tilesets
public string name { get; set; }
}
+
+ public class sqlite_sequence
+ {
+ public string name { get; set; }
+ public int seq { get; set; }
+ }
}
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/FileSource.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/FileSource.cs
index 3225832c1..5070aac02 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/FileSource.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/FileSource.cs
@@ -27,6 +27,7 @@ namespace Mapbox.Platform
#endif
#if UNITY_5_3_OR_NEWER
using UnityEngine;
+
#endif
///
@@ -40,7 +41,6 @@ namespace Mapbox.Platform
///
public sealed class FileSource : IFileSource
{
-
private Func _getMapsSkuToken;
private readonly Dictionary _requests = new Dictionary();
private readonly string _accessToken;
@@ -49,8 +49,10 @@ public sealed class FileSource : IFileSource
/// Length of rate-limiting interval in seconds. https://www.mapbox.com/api-documentation/#rate-limit-headers
#pragma warning disable 0414
private int? XRateLimitInterval;
+
/// Maximum number of requests you may make in the current interval before reaching the limit. https://www.mapbox.com/api-documentation/#rate-limit-headers
private long? XRateLimitLimit;
+
/// Timestamp of when the current interval will end and the ratelimit counter is reset. https://www.mapbox.com/api-documentation/#rate-limit-headers
private DateTime? XRateLimitReset;
#pragma warning restore 0414
@@ -59,14 +61,7 @@ public sealed class FileSource : IFileSource
public FileSource(Func getMapsSkuToken, string acessToken = null)
{
_getMapsSkuToken = getMapsSkuToken;
- if (string.IsNullOrEmpty(acessToken))
- {
- _accessToken = Environment.GetEnvironmentVariable("MAPBOX_ACCESS_TOKEN");
- }
- else
- {
- _accessToken = acessToken;
- }
+ _accessToken = acessToken;
}
/// Performs a request asynchronously.
@@ -92,7 +87,8 @@ string url
string skuToken = "sku=" + _getMapsSkuToken();
if (uriBuilder.Query != null && uriBuilder.Query.Length > 1)
{
- uriBuilder.Query = uriBuilder.Query.Substring(1) + "&" + accessTokenQuery + "&" + skuToken;;
+ uriBuilder.Query = uriBuilder.Query.Substring(1) + "&" + accessTokenQuery + "&" + skuToken;
+ ;
}
else
{
@@ -127,16 +123,27 @@ string url
, string tilesetId
)
{
-
// TODO: plugin caching somewhere around here
var request = IAsyncRequestFactory.CreateRequest(
url
, (Response response) =>
{
- if (response.XRateLimitInterval.HasValue) { XRateLimitInterval = response.XRateLimitInterval; }
- if (response.XRateLimitLimit.HasValue) { XRateLimitLimit = response.XRateLimitLimit; }
- if (response.XRateLimitReset.HasValue) { XRateLimitReset = response.XRateLimitReset; }
+ if (response.XRateLimitInterval.HasValue)
+ {
+ XRateLimitInterval = response.XRateLimitInterval;
+ }
+
+ if (response.XRateLimitLimit.HasValue)
+ {
+ XRateLimitLimit = response.XRateLimitLimit;
+ }
+
+ if (response.XRateLimitReset.HasValue)
+ {
+ XRateLimitReset = response.XRateLimitReset;
+ }
+
callback(response);
lock (_lock)
{
@@ -161,6 +168,7 @@ string url
_requests.Add(request, 0);
}
}
+
//yield return request;
return request;
}
@@ -193,13 +201,13 @@ public IEnumerator WaitForAllRequests()
}
}
}
+
yield return new WaitForSeconds(0.2f);
}
}
#endif
-
#if !UNITY_5_3_OR_NEWER
///
/// Block until all the requests are processed.
@@ -252,4 +260,4 @@ public void WaitForAllRequests()
}
#endif
}
-}
+}
\ No newline at end of file
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/IAsyncRequestFactory.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/IAsyncRequestFactory.cs
index 195d1e428..01e6e72e2 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/IAsyncRequestFactory.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/IAsyncRequestFactory.cs
@@ -34,6 +34,22 @@ string url
#endif
}
-
+ public static IAsyncRequest CreateRequest(
+ string url
+ , int timeout
+ , string headerName
+ , string headerValue
+ , Action callback
+ ) {
+#if !UNITY
+ if (Environment.ProcessorCount > 2) {
+ return new HTTPRequestThreaded(url, callback, timeout);
+ } else {
+ return new HTTPRequestNonThreaded(url, callback, timeout);
+ }
+#else
+ return new Mapbox.Unity.Utilities.HTTPRequest(url, callback, timeout, headerName, headerValue);
+#endif
+ }
}
}
\ No newline at end of file
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Response.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Response.cs
index 5735aa7ca..2c5ded836 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Response.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/Response.cs
@@ -315,7 +315,7 @@ public static Response FromWebResponse(IAsyncRequest request, UnityWebRequest ap
int statusCode = (int)apiResponse.responseCode;
response.StatusCode = statusCode;
- if (statusCode != 200)
+ if (statusCode != 200 && statusCode != 304)
{
response.AddException(new Exception(string.Format("Status Code {0}", apiResponse.responseCode)));
}
diff --git a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/SQLite/SQLite.cs b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/SQLite/SQLite.cs
index b28b443c4..008bae6ee 100644
--- a/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/SQLite/SQLite.cs
+++ b/sdkproject/Assets/Mapbox/Core/mapbox-sdk-cs/Platform/SQLite/SQLite.cs
@@ -31,7 +31,7 @@
using System.Linq;
using System.Linq.Expressions;
using System.Threading;
-
+using Mapbox.Platform.Cache;
#if USE_CSHARP_SQLITE
using Sqlite3 = Community.CsharpSqlite.Sqlite3;
using Sqlite3DatabaseHandle = Community.CsharpSqlite.Sqlite3.sqlite3;
@@ -281,12 +281,12 @@ public IEnumerable TableMappings
///
///
/// The type whose mapping to the database is returned.
- ///
+ ///
///
/// Optional flags allowing implicit PK and indexes based on naming conventions
- ///
+ ///
///
- /// The mapping represents the schema of the columns of the database and contains
+ /// The mapping represents the schema of the columns of the database and contains
/// methods to set and get properties of objects.
///
public TableMapping GetMapping(Type type, CreateFlags createFlags = CreateFlags.None)
@@ -308,7 +308,7 @@ public TableMapping GetMapping(Type type, CreateFlags createFlags = CreateFlags.
/// Retrieves the mapping that is automatically generated for the given type.
///
///
- /// The mapping represents the schema of the columns of the database and contains
+ /// The mapping represents the schema of the columns of the database and contains
/// methods to set and get properties of objects.
///
public TableMapping GetMapping()
@@ -363,7 +363,7 @@ public int CreateTable(CreateFlags createFlags = CreateFlags.None)
/// later access this schema by calling GetMapping.
///
/// Type to reflect to a database table.
- /// Optional flags allowing implicit PK and indexes based on naming conventions.
+ /// Optional flags allowing implicit PK and indexes based on naming conventions.
///
/// The number of entries added to the database schema.
///
@@ -805,7 +805,7 @@ public IEnumerable