< Summary

Information
Class: TeleFlow.Generators.TelegramHandlerSymbols
Assembly: TeleFlow.Generators
File(s): /_/src/TeleFlow.Generators/TelegramHandlerSymbols.cs
Line coverage
98%
Covered lines: 104
Uncovered lines: 2
Coverable lines: 106
Total lines: 323
Line coverage: 98.1%
Branch coverage
91%
Covered branches: 112
Total branches: 123
Branch coverage: 91%
Method coverage

Feature is only available for sponsors

Upgrade to PRO version

Metrics

File(s)

/_/src/TeleFlow.Generators/TelegramHandlerSymbols.cs

#LineLine coverage
 1using Microsoft.CodeAnalysis;
 2
 3namespace TeleFlow.Generators;
 4
 5internal static class TelegramHandlerSymbols
 6{
 7    public const string CommandAttribute = "TeleFlow.Annotations.CommandAttribute";
 8    public const string MessageAttribute = "TeleFlow.Annotations.MessageAttribute";
 9    public const string CallbackAttribute = "TeleFlow.Annotations.CallbackAttribute";
 10    public const string GenericCallbackAttribute = "TeleFlow.Annotations.CallbackAttribute<TPayload>";
 11    public const string ErrorAttribute = "TeleFlow.Annotations.ErrorAttribute";
 12    public const string GenericErrorAttribute = "TeleFlow.Annotations.ErrorAttribute<TException>";
 13    public const string CallbackDataAttribute = "TeleFlow.Annotations.CallbackDataAttribute";
 14    public const string TelegramModuleAttribute = "TeleFlow.Annotations.TelegramModuleAttribute";
 15    public const string StateAttribute = "TeleFlow.Annotations.StateAttribute";
 16    public const string GenericStateAttribute = "TeleFlow.Annotations.StateAttribute<TStateGroup>";
 17    public const string StateGroupAttribute = "TeleFlow.Annotations.StateGroupAttribute";
 18    public const string StateValueAttribute = "TeleFlow.Annotations.StateValueAttribute";
 19    public const string SceneAttribute = "TeleFlow.Annotations.SceneAttribute";
 20    public const string SceneStepAttribute = "TeleFlow.Annotations.SceneStepAttribute";
 21    public const string TextAttribute = "TeleFlow.Annotations.TextAttribute";
 22    public const string TextTemplateAttribute = "TeleFlow.Annotations.TextTemplateAttribute";
 23    public const string CommandTemplateAttribute = "TeleFlow.Annotations.CommandTemplateAttribute";
 24    public const string TextRegexAttribute = "TeleFlow.Annotations.TextRegexAttribute";
 25    public const string CommandRegexAttribute = "TeleFlow.Annotations.CommandRegexAttribute";
 26    public const string ChatMemberUpdatedAttribute = "TeleFlow.Annotations.ChatMemberUpdatedAttribute";
 27    public const string MyChatMemberUpdatedAttribute = "TeleFlow.Annotations.MyChatMemberUpdatedAttribute";
 28    public const string ChatMemberTransitionAttribute = "TeleFlow.Annotations.ChatMemberTransitionAttribute";
 29    public const string ChatMemberChangedAttribute = "TeleFlow.Annotations.ChatMemberChangedAttribute";
 30    public const string AutoAnswerCallbackAttribute = "TeleFlow.Annotations.AutoAnswerCallbackAttribute";
 31    public const string RequireTelegramRoleAttribute = "TeleFlow.Annotations.RequireTelegramRoleAttribute";
 32    public const string ChatTypeAttribute = "TeleFlow.Annotations.ChatTypeAttribute";
 33    public const string SenderChatTypeAttribute = "TeleFlow.Annotations.SenderChatTypeAttribute";
 34    public const string ChatIdAttribute = "TeleFlow.Annotations.ChatIdAttribute";
 35    public const string ChatUsernameAttribute = "TeleFlow.Annotations.ChatUsernameAttribute";
 36    public const string FromUserAttribute = "TeleFlow.Annotations.FromUserAttribute";
 37    public const string HasTextAttribute = "TeleFlow.Annotations.HasTextAttribute";
 38    public const string HasPhotoAttribute = "TeleFlow.Annotations.HasPhotoAttribute";
 39    public const string HasDocumentAttribute = "TeleFlow.Annotations.HasDocumentAttribute";
 40    public const string HasCaptionAttribute = "TeleFlow.Annotations.HasCaptionAttribute";
 41    public const string HasVideoAttribute = "TeleFlow.Annotations.HasVideoAttribute";
 42    public const string HasAnimationAttribute = "TeleFlow.Annotations.HasAnimationAttribute";
 43    public const string HasAudioAttribute = "TeleFlow.Annotations.HasAudioAttribute";
 44    public const string HasVoiceAttribute = "TeleFlow.Annotations.HasVoiceAttribute";
 45    public const string HasVideoNoteAttribute = "TeleFlow.Annotations.HasVideoNoteAttribute";
 46    public const string HasStickerAttribute = "TeleFlow.Annotations.HasStickerAttribute";
 47    public const string HasContactAttribute = "TeleFlow.Annotations.HasContactAttribute";
 48    public const string HasLocationAttribute = "TeleFlow.Annotations.HasLocationAttribute";
 49    public const string HasVenueAttribute = "TeleFlow.Annotations.HasVenueAttribute";
 50    public const string HasPollAttribute = "TeleFlow.Annotations.HasPollAttribute";
 51    public const string HasDiceAttribute = "TeleFlow.Annotations.HasDiceAttribute";
 52    public const string FromBotAttribute = "TeleFlow.Annotations.FromBotAttribute";
 53    public const string FromPremiumUserAttribute = "TeleFlow.Annotations.FromPremiumUserAttribute";
 54    public const string IsReplyAttribute = "TeleFlow.Annotations.IsReplyAttribute";
 55    public const string ReplyToBotAttribute = "TeleFlow.Annotations.ReplyToBotAttribute";
 56    public const string MessageThreadIdAttribute = "TeleFlow.Annotations.MessageThreadIdAttribute";
 57    public const string HasMessageThreadAttribute = "TeleFlow.Annotations.HasMessageThreadAttribute";
 58    public const string HasCallbackDataAttribute = "TeleFlow.Annotations.HasCallbackDataAttribute";
 59    public const string CallbackDataPrefixAttribute = "TeleFlow.Annotations.CallbackDataPrefixAttribute";
 60    public const string GenericUseFilterAttribute = "TeleFlow.Annotations.UseFilterAttribute<TFilter>";
 61    public const string GenericTelegramFilterAttribute = "TeleFlow.Annotations.TelegramFilterAttribute<TFilter>";
 62    public const string TextMatchMode = "TeleFlow.Annotations.TextMatchMode";
 63    public const string State = "TeleFlow.Framework.States.State";
 64    public const string MessageContext = "TeleFlow.Telegram.MessageContext";
 65    public const string CallbackQueryContext = "TeleFlow.Telegram.CallbackQueryContext";
 66    public const string ChatMemberUpdatedContext = "TeleFlow.Telegram.ChatMemberUpdatedContext";
 67    public const string TelegramErrorContext = "TeleFlow.Telegram.TelegramErrorContext";
 68    public const string TelegramErrorHandlingResult = "TeleFlow.Telegram.TelegramErrorHandlingResult";
 69    public const string TelegramUpdateContext = "TeleFlow.Telegram.TelegramUpdateContext";
 70    public const string MessageHandler = "TeleFlow.Telegram.MessageHandler";
 71    public const string CallbackHandler = "TeleFlow.Telegram.CallbackHandler";
 72    public const string GenericCallbackHandler = "TeleFlow.Telegram.CallbackHandler<TPayload>";
 73    public const string ChatMemberUpdateHandler = "TeleFlow.Telegram.ChatMemberUpdateHandler";
 74    public const string GenericTelegramFilter = "TeleFlow.Telegram.ITelegramFilter<TContext>";
 75    public const string GenericParameterizedTelegramFilter = "TeleFlow.Telegram.ITelegramFilter<TContext, TAttribute>";
 76    public const string Task = "System.Threading.Tasks.Task";
 77    public const string ValueTask = "System.Threading.Tasks.ValueTask";
 78    public const string CancellationToken = "System.Threading.CancellationToken";
 79    public const string Exception = "System.Exception";
 80
 81    public static bool HasAttribute(
 82        ISymbol symbol,
 83        string metadataName,
 84        bool inherit = false)
 85    {
 821486        return GetAttributes(symbol, metadataName, inherit).Count > 0;
 87    }
 88
 89    public static IReadOnlyList<AttributeData> GetAttributes(
 90        ISymbol symbol,
 91        string metadataName,
 92        bool inherit = false)
 93    {
 1985494        return GetAttributesCore(
 1985495            symbol,
 4079596            attribute => IsAttribute(attribute, metadataName),
 1985497            inherit,
 1985498            AllowsMultiple(metadataName));
 99    }
 100
 101    public static bool HasGenericAttribute(
 102        ISymbol symbol,
 103        string metadataName,
 104        bool inherit = false)
 105    {
 531106        return GetGenericAttributes(symbol, metadataName, inherit).Count > 0;
 107    }
 108
 109    public static IReadOnlyList<AttributeData> GetGenericAttributes(
 110        ISymbol symbol,
 111        string metadataName,
 112        bool inherit = false)
 113    {
 1291114        return GetAttributesCore(
 1291115            symbol,
 2486116            attribute => IsGenericAttribute(attribute, metadataName),
 1291117            inherit,
 1291118            AllowsMultiple(metadataName));
 119    }
 120
 121    public static AttributeData? GetFirstAttribute(
 122        ISymbol symbol,
 123        string metadataName,
 124        bool inherit = false)
 125    {
 468126        IReadOnlyList<AttributeData> attributes = GetAttributes(symbol, metadataName, inherit);
 468127        return attributes.Count > 0 ? attributes[0] : null;
 128    }
 129
 130    public static bool IsAttribute(AttributeData attribute, string metadataName)
 131    {
 41568132        return string.Equals(
 41568133            attribute.AttributeClass?.ToDisplayString(SymbolDisplayFormat.CSharpErrorMessageFormat),
 41568134            metadataName,
 41568135            StringComparison.Ordinal);
 136    }
 137
 138    public static bool IsGenericAttribute(AttributeData attribute, string metadataName)
 139    {
 2872140        return string.Equals(
 2872141            attribute.AttributeClass?.OriginalDefinition.ToDisplayString(SymbolDisplayFormat.CSharpErrorMessageFormat),
 2872142            metadataName,
 2872143            StringComparison.Ordinal);
 144    }
 145
 146    public static bool IsType(ITypeSymbol symbol, string metadataName)
 147    {
 876148        return string.Equals(
 876149            symbol.ToDisplayString(SymbolDisplayFormat.CSharpErrorMessageFormat),
 876150            metadataName,
 876151            StringComparison.Ordinal);
 152    }
 153
 154    public static IReadOnlyList<AttributeData> GetTelegramFilterAttributes(
 155        ISymbol symbol,
 156        bool inherit = false)
 157    {
 303158        return GetAttributesCore(
 303159            symbol,
 772160            static attribute => TryGetTelegramFilterAttributeFilterType(attribute, out _),
 303161            inherit,
 303162            allowMultiple: true);
 163    }
 164
 165    public static bool TryGetTelegramFilterAttributeFilterType(
 166        AttributeData attribute,
 167        out ITypeSymbol filterType)
 168    {
 774169        filterType = null!;
 170
 774171        if (attribute.AttributeClass is not { } attributeType)
 172        {
 0173            return false;
 174        }
 175
 6662176        for (INamedTypeSymbol? current = attributeType; current is not null; current = current.BaseType)
 177        {
 2562178            if (string.Equals(
 2562179                    current.OriginalDefinition.ToDisplayString(SymbolDisplayFormat.CSharpErrorMessageFormat),
 2562180                    GenericTelegramFilterAttribute,
 2562181                    StringComparison.Ordinal) &&
 2562182                current.TypeArguments.Length == 1)
 183            {
 5184                filterType = current.TypeArguments[0];
 5185                return true;
 186            }
 187        }
 188
 769189        return false;
 190    }
 191
 192    public static bool HasAnyRouteAttribute(ISymbol symbol)
 193    {
 679194        return HasAttribute(symbol, CommandAttribute, inherit: true) ||
 679195               HasAttribute(symbol, MessageAttribute, inherit: true) ||
 679196               HasAttribute(symbol, TextAttribute, inherit: true) ||
 679197               HasAttribute(symbol, TextTemplateAttribute, inherit: true) ||
 679198               HasAttribute(symbol, CommandTemplateAttribute, inherit: true) ||
 679199               HasAttribute(symbol, TextRegexAttribute, inherit: true) ||
 679200               HasAttribute(symbol, CommandRegexAttribute, inherit: true) ||
 679201               HasAttribute(symbol, CallbackAttribute, inherit: true) ||
 679202               HasGenericAttribute(symbol, GenericCallbackAttribute, inherit: true) ||
 679203               HasAttribute(symbol, ChatMemberUpdatedAttribute, inherit: true) ||
 679204               HasAttribute(symbol, MyChatMemberUpdatedAttribute, inherit: true);
 205    }
 206
 207    public static bool HasAnyErrorAttribute(ISymbol symbol)
 208    {
 419209        return GetErrorAttributes(symbol, inherit: true).Count > 0;
 210    }
 211
 212    public static IReadOnlyList<AttributeData> GetErrorAttributes(
 213        ISymbol symbol,
 214        bool inherit = false)
 215    {
 571216        return GetAttributesCore(
 571217            symbol,
 401218            static attribute => IsAttribute(attribute, ErrorAttribute) ||
 401219                                IsGenericAttribute(attribute, GenericErrorAttribute),
 571220            inherit,
 571221            allowMultiple: true);
 222    }
 223
 224    private static IReadOnlyList<AttributeData> GetAttributesCore(
 225        ISymbol symbol,
 226        Func<AttributeData, bool> predicate,
 227        bool inherit,
 228        bool allowMultiple)
 229    {
 22019230        if (!inherit)
 231        {
 621232            return GetDirectAttributes(symbol, predicate);
 233        }
 234
 21398235        return symbol switch
 21398236        {
 14822237            IMethodSymbol method => GetInheritedMethodAttributes(method, predicate, allowMultiple),
 6576238            INamedTypeSymbol type => GetInheritedTypeAttributes(type, predicate, allowMultiple),
 0239            _ => GetDirectAttributes(symbol, predicate)
 21398240        };
 241    }
 242
 243    private static IReadOnlyList<AttributeData> GetInheritedMethodAttributes(
 244        IMethodSymbol method,
 245        Func<AttributeData, bool> predicate,
 246        bool allowMultiple)
 247    {
 14822248        List<AttributeData> attributes = new List<AttributeData>();
 249
 59612250        for (IMethodSymbol? current = method; current is not null; current = current.OverriddenMethod)
 251        {
 15300252            AttributeData[] directAttributes = GetDirectAttributes(current, predicate);
 253
 15300254            if (allowMultiple)
 255            {
 6202256                attributes.AddRange(directAttributes);
 6202257                continue;
 258            }
 259
 9098260            if (directAttributes.Length > 0)
 261            {
 316262                return directAttributes;
 263            }
 264        }
 265
 14506266        return attributes;
 267    }
 268
 269    private static IReadOnlyList<AttributeData> GetInheritedTypeAttributes(
 270        INamedTypeSymbol type,
 271        Func<AttributeData, bool> predicate,
 272        bool allowMultiple)
 273    {
 6576274        List<AttributeData> attributes = new List<AttributeData>();
 275
 42266276        for (INamedTypeSymbol? current = type; current is not null; current = current.BaseType)
 277        {
 14598278            AttributeData[] directAttributes = GetDirectAttributes(current, predicate);
 279
 14598280            if (allowMultiple)
 281            {
 3909282                attributes.AddRange(directAttributes);
 3909283                continue;
 284            }
 285
 10689286            if (directAttributes.Length > 0)
 287            {
 41288                return directAttributes;
 289            }
 290        }
 291
 6535292        return attributes;
 293    }
 294
 295    private static AttributeData[] GetDirectAttributes(
 296        ISymbol symbol,
 297        Func<AttributeData, bool> predicate)
 298    {
 30519299        return symbol
 30519300            .GetAttributes()
 30519301            .Where(predicate)
 30519302            .ToArray();
 303    }
 304
 305    private static bool AllowsMultiple(string metadataName)
 306    {
 21145307        return metadataName is CommandAttribute or
 21145308            TextAttribute or
 21145309            TextTemplateAttribute or
 21145310            CommandTemplateAttribute or
 21145311            TextRegexAttribute or
 21145312            CommandRegexAttribute or
 21145313            ChatMemberTransitionAttribute or
 21145314            ChatMemberChangedAttribute or
 21145315            RequireTelegramRoleAttribute or
 21145316            StateAttribute or
 21145317            GenericStateAttribute or
 21145318            GenericUseFilterAttribute or
 21145319            GenericTelegramFilterAttribute or
 21145320            ErrorAttribute or
 21145321            GenericErrorAttribute;
 322    }
 323}

