private string GetWriterOutput(IEdmModel model, Action <ODataMessageWriter> writeAction)
        {
            MemoryStream          outputStream = new MemoryStream();
            IODataResponseMessage message      = new InMemoryMessage()
            {
                Stream = outputStream
            };

            message.SetHeader("Content-Type", "application/json;odata.metadata=minimal");
            ODataMessageWriterSettings settings = new ODataMessageWriterSettings();

            settings.SetServiceDocumentUri(new Uri("http://example.com"));

            string output;

            using (var messageWriter = new ODataMessageWriter(message, settings, model))
            {
                writeAction(messageWriter);
                outputStream.Seek(0, SeekOrigin.Begin);
                output = new StreamReader(outputStream).ReadToEnd();
            }

            return(output);
        }
        public void ValidateWriteMethodGroup()
        {
            // setup model
            var model       = new EdmModel();
            var complexType = new EdmComplexType("NS", "ComplexType");

            complexType.AddStructuralProperty("PrimitiveProperty1", EdmPrimitiveTypeKind.Int64);
            complexType.AddStructuralProperty("PrimitiveProperty2", EdmPrimitiveTypeKind.Int64);
            var entityType = new EdmEntityType("NS", "EntityType", null, false, true);

            entityType.AddKeys(
                entityType.AddStructuralProperty("PrimitiveProperty", EdmPrimitiveTypeKind.Int64));
            var container = new EdmEntityContainer("NS", "Container");
            var entitySet = container.AddEntitySet("EntitySet", entityType);

            model.AddElements(new IEdmSchemaElement[] { complexType, entityType, container });

            // write payload using new API
            string str1;
            {
                // setup
                var stream  = new MemoryStream();
                var message = new InMemoryMessage {
                    Stream = stream
                };
                message.SetHeader("Content-Type", "application/json;odata.metadata=full");
                var settings = new ODataMessageWriterSettings
                {
                    ODataUri = new ODataUri
                    {
                        ServiceRoot = new Uri("http://svc/")
                    },
                };
                var writer = new ODataMessageWriter((IODataResponseMessage)message, settings, model);

                var entitySetWriter = writer.CreateODataResourceSetWriter(entitySet);
                entitySetWriter.Write(new ODataResourceSet(), () => entitySetWriter
                                      .Write(new ODataResource
                {
                    Properties = new[] { new ODataProperty {
                                             Name = "PrimitiveProperty", Value = 1L
                                         } }
                })
                                      .Write(new ODataResource
                {
                    Properties = new[] { new ODataProperty {
                                             Name = "PrimitiveProperty", Value = 2L
                                         } }
                }, () => entitySetWriter
                                             .Write(new ODataNestedResourceInfo {
                    Name = "DynamicNavProperty"
                })
                                             .Write(new ODataNestedResourceInfo
                {
                    Name         = "DynamicCollectionProperty",
                    IsCollection = true
                }, () => entitySetWriter
                                                    .Write(new ODataResourceSet {
                    TypeName = "Collection(NS.ComplexType)"
                })))
                                      );
                str1 = Encoding.UTF8.GetString(stream.ToArray());
            }
            // write payload using old API
            string str2;

            {
                // setup
                var stream  = new MemoryStream();
                var message = new InMemoryMessage {
                    Stream = stream
                };
                message.SetHeader("Content-Type", "application/json;odata.metadata=full");
                var settings = new ODataMessageWriterSettings
                {
                    ODataUri = new ODataUri
                    {
                        ServiceRoot = new Uri("http://svc/")
                    },
                };
                var writer = new ODataMessageWriter((IODataResponseMessage)message, settings, model);

                var entitySetWriter = writer.CreateODataResourceSetWriter(entitySet);
                entitySetWriter.WriteStart(new ODataResourceSet());
                entitySetWriter.WriteStart(new ODataResource
                {
                    Properties = new[] { new ODataProperty {
                                             Name = "PrimitiveProperty", Value = 1L
                                         } }
                });
                entitySetWriter.WriteEnd();
                entitySetWriter.WriteStart(new ODataResource
                {
                    Properties = new[] { new ODataProperty {
                                             Name = "PrimitiveProperty", Value = 2L
                                         } }
                });
                entitySetWriter.WriteStart(new ODataNestedResourceInfo {
                    Name = "DynamicNavProperty"
                });
                entitySetWriter.WriteEnd();
                entitySetWriter.WriteStart(new ODataNestedResourceInfo
                {
                    Name         = "DynamicCollectionProperty",
                    IsCollection = true
                });
                entitySetWriter.WriteStart(new ODataResourceSet {
                    TypeName = "Collection(NS.ComplexType)"
                });
                entitySetWriter.WriteEnd();
                entitySetWriter.WriteEnd();
                entitySetWriter.WriteEnd();
                entitySetWriter.WriteEnd();
                str2 = Encoding.UTF8.GetString(stream.ToArray());
            }
            Assert.Equal(str1, str2);
        }
