Exemple #1
0
        public void TestNonSupportedInput()
        {
            var echoModel = new EchoModel();

            echoModel.RegisterModel();

            var model      = nameof(EchoModel);
            var input      = Expression.Value("string");
            var prediction = Function.Prediction(model, input);

            //Due to possibility of optimization on new SQLite, SQLite skips these expensive query calls if there is no document before running a query.
            using (var doc = new MutableDocument()) {
                doc.SetInt("number", 1);
                SaveDocument(doc);
            }

            using (var q = QueryBuilder.Select(SelectResult.Expression(prediction))
                           .From(DataSource.Database(Db))) {
                q.Invoking(x => x.Execute()).Should().Throw <CouchbaseSQLiteException>()
                .Where(x => x.BaseError == SQLiteStatus.Error);
            }

            var dict = new Dictionary <string, object> {
                ["key"] = this
            };

            input      = Expression.Dictionary(dict);
            prediction = Function.Prediction(model, input);

            using (var q = QueryBuilder.Select(SelectResult.Expression(prediction))
                           .From(DataSource.Database(Db))) {
                q.Invoking(x => x.Execute()).Should().Throw <ArgumentException>();
            }
        }
        static void Main(string[] args)
        {
            Console.WriteLine("Press any key to start...");
            Console.ReadKey();
            using (var db = new Database("db")) {
                var config = new ReplicatorConfiguration(db, new URLEndpoint(new Uri("ws://localhost:5984/db")))
                {
                    Continuous = true
                };
                var repl = new Replicator(config);
                repl.Start();

                var key = new ConsoleKeyInfo();
                var r   = new Random();
                do
                {
                    Console.WriteLine("Press A to add document, Press E to end");
                    key = Console.ReadKey();
                    if (key.Key == ConsoleKey.A)
                    {
                        using (var doc = new MutableDocument()) {
                            doc.SetInt("rand", r.Next());
                            db.Save(doc);
                        }
                    }
                } while (key.Key != ConsoleKey.E);

                repl.Stop();
                while (repl.Status.Activity != ReplicatorActivityLevel.Stopped)
                {
                    Console.WriteLine("Waiting for replicator to stop...");
                    Thread.Sleep(2000);
                }
            }
        }
        public void TestPurgePreSaveDoc()
        {
            var doc = new MutableDocument("doc1");

            doc.SetInt("key", 1);

            Db.Purge(doc);
            Db.Count.Should().Be(0UL, "because the database should still be empty");
        }
Exemple #4
0
        public void TestPurgePreSaveDoc()
        {
            var doc = new MutableDocument("doc1");

            doc.SetInt("key", 1);

            Db.Invoking(db => db.Purge(doc)).ShouldThrow <CouchbaseLiteException>()
            .Where(e => e.Error == CouchbaseLiteError.NotFound);

            Db.Count.Should().Be(0UL, "because the database should still be empty");
        }
        private Document GenerateDocument(string docID)
        {
            using (var doc = new MutableDocument(docID)) {
                doc.SetInt("key", 1);

                var saveDoc = Db.Save(doc);
                Db.Count.Should().Be(1UL, "because this is the first document");
                saveDoc.Sequence.Should().Be(1UL, "because this is the first document");
                return(saveDoc);
            }
        }
        public void TestSaveDocToDeletedDB()
        {
            DeleteDB(Db);
            var doc = new MutableDocument("doc1");

            doc.SetInt("key", 1);

            Db.Invoking(d => d.Save(doc))
            .ShouldThrow <InvalidOperationException>()
            .WithMessage("Attempt to perform an operation on a closed database",
                         "because this operation is invalid");
        }
        public void TestDeletePreSaveDoc()
        {
            var doc = new MutableDocument("doc1");

            doc.SetInt("key", 1);

            Db.Invoking(d => d.Delete(doc))
            .ShouldThrow <CouchbaseLiteException>()
            .Which.Status.Should()
            .Be(StatusCode.NotAllowed, "because deleting an unsaved document is not allowed");
            Db.Count.Should().Be(0UL, "because the database should still be empty");
        }
Exemple #8
0
        public void TestCompactEncryptedDatabase()
        {
            Database.Delete("seekrit", Directory);
            using (var seekrit = OpenSeekrit("letmein")) {
                using (var doc = new MutableDocument(new Dictionary <string, object>
                {
                    ["answer"] = 42
                })) {
                    seekrit.Save(doc);
                    doc.SetInt("answer", 84);

                    seekrit.Compact();

                    doc.SetInt("answer", 85);
                    seekrit.Save(doc);
                }
            }

            using (var seekrit = OpenSeekrit("letmein")) {
                seekrit.Count.Should().Be(1UL);
            }
        }
