问题
this is my class
[ProtoContract]
internal class Powershellresults
{
internal Powershellresults()
{
}
[ProtoMember(1)]
public Collection<PSObject> PsObjects { get; set; }
[ProtoMember(2)]
public string Script { get; set; }
[ProtoMember(3)]
public string Viewname { get; set; }
}
but i get No serializer defined for type: System.Management.Automation.PSObject when i try to serialize it
private byte[] SerializeResults(Powershellresults obj)
{
byte[] data;
using (var ms = new MemoryStream())
{
ProtoBuf.Serializer.Serialize(ms, obj);
data = ms.ToArray(); ;
}
return data;
}
PsObject is part of System.Management.Automation
Can i get around this and actually serialize this collection?
UPDATE: by adding to my serialization method
RuntimeTypeModel.Default.Add(typeof(PSObject), true);
I can get it to serialize- but it loses most of it's fields once serialized how do i get it to "clone" the original object so it keeps all of its fields and properties?
EDIT
I figured it out! I thought to myself that Powershell had to be able to serialize it's objects, because you can poll remote machines - how else would it be able to send the PSObject between machines - which it does! (woohoo!!!!)
Well, i found an article that described this, and found my keyword System.Management.Automation.PSSerializer
Collection<PSObject> PSCol = Powershell.Invoke();
string SerializedCollection = PSSerializer.Serialize(PSCol);
//serialization to XML done!
then Serialize the string using Protobuf-net or what ever...
Deserialization is a bit awkward but pretty straight forward for deserialization use: Use Protobuf to deserialize the string and then...
PSObject obj = PSSerializer.Deserialize(DeserializedString) as PSObject;
Collection<PSObject> DeserializedCollection = new Collection<PSObject>(((ArrayList)obj.ImmediateBaseObject).Cast<PSObject>().ToArray());
and thats it..
回答1:
I figured it out! I thought to myself that Powershell had to be able to serialize it's objects, because you can poll remote machines - how else would it be able to send the PSObject between machines - which it does! (woohoo!!!!)
Well, i found an article that described this, and found my keyword System.Management.Automation.PSSerializer
Collection<PSObject> PSCol = Powershell.Invoke();
string SerializedCollection = PSSerializer.Serialize(PSCol);
//serialization to XML done!
then Serialize the string using Protobuf-net or what ever...
Deserialization is a bit awkward but pretty straight forward for deserialization use: Use Protobuf to deserialize the string and then...
PSObject obj = PSSerializer.Deserialize(DeserializedString) as PSObject;
Collection<PSObject> DeserializedCollection = new Collection<PSObject>(((ArrayList)obj.ImmediateBaseObject).Cast<PSObject>().ToArray());
and thats it..
回答2:
PSObject
is too vague to make a good serialization candidate (not least, it is a dynamic
provider, etc); I strongly recommend that you construct a well defined DTO model, i.e.
[ProtoMember(1)]
public Collection<SomeTypeThatYouOwn> Items {get;set;}
where SomeTypeThatYouOwn
has meaningful properties etc. You can always convert to/from SomeTypeThatYouOwn
close to the serialize/deserialize setp. PSObject
is basically a property-bag, and that doesn't work well since protobuf doesn't include any metadata (you need to know the shape of the data in advance to deserialize it meaningfully).
来源:https://stackoverflow.com/questions/19811921/no-serializer-defined-for-type-system-management-automation-psobject-in-protobu