private XmlRpcRequest MakeXmlRpcRequest(WebRequest webReq, MethodInfo mi, object[] parameters, object clientObj, string xmlRpcMethod, Guid proxyId)
        {
            webReq.Method      = "POST";
            webReq.ContentType = "text/xml";
            var rpcMethodName = XmlRpcTypeInfo.GetRpcMethodName(mi);

            return(new XmlRpcRequest(rpcMethodName, parameters, mi, xmlRpcMethod, proxyId));
        }
Beispiel #2
0
 private void CheckImplictString(Type valType, MappingStack mappingStack)
 {
     if (valType != null && valType != typeof(string) && !valType.IsEnum)
     {
         throw new XmlRpcTypeMismatchException(mappingStack.MappingType
                                               + " contains implicit string value where "
                                               + XmlRpcTypeInfo.GetXmlRpcTypeString(valType)
                                               + " expected " + StackDump(mappingStack));
     }
 }
        string GetEffectiveUrl(object clientObj)
        {
            // client can either have define URI in attribute or have set it
            // via proxy's ServiceURI property - but must exist by now
            if (!string.IsNullOrEmpty(Url))
            {
                return(Url);
            }

            var useUrl = XmlRpcTypeInfo.GetUrlFromAttribute(clientObj.GetType());

            if (!string.IsNullOrEmpty(useUrl))
            {
                return(useUrl);
            }

            throw new XmlRpcMissingUrl("Proxy XmlRpcUrl attribute or Url property not set.");
        }
