Class: Alexander::XslProcessor

Inherits:
Object
  • Object
show all
Defined in:
lib/alexander/xsl_processor.rb

Instance Method Summary collapse

Constructor Details

#initialize(app) ⇒ XslProcessor

Returns a new instance of XslProcessor.



17
18
19
# File 'lib/alexander/xsl_processor.rb', line 17

def initialize(app)
  @app = app
end

Instance Method Details

#body_to_string(body) ⇒ Object



67
68
69
70
71
72
# File 'lib/alexander/xsl_processor.rb', line 67

def body_to_string(body)
  result = ""
  body.each { |it| result << it }
  body.close if body.respond_to? :close
  result
end

#call(env) ⇒ Object



21
22
23
24
25
26
27
28
29
30
31
32
# File 'lib/alexander/xsl_processor.rb', line 21

def call(env)
  status, headers, body = @app.call(env)

  return [status, headers, body] unless xml?(headers)
  return [status, headers, body] if xlst_enable_browser?(env)

  html_response = to_html(env, body)
  return [status, headers, body] unless html_response

  headers["Content-type"] = "text/html"
  Rack::Response.new([html_response], status, headers).finish
end

#detect_xslt_processing_instruction(xml) ⇒ Object



62
63
64
65
# File 'lib/alexander/xsl_processor.rb', line 62

def detect_xslt_processing_instruction(xml)
  match = xml.match(/<\?xml-stylesheet.*href="([^"]+)"/)
  return match[1] if match
end

#to_html(env, body) ⇒ Object



44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
# File 'lib/alexander/xsl_processor.rb', line 44

def to_html(env, body)
  xml = body_to_string(body)
  xslt_request = detect_xslt_processing_instruction(xml)
  return unless xslt_request

  ask_xslt = env.dup
  ask_xslt["PATH_INFO"] = xslt_request
  ask_xslt["REQUEST_PATH"] = xslt_request
  ask_xslt["REQUEST_URI"] = xslt_request
  ask_xslt["QUERY_STRING"] = ""
  status, headers, xslt = @app.call(ask_xslt)
  return unless status == 200

  xml_parsed = Nokogiri::XML(xml)
  xsl_parsed = Nokogiri::XSLT(body_to_string(xslt))
  xsl_parsed.transform(xml_parsed).to_s
end

#xlst_enable_browser?(env) ⇒ Boolean

Returns:

  • (Boolean)


38
39
40
41
42
# File 'lib/alexander/xsl_processor.rb', line 38

def xlst_enable_browser?(env)
  return false unless env && env["HTTP_USER_AGENT"]
  user_agent = UserAgent.parse(env["HTTP_USER_AGENT"])
  XSLT_ENABLE_BROWSERS.detect { |browser| user_agent >= browser }
end

#xml?(headers) ⇒ Boolean

Returns:

  • (Boolean)


34
35
36
# File 'lib/alexander/xsl_processor.rb', line 34

def xml?(headers)
  headers["Content-Type"] =~ /\bapplication\/xml\b/
end