示例#1
0
        // Returns one of:
        // - Document and Key, Key may be missing
        // - Array and Index, Index is always valid
        public static ResolvedDocumentPath ResolvePath(this BsonDocument that, string path, ResolvePathOptions options = ResolvePathOptions.None)
        {
            var r = new ResolvedDocumentPath();

            if (path.IndexOf('.') < 0)
            {
                r.Document = that;
                r.Key      = path;
                return(r);
            }

            var document = that;
            var keys     = path.Split('.');
            int last     = keys.Length - 1;

            for (int i = 0; i <= last; ++i)
            {
                var key = keys[i];
                if (i == last)
                {
                    r.Document = document;
                    r.Key      = key;
                    return(r);
                }

                BsonValue value;
                if (!document.TryGetValue(key, out value))
                {
                    return(null);
                }

                if (value.BsonType == BsonType.Document)
                {
                    document = value.AsBsonDocument;
                    continue;
                }

                int arrayIndex;
                if (value.BsonType != BsonType.Array || !int.TryParse(keys[i + 1], out arrayIndex))
                {
                    return(null);
                }

                if ((options & ResolvePathOptions.NoArray) != ResolvePathOptions.None)
                {
                    throw new InvalidOperationException("Array indexes are not supported.");
                }

                //_140322_065506
                if (arrayIndex < 0)
                {
                    if ((options & ResolvePathOptions.YesNegativeIndex) != ResolvePathOptions.None)
                    {
                        return(null);
                    }
                    throw new InvalidOperationException(string.Format(null, "Invalid negative array index in ({0}).", path));
                }

                var array = value.AsBsonArray;
                if (arrayIndex >= array.Count)
                {
                    return(null);
                }

                if (i == last - 1)
                {
                    r.Array = array;
                    r.Index = arrayIndex;
                    return(r);
                }

                var value2 = array[arrayIndex];
                if (value2.BsonType != BsonType.Document)
                {
                    return(null);
                }

                document = value2.AsBsonDocument;
                ++i;
            }

            return(null);
        }
示例#2
0
        public static ResolvedDocumentPath EnsurePath(this BsonDocument that, string path)
        {
            var r = new ResolvedDocumentPath();

            if (path.IndexOf('.') < 0)
            {
                r.Document = that;
                r.Key      = path;
                return(r);
            }

            var document = that;
            var keys     = path.Split('.');
            int last     = keys.Length - 1;

            for (int i = 0; i <= last; ++i)
            {
                var key = keys[i];
                if (i == last)
                {
                    r.Document = document;
                    r.Key      = key;
                    return(r);
                }

                BsonValue value;
                if (!document.TryGetValue(key, out value))
                {
                    var newDocument = new BsonDocument();
                    document.Add(key, newDocument);
                    document = newDocument;
                    continue;
                }

                if (value.BsonType == BsonType.Document)
                {
                    document = value.AsBsonDocument;
                    continue;
                }

                int arrayIndex;
                if (value.BsonType == BsonType.Array && int.TryParse(keys[i + 1], out arrayIndex))
                {
                    var array = value.AsBsonArray;
                    if (i == last - 1)
                    {
                        r.Array = array;
                        r.Index = arrayIndex;
                        return(r);
                    }

                    if (!array.InsertOutOfRange(arrayIndex, () => document = new BsonDocument()))
                    {
                        var value2 = array[arrayIndex];
                        if (value2.BsonType != BsonType.Document)
                        {
                            throw new InvalidOperationException(string.Format(null, "Array item at ({0}) in ({1}) is not a document.", arrayIndex, path));
                        }

                        document = value2.AsBsonDocument;
                    }
                    ++i;
                    continue;
                }

                throw new InvalidOperationException(string.Format(null, "Field ({0}) in ({1}) is not a document.", key, path));
            }

            return(null);
        }