예제 #1
0
        private bool ReadReference()
        {
            switch (CurrentState)
            {
            case State.ObjectStart:
            {
                SetToken(JsonToken.PropertyName, "$ref");
                _bsonReaderState = BsonReaderState.ReferenceRef;
                return(true);
            }

            case State.Property:
            {
                if (_bsonReaderState == BsonReaderState.ReferenceRef)
                {
                    SetToken(JsonToken.String, ReadLengthString());
                    return(true);
                }
                else if (_bsonReaderState == BsonReaderState.ReferenceId)
                {
                    SetToken(JsonToken.Bytes, ReadBytes(12));
                    return(true);
                }
                else
                {
                    throw ExceptionUtils.CreateJsonReaderException(this, "Unexpected state when reading BSON reference: " + _bsonReaderState);
                }
            }

            case State.PostValue:
            {
                if (_bsonReaderState == BsonReaderState.ReferenceRef)
                {
                    SetToken(JsonToken.PropertyName, "$id");
                    _bsonReaderState = BsonReaderState.ReferenceId;
                    return(true);
                }
                else if (_bsonReaderState == BsonReaderState.ReferenceId)
                {
                    SetToken(JsonToken.EndObject);
                    _bsonReaderState = BsonReaderState.Normal;
                    return(true);
                }
                else
                {
                    throw ExceptionUtils.CreateJsonReaderException(this, "Unexpected state when reading BSON reference: " + _bsonReaderState);
                }
            }

            default:
                throw ExceptionUtils.CreateJsonReaderException(this, "Unexpected state when reading BSON reference: " + CurrentState);
            }
        }
예제 #2
0
        /// <summary>
        /// Reads the next JSON token from the underlying <see cref="Stream"/>.
        /// </summary>
        /// <returns>
        /// <c>true</c> if the next token was read successfully; <c>false</c> if there are no more tokens to read.
        /// </returns>
        public override bool Read()
        {
            try
            {
                bool success;

                switch (_bsonReaderState)
                {
                case BsonReaderState.Normal:
                    success = ReadNormal();
                    break;

                case BsonReaderState.ReferenceStart:
                case BsonReaderState.ReferenceRef:
                case BsonReaderState.ReferenceId:
                    success = ReadReference();
                    break;

                case BsonReaderState.CodeWScopeStart:
                case BsonReaderState.CodeWScopeCode:
                case BsonReaderState.CodeWScopeScope:
                case BsonReaderState.CodeWScopeScopeObject:
                case BsonReaderState.CodeWScopeScopeEnd:
                    success = ReadCodeWScope();
                    break;

                default:
                    throw ExceptionUtils.CreateJsonReaderException(this, "Unexpected state: {0}".FormatWith(CultureInfo.InvariantCulture, _bsonReaderState));
                }

                if (!success)
                {
                    SetToken(JsonToken.None);
                    return(false);
                }

                return(true);
            }
            catch (EndOfStreamException)
            {
                SetToken(JsonToken.None);
                return(false);
            }
        }
예제 #3
0
        private bool ReadNormal()
        {
            switch (CurrentState)
            {
            case State.Start:
            {
                JsonToken token = (!_readRootValueAsArray) ? JsonToken.StartObject : JsonToken.StartArray;
                BsonType  type  = (!_readRootValueAsArray) ? BsonType.Object : BsonType.Array;

                SetToken(token);
                ContainerContext newContext = new ContainerContext(type);
                PushContext(newContext);
                newContext.Length = ReadInt32();
                return(true);
            }

            case State.Complete:
            case State.Closed:
                return(false);

            case State.Property:
            {
                ReadType(_currentElementType);
                return(true);
            }

            case State.ObjectStart:
            case State.ArrayStart:
            case State.PostValue:
                ContainerContext context = _currentContext;
                if (context == null)
                {
                    return(false);
                }

                int lengthMinusEnd = context.Length - 1;

                if (context.Position < lengthMinusEnd)
                {
                    if (context.Type == BsonType.Array)
                    {
                        ReadElement();
                        ReadType(_currentElementType);
                        return(true);
                    }
                    else
                    {
                        SetToken(JsonToken.PropertyName, ReadElement());
                        return(true);
                    }
                }
                else if (context.Position == lengthMinusEnd)
                {
                    if (ReadByte() != 0)
                    {
                        throw ExceptionUtils.CreateJsonReaderException(this, "Unexpected end of object byte value.");
                    }

                    PopContext();
                    if (_currentContext != null)
                    {
                        MovePosition(context.Length);
                    }

                    JsonToken endToken = (context.Type == BsonType.Object) ? JsonToken.EndObject : JsonToken.EndArray;
                    SetToken(endToken);
                    return(true);
                }
                else
                {
                    throw ExceptionUtils.CreateJsonReaderException(this, "Read past end of current container context.");
                }

            case State.ConstructorStart:
                break;

            case State.Constructor:
                break;

            case State.Error:
                break;

            case State.Finished:
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }

            return(false);
        }