Tôi có biểu đồ đối tượng hình tròn trong mô hình của mình, nhưng điều đó là không thể tránh khỏi.Nhận mã trạng thái 500 http trống từ API Web
Theo lời khuyên được đưa ra trong this article, tôi đã sử dụng DataContractAttribute
và đặt IsReference = true
trên tất cả các thành viên. Tôi cũng đã cung cấp DataMemberAttribute
trên tất cả các thuộc tính mà tôi muốn tuần tự hóa.
Để đảm bảo rằng bộ nối tiếp không gặp phải bất kỳ vấn đề nào một lần nữa, tôi chỉ chọn không để tuần tự hóa các thuộc tính điều hướng.
Tuy nhiên, tôi vẫn gặp phải ngoại lệ trong khối catch của mình. Các chi tiết của các ngoại lệ như sau:
_innerException: {"Type
'System.Data.Entity.DynamicProxies.Author_615FB9F8BB22B55A7CA168DA5ED29EC6A0B59F62FD79D1346045351BE2F163A4' with data contract name
'Author_615FB9F8BB22B55A7CA168DA5ED29EC6A0B59F62FD79D1346045351BE2F163A4:
http://schemas.datacontract
.org/2004/07/System.Data.Entity.DynamicProxies' is not expected.
Consider using a
DataContractResolver or add any types not known statically to
the list of known types - for
example, by using the KnownTypeAttribute attribute or by adding them
to the list of known types
passed to DataContractSerializer."}
tôi có thể nhưng không muốn:
1) Vô hiệu hoá tạo proxy. Tôi có thể loại bỏ proxy tạo ra chỉ vì lợi ích của serialization, mà tôi có thể làm. Nhưng tôi cũng muốn tìm hiểu lý do tại sao tôi vẫn nhận được ngoại lệ và những gì tôi có thể làm về nó.
2) Xóa tham chiếu vòng tròn. Lý do: Các kiểu tham chiếu này rất phổ biến trong các mô hình tạo ra khung Entity Framework. Nếu tôi đang làm một dự án lớn với 800 - 1000 lớp học trong mô hình, đó là một cơn ác mộng để thực hiện nó bằng cách loại bỏ các tham chiếu vòng tròn.
Tôi đã mô tả các yếu tố kiến trúc của giải pháp tăng đột biến nhỏ này bên dưới.
Database Schema
Id AuthorName
-------------------------------
1 Charles Dickens
2 Charles Petzold
3 Charles Darwin
4 Charles Chaplin
5 Leo Tolstoy
6 Fydor Dostoevsky
7 Ayn Rand
8 Napolean Hill
9 Claude M. Bristol
10 Edward Dwight Easty
11 O. Henry
12 William Shakespeare
13 Juwal Lowy
14 Jeffrey Richter
15 Chris Sells
16 Don Box
17 Steven Pinker
18 Jim Rohn
19 George Eliot
20 Sathyaish Chakravarthy
Id Title AuthorId
----------- -------------------------------------------------- -----------
1 Nicholas Nickleby 1
Id BookId Review
----------- ---------------------------------------------------------------
1 1 How do I know? I haven't read it.
Mẫu
using System.Collections.Generic;
using System.Runtime.Serialization;
namespace BookReviewsModel
{
[DataContract(IsReference = true)]
public partial class Author
{
[DataMember]
public virtual int Id { get; set; }
[DataMember]
public virtual string AuthorName { get; set; }
public virtual ICollection<Book> Books { get; set; }
}
}
namespace BookReviewsModel
{
[DataContract(IsReference = true)]
public partial class Book
{
[DataMember]
public virtual int Id { get; set; }
[DataMember]
public virtual string Title { get; set; }
[DataMember]
public virtual int AuthorId { get; set; }
public virtual Author Author { get; set; }
public virtual ICollection<BookReview> BookReviews { get; set; }
}
}
namespace BookReviewsModel
{
[DataContract(IsReference = true)]
public partial class BookReview
{
[DataMember]
public virtual int Id { get; set; }
[DataMember]
public virtual int BookId { get; set; }
[DataMember]
[AllowHtml]
public virtual string Review { get; set; }
public virtual Book Book { get; set; }
}
}
điều khiển Mã
namespace BookReviews.Controllers
{
public class AuthorController : ApiController
{
[HttpGet]
public IEnumerable<Author> Index()
{
try
{
using (var context = new BookReviewEntities())
{
var authors = context.Authors.ToList();
var str = Serialize(new XmlMediaTypeFormatter(), authors);
System.Diagnostics.Debugger.Break();
System.Diagnostics.Debug.Print(str);
return authors;
}
}
catch (Exception ex)
{
var responseMessage = new HttpResponseMessage
{
Content = new StringContent("Couldn't retreive the list of authors."),
ReasonPhrase = ex.Message.Replace('\n', ' ')
};
throw new HttpResponseException(responseMessage);
}
}
string Serialize<T>(MediaTypeFormatter formatter, T value)
{
Stream stream = new MemoryStream();
var content = new StreamContent(stream);
formatter.WriteToStreamAsync(typeof(T), value, stream, content, null).Wait();
stream.Position = 0;
return content.ReadAsStringAsync().Result;
}
}
}
tất cả các lớp học của bạn là một phần - có thể gây ra bất kỳ vấn đề bổ sung? Các phần khác của lớp học có được đánh dấu bằng thuộc tính hoặc không bắt buộc phải không? –
Tôi có thể xác nhận điều này xảy ra mà không có các lớp học một phần, tuy nhiên, trong trường hợp của tôi nguyên nhân gốc có vẻ là việc sử dụng thuộc tính điều hướng ảo (không được đánh dấu để tuần tự hóa). Cần phải có một giải pháp thay thế cho điều này tương tự như giải pháp ProxyDataContractResolver + IObjectBehavior có sẵn cho các dịch vụ WCF. –
Bạn đã thử tìm cách này: http://stackoverflow.com/questions/11851207/prevent-property-from-being-serialized-in-web-api hoặc http://stackoverflow.com/questions/1411577/ bỏ qua-a-field-trong-net-json-serialization-tương tự-to-xmlignore –