コード例 #1
0
        /// <summary>
        /// Process local variable declaration.
        /// </summary>
        /// <param name="localVariableDeclaration">
        /// The local variable declaration.
        /// </param>
        private static void ProcessLocalVariableDeclaration(ILocalVariableDeclaration localVariableDeclaration)
        {
            IMultipleLocalVariableDeclaration multipleDeclaration = MultipleLocalVariableDeclarationNavigator.GetByDeclarator(localVariableDeclaration);

            if (multipleDeclaration.Declarators.Count > 1)
            {
                IType newType = CSharpTypeFactory.CreateType(multipleDeclaration.TypeUsage);

                using (WriteLockCookie.Create(true))
                {
                    multipleDeclaration.SetTypeUsage(CSharpElementFactory.GetInstance(localVariableDeclaration.GetPsiModule()).CreateTypeUsageNode(newType));
                }
            }
            else
            {
                ILocalVariable variable = localVariableDeclaration.DeclaredElement;
                if (variable != null)
                {
                    if (!multipleDeclaration.IsVar)
                    {
                        using (WriteLockCookie.Create(true))
                        {
                            localVariableDeclaration.SetType(variable.Type);
                        }
                    }
                }
            }
        }
コード例 #2
0
        private void AddSpecflowStep(IPsiSourceFile targetFile, string classClrName, GherkinStepKind stepKind, string stepText)
        {
            var cSharpFile = targetFile.GetProject().GetCSharpFile(targetFile.DisplayName.Substring(targetFile.DisplayName.LastIndexOf('>') + 2));

            if (cSharpFile == null)
            {
                return;
            }

            foreach (var type in cSharpFile.GetChildrenInSubtrees <IClassDeclaration>())
            {
                if (!(type is IClassDeclaration classDeclaration))
                {
                    continue;
                }
                if (classDeclaration.CLRName != classClrName)
                {
                    continue;
                }
                if (classDeclaration.DeclaredElement?.GetAttributeInstances(AttributesSource.Self).All(x => x.GetAttributeType().GetClrName().FullName != "TechTalk.SpecFlow.Binding") != true)
                {
                    continue;
                }

                var factory    = CSharpElementFactory.GetInstance(classDeclaration);
                var methodName = _stepDefinitionBuilder.GetStepDefinitionMethodNameFromStepText(stepKind, stepText, _reference.IsInsideScenarioOutline());
                methodName = cSharpFile.GetPsiServices().Naming.Suggestion.GetDerivedName(methodName, NamedElementKinds.Method, ScopeKind.Common, CSharpLanguage.Instance, new SuggestionOptions(), targetFile);
                var parameters = _stepDefinitionBuilder.GetStepDefinitionParameters(stepText, _reference.IsInsideScenarioOutline());
                var pattern    = _stepDefinitionBuilder.GetPattern(stepText, _reference.IsInsideScenarioOutline());

                var attributeType     = CSharpTypeFactory.CreateType(SpecflowAttributeHelper.GetAttributeClrName(stepKind), classDeclaration.GetPsiModule());
                var formatString      = $"[$0(@\"$1\")] public void {methodName}() {{ScenarioContext.StepIsPending();}}";
                var methodDeclaration = factory.CreateTypeMemberDeclaration(formatString, attributeType, pattern.Replace("\"", "\"\"")) as IMethodDeclaration;
                if (methodDeclaration == null)
                {
                    continue;
                }
                var psiModule = classDeclaration.GetPsiModule();
                foreach (var(parameterName, parameterType) in parameters)
                {
                    methodDeclaration.AddParameterDeclarationAfter(ParameterKind.VALUE, CSharpTypeFactory.CreateType(parameterType, psiModule), parameterName, null);
                }

                IClassMemberDeclaration insertedDeclaration;
                using (new PsiTransactionCookie(type.GetPsiServices(), DefaultAction.Commit, "Generate specflow step"))
                {
                    insertedDeclaration = classDeclaration.AddClassMemberDeclaration((IClassMemberDeclaration)methodDeclaration);
                }

                var invocationExpression = insertedDeclaration.GetChildrenInSubtrees <IInvocationExpression>().FirstOrDefault();
                if (invocationExpression != null)
                {
                    invocationExpression.NavigateToNode(true);
                }
                else
                {
                    insertedDeclaration.NavigateToNode(true);
                }
            }
        }