Exemple #9
0
        public void TestDeletePreSaveDoc()
        {
            var doc = new MutableDocument("doc1");

            doc.SetInt("key", 1);

            Db.Invoking(d => d.Delete(doc))
            .ShouldThrow <CouchbaseLiteException>()
            .Where(
                e => e.Error == CouchbaseLiteError.NotFound &&
                e.Domain == CouchbaseLiteErrorType.CouchbaseLite,
                "because deleting an unsaved document is not allowed");
            Db.Count.Should().Be(0UL, "because the database should still be empty");
        }
        public void TestSaveAndGetMultipleDocs()
        {
            const int NumDocs = 10;

            for (var i = 0; i < NumDocs; i++)
            {
                using (var doc = new MutableDocument($"doc_{i:D3}")) {
                    doc.SetInt("key", i);
                    Db.Save(doc).Dispose();
                }
            }

            Db.Count.Should().Be(NumDocs);
            ValidateDocs(NumDocs);
        }
        private IList <Document> CreateDocs(int n)
        {
            var docs = new List <Document>();

            for (int i = 0; i < n; i++)
            {
                using (var doc = new MutableDocument($"doc_{i:D3}")) {
                    doc.SetInt("key", i);
                    docs.Add(Db.Save(doc));
                }
            }

            Db.Count.Should().Be((ulong)n, "because otherwise an incorrect number of documents were made");
            return(docs);
        }
        public void TestDeleteAndOpenDB()
        {
            using (var database1 = new Database("application")) {
                database1.Delete();

                using (var database2 = new Database("application")) {
                    database2.InBatch(() =>
                    {
                        for (var i = 0; i < 100; i++)
                        {
                            using (var doc = new MutableDocument()) {
                                doc.SetInt("index", i);
                                for (var j = 0; j < 10; j++)
                                {
                                    doc.SetInt($"item_{j}", j);
                                }

                                database2.Save(doc).Dispose();
                            }
                        }
                    });
                }
            }
        }
        public void TestConflict()
        {
            ConflictResolver = new TheirsWins();
            ReopenDB();
            var doc1      = SetupConflict();
            var savedDoc1 = Db.Save(doc1);

            savedDoc1["name"].ToString().Should().Be("Scotty", "because the 'theirs' version should win");
            doc1.Dispose();
            savedDoc1.Dispose();

            ConflictResolver = new MergeThenTheirsWins();
            ReopenDB();

            var doc2 = new MutableDocument("doc2");

            doc2.SetString("type", "profile");
            doc2.SetString("name", "Scott");
            var savedDoc2 = Db.Save(doc2);

            // Force a conflict again
            var properties = doc2.ToDictionary();

            properties["type"]   = "bio";
            properties["gender"] = "male";
            SaveProperties(properties, doc2.Id);
            doc2.Dispose();

            // Save and make sure that the correct conflict resolver won
            doc2 = savedDoc2.ToMutable();
            doc2.SetString("type", "bio");
            doc2.SetInt("age", 31);

            savedDoc2.Dispose();
            savedDoc2 = Db.Save(doc2);
            doc2.Dispose();

            savedDoc2["age"].Long.Should().Be(31L, "because 'age' was changed by 'mine' and not 'theirs'");
            savedDoc2["type"].String.Should().Be("bio", "because 'type' was changed by 'mine' and 'theirs' so 'theirs' should win");
            savedDoc2["gender"].String.Should().Be("male", "because 'gender' was changed by 'theirs' but not 'mine'");
            savedDoc2["name"].String.Should().Be("Scott", "because 'name' was unchanged");
            savedDoc2.Dispose();
        }
        private void SetDocument(T entity, MutableDocument mutableDocument)
        {
            var properties = ObjectToDictionaryHelper.ToDictionary(entity);

            foreach (var prop in properties)
            {
                if (prop.Value is int)
                {
                    mutableDocument.SetInt(prop.Key, (int)prop.Value);
                }
                else if (prop.Value is long)
                {
                    mutableDocument.SetLong(prop.Key, (long)prop.Value);
                }
                else if (prop.Value is bool)
                {
                    mutableDocument.SetBoolean(prop.Key, (bool)prop.Value);
                }
                else if (prop.Value is DateTimeOffset)
                {
                    if ((DateTimeOffset)prop.Value != default(DateTimeOffset))
                    {
                        mutableDocument.SetDate(prop.Key, (DateTimeOffset)prop.Value);
                    }
                }
                else if (prop.Value is double)
                {
                    mutableDocument.SetDouble(prop.Key, (double)prop.Value);
                }
                else if (prop.Value is float)
                {
                    mutableDocument.SetFloat(prop.Key, (float)prop.Value);
                }
                else if (prop.Value is string)
                {
                    mutableDocument.SetString(prop.Key, (string)prop.Value);
                }
                else
                {
                    mutableDocument.SetValue(prop.Key, prop.Value);
                }
            }
        }
        public void TestGetFragmentFromInteger()
        {
            var doc = new MutableDocument("doc1");

            doc.SetInt("integer", 10);
            SaveDocument(doc, d =>
            {
                var fragment = d["integer"];
                fragment.Exists.Should().BeTrue("because this portion of the data exists");
                fragment.String.Should().BeNull("because this fragment is not of this type");
                fragment.Array.Should().BeNull("because this fragment is not of this type");
                fragment.Dictionary.Should().BeNull("because this fragment is not of this type");
                fragment.Int.Should().Be(10, "because that is the stored value");
                fragment.Long.Should().Be(10L, "because that is the converted value");
                fragment.Double.Should().Be(10.0, "because that is the converted value");
                fragment.Float.Should().Be(10.0f, "because that is the converted value");
                fragment.Boolean.Should().Be(true, "because that is the converted value");
                fragment.Date.Should().Be(DateTimeOffset.MinValue, "because that is the default value");
                fragment.Value.Should().NotBeNull("because this fragment has a value");
            });
        }
        private void UpdateDoc(MutableDocument doc, int rounds, string tag)
        {
            for (var i = 1; i <= rounds; i++)
            {
                doc.SetInt("update", i);
                doc.SetString("tag", tag);

                var address = doc.GetDictionary("address");
                address.Should().NotBeNull();
                var street = $"{i} street.";
                address.SetString("street", street);

                var phones = doc.GetArray("phones");
                phones.Should().NotBeNull();
                phones.Count.Should().Be(2);
                var phone = $"650-000-{i:D4}";
                phones.SetString(0, phone);

                doc.SetDate("updated", DateTimeOffset.UtcNow);

                Db.Save(doc).Dispose();
            }
        }
        public void TestConflictWithoutCommonAncestor()
        {
            ConflictResolver = new NoCommonAncestorValidator();
            ReopenDB();

            var props = new Dictionary <string, object> {
                ["hello"] = "world"
            };

            var doc = new MutableDocument("doc1", props);

            Db.Save(doc);

            doc = Db.GetDocument(doc.Id).ToMutable();
            doc.SetInt("university", 1);
            Db.Save(doc);

            // Create a conflict
            doc = new MutableDocument(doc.Id, props);
            doc.SetInt("university", 2);

            Db.Invoking(d => d.Save(doc)).ShouldThrow <LiteCoreException>().Which.Error.Should()
            .Be(new C4Error(C4ErrorCode.Conflict));
        }
