示例#1
0
        protected override void OnDocumentStructureCreated(
            RazorCodeDocument codeDocument,
            NamespaceDeclarationIntermediateNode @namespace,
            ClassDeclarationIntermediateNode @class,
            MethodDeclarationIntermediateNode method)
        {
            base.OnDocumentStructureCreated(codeDocument, @namespace, @class, method);

            @namespace.Content = "AspNetCore";

            @class.BaseType = "global::Microsoft.AspNetCore.Mvc.RazorPages.Page";

            var filePath = codeDocument.Source.RelativePath ?? codeDocument.Source.FilePath;

            @class.ClassName = CSharpIdentifier.GetClassNameFromPath(filePath);

            @class.Modifiers.Clear();
            @class.Modifiers.Add("public");

            method.MethodName = "ExecuteAsync";
            method.Modifiers.Clear();
            method.Modifiers.Add("public");
            method.Modifiers.Add("async");
            method.Modifiers.Add("override");
            method.ReturnType = $"global::{typeof(System.Threading.Tasks.Task).FullName}";

            var document = codeDocument.GetDocumentIntermediateNode();

            PageDirective.TryGetPageDirective(document, out var pageDirective);

            EnsureValidPageDirective(codeDocument, pageDirective);

            AddRouteTemplateMetadataAttribute(@namespace, @class, pageDirective);
        }
示例#2
0
        protected override void OnDocumentStructureCreated(
            RazorCodeDocument codeDocument,
            NamespaceDeclarationIntermediateNode @namespace,
            ClassDeclarationIntermediateNode @class,
            MethodDeclarationIntermediateNode method)
        {
            base.OnDocumentStructureCreated(codeDocument, @namespace, @class, method);

            @namespace.Content = "AspNetCore";

            var filePath = codeDocument.Source.RelativePath ?? codeDocument.Source.FilePath;

            if (string.IsNullOrEmpty(filePath))
            {
                // It's possible for a Razor document to not have a file path.
                // Eg. When we try to generate code for an in memory document like default imports.
                var checksum = BytesToString(codeDocument.Source.GetChecksum());
                @class.ClassName = $"AspNetCore_{checksum}";
            }
            else
            {
                @class.ClassName = CSharpIdentifier.GetClassNameFromPath(filePath);
            }

            @class.BaseType = "global::Microsoft.AspNetCore.Mvc.Razor.RazorPage<TModel>";
            @class.Modifiers.Clear();
            @class.Modifiers.Add("public");

            method.MethodName = "ExecuteAsync";
            method.Modifiers.Clear();
            method.Modifiers.Add("public");
            method.Modifiers.Add("async");
            method.Modifiers.Add("override");
            method.ReturnType = $"global::{typeof(System.Threading.Tasks.Task).FullName}";
        }