コード例 #3
0
            public MemberGenerationContext(
                [NotNull] ITypeDeclaration typeDeclaration,
                [CanBeNull] IModifiersList modifiersList,
                [CanBeNull] ITypeUsage expectedReturnTypeUsage,
                [NotNull] TextLookupRanges memberReplaceRanges)
            {
                TypeDeclaration      = typeDeclaration;
                PsiModule            = typeDeclaration.GetPsiModule();
                ModifiersList        = modifiersList;
                MemberReplaceRanges  = memberReplaceRanges;
                ExpectedAccessRights = ModifiersUtil.GetAccessRightsModifiers(modifiersList);

                if (expectedReturnTypeUsage != null)
                {
                    ExpectedReturnType = CSharpTypeFactory.CreateType(expectedReturnTypeUsage);
                }
            }
コード例 #4
0
        /// <summary>
        /// Get return type.
        /// </summary>
        /// <param name="declaration">
        /// The declaration.
        /// </param>
        /// <returns>
        /// An IType for the return type.
        /// </returns>
        public static IType GetReturnType(this IMethodDeclaration declaration)
        {
            IMethodDeclaration methodDeclarationNode = declaration;

            if (methodDeclarationNode == null)
            {
                return(null);
            }

            ITypeUsage typeUsage = methodDeclarationNode.TypeUsage;

            if (typeUsage == null)
            {
                return(null);
            }

            return(CSharpTypeFactory.CreateType(typeUsage));
        }
コード例 #5
0
        public override ReferenceCollection GetReferences(ITreeNode element, ReferenceCollection oldReferences)
        {
            if (ResolveUtil.CheckThatAllReferencesBelongToElement <SyncVarHookReference>(oldReferences, element))
            {
                return(oldReferences);
            }

            var literal = element as ILiteralExpression;

            if (literal == null || !literal.ConstantValue.IsString())
            {
                return(ReferenceCollection.Empty);
            }

            var propertyAssignment          = literal.GetContainingNode <IPropertyAssignment>();
            var propertyAssignmentReference = propertyAssignment?.Reference;

            if (propertyAssignmentReference == null || propertyAssignmentReference.GetName() != "hook")
            {
                return(ReferenceCollection.Empty);
            }

            var assignedField = propertyAssignmentReference.Resolve().DeclaredElement as IField;
            var attributeType = assignedField?.GetContainingType();

            if (attributeType == null || !Equals(attributeType.GetClrName(), KnownTypes.SyncVarAttribute))
            {
                return(ReferenceCollection.Empty);
            }

            var multipleFieldDeclaration = propertyAssignment.GetContainingNode <IMultipleFieldDeclaration>();
            var declaredFieldTypeUsage   = multipleFieldDeclaration?.TypeUsage;
            var containingType           = multipleFieldDeclaration?.GetContainingNode <IClassLikeDeclaration>()?.DeclaredElement;

            if (containingType != null && declaredFieldTypeUsage != null)
            {
                var declaredFieldType = CSharpTypeFactory.CreateType(declaredFieldTypeUsage);
                var reference         = new SyncVarHookReference(containingType, declaredFieldType, literal);
                return(new ReferenceCollection(reference));
            }

            return(ReferenceCollection.Empty);
        }
コード例 #6
0
        public IEnumerable <AvailableBindingClass> GetBindingTypes(IPsiModule module)
        {
            foreach (var(fullClassName, sourceFile) in _mergeData.SpecflowBindingTypes.SelectMany(e => e.Value.Select(v => (fullClassName: e.Key, sourceFile: v))))
            {
                if (!module.Equals(sourceFile.PsiModule) && !module.References(sourceFile.PsiModule))
                {
                    continue;
                }
                yield return(new AvailableBindingClass(sourceFile, fullClassName));
            }

            // Since we cannot know when cache are built if a partial class in a given file has an attribute or not.
            // This is due to the fact that `DeclaredElement` are resolved using cache and we cannot depends ond cache when building a cache.
            // The check need to be done at this time.
            foreach (var(fullClassName, sourceFile) in _mergeData.PotentialSpecflowBindingTypes.SelectMany(e => e.Value.Select(v => (fullClassName: e.Key, sourceFile: v))))
            {
                if (!module.Equals(sourceFile.PsiModule) && !module.References(sourceFile.PsiModule))
                {
                    continue;
                }
                var type = CSharpTypeFactory.CreateType(fullClassName, sourceFile.PsiModule);
                if (!(type is DeclaredTypeFromCLRName declaredTypeFromClrName))
                {
                    continue;
                }
                var resolveResult = declaredTypeFromClrName.Resolve();
                if (!resolveResult.IsValid())
                {
                    continue;
                }
                if (!(resolveResult.DeclaredElement is IClass @class))
                {
                    continue;
                }
                if (@class.GetAttributeInstances(AttributesSource.Self).All(x => x.GetAttributeType().GetClrName().FullName != "TechTalk.SpecFlow.BindingAttribute"))
                {
                    continue;
                }
                yield return(new AvailableBindingClass(sourceFile, fullClassName));
            }
        }