Exemple #18
0
        private void RunTwoStepContinuous(ReplicatorType type, string uid)
        {
            var listener = new MessageEndpointListener(new MessageEndpointListenerConfiguration(_otherDB, ProtocolType.ByteStream));
            var server   = new MockServerConnection(listener, ProtocolType.ByteStream);
            var config   = new ReplicatorConfiguration(Db,
                                                       new MessageEndpoint(uid, server, ProtocolType.ByteStream, new MockConnectionFactory(null)))
            {
                ReplicatorType = type,
                Continuous     = true
            };
            var replicator = new Replicator(config);

            replicator.Start();

            Database firstSource  = null;
            Database secondSource = null;
            Database firstTarget  = null;
            Database secondTarget = null;

            if (type == ReplicatorType.Push)
            {
                firstSource  = Db;
                secondSource = Db;
                firstTarget  = _otherDB;
                secondTarget = _otherDB;
            }
            else if (type == ReplicatorType.Pull)
            {
                firstSource  = _otherDB;
                secondSource = _otherDB;
                firstTarget  = Db;
                secondTarget = Db;
            }
            else
            {
                firstSource  = Db;
                secondSource = _otherDB;
                firstTarget  = _otherDB;
                secondTarget = Db;
            }

            using (var mdoc = new MutableDocument("livesindb")) {
                mdoc.SetString("name", "db");
                mdoc.SetInt("version", 1);
                firstSource.Save(mdoc);
            }

            var count = 0;

            while (replicator.Status.Progress.Completed == 0 ||
                   replicator.Status.Activity != ReplicatorActivityLevel.Idle)
            {
                Thread.Sleep(500);
                count++;
                count.Should().BeLessThan(10, "because otherwise the replicator did not advance");
            }

            var previousCompleted = replicator.Status.Progress.Completed;

            firstTarget.Count.Should().Be(1);

            using (var savedDoc = secondSource.GetDocument("livesindb"))
                using (var mdoc = savedDoc.ToMutable()) {
                    mdoc.SetInt("version", 2);
                    secondSource.Save(mdoc);
                }

            count = 0;
            while (replicator.Status.Progress.Completed == previousCompleted ||
                   replicator.Status.Activity != ReplicatorActivityLevel.Idle)
            {
                Thread.Sleep(500);
                count++;
                count.Should().BeLessThan(10, "because otherwise the replicator did not advance");
            }

            using (var savedDoc = secondTarget.GetDocument("livesindb")) {
                savedDoc.GetInt("version").Should().Be(2);
            }

            replicator.Stop();
            while (replicator.Status.Activity != ReplicatorActivityLevel.Stopped)
            {
                Thread.Sleep(100);
            }

            replicator.Dispose();
        }
        public void TestPredictionInputOutput()
        {
            var echoModel = new EchoModel();

            echoModel.RegisterModel();

            using (var doc = new MutableDocument()) {
                doc.SetString("name", "Daniel");
                doc.SetInt("number", 2);
                doc.SetDouble("max", Double.MaxValue);
                Db.Save(doc);
            }

            var date  = DateTimeOffset.Now;
            var power = Function.Power(Expression.Property("number"), Expression.Int(2));
            var map   = new Dictionary <string, object>
            {
                ["null"]               = null,
                ["number1"]            = 10,
                ["number2"]            = 10.1,
                ["int_min"]            = Int32.MinValue,
                ["int_max"]            = Int32.MaxValue,
                ["int64_min"]          = Int64.MinValue,
                ["int64_max"]          = Int64.MaxValue,
                ["float_min"]          = Single.MinValue,
                ["float_max"]          = Single.MaxValue, // NOTE: Double limits are not guaranteed
                ["boolean_true"]       = true,
                ["boolean_false"]      = false,
                ["string"]             = "hello",
                ["date"]               = date,
                ["expr_property"]      = Expression.Property("name"),
                ["expr_value_number1"] = Expression.Value(20),
                ["expr_value_number2"] = Expression.Value(20.1),
                ["expr_value_boolean"] = Expression.Value(true),
                ["expr_value_string"]  = Expression.Value("hi"),
                ["expr_value_date"]    = Expression.Value(date),
                ["expr_value_null"]    = Expression.Value(null),
                ["expr_power"]         = power
            };

            var submap = new Dictionary <string, object> {
                ["foo"] = "bar"
            };

            map["dict"] = submap;
            var subList = new[] { "1", "2", "3" };

            map["array"] = subList;

            var subExprMap = new Dictionary <string, object> {
                ["ping"] = "pong"
            };

            map["expr_value_dict"] = Expression.Value(subExprMap);
            var subExprList = new[] { "4", "5", "6" };

            map["expr_value_array"] = Expression.Value(subExprList);

            var input      = Expression.Value(map);
            var model      = nameof(EchoModel);
            var prediction = Function.Prediction(model, input);

            using (var q = QueryBuilder.Select(SelectResult.Expression(prediction))
                           .From(DataSource.Database(Db)))
            {
                var rows = VerifyQuery(q, (n, result) =>
                {
                    var pred = result.GetDictionary(0);
                    pred.Count.Should().Be(map.Count,
                                           "because all properties should be serialized and recovered correctly");
                    pred.GetInt("number1").Should().Be(10);
                    pred.GetDouble("number2").Should().Be(10.1);
                    pred.GetInt("int_min").Should().Be(Int32.MinValue);
                    pred.GetInt("int_max").Should().Be(Int32.MaxValue);
                    pred.GetLong("int64_min").Should().Be(Int64.MinValue);
                    pred.GetLong("int64_max").Should().Be(Int64.MaxValue);
                    pred.GetFloat("float_min").Should().Be(Single.MinValue);
                    pred.GetFloat("float_max").Should().Be(Single.MaxValue);
                    pred.GetBoolean("boolean_true").Should().BeTrue();
                    pred.GetBoolean("boolean_false").Should().BeFalse();
                    pred.GetString("string").Should().Be("hello");
                    pred.GetDate("date").Should().Be(date);
                    pred.GetString("null").Should().BeNull();
                    pred.GetDictionary("dict").Should().Contain(submap);
                    pred.GetArray("array").Should().ContainInOrder(subList);

                    pred.GetString("expr_property").Should().Be("Daniel");
                    pred.GetInt("expr_value_number1").Should().Be(20);
                    pred.GetDouble("expr_value_number2").Should().Be(20.1);
                    pred.GetBoolean("expr_value_boolean").Should().BeTrue();
                    pred.GetString("expr_value_string").Should().Be("hi");
                    pred.GetDate("expr_value_date").Should().Be(date);
                    pred.GetString("expr_value_null").Should().BeNull();
                    pred.GetDictionary("expr_value_dict").Should().Contain(subExprMap);
                    pred.GetArray("expr_value_array").Should().ContainInOrder(subExprList);
                    pred.GetInt("expr_power").Should().Be(4);
                });

                rows.Should().Be(1);
            }
        }
