private TSR.ScriptArray ConvertArrayObject(SC.IEnumerable array, int recurseDepth = 0)
        {
            if ((_infiniteDepth == false) && (recurseDepth >= this.Depth))
            {
                base.WriteWarning(string.Format(RS.MaxDepthForEnumerableReached, this.Depth));
                return(new TSR.ScriptArray(array));
            }

            TSR.ScriptArray scriptArray = new TSR.ScriptArray();

            foreach (object item in array)
            {
                if (item is Array)
                {
                    scriptArray.Add(ConvertArrayObject((SC.IEnumerable)item, recurseDepth + 1));
                }
                else
                {
                    if (item is SC.Hashtable)
                    {
                        scriptArray.Add(ConvertHashtableToScriptObject((SC.Hashtable)item, recurseDepth + 1));
                    }
                    else if (item is PSObject)
                    {
                        scriptArray.Add(ConvertPSObjectToScriptObject((PSObject)item, recurseDepth + 1));
                    }
                    else
                    {
                        scriptArray.Add(item);
                    }
                }
            }

            return(scriptArray);
        }
Exemple #2
0
 public abstract object Invoke(TemplateContext context, ScriptNode callerContext, ScriptArray arguments, ScriptBlockStatement blockStatement);
Exemple #3
0
            public override object Invoke(TemplateContext context, ScriptNode callerContext, ScriptArray arguments, ScriptBlockStatement blockStatement)
            {
                int expectedNumberOfParameters = Parameters.Length;

                if (_hasTemplateContext)
                {
                    expectedNumberOfParameters--;
                    if (_hasSpan)
                    {
                        expectedNumberOfParameters--;
                    }
                }

                int minimumRequiredParameters = expectedNumberOfParameters - _optionalParameterCount;

                // Check parameters
                if ((_hasObjectParams && arguments.Count < minimumRequiredParameters - 1) || (!_hasObjectParams && arguments.Count < minimumRequiredParameters))
                {
                    if (minimumRequiredParameters != expectedNumberOfParameters)
                    {
                        throw new ScriptRuntimeException(callerContext.Span, string.Format(RS.FuncMinArgCountMismatch, arguments.Count, callerContext, minimumRequiredParameters));
                    }
                    else
                    {
                        throw new ScriptRuntimeException(callerContext.Span, string.Format(RS.FuncArgCountMismatch, arguments.Count, callerContext, expectedNumberOfParameters));
                    }
                }

                // Convert arguments
                object[] paramArguments = null;
                if (_hasObjectParams)
                {
                    paramArguments = new object[arguments.Count - _lastParamsIndex];
                    _arguments[_lastParamsIndex] = paramArguments;
                }

                // Copy TemplateContext/SourceSpan parameters
                int argOffset = 0;
                int argMask   = 0;

                if (_hasTemplateContext)
                {
                    _arguments[0] = context;
                    argOffset++;
                    argMask |= 1;
                    if (_hasSpan)
                    {
                        _arguments[1] = callerContext.Span;
                        argOffset++;
                        argMask |= 2;
                    }
                }

                int argOrderedIndex = argOffset;

                // Setup any default parameters
                if (_optionalParameterCount > 0)
                {
                    for (int i = Parameters.Length - 1; i >= Parameters.Length - _optionalParameterCount; i--)
                    {
                        _arguments[i] = Parameters[i].DefaultValue;
                        argMask      |= 1 << i;
                    }
                }

                int paramsIndex = 0;

                for (int i = 0; i < arguments.Count; i++)
                {
                    Type argType = null;
                    try
                    {
                        int argIndex;
                        var arg      = arguments[i];
                        var namedArg = arg as ScriptNamedArgument;
                        if (namedArg != null)
                        {
                            arg = GetNamedArgument(context, callerContext, namedArg, out argIndex, out argType);
                            if (_hasObjectParams && argIndex == _lastParamsIndex)
                            {
                                argType  = _paramsElementType;
                                argIndex = argIndex + paramsIndex;
                                paramsIndex++;
                            }
                        }
                        else
                        {
                            argIndex = argOrderedIndex;
                            if (_hasObjectParams && argIndex == _lastParamsIndex)
                            {
                                argType  = _paramsElementType;
                                argIndex = argIndex + paramsIndex;
                                paramsIndex++;
                            }
                            else
                            {
                                argType = Parameters[argIndex].ParameterType;
                                argOrderedIndex++;
                            }
                        }

                        var argValue = context.ToObject(callerContext.Span, arg, argType);
                        if (paramArguments != null && argIndex >= _lastParamsIndex)
                        {
                            paramArguments[argIndex - _lastParamsIndex] = argValue;
                            argMask |= 1 << _lastParamsIndex;
                        }
                        else
                        {
                            _arguments[argIndex] = argValue;
                            argMask |= 1 << argIndex;
                        }
                    }
                    catch (Exception exception)
                    {
                        throw new ScriptRuntimeException(callerContext.Span, string.Format(RS.FuncCastArgTypeError, i, arguments[i]?.GetType(), argType), exception);
                    }
                }

                // In case we have named arguments we need to verify that all arguments were set
                if (argMask != (1 << Parameters.Length) - 1)
                {
                    if (minimumRequiredParameters != expectedNumberOfParameters)
                    {
                        throw new ScriptRuntimeException(callerContext.Span, string.Format(RS.FuncMinArgCountMismatch, arguments.Count, callerContext, minimumRequiredParameters));
                    }
                    else
                    {
                        throw new ScriptRuntimeException(callerContext.Span, string.Format(RS.FuncArgCountMismatch, arguments.Count, callerContext, expectedNumberOfParameters));
                    }
                }

                // Call method
                try
                {
                    var result = Method.Invoke(_target, _arguments);
                    return(result);
                }
                catch (TargetInvocationException exception)
                {
                    throw new ScriptRuntimeException(callerContext.Span, string.Format(RS.CallContextError, callerContext), exception.InnerException);
                }
            }