예제 #3
0
        public async Task WriteResponseMessage_APIsShouldYieldSameResult()
        {
            var nestedWriterSettings = new ODataMessageWriterSettings
            {
                Version = ODataVersion.V4,
                EnableMessageStreamDisposal = false
            };

            nestedWriterSettings.SetServiceDocumentUri(new Uri(ServiceUri));
            var customerResponse = new ODataResource
            {
                TypeName   = "NS.Customer",
                Properties = new List <ODataProperty>
                {
                    new ODataProperty
                    {
                        Name              = "Id",
                        Value             = 1,
                        SerializationInfo = new ODataPropertySerializationInfo {
                            PropertyKind = ODataPropertyKind.Key
                        }
                    },
                    new ODataProperty {
                        Name = "Name", Value = "Customer 1"
                    }
                }
            };

            IODataResponseMessage asyncResponseMessage = new InMemoryMessage {
                StatusCode = 200, Stream = this.asyncStream
            };

            using (var messageWriter = new ODataMessageWriter(asyncResponseMessage, writerSettings))
            {
                var asynchronousWriter = await messageWriter.CreateODataAsynchronousWriterAsync();

                var responseMessage = await asynchronousWriter.CreateResponseMessageAsync();

                responseMessage.StatusCode = 200;

                using (var nestedMessageWriter = new ODataMessageWriter(responseMessage, nestedWriterSettings, this.model))
                {
                    var writer = await nestedMessageWriter.CreateODataResourceWriterAsync(this.customerEntitySet, this.customerEntityType);

                    await writer.WriteStartAsync(customerResponse);

                    await writer.WriteEndAsync();

                    await writer.FlushAsync();
                }

                await asynchronousWriter.FlushAsync();
            }

            this.asyncStream.Position = 0;
            var asyncResult = await new StreamReader(this.asyncStream).ReadToEndAsync();

            var syncResult = await TaskUtils.GetTaskForSynchronousOperation(() =>
            {
                IODataResponseMessage syncResponseMessage = new InMemoryMessage {
                    StatusCode = 200, Stream = this.syncStream
                };
                using (var messageWriter = new ODataMessageWriter(syncResponseMessage, writerSettings))
                {
                    var asynchronousWriter     = messageWriter.CreateODataAsynchronousWriter();
                    var responseMessage        = asynchronousWriter.CreateResponseMessage();
                    responseMessage.StatusCode = 200;

                    using (var nestedMessageWriter = new ODataMessageWriter(responseMessage, nestedWriterSettings, this.model))
                    {
                        var writer = nestedMessageWriter.CreateODataResourceWriter(this.customerEntitySet, this.customerEntityType);

                        writer.WriteStart(customerResponse);
                        writer.WriteEnd();
                        writer.Flush();
                    }

                    asynchronousWriter.Flush();
                }

                this.syncStream.Position = 0;
                return(new StreamReader(this.syncStream).ReadToEnd());
            });

            var expected = @"HTTP/1.1 200 OK
OData-Version: 4.0
Content-Type: application/json;odata.metadata=minimal;odata.streaming=true;IEEE754Compatible=false;charset=utf-8

{""@odata.context"":""http://tempuri.org/$metadata#Customers/$entity"",""Id"":1,""Name"":""Customer 1""}";

            Assert.Equal(expected, asyncResult);
            Assert.Equal(expected, syncResult);
        }
예제 #4
0
        public async Task WriteInStreamError_APIsShouldYieldSameResult()
        {
            var nestedWriterSettings = new ODataMessageWriterSettings
            {
                Version = ODataVersion.V4,
                EnableMessageStreamDisposal = false
            };

            nestedWriterSettings.SetServiceDocumentUri(new Uri(ServiceUri));

            var asyncException = await Assert.ThrowsAsync <ODataException>(async() =>
            {
                IODataResponseMessage asyncResponseMessage = new InMemoryMessage {
                    StatusCode = 200, Stream = this.asyncStream
                };
                using (var messageWriter = new ODataMessageWriter(asyncResponseMessage, writerSettings))
                {
                    // Call to CreateODataAsynchronousWriterAsync triggers setting of output in-stream error listener
                    var asynchronousWriter     = await messageWriter.CreateODataAsynchronousWriterAsync();
                    var responseMessage        = await asynchronousWriter.CreateResponseMessageAsync();
                    responseMessage.StatusCode = 200;

                    // Next section added is to demonstrate that what was already written is flushed to the buffer before exception is thrown
                    using (var nestedMessageWriter = new ODataMessageWriter(responseMessage, nestedWriterSettings))
                    {
                        var writer = await nestedMessageWriter.CreateODataResourceWriterAsync();
                    }

                    await messageWriter.WriteErrorAsync(
                        new ODataError {
                        ErrorCode = "NRE", Message = "Object reference not set to an instance of an object."
                    },
                        /*includeDebugInformation*/ true);
                }
            });

            this.asyncStream.Position = 0;
            var asyncResult = await new StreamReader(this.asyncStream).ReadToEndAsync();

            var syncException = await Assert.ThrowsAsync <ODataException>(
                () => TaskUtils.GetTaskForSynchronousOperation(() =>
            {
                IODataResponseMessage syncResponseMessage = new InMemoryMessage {
                    StatusCode = 200, Stream = this.syncStream
                };
                using (var messageWriter = new ODataMessageWriter(syncResponseMessage, writerSettings))
                {
                    // Call to CreateODataAsynchronousWriterAsync triggers setting of output in-stream error listener
                    var asynchronousWriter     = messageWriter.CreateODataAsynchronousWriter();
                    var responseMessage        = asynchronousWriter.CreateResponseMessage();
                    responseMessage.StatusCode = 200;

                    // Next section is added to demonstrate that what was already written is flushed to the buffer before exception is thrown
                    using (var nestedMessageWriter = new ODataMessageWriter(responseMessage, nestedWriterSettings))
                    {
                        var writer = nestedMessageWriter.CreateODataResourceWriter();
                    }

                    messageWriter.WriteError(
                        new ODataError {
                        ErrorCode = "NRE", Message = "Object reference not set to an instance of an object."
                    },
                        /*includeDebugInformation*/ true);
                }
            }));

            this.syncStream.Position = 0;
            var syncResult = await new StreamReader(this.syncStream).ReadToEndAsync();

            var expected = @"HTTP/1.1 200 OK
OData-Version: 4.0
Content-Type: application/json;odata.metadata=minimal;odata.streaming=true;IEEE754Compatible=false;charset=utf-8

";

            Assert.Equal(Strings.ODataAsyncWriter_CannotWriteInStreamErrorForAsync, asyncException.Message);
            Assert.Equal(Strings.ODataAsyncWriter_CannotWriteInStreamErrorForAsync, syncException.Message);
            Assert.Equal(expected, asyncResult);
            Assert.Equal(expected, syncResult);
        }