public override void AddSourceMappingFor(IntermediateNode node) { if (node == null) { throw new ArgumentNullException(nameof(node)); } if (node.Source == null) { return; } if (SourceDocument.FilePath != null && !string.Equals(SourceDocument.FilePath, node.Source.Value.FilePath, StringComparison.OrdinalIgnoreCase)) { // We don't want to generate line mappings for imports. return; } var source = node.Source.Value; var generatedLocation = new SourceSpan(CodeWriter.Location, source.Length); var sourceMapping = new SourceMapping(source, generatedLocation); SourceMappings.Add(sourceMapping); }
public void WriteUsingDirective_WithSource_WritesContentWithLinePragmaAndMapping() { // Arrange var writer = new DesignTimeNodeWriter(); var sourceDocument = TestRazorSourceDocument.Create("@using System;"); var context = TestCodeRenderingContext.CreateDesignTime(); var originalSpan = new SourceSpan("test.cshtml", 0, 0, 0, 6); var generatedSpan = new SourceSpan(null, 21 + Environment.NewLine.Length, 1, 0, 6); var expectedSourceMapping = new SourceMapping(originalSpan, generatedSpan); var node = new UsingDirectiveIntermediateNode() { Content = "System", Source = originalSpan, }; // Act writer.WriteUsingDirective(context, node); // Assert var mapping = Assert.Single(((DefaultCodeRenderingContext)context).SourceMappings); Assert.Equal(expectedSourceMapping, mapping); var csharp = context.CodeWriter.GenerateCode(); Assert.Equal( @"#line 1 ""test.cshtml"" using System; #line default #line hidden ", csharp, ignoreLineEndingDifferences: true); }
public void SourceMapCache_HandlesDuplicateNames() { var cache = new SourceMapCache(new SourceMap() { version = 3, file = "foo.js", sources = new string[] { "source.js" }, names = new string[] { "name1", "name1", "name3" }, mappings = ";EAACA;;IAEEA;;MAEEE", sourceRoot = "http://example.com" }); { var expected = new SourceMapping(1, 1, 2, 2, "source.js", "name1"); var actual = cache.SourceMappingFor(2, 2); Assert.AreEqual(expected, actual); } { var expected = new SourceMapping(3, 3, 4, 4, "source.js", "name1"); var actual = cache.SourceMappingFor(4, 4); Assert.AreEqual(expected, actual); } { var expected = new SourceMapping(5, 5, 6, 6, "source.js", "name3"); var actual = cache.SourceMappingFor(6, 6); Assert.AreEqual(expected, actual); } }
private void AssertNotEqual(SourceMapping left, SourceMapping right) { Assert.False(left == right); Assert.False(left.Equals(right)); Assert.False(right.Equals(left)); Assert.False(Equals(left, right)); }
static Range ConvertMapping(RazorSourceDocument sourceDocument, SourceMapping mapping) { var startLocation = sourceDocument.Lines.GetLocation(mapping.OriginalSpan.AbsoluteIndex); var endLocation = sourceDocument.Lines.GetLocation(mapping.OriginalSpan.AbsoluteIndex + mapping.OriginalSpan.Length); var convertedRange = new Range( new Position(startLocation.LineIndex, startLocation.CharacterIndex), new Position(endLocation.LineIndex, endLocation.CharacterIndex)); return(convertedRange); }
public void GeneratedCodeMappingsAreNotEqualIfAbsoluteIndexIsNotEqual() { // Arrange var left = new SourceMapping( new SourceSpan(new SourceLocation(1, 2, 3), 4), new SourceSpan(new SourceLocation(4, 6, 7), 8)); var right = new SourceMapping( new SourceSpan(new SourceLocation(1, 2, 3), 4), new SourceSpan(new SourceLocation(5, 6, 7), 9)); // Assert AssertNotEqual(left, right); }
public void GeneratedCodeMappingsAreNotEqualIfStartLineIsNotEqual() { // Arrange var left = new SourceMapping( new SourceSpan(new SourceLocation(1, 2, 3), 4), new SourceSpan(new SourceLocation(5, 5, 7), 8)); var right = new SourceMapping( new SourceSpan(new SourceLocation(1, 1, 3), 4), new SourceSpan(new SourceLocation(5, 6, 7), 8)); // Assert AssertNotEqual(left, right); }
public void GeneratedCodeMappingsAreEqualIfDataIsEqual() { // Arrange var left = new SourceMapping( new SourceSpan(new SourceLocation(1, 2, 3), 4), new SourceSpan(new SourceLocation(5, 6, 7), 8)); var right = new SourceMapping( new SourceSpan(new SourceLocation(1, 2, 3), 4), new SourceSpan(new SourceLocation(5, 6, 7), 8)); // Assert Assert.True(left.Equals(right)); Assert.True(right.Equals(left)); Assert.True(Equals(left, right)); }
private void FindPendingReferenceIncludes(NavigationTreeNode node, SourceMapping sourceMapping) { if (node.Navigation != null && node.Navigation.IsCollection()) { return; } if (node.Included == NavigationTreeNodeIncludeMode.ReferencePending && node.ExpansionMode != NavigationTreeNodeExpansionMode.ReferenceComplete) { PendingIncludes[node] = sourceMapping; } foreach (var child in node.Children) { FindPendingReferenceIncludes(child, sourceMapping); } }
public void SourceMapCache_ParsesSimpleSourceMap() { var cache = new SourceMapCache(new SourceMap() { version = 3, file = "foo.js", sourceRoot = "http://example.com/", sources = new string[] { "/a" }, names = new string[] { }, mappings = "AACA" }); var expected = new SourceMapping(2, 0, 1, 0, "/a", ""); var actual = cache.SourceMappingFor(1, 0); Assert.AreEqual(expected, actual); }
public static Expression CreateCollectionNavigationExpression( NavigationTreeNode navigationTreeNode, ParameterExpression rootParameter, SourceMapping sourceMapping) { var collectionEntityType = navigationTreeNode.Navigation.ForeignKey.DeclaringEntityType; var entityQueryable = (Expression)NullAsyncQueryProvider.Instance.CreateEntityQueryableExpression(collectionEntityType.ClrType); var outerBinding = new NavigationBindingExpression( rootParameter, navigationTreeNode.Parent, navigationTreeNode.Navigation.DeclaringEntityType, sourceMapping, navigationTreeNode.Navigation.DeclaringEntityType.ClrType); var outerKeyAccess = NavigationExpansionHelpers.CreateKeyAccessExpression( outerBinding, navigationTreeNode.Navigation.ForeignKey.PrincipalKey.Properties, addNullCheck: outerBinding.NavigationTreeNode.Optional); var collectionCurrentParameter = Expression.Parameter(collectionEntityType.ClrType, collectionEntityType.ClrType.GenerateParameterName()); var innerKeyAccess = NavigationExpansionHelpers.CreateKeyAccessExpression( collectionCurrentParameter, navigationTreeNode.Navigation.ForeignKey.Properties); var predicate = Expression.Lambda( CreateKeyComparisonExpressionForCollectionNavigationSubquery( outerKeyAccess, innerKeyAccess, outerBinding), collectionCurrentParameter); var operand = Expression.Call( LinqMethodHelpers.QueryableWhereMethodInfo.MakeGenericMethod(collectionEntityType.ClrType), entityQueryable, predicate); var result = NavigationExpansionHelpers.CreateNavigationExpansionRoot(operand, collectionEntityType, navigationTreeNode.Navigation); // this is needed for cases like: root.Include(r => r.Collection).ThenInclude(c => c.Reference).Select(r => r.Collection) // result should be elements of the collection navigation with their 'Reference' included var newSourceMapping = result.State.SourceMappings.Single(); IncludeHelpers.CopyIncludeInformation(navigationTreeNode, newSourceMapping.NavigationTree, newSourceMapping); return(result); }
private IncludeExpression CreateIncludeReferenceCall(Expression caller, NavigationTreeNode node, ParameterExpression rootParameter, SourceMapping sourceMapping) { var entityType = node.Navigation.GetTargetType(); var included = (Expression) new NavigationBindingExpression(rootParameter, node, entityType, sourceMapping, entityType.ClrType); foreach (var child in node.Children.Where(n => n.Included == NavigationTreeNodeIncludeMode.ReferencePending || n.Included == NavigationTreeNodeIncludeMode.Collection)) { included = CreateIncludeCall(included, child, rootParameter, sourceMapping); } return(new IncludeExpression(caller, included, node.Navigation)); }
private IncludeExpression CreateIncludeCall(Expression caller, NavigationTreeNode node, ParameterExpression rootParameter, SourceMapping sourceMapping) => node.Navigation.IsCollection() ? CreateIncludeCollectionCall(caller, node, rootParameter, sourceMapping) : CreateIncludeReferenceCall(caller, node, rootParameter, sourceMapping);
private IncludeExpression CreateIncludeCollectionCall(Expression caller, NavigationTreeNode node, ParameterExpression rootParameter, SourceMapping sourceMapping) { var included = CollectionNavigationRewritingVisitor.CreateCollectionNavigationExpression(node, rootParameter, sourceMapping); return(new IncludeExpression(caller, included, node.Navigation)); }