Exemple #4
0
 public object Invoke(TemplateContext context, ScriptNode callerContext, ScriptArray arguments, ScriptBlockStatement blockStatement)
 {
     return(_customFunction(context, callerContext, arguments));
 }
        private TSR.ScriptObject ConvertHashtableToScriptObject(SC.Hashtable hashtable, int recurseDepth = 0)
        {
            if (hashtable == null)
            {
                return(null);
            }

            TSR.ScriptObject templateScriptObj = new TSR.ScriptObject();

            SC.ICollection keys = hashtable.Keys;
            foreach (object key in keys)
            {
                string           propertyName                = key.ToString();
                object           propertyValue               = hashtable[key];
                TSR.ScriptObject convertedPropertyValue      = null;
                TSR.ScriptArray  convertedPropertyArrayValue = null;

                if (propertyValue is Array)
                {
                    if ((_infiniteDepth == true) || (recurseDepth < this.Depth))
                    {
                        convertedPropertyArrayValue = ConvertArrayObject((SC.IEnumerable)propertyValue, recurseDepth + 1);
                    }

                    if (convertedPropertyArrayValue != null)
                    {
                        templateScriptObj.Add(propertyName, convertedPropertyArrayValue);
                    }
                    else
                    {
                        templateScriptObj.Add(propertyName, propertyValue);
                    }
                }
                else
                {
                    // recursively convert property value to script object
                    // supports hashtable, psobject and pscustomobject
                    if (propertyValue is SC.Hashtable)
                    {
                        if (_convertHashtableRecurse &&
                            ((_infiniteDepth == true) || (recurseDepth < this.Depth)))
                        {
                            convertedPropertyValue = ConvertHashtableToScriptObject((SC.Hashtable)propertyValue, recurseDepth + 1);
                        }

                        //base.WriteObject(string.Format("{0} is hashtable", propertyName));
                    }
                    else if (propertyValue is PSObject)
                    {
                        if ((_infiniteDepth == true) || (recurseDepth < this.Depth))
                        {
                            convertedPropertyValue = ConvertPSObjectToScriptObject((PSObject)propertyValue, recurseDepth + 1);
                        }

                        //base.WriteObject(string.Format("{0} is psobject", propertyName));
                    }
                    else
                    {
                        // do nothing
                    }

                    if (convertedPropertyValue != null)
                    {
                        templateScriptObj.Add(propertyName, convertedPropertyValue);
                    }
                    else
                    {
                        templateScriptObj.Add(propertyName, propertyValue);
                    }
                }
            }

            return(templateScriptObj);
        }
        private TSR.ScriptObject ConvertPSObjectToScriptObject(PSObject psObject, int recurseDepth = 0)
        {
            if (psObject == null)
            {
                return(null);
            }

            TSR.ScriptObject templateScriptObj = new TSR.ScriptObject();

            foreach (PSPropertyInfo psProperty in psObject.Properties)
            {
                string           propertyName                = psProperty.Name;
                object           propertyValue               = psProperty.Value;
                TSR.ScriptObject convertedPropertyValue      = null;
                TSR.ScriptArray  convertedPropertyArrayValue = null;

                // handle object arrays
                if (propertyValue is Array)
                {
                    if ((_infiniteDepth == true) || (recurseDepth < this.Depth))
                    {
                        convertedPropertyArrayValue = ConvertArrayObject((SC.IEnumerable)propertyValue, recurseDepth + 1);
                    }
                    else
                    {
                        base.WriteWarning(string.Format(RS.MaxDepthReached, propertyName, "IEnumerable", this.Depth));
                    }

                    if (convertedPropertyArrayValue != null)
                    {
                        templateScriptObj.Add(propertyName, convertedPropertyArrayValue);
                    }
                    else
                    {
                        templateScriptObj.Add(propertyName, propertyValue);
                    }
                }
                else
                {
                    if (propertyValue is SC.Hashtable)
                    {
                        if (_convertHashtableRecurse &&
                            ((_infiniteDepth == true) || (recurseDepth < this.Depth)))
                        {
                            convertedPropertyValue = ConvertHashtableToScriptObject((SC.Hashtable)propertyValue, recurseDepth + 1);
                        }
                        else
                        {
                            // only warn if it's because max depth is reached
                            if (_convertHashtableRecurse == true)
                            {
                                base.WriteWarning(string.Format(RS.MaxDepthReached, propertyName, "Hashtable", this.Depth));
                            }
                        }
                    }
                    else if (propertyValue is PSObject)
                    {
                        if ((_infiniteDepth == true) || (recurseDepth < this.Depth))
                        {
                            convertedPropertyValue = ConvertPSObjectToScriptObject((PSObject)propertyValue, recurseDepth + 1);
                        }
                        else
                        {
                            base.WriteWarning(string.Format(RS.MaxDepthReached, propertyName, "PSObject", this.Depth));
                        }
                    }
                    else
                    {
                        // do nothing
                        //base.WriteObject(string.Format("{0} is {1}", propertyName, propertyValue.GetType().ToString()));
                    }

                    if (convertedPropertyValue != null)
                    {
                        templateScriptObj.Add(propertyName, convertedPropertyValue);
                    }
                    else
                    {
                        templateScriptObj.Add(propertyName, propertyValue);
                    }
                }
            }

            return(templateScriptObj);
        }