コード例 #7
0
        private IType CreateIType([NotNull] string typeName)
        {
            var type = CSharpTypeFactory.CreateType(typeName, classDeclaration);

            return(!type.IsResolved ? null : type);
        }
コード例 #8
0
        public override bool Execute(IProgressIndicator progressIndicator)
        {
            var languageService = CSharpLanguage.Instance.LanguageService();

            if (languageService == null)
            {
                return(false);
            }
            var ctor = _ctor.FindDeclaredElement();

            if (ctor == null)
            {
                return(false);
            }
            var definingClass = _class.FindDeclaredElement();

            if (definingClass == null)
            {
                return(false);
            }
            var factory  = CSharpElementFactory.GetInstance(ctor.Module);
            var ctorDecl = ctor.GetDeclarations().FirstOrDefault();

            if (ctorDecl == null)
            {
                var typeDecl = definingClass.GetDeclarations().FirstOrDefault() as IClassLikeDeclaration;
                if (typeDecl == null)
                {
                    return(false);
                }
                var typeBody = typeDecl.Body;
                ctorDecl = factory.CreateTypeMemberDeclaration("public $0() {}", typeDecl.DeclaredName);
                if (typeBody.FirstChild == null)
                {
                    return(false);
                }

                ctorDecl = ModificationUtil.AddChildBefore(
                    typeBody,
                    typeBody.FirstChild.NextSibling,
                    ctorDecl).GetContainingNode <IConstructorDeclaration>(true);
            }
            if (ctorDecl == null)
            {
                return(false);
            }
            var type = CSharpTypeFactory.CreateType(_parameterType, ctorDecl);

            if (!type.IsResolved)
            {
                type = CSharpTypeFactory.CreateType(_parameterType, ctorDecl.GetPsiModule());
            }
            string recommendedName = null;

            if (!type.IsResolved)
            {
                var presentableName = type.GetPresentableName(CSharpLanguage.Instance);
                var indexOfGeneric  = presentableName.IndexOf('<');
                if (indexOfGeneric != -1)
                {
                    var interfaceName   = presentableName.Substring(1, indexOfGeneric - 1);
                    var genericArgument = presentableName.Substring(indexOfGeneric).Trim('<', '>');
                    recommendedName = type.GetPsiServices().Naming.Suggestion.GetDerivedName(
                        genericArgument + interfaceName,
                        NamedElementKinds.Parameters,
                        ScopeKind.Common,
                        CSharpLanguage.Instance,
                        new SuggestionOptions(),
                        ctorDecl.GetSourceFile());
                }
                var interfaceDecl = factory.CreateTypeMemberDeclaration("public interface IFoo {}");
                interfaceDecl.SetName(presentableName);
                languageService.CodeFormatter.Format(interfaceDecl, CodeFormatProfile.GENERATOR);
                var containingType = ctor.GetContainingType();
                if (containingType == null)
                {
                    return(false);
                }
                var containingTypeDecl = containingType.GetDeclarations().First();
                ModificationUtil.AddChildBefore(containingTypeDecl, interfaceDecl);
            }
            type = CSharpTypeFactory.CreateType(_parameterType, ctorDecl);
            if (recommendedName == null)
            {
                var suggestionOptions = new SuggestionOptions();
                recommendedName = type.GetPsiServices().Naming.Suggestion.GetDerivedName(
                    type.GetPresentableName(CSharpLanguage.Instance),
                    NamedElementKinds.Parameters,
                    ScopeKind.Common,
                    CSharpLanguage.Instance,
                    suggestionOptions,
                    ctorDecl.GetSourceFile());
            }
            var parametersOwner = ctorDecl as ICSharpParametersOwnerDeclaration;
            var references      = FindReferences(parametersOwner, progressIndicator);

            if (parametersOwner == null)
            {
                return(false);
            }
            parametersOwner.AddParameterDeclarationAfter(
                ParameterKind.VALUE, type, recommendedName,
                parametersOwner.ParameterDeclarations.LastOrDefault());

            foreach (var reference in references)
            {
                ChangeReference(reference, recommendedName, type);
            }

            return(true);
        }