Beispiel #4
0
        private void CheckExpectedType(Type expectedType, Type actualType, MappingStack mappingStack)
        {
            if (expectedType != null && expectedType.IsEnum)
            {
                Type[] i4Types = { typeof(byte), typeof(sbyte), typeof(short), typeof(ushort), typeof(int) };
                Type[] i8Types = { typeof(uint), typeof(long) };

                var underlyingType = Enum.GetUnderlyingType(expectedType);

                if (Array.IndexOf(i4Types, underlyingType) >= 0)
                {
                    expectedType = typeof(int);
                }
                else if (Array.IndexOf(i8Types, underlyingType) >= 0)
                {
                    expectedType = typeof(long);
                }
                else
                {
                    throw new XmlRpcInvalidEnumValue(mappingStack.MappingType +
                                                     " contains "
                                                     + XmlRpcTypeInfo.GetXmlRpcTypeString(actualType)
                                                     + " which cannot be mapped to  "
                                                     + XmlRpcTypeInfo.GetXmlRpcTypeString(expectedType)
                                                     + " " + StackDump(mappingStack));
                }
            }
            // TODO: throw exception for invalid enum type
            if (expectedType != null && expectedType != typeof(object) && expectedType != actualType &&
                (actualType.IsValueType && expectedType != typeof(Nullable <>).MakeGenericType(actualType)))
            {
                throw new XmlRpcTypeMismatchException(mappingStack.MappingType +
                                                      " contains "
                                                      + XmlRpcTypeInfo.GetXmlRpcTypeString(actualType)
                                                      + " value where "
                                                      + XmlRpcTypeInfo.GetXmlRpcTypeString(expectedType)
                                                      + " expected " + StackDump(mappingStack));
            }
        }
        public void Serialize(XmlWriter xtw, object o, MappingActions mappingActions, List <object> nestedObjs)
        {
            if (nestedObjs.Contains(o))
            {
                throw new XmlRpcUnsupportedTypeException(nestedObjs[0].GetType(),
                                                         "Cannot serialize recursive data structure");
            }
            nestedObjs.Add(o);
            try
            {
                xtw.WriteStartElement("", "value", "");
                var xType = XmlRpcTypeInfo.GetXmlRpcType(o);
                switch (xType)
                {
                case XmlRpcType.tArray:
                    xtw.WriteStartElement("", "array", "");
                    xtw.WriteStartElement("", "data", "");
                    var a = (Array)o;
                    foreach (object aobj in a)
                    {
                        //if (aobj == null)
                        //  throw new XmlRpcMappingSerializeException(String.Format(
                        //    "Items in array cannot be null ({0}[]).",
                        //o.GetType().GetElementType()));
                        Serialize(xtw, aobj, mappingActions, nestedObjs);
                    }
                    WriteFullEndElement(xtw);
                    WriteFullEndElement(xtw);
                    break;

                case XmlRpcType.tMultiDimArray:
                    var mda     = (Array)o;
                    var indices = new int[mda.Rank];
                    BuildArrayXml(xtw, mda, 0, indices, mappingActions, nestedObjs);
                    break;

                case XmlRpcType.tBase64:
                    var buf = (byte[])o;
                    xtw.WriteStartElement("", "base64", "");
                    xtw.WriteBase64(buf, 0, buf.Length);
                    WriteFullEndElement(xtw);
                    break;

                case XmlRpcType.tBoolean:
                    var strBoolVal = (bool)o ? "1" : "0";
                    WriteFullElementString(xtw, "boolean", strBoolVal);
                    break;

                case XmlRpcType.tDateTime:
                    var dt  = (DateTime)o;
                    var sdt = dt.ToString("yyyyMMdd'T'HH':'mm':'ss",
                                          DateTimeFormatInfo.InvariantInfo);
                    WriteFullElementString(xtw, "dateTime.iso8601", sdt);
                    break;

                case XmlRpcType.tDouble:
                    double doubleVal = (double)o;
                    WriteFullElementString(xtw, "double", doubleVal.ToString(null,
                                                                             CultureInfo.InvariantCulture));
                    break;

                case XmlRpcType.tHashtable:
                    xtw.WriteStartElement("", "struct", "");
                    var xrs = o as XmlRpcStruct;
                    foreach (object obj in xrs.Keys)
                    {
                        string skey = obj as string;
                        xtw.WriteStartElement("", "member", "");
                        WriteFullElementString(xtw, "name", skey);
                        Serialize(xtw, xrs[skey], mappingActions, nestedObjs);
                        WriteFullEndElement(xtw);
                    }
                    WriteFullEndElement(xtw);
                    break;

                case XmlRpcType.tInt32:
                    o = SerializeInt32(xtw, o, mappingActions);
                    break;

                case XmlRpcType.tInt64:
                    o = SerializeInt64(xtw, o, mappingActions);
                    break;

                case XmlRpcType.tString:
                    SerializeString(xtw, o);
                    break;

                case XmlRpcType.tStruct:
                    MappingActions structActions = GetMappingActions(o.GetType(), mappingActions);
                    xtw.WriteStartElement("", "struct", "");
                    MemberInfo[] mis = o.GetType().GetMembers();
                    foreach (var mi in mis)
                    {
                        if (Attribute.IsDefined(mi, typeof(NonSerializedAttribute)))
                        {
                            continue;
                        }

                        if (mi.MemberType == MemberTypes.Field)
                        {
                            var fi      = (FieldInfo)mi;
                            var member  = fi.Name;
                            var attrchk = Attribute.GetCustomAttribute(fi, typeof(XmlRpcMemberAttribute));
                            if (attrchk != null && attrchk is XmlRpcMemberAttribute)
                            {
                                var mmbr = ((XmlRpcMemberAttribute)attrchk).Member;
                                if (mmbr != "")
                                {
                                    member = mmbr;
                                }
                            }
                            var memberActions = MemberMappingActions(o.GetType(), fi.Name, structActions);
                            if (fi.GetValue(o) == null)
                            {
                                if (memberActions.NullMappingAction == NullMappingAction.Ignore)
                                {
                                    continue;
                                }

                                if (memberActions.NullMappingAction == NullMappingAction.Error)
                                {
                                    throw new XmlRpcMappingSerializeException(@"Member """ + member +
                                                                              @""" of struct """ + o.GetType().Name + @""" cannot be null.");
                                }
                            }
                            xtw.WriteStartElement("", "member", "");
                            WriteFullElementString(xtw, "name", member);
                            Serialize(xtw, fi.GetValue(o), memberActions, nestedObjs);
                            WriteFullEndElement(xtw);
                        }
                        else if (mi.MemberType == MemberTypes.Property)
                        {
                            var pi      = (PropertyInfo)mi;
                            var member  = pi.Name;
                            var attrchk = Attribute.GetCustomAttribute(pi, typeof(XmlRpcMemberAttribute));
                            if (attrchk != null && attrchk is XmlRpcMemberAttribute)
                            {
                                var mmbr = ((XmlRpcMemberAttribute)attrchk).Member;
                                if (mmbr != "")
                                {
                                    member = mmbr;
                                }
                            }
                            var memberActions = MemberMappingActions(o.GetType(), pi.Name, structActions);
                            if (pi.GetValue(o, null) == null)
                            {
                                if (memberActions.NullMappingAction == NullMappingAction.Ignore)
                                {
                                    continue;
                                }

                                if (memberActions.NullMappingAction == NullMappingAction.Error)
                                {
                                    throw new XmlRpcMappingSerializeException(@"Member """ + member +
                                                                              @""" of struct """ + o.GetType().Name + @""" cannot be null.");
                                }
                            }
                            xtw.WriteStartElement("", "member", "");
                            WriteFullElementString(xtw, "name", member);
                            Serialize(xtw, pi.GetValue(o, null), memberActions, nestedObjs);
                            WriteFullEndElement(xtw);
                        }
                    }
                    WriteFullEndElement(xtw);
                    break;

                case XmlRpcType.tVoid:
                    WriteFullElementString(xtw, "string", "");
                    break;

                case XmlRpcType.tNil:
                    xtw.WriteStartElement("nil");
                    WriteFullEndElement(xtw);
                    break;

                default:
                    throw new XmlRpcUnsupportedTypeException(o.GetType());
                }

                WriteFullEndElement(xtw);
            }
            catch (NullReferenceException)
            {
                throw new XmlRpcNullReferenceException("Attempt to serialize data "
                                                       + "containing null reference");
            }
            finally
            {
                nestedObjs.RemoveAt(nestedObjs.Count - 1);
            }
        }
Beispiel #6
0
        private object MapArray(IEnumerator <Node> iter, Type valType, MappingStack mappingStack, MappingAction mappingAction, out Type mappedType)
        {
            mappedType = null;
            // required type must be an array
            if (valType != null && !(valType.IsArray == true || valType == typeof(Array) || valType == typeof(object)))
            {
                throw new XmlRpcTypeMismatchException(mappingStack.MappingType
                                                      + $" contains array value where{XmlRpcTypeInfo.GetXmlRpcTypeString(valType)}"
                                                      + $" expected {StackDump(mappingStack)}");
            }

            if (valType != null)
            {
                XmlRpcType xmlRpcType = XmlRpcTypeInfo.GetXmlRpcType(valType);
                if (xmlRpcType == XmlRpcType.tMultiDimArray)
                {
                    mappingStack.Push("array mapped to type " + valType.Name);
                    return(MapMultiDimArray(iter, valType, mappingStack, mappingAction));
                }
                mappingStack.Push("array mapped to type " + valType.Name);
            }
            else
            {
                mappingStack.Push("array");
            }

            var values   = new List <object>();
            var elemType = DetermineArrayItemType(valType);

            while (iter.MoveNext() && iter.Current is ValueNode)
            {
                mappingStack.Push(string.Format("element {0}", values.Count));
                var value = MapValueNode(iter, elemType, mappingStack, mappingAction);
                values.Add(value);
                mappingStack.Pop();
            }

            var  bGotType = false;
            Type useType  = null;

            foreach (object value in values)
            {
                if (value == null)
                {
                    continue;
                }

                if (bGotType)
                {
                    if (useType != value.GetType())
                    {
                        useType = null;
                    }

                    continue;
                }

                useType  = value.GetType();
                bGotType = true;
            }

            var args = new object[1];

            args[0] = values.Count;
            object retObj = null;

            if (valType != null && valType != typeof(Array) && valType != typeof(object))
            {
                retObj = CreateArrayInstance(valType, args);
            }
            else
            {
                if (useType == null)
                {
                    retObj = CreateArrayInstance(typeof(object[]), args);
                }
                else
                {
                    retObj = Array.CreateInstance(useType, (int)args[0]);
                }
            }

            for (int j = 0; j < values.Count; j++)
            {
                ((Array)retObj).SetValue(values[j], j);
            }

            mappingStack.Pop();

            return(retObj);
        }
Beispiel #7
0
        private object MapStruct(IEnumerator <Node> iter, Type valueType, MappingStack mappingStack, MappingAction mappingAction, out Type mappedType)
        {
            mappedType = null;

            if (valueType.IsPrimitive)
            {
                throw new XmlRpcTypeMismatchException(mappingStack.MappingType
                                                      + " contains struct value where "
                                                      + XmlRpcTypeInfo.GetXmlRpcTypeString(valueType)
                                                      + " expected " + StackDump(mappingStack));
            }
            if (valueType.IsGenericType &&
                valueType.GetGenericTypeDefinition() == typeof(Nullable <>))
            {
                valueType = valueType.GetGenericArguments()[0];
            }
            object retObj;

            try
            {
                retObj = Activator.CreateInstance(valueType);
            }
            catch (Exception)
            {
                throw new XmlRpcTypeMismatchException(mappingStack.MappingType
                                                      + " contains struct value where "
                                                      + XmlRpcTypeInfo.GetXmlRpcTypeString(valueType)
                                                      + $" expected (as type {valueType.Name}) "
                                                      + StackDump(mappingStack));
            }
            // Note: mapping action on a struct is only applied locally - it
            // does not override the global mapping action when members of the
            // struct are mapped
            var localAction = mappingAction;

            if (valueType != null)
            {
                mappingStack.Push("struct mapped to type " + valueType.Name);
                localAction = StructMappingAction(valueType, mappingAction);
            }
            else
            {
                mappingStack.Push("struct");
            }
            // create map of field names and remove each name from it as
            // processed so we can determine which fields are missing
            var names = new List <string>();

            CreateFieldNamesMap(valueType, names);

            var fieldCount = 0;
            var rpcNames   = new List <string>();

            try
            {
                while (iter.MoveNext())
                {
                    if (!(iter.Current is StructMember))
                    {
                        break;
                    }

                    var rpcName = (iter.Current as StructMember).Value;
                    if (rpcNames.Contains(rpcName))
                    {
                        if (!IgnoreDuplicateMembers)
                        {
                            throw new XmlRpcInvalidXmlRpcException(mappingStack.MappingType
                                                                   + $" contains struct value with duplicate member {rpcName} {StackDump(mappingStack)}");
                        }

                        continue;
                    }
                    rpcNames.Add(rpcName);

                    var        name = GetStructName(valueType, rpcName) ?? rpcName;
                    MemberInfo mi   = valueType.GetField(name);
                    if (mi == null)
                    {
                        mi = valueType.GetProperty(name);
                    }

                    if (mi == null)
                    {
                        iter.MoveNext();  // move to value
                        if (iter.Current is ComplexValueNode)
                        {
                            int depth = iter.Current.Depth;
                            while (!(iter.Current is EndComplexValueNode && iter.Current.Depth == depth))
                            {
                                iter.MoveNext();
                            }
                        }
                        continue;
                    }
                    if (names.Contains(name))
                    {
                        names.Remove(name);
                    }
                    else
                    {
                        if (Attribute.IsDefined(mi, typeof(NonSerializedAttribute)))
                        {
                            mappingStack.Push($"member {name}");
                            throw new XmlRpcNonSerializedMember("Cannot map XML-RPC struct member onto member marked as [NonSerialized]: " + StackDump(mappingStack));
                        }
                    }

                    var memberType = mi.MemberType == MemberTypes.Field ? (mi as FieldInfo).FieldType : (mi as PropertyInfo).PropertyType;

                    var mappingMsg = valueType == null
                        ? $"member {name}"
                        : $"member {name} mapped to type {memberType.Name}";

                    iter.MoveNext();
                    var valObj = OnStack(mappingMsg, mappingStack, () => MapValueNode(iter, memberType, mappingStack, mappingAction));

                    if (mi.MemberType == MemberTypes.Field)
                    {
                        (mi as FieldInfo).SetValue(retObj, valObj);
                    }
                    else
                    {
                        (mi as PropertyInfo).SetValue(retObj, valObj, null);
                    }

                    fieldCount++;
                }

                if (localAction == MappingAction.Error && names.Count > 0)
                {
                    ReportMissingMembers(valueType, names, mappingStack);
                }

                return(retObj);
            }
            finally
            {
                mappingStack.Pop();
            }
        }