10

Я написал собственный VirtualPathProvider (источник here), который будет возвращать содержимое из EmbeddedResources или из исходного файла, если ему было сказано, где его найти (это позволяет редактировать и обновлять файлы без необходимости перестроить). Пока все работает нормально.Не удается отладить просмотры EmbeddedResource, загруженные с помощью пользовательского VirtualPathProvider

Что не работает, это отладка. Если я добавлю точку останова в представление, она не загрузит символы. Я понимаю, почему это сложно (как компилятор ASP знает, где находится исходный файл, чтобы определить точки останова?), Но я ищу способ подсказки компилятору, где можно найти исходный файл.

Пример проекта здесь: http://dl.dropbox.com/u/2808109/VppDebugTest.zip

редактировать:

Я экспериментировал с страницы ASPX, загруженной через VPP, и просмотрев Составитель Источник (с использованием David Ebbo's technique), а линия псевдокомментарии генерируются как так:

Line 275:    #line 1 "http://server/EmbeddedPage.aspx" 
Line 276:    this.InitializeCulture(); 

Обычно, они образуются вдоль линий

Line 275:    #line 1 "d:/somesln/someproj/EmbeddedPage.aspx" 

Не знаю, поможет ли это кому или нет ...

редактировать 2:

После Давид прислал мне свой код, я сделал некоторые дополнительные исследования и следующие вещи кажутся, чтобы быть правдой:

  1. вы не можете установить точку останова в .aspx, если system.web не упоминается (в VS 2010)
  2. если вы создаете минимальную страницу .aspx с директивами <%@ Page Language="C#" %> и установить контрольную точку, В.С. остановится на breakpoi нт в исходном файле

  3. , если создать не минимальный .aspx с директивами <%@ Page Language="C#" AutoEventWireup="true" CodeBehind="WebForm1.aspx.cs" Inherits="VppDebugTest.WebForm1" %> и установить контрольную точку, если смотреть VS приведет вас к dissasembly зрения отладки

--- http://server/WebForm1.aspx ------------------------------------------------ 0000003a mov ecx,dword ptr [ebp-3Ch] 0000003d call 63EC54F0 00000042 mov dword ptr [ebp-44h],eax 00000045 mov edx,dword ptr ds:[03E62200h] 0000004b mov ecx,dword ptr [ebp-44h]

It по-прежнему не останавливаются ни на каких контрольных точках в представлениях Razor, что, к сожалению, я действительно должен уметь делать! Этот материал .aspx может быть красной селедкой.

редактировать:

5: Если я ставлю вызов Debugger.Break() в моем Index.cshtml, отладчик останавливается в целях разборки, и нет псевдокомментарии вообще, неправильно или иначе

  1. Если я вручную напишу @{ #line 1 "C:\Users\Harry\Desktop\VppDebugTest\VppDebugTest.Views\Views\Home\Index.cshtml" }, на мой взгляд, отладка остановится в файле. Так, может быть, решение для моего VPP вставить прайсы #line в сами файлы cshtml ??
+0

В вашем прилагаемом проекте, каковы точные шаги, которые приводят к просмотру? например к чему я отношусь, когда я прикрепляю, где я устанавливаю BP и т. д. –

+0

Установите точку останова внутри index.cshtml (например, в строке @ ViewBag.Message), и отладчик не остановится там, если вы запустите проект. Добавьте вызов в Debugger.Break(), и вы получите разборку, а не исходный код. – mcintyre321

+0

Хммм, это странно. Сгенерированный файл в этом случае не содержит никаких прагм! Обратите внимание, что генераторы кода для страниц aspx и cshtml (aka Razor) совершенно разные, поэтому это может быть проблемой, характерной для Razor. –

ответ

2

У меня была такая же проблема и, наконец, она работала, используя пользовательский RazorHost. Кажется, что физическое местоположение файла разрешено с использованием метода HostingEnvironment.MapPath(), который не возвращает правильный результат для встроенных файлов.

Что я сделал:

public class MyCustomRazorHostFactory : WebRazorHostFactory 
{ 
    public override System.Web.WebPages.Razor.WebPageRazorHost CreateHost(string virtualPath, string physicalPath) 
    { 
     // Implementation stolen from MvcRazorHostFactory :) 
     var host = base.CreateHost(virtualPath, physicalPath); 

     if(!host.IsSpecialPage) 
     { 
      return new MyCustomRazorHost(virtualPath, physicalPath); 
     } 

     return host; 
    } 
} 

public class MyCustomRazorHost : MvcWebPageRazorHost 
{ 
    public MyCustomRazorHost(string virtualPath, string physicalPath) 
     : base(virtualPath, physicalPath) 
    { 
     if(MyMagicHelper.IsEmbeddedFile(virtualPath)) 
     { 
      PhysicalPath = MyMagicHelper.GetPhysicalFilePath(virtualPath); 
     } 
    } 
} 

// Simplified for demonstration purpose 
public static class MyMagicHelper 
{ 
    public static bool IsEmbeddedFile(string virtualPath) 
    { 
     // ... check if the path is an embedded file path 
    } 

    public static string GetPhysicalFilePath(string virtualPath) 
    { 
     // ... resolve the virtual file and return the correct physical file path 
    } 
} 

В качестве последнего шага вам нужно сказать ASP.NET, который хозяин завода он должен использовать. Это делается в web.config:

<system.web.webPages.razor> 
    <host factoryType="My.Custom.Namespace.MyCustomRazorHostFactory" /> 
</system.web.webPages.razor> 

Я знаю, что мой ответ приходит немного поздно, но, надеюсь, кто-то может использовать его, когда наткнуться на этот вопрос, как я. :)

+0

wow great, я посмотрю, смогу ли я интегрировать это в свой пакет nuget, когда я получу шанс – mcintyre321

+1

Наконец-то чтобы сделать это, и он работает !!! Я опубликовал некоторые свойства моего проекта EmbeddedResourceVirtualPathProvider для реализации методов, gist на https://gist.github.com/mcintyre321/ff67ffa8e2f0c8ef86da – mcintyre321

1

Я попытался сыграть с вашим кодом немного, и когда я добавил тестовый aspx в ресурсы, отладка, похоже, работала нормально. Я смог установить BP в Page_Load, и он там.

Вы можете увидеть мои изменения в https://github.com/davidebbo/EmbeddedResourceVirtualPathProvider

Обратите внимание, что я отключить логику резервного, как я хотел бы сосредоточиться на встроенном случае, хотя я не думаю, что делает разницу.

Обратите внимание, что я использую VS2012, поэтому мне также пришлось обновить проект/sln (но они все равно будут работать в 2010 году).

Причина, по которой ASP.NET генерирует прагму http-строки, заключается в том, что она не может найти физический файл aspx в стандартном местоположении (то есть, что вернет MapPath). На самом деле существует малоизвестный способ всегда включать это поведение: set urlLinePragmas = true в разделе (http://msdn.microsoft.com/en-us/library/system.web.configuration.compilationsection.urllinepragmas.aspx) ,

+0

Спасибо, что посмотрели на это! Вы подняли несколько интересных вещей, я обновлю вопрос, чтобы отразить их. – mcintyre321

+0

Есть ли способ, с помощью которого я могу подключиться к поисковому ASP? делает для urlLinePragmas и сообщает, где находится настоящий исходный файл? (Это исправить мою проблему с просмотрами Razor) – mcintyre321