Asp.net 典型网站上的实时输出流。如果你是amazon.com之类的,当然是YMMV
我开发它的最初目的是从内容管理系统中操作HTML。一旦我安装并运行了它,我发现使用CSS选择器和jQueryAPI比使用web控件要有趣得多,于是开始将它用作服务器呈现页面的主要HTML操作工具,并将其构建成几乎涵盖所有CSS、jQuery和浏览器DOM。从那以后,我再也没有接触过web控件 要使用CsQuery截取webforms中的HTML,请在页面代码隐藏中执行此操作:Asp.net 典型网站上的实时输出流。如果你是amazon.com之类的,当然是YMMV,asp.net,xml-parsing,webforms,html-parsing,csquery,Asp.net,Xml Parsing,Webforms,Html Parsing,Csquery,我开发它的最初目的是从内容管理系统中操作HTML。一旦我安装并运行了它,我发现使用CSS选择器和jQueryAPI比使用web控件要有趣得多,于是开始将它用作服务器呈现页面的主要HTML操作工具,并将其构建成几乎涵盖所有CSS、jQuery和浏览器DOM。从那以后,我再也没有接触过web控件 要使用CsQuery截取webforms中的HTML,请在页面代码隐藏中执行此操作: using CsQuery; using CsQuery.Web; protected override void R
using CsQuery;
using CsQuery.Web;
protected override void Render(HtmlTextWriter writer)
{
var csqContext = WebForms.CreateFromRender(Page, base.Render, writer);
// CQ object is like a jQuery object. The "Dom" property of the context
// returned above represents the output of this page.
CQ doc = csqContext.Dom;
doc["li > a"].AddClass("foo");
// write it
csqContext.Render();
}
要在ASP.NET MVC中执行相同的操作,请参见描述
GitHub上有CsQuery的基本文档。除了输入和输出HTML之外,它的工作原理与jQuery非常相似。上面的WebForms
对象只是为了帮助您处理与htmltexwriter
对象和Render
方法的交互。通用用途非常简单:
var doc = CQ.Create(htmlString);
// or (useful for scraping and testing)
var doc = CQ.CreateFromUrl(url);
// do stuff with doc, a CQ object that acts like a jQuery object
doc["table tr:first"].Append("<td>A new cell</td>");
当然,在C#中,您可以使用大量其他通用工具,如LINQ。或者:
var element = dom["div > input[type=checkbox]:first-child"].Single();
a.Checked=true;
当您完成对文档的操作后,您可能希望将HTML输出:
string html = doc.Render();
就这些。在CQ
对象上有大量方法,涵盖了所有jquerydom操作技术。还有处理JSON的实用方法,它广泛支持动态和匿名类型,使传递数据结构(例如,一组CSS类)尽可能容易,就像jQuery一样
一些更高级的东西
我不建议您这样做,除非您熟悉asp.net http工作流的底层修补。没有什么是可以撤销的,但是如果您从未听说过HttpHandler,那么将会有一个学习曲线
如果您想完全跳过WebForms引擎,可以创建一个自动解析HTML文件的IHttpHandler
。这肯定会比在ASPX引擎上进行叠加要好——谁知道呢,甚至可能比使用web控件进行类似数量的服务器端处理还要快。然后,您可以为特定的扩展(如htm
和html
)
另一种自动拦截的方法是路由。您可以毫不费力地在webforms应用程序中使用MVC路由库,然后您可以创建与您想要的任何模式匹配的路由(同样,可能是*.html
),并将处理传递给自定义IHttpHandler
或类。在本例中,您正在做所有事情:您将需要查看路径,从文件系统加载文件,使用CsQuery解析它,并流式处理响应
当然,使用这两种机制,您都需要一种方法来告诉您的项目每个页面要运行哪些代码。也就是说,仅仅因为您创建了一个漂亮的HTML解析器,那么如何告诉它为该页面运行正确的“代码隐藏”
MVC只需定位一个名为“PageNameController.cs”的控制器并调用一个与参数名匹配的方法即可实现这一点。你可以做任何你想做的事;e、 g.您可以添加一个元素:
<script type="controller" src="MyPageController"></script>
您的泛型处理程序代码可以查找这样的元素,然后使用反射来定位要调用的正确命名类和方法。这相当复杂,超出了这个答案的范围;但是,如果你想构建一个全新的框架或其他东西,你就应该这样做。在发送页面之前拦截页面内容相当简单。不久前,我在一个动态压缩内容的项目中这样做了:(这很难看,但它完成了它的工作,您可能能够修复一些代码)。无论如何,您要做的是: 1) 创建一个流对象,在调用Flush之前保存页面内容。例如,我在我的压缩项目中使用了这个:就像我之前说过的,它并不漂亮。但我的观点是,您需要创建自己的流类来完成您想要的任务(在本例中,为您提供页面的字符串输出,解析/修改字符串,然后将其输出给用户) 2) 将页面的筛选器对象分配给它。(Page.Response.Filter)请注意,您需要尽早完成此操作,以便捕获所有内容。我使用一个在PreRequestHandlerExecute事件上运行的HTTP模块实现了这一点。但是如果你做了这样的事情:
protected override void OnPreInit(EventArgs e)
{
this.Response.Filter = new MyStream();
base.OnPreInit(e);
}
这也很可能奏效
3) 您应该能够使用类似的方法来解析HTML并从中修改它
在我看来,这似乎是最简单的方法。在发送页面之前拦截页面内容相当简单。不久前,我在一个动态压缩内容的项目中这样做了:(这很难看,但它完成了它的工作,您可能能够修复一些代码)。无论如何,您要做的是: 1) 创建一个流对象,在调用Flush之前保存页面内容。例如,我在我的压缩项目中使用了这个:就像我之前说过的,它并不漂亮。但我的观点是,您需要创建自己的流类来完成您想要的任务(在本例中,为您提供页面的字符串输出,解析/修改字符串,然后将其输出给用户) 2) 将页面的筛选器对象分配给它。(Page.Response.Filter)请注意,您需要尽早完成此操作,以便捕获所有内容。我使用一个在PreRequestHandlerExecute事件上运行的HTTP模块实现了这一点。但是如果你做了这样的事情:
protected override void OnPreInit(EventArgs e)
{
this.Response.Filter = new MyStream();
base.OnPreInit(e);
}
这也很可能奏效
3) 您应该能够使用类似的方法来解析HTML并从中修改它
对我来说,这似乎是最简单的方法。我对这种方法没有答案,但如果你想编写可重用的CSS,我建议你学习一种CSS生成语言,比如or。嗯,这种方法可能会导致严重的性能问题(实现最终的H