Methods/Properties

HasAttribute(Microsoft.CodeAnalysis.ISymbol,System.String,System.Boolean)
GetAttributes(Microsoft.CodeAnalysis.ISymbol,System.String,System.Boolean)
HasGenericAttribute(Microsoft.CodeAnalysis.ISymbol,System.String,System.Boolean)
GetGenericAttributes(Microsoft.CodeAnalysis.ISymbol,System.String,System.Boolean)
GetFirstAttribute(Microsoft.CodeAnalysis.ISymbol,System.String,System.Boolean)
IsAttribute(Microsoft.CodeAnalysis.AttributeData,System.String)
IsGenericAttribute(Microsoft.CodeAnalysis.AttributeData,System.String)
IsType(Microsoft.CodeAnalysis.ITypeSymbol,System.String)
GetTelegramFilterAttributes(Microsoft.CodeAnalysis.ISymbol,System.Boolean)
TryGetTelegramFilterAttributeFilterType(Microsoft.CodeAnalysis.AttributeData,Microsoft.CodeAnalysis.ITypeSymbol&)
HasAnyRouteAttribute(Microsoft.CodeAnalysis.ISymbol)
HasAnyErrorAttribute(Microsoft.CodeAnalysis.ISymbol)
GetErrorAttributes(Microsoft.CodeAnalysis.ISymbol,System.Boolean)
GetAttributesCore(Microsoft.CodeAnalysis.ISymbol,System.Func`2<Microsoft.CodeAnalysis.AttributeData,System.Boolean>,System.Boolean,System.Boolean)
GetInheritedMethodAttributes(Microsoft.CodeAnalysis.IMethodSymbol,System.Func`2<Microsoft.CodeAnalysis.AttributeData,System.Boolean>,System.Boolean)
GetInheritedTypeAttributes(Microsoft.CodeAnalysis.INamedTypeSymbol,System.Func`2<Microsoft.CodeAnalysis.AttributeData,System.Boolean>,System.Boolean)
GetDirectAttributes(Microsoft.CodeAnalysis.ISymbol,System.Func`2<Microsoft.CodeAnalysis.AttributeData,System.Boolean>)
AllowsMultiple(System.String)