Exemple #20
0
        private void RunTwoStepContinuous(ReplicatorType type, string uid)
        {
            using (var OtherDb1 = OpenDB(OtherDb.Name))
                using (var Db1 = OpenDB(Db.Name)) {
                    var listener = new MessageEndpointListener(new MessageEndpointListenerConfiguration(OtherDb1, ProtocolType.ByteStream));
                    var server   = new MockServerConnection(listener, ProtocolType.ByteStream);
                    var config   = new ReplicatorConfiguration(Db1,
                                                               new MessageEndpoint(uid, server, ProtocolType.ByteStream, new MockConnectionFactory(null)))
                    {
                        ReplicatorType = type,
                        Continuous     = true
                    };

                    using (var replicator = new Replicator(config)) {
                        Database firstSource  = null;
                        Database secondSource = null;
                        Database firstTarget  = null;
                        Database secondTarget = null;
                        if (type == ReplicatorType.Push)
                        {
                            firstSource  = Db1;
                            secondSource = Db1;
                            firstTarget  = OtherDb1;
                            secondTarget = OtherDb1;
                        }
                        else if (type == ReplicatorType.Pull)
                        {
                            firstSource  = OtherDb1;
                            secondSource = OtherDb1;
                            firstTarget  = Db1;
                            secondTarget = Db1;
                        }
                        else
                        {
                            firstSource  = Db1;
                            secondSource = OtherDb1;
                            firstTarget  = OtherDb1;
                            secondTarget = Db1;
                        }

                        replicator.Start();

                        using (var mdoc = new MutableDocument("livesindb")) {
                            mdoc.SetString("name", "db");
                            mdoc.SetInt("version", 1);
                            firstSource.Save(mdoc);
                        }

                        var count = 0;
                        if (type != ReplicatorType.Push)
                        {
                            while (true)
                            {
                                count++;
                                Thread.Sleep(1000);
                                if (replicator.Status.Progress.Completed > 0 &&
                                    replicator.Status.Activity == ReplicatorActivityLevel.Idle)
                                {
                                    break;
                                }
                            }

                            count.Should().BeLessThan(10, "because otherwise the replicator did not advance");
                        }
                        else //when both doc updates happens on local side with push only, replicator.Status.Progress value wipe out too fast, so skip while loop
                        {
                            Thread.Sleep(1000);
                        }

                        var previousCompleted = replicator.Status.Progress.Completed;
                        firstTarget.Count.Should().Be(1);

                        using (var savedDoc = secondSource.GetDocument("livesindb"))
                            using (var mdoc = savedDoc.ToMutable()) {
                                mdoc.SetInt("version", 2);
                                secondSource.Save(mdoc);
                            }

                        count = 0;
                        if (type != ReplicatorType.Push)
                        {
                            while (true)
                            {
                                count++;
                                Thread.Sleep(1000);
                                if (replicator.Status.Progress.Completed > previousCompleted &&
                                    replicator.Status.Activity == ReplicatorActivityLevel.Idle)
                                {
                                    break;
                                }
                            }

                            count.Should().BeLessThan(10, "because otherwise the replicator did not advance");
                        }
                        else //when both doc updates happens on local side with push only, replicator.Status.Progress value wipe out too fast, so skip while loop
                        {
                            Thread.Sleep(1000);
                        }

                        using (var savedDoc = secondTarget.GetDocument("livesindb")) {
                            savedDoc.GetInt("version").Should().Be(2);
                        }

                        replicator.Stop();
                        Thread.Sleep(100);
                        while (true)
                        {
                            if (replicator.Status.Activity == ReplicatorActivityLevel.Stopped)
                            {
                                break;
                            }
                        }
                    }
                }
        }