【问题标题】:Bundle prebuilt Realm files from Xamarin从 Xamarin 捆绑预构建的 Realm 文件
【发布时间】:2016-09-26 15:48:32
【问题描述】:

我看过一些 SO 帖子,详细介绍了如何将预构建的 Realm 文件与 iOS (Obj-c/swift) 和 Android (Java) 捆绑在一起,但我找不到任何关于从 PCL 或共享的 Xamarin 捆绑的信息项目;这可能吗?

由于文件在每个平台上的分布方式存在细微差别,我认为它需要每个项目的 *.realm 文件(例如,在编译时从单个源复制),但这是一个很小的代价从两个平台上的共享代码访问预构建数据。

我的目标是在首次启动应用程序时避免初始下载过程。

【问题讨论】:

    标签: xamarin realm


    【解决方案1】:

    对于想要在本机 Xamarin.Android 上捆绑领域文件的任何人,您可以使用以下代码。捆绑的领域文件可以与最终领域文件同名。只需将领域文件复制到 Assets 目录并确保构建操作设置为 AndroidAsset。

    var realmDB = "somerealm.realm";
    var documentsPath = System.Environment.GetFolderPath(System.Environment.SpecialFolder.MyDocuments);
    var filePath = Path.Combine(documentsPath, realmDB);
    if (!File.Exists(filePath))
    {
        using (var asset = Assets.Open(realmDB))
        using (var destination = File.OpenWrite(filePath))
        {
            asset.CopyTo(destination);
        }
    }
    

    【讨论】:

      【解决方案2】:

      此答案适用于 Android,而接受的答案仅适用于 iOS。

      1. 将 prepopulated.realm 文件添加到 PCL 资源文件夹。通过右键单击并选择“Build Action”>“EmbeddedResource”将其标记为嵌入式资源。

      2. 构建应用程序。

      3. 从命令行在您的 dll 文件上运行 monodic --manifest YourApp.dll,该文件在 YourApp/Droid/bin/Debug 中用于调试。找到prepopulated.realm所在的行,复制资源字符串。

      4. 编辑您的 MainActivity.cs 并在 base.OnCreate(savedInstanceState); 行之后添加以下代码。

      【讨论】:

        【解决方案3】:

        您可以将预先填充的 .realm 数据库作为资源 (BundleResource Build Action) 添加到您的应用程序 iOS 包中,并作为原始资产添加到您的 Android 资产目录 (AndroidAsset Build Action)。

        使用 Realm 中基于 Xamarin.FormsJournal 示例,您可以将填充的数据库作为链接项添加到每个本机项目并在应用程序启动时复制它。

        示例:

        如果用户数据库存在(即这是应用程序第一次运行时):

        public override bool FinishedLaunching(UIApplication app, NSDictionary options)
        {
            var prepopulated = "prepopulated.realm";
            var realmDB = "journal.realm";
            var documentsPath = Environment.GetFolderPath(Environment.SpecialFolder.Personal);
            if (!File.Exists(Path.Combine(documentsPath, realmDB)))
            {
                File.Copy(prepopulated, Path.Combine(documentsPath, realmDB));
            }
            global::Xamarin.Forms.Forms.Init();
            LoadApplication(new App());
            return base.FinishedLaunching(app, options);
        }
        

        注意:同样的技术可以用在你的其他“原生”项目中

        注意:自定义编写的 Xamarin.Forms 依赖服务可以替代这种方式,但结果是一样的

        由于我们在应用程序文档目录中将prepopulated.realm 复制到journal.realm,我们可以告诉Realm 打开这个数据库,而不是创建/使用default.realm 一个。

        Xamarin.Form Journal 项目的JournalEntriesViewModel.cs 中,更新代码以打开此journal.realm

        public JournalEntriesViewModel()
        {
            _realm = Realm.GetInstance("journal.realm");
            Entries = _realm.All<JournalEntry>();
            AddEntryCommand = new Command(AddEntry);
            DeleteEntryCommand = new Command<JournalEntry>(DeleteEntry);
        }
        

        解决方案中的相同预填充数据库链接到不同的“本地”项目:

        【讨论】:

        • 感谢您提供包括截图在内的精彩示例! (我是 Realm Xamarin 的作者之一)。
        • @AndyDent 谢谢。到目前为止爱Realm Xamarin,很棒的工作!!!到目前为止,仅在一个基于Swift 的大型/生产项目中使用了 Realm,但它非常棒,而且 SQLite 上的查询性能完全让该应用程序大放异彩。如果Akavache 得到一个工作的 Realm IO 提供者github.com/akavache/Akavache/pull/292,我会跳舞
        • 感谢@SushiHangover,这太棒了。我仍处于计划阶段,但我接受这是解决方案!
        • 很高兴地说,我们现在将这个答案链接为关于捆绑的“官方”文档,来自realm.io/docs/xamarin/0.75.0/#bundling-realm-files
        • @SushiHangover 感谢您详细的回答。不幸的是,今天是我在所有 3 台上的第三天——Mac、Realm 和 Xamarin。因此,我仍在弄清楚放置此代码的正确位置。所以我请求你是否可以分享你的演示项目的 GitHub 链接,这将非常有帮助。
        猜你喜欢
        • 1970-01-01
        • 2019-01-12
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-04-20
        • 1970-01-01
        • 2019-04-09
        相关资源
        最近更新 更多