示例#3
0
        // internal for testing.
        //
        // This code does a best-effort attempt to compute a namespace 'suffix' - the path difference between
        // where the @namespace directive appears and where the current document is on disk.
        //
        // In the event that these two source either don't have FileNames set or don't follow a coherent hierarchy,
        // we will just use the namespace verbatim.
        internal static bool TryComputeNamespace(string source, DirectiveIntermediateNode directive, out string @namespace)
        {
            var directiveSource = NormalizeDirectory(directive.Source?.FilePath);

            var baseNamespace = directive.Tokens.FirstOrDefault()?.Content;

            if (string.IsNullOrEmpty(baseNamespace))
            {
                // The namespace directive was incomplete.
                @namespace = string.Empty;
                return(false);
            }

            if (string.IsNullOrEmpty(source) || directiveSource == null)
            {
                // No sources, can't compute a suffix.
                @namespace = baseNamespace;
                return(false);
            }

            // We're specifically using OrdinalIgnoreCase here because Razor treats all paths as case-insensitive.
            if (!source.StartsWith(directiveSource, StringComparison.OrdinalIgnoreCase) ||
                source.Length <= directiveSource.Length)
            {
                // The imports are not from the directory hierarchy, can't compute a suffix.
                @namespace = baseNamespace;
                return(false);
            }

            // OK so that this point we know that the 'imports' file containing this directive is in the directory
            // hierarchy of this soure file. This is the case where we can append a suffix to the baseNamespace.
            //
            // Everything so far has just been defensiveness on our part.

            var builder = new StringBuilder(baseNamespace);

            var segments = source.Substring(directiveSource.Length).Split(Separators);

            // Skip the last segment because it's the FileName.
            for (var i = 0; i < segments.Length - 1; i++)
            {
                builder.Append('.');
                builder.Append(CSharpIdentifier.SanitizeClassName(segments[i]));
            }

            @namespace = builder.ToString();
            return(true);
        }
        private static string GetClassNameFromPath(string path)
        {
            const string cshtmlExtension = ".cshtml";

            if (string.IsNullOrEmpty(path))
            {
                return(path);
            }

            if (path.EndsWith(cshtmlExtension, StringComparison.OrdinalIgnoreCase))
            {
                path = path.Substring(0, path.Length - cshtmlExtension.Length);
            }

            return(CSharpIdentifier.SanitizeIdentifier(path));
        }
示例#5
0
            protected override void ExecuteCore(RazorCodeDocument codeDocument, DocumentIntermediateNode documentNode)
            {
                if (documentNode.DocumentKind != RazorPageDocumentClassifierPass.RazorPageDocumentKind &&
                    documentNode.DocumentKind != MvcViewDocumentClassifierPass.MvcViewDocumentKind)
                {
                    // Not a page. Skip.
                    return;
                }

                var visitor = new Visitor();

                visitor.Visit(documentNode);

                var directive = visitor.LastNamespaceDirective;

                if (directive == null)
                {
                    // No namespace set. Skip.
                    return;
                }

                var @namespace = visitor.FirstNamespace;

                if (@namespace == null)
                {
                    // No namespace node. Skip.
                    return;
                }

                if (TryComputeNamespace(codeDocument.Source.FilePath, directive, out var computedNamespace))
                {
                    // Beautify the class name since we're using a hierarchy for namespaces.
                    var @class = visitor.FirstClass;
                    var prefix = CSharpIdentifier.SanitizeClassName(Path.GetFileNameWithoutExtension(codeDocument.Source.FilePath));
                    if (@class != null && documentNode.DocumentKind == RazorPageDocumentClassifierPass.RazorPageDocumentKind)
                    {
                        @class.ClassName = prefix + "_Page";
                    }
                    else if (@class != null && documentNode.DocumentKind == MvcViewDocumentClassifierPass.MvcViewDocumentKind)
                    {
                        @class.ClassName = prefix + "_View";
                    }
                }

                @namespace.Content = computedNamespace;
            }
示例#6
0
        protected override void OnDocumentStructureCreated(
            RazorCodeDocument codeDocument,
            NamespaceDeclarationIntermediateNode @namespace,
            ClassDeclarationIntermediateNode @class,
            MethodDeclarationIntermediateNode method)
        {
            base.OnDocumentStructureCreated(codeDocument, @namespace, @class, method);

            @namespace.Content = "AspNetCore";

            var filePath = codeDocument.Source.RelativePath ?? codeDocument.Source.FilePath;

            @class.ClassName = CSharpIdentifier.GetClassNameFromPath(filePath);
            @class.BaseType  = "global::Microsoft.AspNetCore.Mvc.Razor.RazorPage<TModel>";
            @class.Modifiers.Clear();
            @class.Modifiers.Add("public");

            method.MethodName = "ExecuteAsync";
            method.Modifiers.Clear();
            method.Modifiers.Add("public");
            method.Modifiers.Add("async");
            method.Modifiers.Add("override");
            method.ReturnType = $"global::{typeof(System.Threading.Tasks.Task).FullName}";
        }