2010-05-30 1 views
8

저는 2 시간 동안 인터넷 검색을했는데 좋은 답변을 찾을 수 없으므로 인간이 Google 컴퓨터를 이길 수 있는지 봅시다.Nokogiri로 스타일 시트를 구문 분석 할 수 있습니까?

Ruby에서 스타일 시트를 구문 분석하여 해당 스타일을 내 문서의 요소에 적용하여 스타일을 인라인으로 만들 수 있습니다. 그래서, 뭔가를 가지고 싶어요

<style> 
.mystyle { 
    color:white; 
} 
</style> 

그리고 어떤 종류의 Nokogiri 개체로 추출 할 수 있습니다.

Nokogiri 클래스 "CSS :: Parser"(http://nokogiri.rubyforge.org/nokogiri/Nokogiri/CSS/Parser.html)는 확실히 유망한 이름을 가지고 있지만 그것이 무엇인지 또는 어떻게 작동하는지에 대한 문서를 찾을 수 없으므로 내가 할 수 있는지 전혀 모른다. 내가 여기있어.

a_web_page = Nokogiri::HTML(html_page_as_string) 
parsed_styles = Nokogiri::CSS.parse(html_page_as_string) 
parsed_styles.each do |style| 
    existing_inlined_style = a_web_page.css(style.declaration) || '' 
    a_web_page.css(style.declaration)['css'] = existing_inlined_style + style.definition 
end 

스타일 시트에서 스타일을 추출하고 내 문서에 인라인 스타일로 모두를 추가 :

내 최종 목표는 같은 코드 뭔가를 쓸 수 있어야하는 것입니다.

답변

4

@molf는 확실히 거기에서 시작점이 좋았지 만, 제작 과정에서 문제를 디버깅해야했습니다.

html = Nokogiri::HTML(html_string) 
css = CssParser::Parser.new 
css.add_block!(html_string) # Warning: This line modifies the string passed into it. In potentially bad ways. Make sure the string has been duped and stored elsewhere before passing this. 

css.each_selector do |selector, declarations, specificity| 
    next unless selector =~ /^[\d\w\s\#\.\-]*$/ # Some of the selectors given by css_parser aren't actually selectors. 
    begin 
    elements = html.css(selector) 
    elements.each do |match| 
     match["style"] = [match["style"], declarations].compact.join(" ") 
    end 
    rescue 
    logger.info("Couldn't parse selector '#{selector}'") 
    end 
end 

html_with_inline_styles = html.to_s 
15

Nokogiri는 CSS 스타일 시트를 구문 분석 할 수 없습니다.

CSS::Parser은 CSS 표현을 구문 분석합니다. XPath가 아닌 CSS 선택기로 HTML 트리를 탐색 할 때마다 사용됩니다 (Nokogiri의 cool feature).

루비 CSS parser가 있습니다. Nokogiri와 함께 사용하면 원하는 것을 얻을 수 있습니다.

require "nokogiri" 
require "css_parser" 

html = Nokogiri::HTML(html_string) 

css = CssParser::Parser.new 
css.add_block!(css_string) 

css.each_selector do |selector, declarations, specificity| 
    element = html.css(selector) 
    element["style"] = [element["style"], declarations].compact.join(" ") 
end 
+1

html.css (선택기) 요소들의 어레이가 반환 여기서이 현재 테스트 버전이다. 그래서 그것은 elements.each do | element |이어야합니다. – Alagu