From c43bfb51be5c0d70a0a5d9822d589543ceaf7dde Mon Sep 17 00:00:00 2001 From: gaoyuan <gaoyuan@gaoyuandeMacBook-Air.local> Date: Sat, 12 Mar 2022 01:08:17 +0800 Subject: [PATCH] fix crash of sqlite in release mode --- Billing.Shared/App.cs | 10 +- Billing.Shared/Helper.cs | 8 +- Billing.Shared/Store/StoreHelper.cs | 154 ++++++++++-------- .../Billing.Android/Billing.Android.csproj | 1 - .../Properties/AndroidManifest.xml | 2 +- Billing/Billing.iOS/Billing.iOS.csproj | 14 +- Billing/Billing.iOS/Info.plist | 32 ++-- 7 files changed, 118 insertions(+), 103 deletions(-) diff --git a/Billing.Shared/App.cs b/Billing.Shared/App.cs index 9cddec6..3f52985 100644 --- a/Billing.Shared/App.cs +++ b/Billing.Shared/App.cs @@ -30,7 +30,6 @@ namespace Billing InitResources(); MainPage = new MainShell(); - //Shell.Current.GoToAsync("//Splash"); } protected override void OnStart() @@ -39,12 +38,13 @@ namespace Billing Helper.Debug($"cache folder: {StoreHelper.CacheFolder}"); } - internal static async Task InitializeData() + public static async Task InitializeData() { + var instance = await StoreHelper.Instance; await Task.WhenAll( - Task.Run(async () => accounts = await StoreHelper.GetAccountsAsync()), - Task.Run(async () => categories = await StoreHelper.GetCategoriesAsync()), - Task.Run(async () => bills = await StoreHelper.GetBillsAsync())); + Task.Run(async () => accounts = await instance.GetListAsync<Account>()), + Task.Run(async () => categories = await instance.GetListAsync<Category>()), + Task.Run(async () => bills = await instance.GetListAsync<Bill>())); } protected override void OnResume() diff --git a/Billing.Shared/Helper.cs b/Billing.Shared/Helper.cs index b4fd510..3ee9136 100644 --- a/Billing.Shared/Helper.cs +++ b/Billing.Shared/Helper.cs @@ -39,6 +39,7 @@ namespace Billing public static void Error(string category, Exception ex) { + MainThread.BeginInvokeOnMainThread(async () => await Shell.Current.DisplayAlert(category, ex.ToString(), "Ok")); } public static void Error(string category, string message) @@ -139,15 +140,10 @@ namespace Billing public delegate void PropertyValueChanged<TResult, TOwner>(TOwner obj, TResult old, TResult @new); } - internal class AsyncLazy<T> + public class AsyncLazy<T> { private readonly Lazy<Task<T>> instance; - public AsyncLazy(Func<T> factory) - { - instance = new Lazy<Task<T>>(() => Task.Run(factory)); - } - public AsyncLazy(Func<Task<T>> factory) { instance = new Lazy<Task<T>>(() => Task.Run(factory)); diff --git a/Billing.Shared/Store/StoreHelper.cs b/Billing.Shared/Store/StoreHelper.cs index 2ad5562..a864f65 100644 --- a/Billing.Shared/Store/StoreHelper.cs +++ b/Billing.Shared/Store/StoreHelper.cs @@ -28,68 +28,97 @@ namespace Billing.Store { return false; } - if (database != null) + try { - await database.CloseAsync(); + if (database != null) + { + await database.CloseAsync(); + } + } + catch (Exception ex) + { + Helper.Error("database.close", ex); + } + try + { + File.Copy(file, path, true); + } + catch (Exception ex) + { + Helper.Error("file.import", ex); + } + try + { + database = new SQLiteAsyncConnection(path, + SQLiteOpenFlags.ReadWrite | + SQLiteOpenFlags.Create | + SQLiteOpenFlags.SharedCache); + } + catch (Exception ex) + { + Helper.Error("database.connect", ex); } - File.Copy(file, path, true); - database = new SQLiteAsyncConnection(path, - SQLiteOpenFlags.ReadWrite | - SQLiteOpenFlags.Create | - SQLiteOpenFlags.SharedCache); return true; } - private static readonly AsyncLazy<StoreHelper> Instance = new(async () => + public static readonly AsyncLazy<StoreHelper> Instance = new(async () => { var instance = new StoreHelper(); - await database.CreateTablesAsync<Category, Account, Bill>(); - var count = await database.ExecuteScalarAsync<int>("SELECT COUNT(Id) FROM [Category]"); - if (count <= 0) + try { - // init categories - await database.InsertAllAsync(new List<Category> + await database.CreateTablesAsync<Category, Account, Bill>(); + } catch (Exception ex) + { + Helper.Error("database.init.table", ex); + } + try + { + var count = await database.ExecuteScalarAsync<int>("SELECT COUNT(Id) FROM [Category]"); + if (count <= 0) { - // sample categories - new() { Name = Resource.Clothing, Icon = "clothes" }, - new() { Name = Resource.Food, Icon = "food" }, - new() { Name = Resource.Daily, Icon = "daily" }, - new() { Name = Resource.Trans, Icon = "trans" }, - new() { Name = Resource.Entertainment, Icon = "face" }, - new() { Name = Resource.Learn, Icon = "learn" }, - new() { Name = Resource.Medical, Icon = "medical" }, - new() { Name = Resource.OtherSpending, Icon = "plus" }, + // init categories + await database.InsertAllAsync(new List<Category> + { + // sample categories + new() { Name = Resource.Clothing, Icon = "clothes" }, + new() { Name = Resource.Food, Icon = "food" }, + new() { Name = Resource.Daily, Icon = "daily" }, + new() { Name = Resource.Trans, Icon = "trans" }, + new() { Name = Resource.Entertainment, Icon = "face" }, + new() { Name = Resource.Learn, Icon = "learn" }, + new() { Name = Resource.Medical, Icon = "medical" }, + new() { Name = Resource.OtherSpending, Icon = "plus" }, - new() { Type = CategoryType.Income, Name = Resource.Earnings, Icon = "#brand#btc" }, - new() { Type = CategoryType.Income, Name = Resource.OtherIncome, Icon = "plus" }, + new() { Type = CategoryType.Income, Name = Resource.Earnings, Icon = "#brand#btc" }, + new() { Type = CategoryType.Income, Name = Resource.OtherIncome, Icon = "plus" }, - // sub-categories - new() { ParentId = 1, Name = Resource.Jewellery, Icon = "gem" }, - new() { ParentId = 1, Name = Resource.Cosmetics, Icon = "makeup" }, - new() { ParentId = 2, Name = Resource.Brunch, Icon = "brunch" }, - new() { ParentId = 2, Name = Resource.Dinner, Icon = "dinner" }, - new() { ParentId = 2, Name = Resource.Drinks, Icon = "drink" }, - new() { ParentId = 2, Name = Resource.Fruit, Icon = "fruit" }, - new() { ParentId = 3, Name = Resource.UtilityBill, Icon = "bill" }, - new() { ParentId = 3, Name = Resource.PropertyFee, Icon = "fee" }, - new() { ParentId = 3, Name = Resource.Rent, Icon = "rent" }, - new() { ParentId = 3, Name = Resource.Maintenance, Icon = "maintenance" }, - new() { ParentId = 4, Name = Resource.LightRail, Icon = "rail" }, - new() { ParentId = 4, Name = Resource.Taxi, Icon = "taxi" }, - new() { ParentId = 5, Name = Resource.Fitness, Icon = "fitness" }, - new() { ParentId = 5, Name = Resource.Party, Icon = "party" }, - new() { ParentId = 9, Type = CategoryType.Income, Name = Resource.Salary, Icon = "#brand#buffer" }, - new() { ParentId = 9, Type = CategoryType.Income, Name = Resource.Bonus, Icon = "dollar" }, - }); + // sub-categories + new() { ParentId = 1, Name = Resource.Jewellery, Icon = "gem" }, + new() { ParentId = 1, Name = Resource.Cosmetics, Icon = "makeup" }, + new() { ParentId = 2, Name = Resource.Brunch, Icon = "brunch" }, + new() { ParentId = 2, Name = Resource.Dinner, Icon = "dinner" }, + new() { ParentId = 2, Name = Resource.Drinks, Icon = "drink" }, + new() { ParentId = 2, Name = Resource.Fruit, Icon = "fruit" }, + new() { ParentId = 3, Name = Resource.UtilityBill, Icon = "bill" }, + new() { ParentId = 3, Name = Resource.PropertyFee, Icon = "fee" }, + new() { ParentId = 3, Name = Resource.Rent, Icon = "rent" }, + new() { ParentId = 3, Name = Resource.Maintenance, Icon = "maintenance" }, + new() { ParentId = 4, Name = Resource.LightRail, Icon = "rail" }, + new() { ParentId = 4, Name = Resource.Taxi, Icon = "taxi" }, + new() { ParentId = 5, Name = Resource.Fitness, Icon = "fitness" }, + new() { ParentId = 5, Name = Resource.Party, Icon = "party" }, + new() { ParentId = 9, Type = CategoryType.Income, Name = Resource.Salary, Icon = "#brand#buffer" }, + new() { ParentId = 9, Type = CategoryType.Income, Name = Resource.Bonus, Icon = "dollar" }, + }); + } + } + catch (Exception ex) + { + Helper.Error("database.init.category", ex); } return instance; }); - public static async Task<List<Account>> GetAccountsAsync() - { - var instance = await Instance; - return await instance.GetListAsync<Account>(); - } public static async Task<int> SaveAccountItemAsync(Account account) { var instance = await Instance; @@ -101,11 +130,6 @@ namespace Billing.Store return await instance.DeleteItemAsync(account); } - public static async Task<List<Bill>> GetBillsAsync() - { - var instance = await Instance; - return await instance.GetListAsync<Bill>(); - } public static async Task<int> SaveBillItemAsync(Bill bill) { var instance = await Instance; @@ -117,11 +141,6 @@ namespace Billing.Store return await instance.DeleteItemAsync(bill); } - public static async Task<List<Category>> GetCategoriesAsync() - { - var instance = await Instance; - return await instance.GetListAsync<Category>(); - } public static async Task<int> SaveCategoryItemAsync(Category category) { var instance = await Instance; @@ -137,10 +156,17 @@ namespace Billing.Store { if (database == null) { - database = new SQLiteAsyncConnection(DatabasePath, - SQLiteOpenFlags.ReadWrite | - SQLiteOpenFlags.Create | - SQLiteOpenFlags.SharedCache); + try + { + database = new SQLiteAsyncConnection(DatabasePath, + SQLiteOpenFlags.ReadWrite | + SQLiteOpenFlags.Create | + SQLiteOpenFlags.SharedCache); + } + catch (Exception ex) + { + Helper.Error("database.ctor.connect", ex); + } } } @@ -178,7 +204,7 @@ namespace Billing.Store #region Helper - private Task<List<T>> GetListAsync<T>() where T : new() + public Task<List<T>> GetListAsync<T>() where T : new() { try { @@ -191,7 +217,7 @@ namespace Billing.Store return default; } - private Task<int> SaveItemAsync<T>(T item) where T : IIdItem + public Task<int> SaveItemAsync<T>(T item) where T : IIdItem { try { @@ -211,7 +237,7 @@ namespace Billing.Store return Task.FromResult(0); } - private Task<int> DeleteItemAsync<T>(T item) where T : IIdItem + public Task<int> DeleteItemAsync<T>(T item) where T : IIdItem { try { diff --git a/Billing/Billing.Android/Billing.Android.csproj b/Billing/Billing.Android/Billing.Android.csproj index 83f151f..f7c92e0 100644 --- a/Billing/Billing.Android/Billing.Android.csproj +++ b/Billing/Billing.Android/Billing.Android.csproj @@ -60,7 +60,6 @@ <Reference Include="System" /> <Reference Include="System.Core" /> <Reference Include="System.Numerics" /> - <Reference Include="System.Numerics.Vectors" /> <Reference Include="System.Xml.Linq" /> <Reference Include="System.Xml" /> </ItemGroup> diff --git a/Billing/Billing.Android/Properties/AndroidManifest.xml b/Billing/Billing.Android/Properties/AndroidManifest.xml index c1fd536..94742bc 100644 --- a/Billing/Billing.Android/Properties/AndroidManifest.xml +++ b/Billing/Billing.Android/Properties/AndroidManifest.xml @@ -1,5 +1,5 @@ <?xml version="1.0" encoding="utf-8"?> -<manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionName="0.10.311" package="org.tsanie.billing" android:installLocation="auto" android:versionCode="10"> +<manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionName="1.0.312" package="org.tsanie.billing" android:installLocation="auto" android:versionCode="11"> <uses-sdk android:minSdkVersion="24" android:targetSdkVersion="30" /> <application android:label="@string/applabel" android:theme="@style/MainTheme"></application> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> diff --git a/Billing/Billing.iOS/Billing.iOS.csproj b/Billing/Billing.iOS/Billing.iOS.csproj index 97d5b5f..12e621d 100644 --- a/Billing/Billing.iOS/Billing.iOS.csproj +++ b/Billing/Billing.iOS/Billing.iOS.csproj @@ -38,6 +38,7 @@ <MtouchLink>None</MtouchLink> <MtouchArch>x86_64</MtouchArch> <CodesignKey>iPhone Distribution</CodesignKey> + <MtouchUseLlvm>true</MtouchUseLlvm> </PropertyGroup> <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|iPhone' "> <DebugSymbols>true</DebugSymbols> @@ -64,6 +65,8 @@ <CodesignKey>iPhone Distribution</CodesignKey> <CodesignEntitlements>Entitlements.plist</CodesignEntitlements> <MtouchLink>SdkOnly</MtouchLink> + <MtouchInterpreter>-all</MtouchInterpreter> + <MtouchUseLlvm>true</MtouchUseLlvm> </PropertyGroup> <ItemGroup> <Compile Include="Definition.cs" /> @@ -166,14 +169,13 @@ <Reference Include="System.Xml.Linq" /> <Reference Include="Xamarin.iOS" /> <Reference Include="System.Numerics" /> - <Reference Include="System.Numerics.Vectors" /> </ItemGroup> <ItemGroup> <PackageReference Include="Microcharts.Forms" Version="0.9.5.9" /> <PackageReference Include="SkiaSharp.Views.Forms" Version="2.80.3" /> + <PackageReference Include="sqlite-net-pcl" Version="1.8.116" /> <PackageReference Include="Xamarin.Forms" Version="5.0.0.2337" /> <PackageReference Include="Xamarin.Essentials" Version="1.7.1" /> - <PackageReference Include="sqlite-net-pcl" Version="1.8.116" /> </ItemGroup> <ItemGroup> <BundleResource Include="Resources\dollar.png" /> @@ -477,14 +479,6 @@ <ItemGroup> <BundleResource Include="Resources\left%403x.png" /> </ItemGroup> - <ItemGroup> - <ProjectReference Include="..\..\Billing.ShareExtension\Billing.ShareExtension.csproj"> - <IsAppExtension>true</IsAppExtension> - <Project>{D4EA6D3A-17E6-4300-80A7-2ED19B738C6B}</Project> - <Name>Billing.ShareExtension</Name> - <ReferenceSourceTarget></ReferenceSourceTarget> - </ProjectReference> - </ItemGroup> <Import Project="..\..\Billing.Shared\Billing.Shared.projitems" Label="Shared" /> <Import Project="$(MSBuildExtensionsPath)\Xamarin\iOS\Xamarin.iOS.CSharp.targets" /> </Project> \ No newline at end of file diff --git a/Billing/Billing.iOS/Info.plist b/Billing/Billing.iOS/Info.plist index 2d44104..6fc8414 100644 --- a/Billing/Billing.iOS/Info.plist +++ b/Billing/Billing.iOS/Info.plist @@ -42,23 +42,23 @@ <string>OpenSans-SemiBold.ttf</string> </array> <key>CFBundleDocumentTypes</key> - <array> - <dict> - <key>CFBundleTypeName</key> - <string>Master SQLite file</string> - <key>LSItemContentTypes</key> - <array> - <string>public.data</string> - </array> - <key>CFBundleTypeIconFiles</key> - <array> - <string>Assets.xcassets/AppIcon.appiconset/Icon180</string> - </array> - </dict> - </array> + <array> + <dict> + <key>CFBundleTypeName</key> + <string>Master SQLite file</string> + <key>LSItemContentTypes</key> + <array> + <string>public.data</string> + </array> + <key>CFBundleTypeIconFiles</key> + <array> + <string>Assets.xcassets/AppIcon.appiconset/Icon180</string> + </array> + </dict> + </array> <key>CFBundleVersion</key> - <string>10</string> + <string>11</string> <key>CFBundleShortVersionString</key> - <string>0.10.311</string> + <string>1.0.312</string> </dict> </plist>