tg-can-controls-gateway 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (72) hide show
  1. data/.gitignore +7 -0
  2. data/Capfile +8 -0
  3. data/README +243 -0
  4. data/Rakefile +54 -0
  5. data/VERSION +1 -0
  6. data/app/controllers/application_controller.rb +10 -0
  7. data/app/helpers/application_helper.rb +3 -0
  8. data/bin/can_controls_gateway +36 -0
  9. data/doc/090630_Gestentracking_RFID.pdf +0 -0
  10. data/doc/README_FOR_APP +3 -0
  11. data/doc/home.png +0 -0
  12. data/doc/life.png +0 -0
  13. data/doc/preshow.png +0 -0
  14. data/doc/recognition-message-example.xml +69 -0
  15. data/etc/init-script_debian +56 -0
  16. data/lib/can-controls-gateway.rb +4 -0
  17. data/lib/ccg_logger.rb +6 -0
  18. data/lib/cursor_vector.rb +60 -0
  19. data/lib/dispatcher.rb +85 -0
  20. data/lib/osc_broadcast_receiver.rb +41 -0
  21. data/lib/osc_broadcast_sender.rb +44 -0
  22. data/lib/osc_package.rb +56 -0
  23. data/lib/osc_to_rca_dispatcher.rb +42 -0
  24. data/lib/ping.rb +84 -0
  25. data/lib/raw_event.rb +33 -0
  26. data/lib/rca_command.rb +42 -0
  27. data/lib/runner.rb +97 -0
  28. data/lib/server.rb +45 -0
  29. data/lib/settings.rb +17 -0
  30. data/log/development.log +0 -0
  31. data/log/production.log +0 -0
  32. data/log/server.log +0 -0
  33. data/log/test.log +0 -0
  34. data/public/404.html +30 -0
  35. data/public/422.html +30 -0
  36. data/public/500.html +30 -0
  37. data/public/favicon.ico +0 -0
  38. data/public/images/gesten/1.png +0 -0
  39. data/public/images/gesten/10.png +0 -0
  40. data/public/images/gesten/11.png +0 -0
  41. data/public/images/gesten/2.png +0 -0
  42. data/public/images/gesten/3.png +0 -0
  43. data/public/images/gesten/4.png +0 -0
  44. data/public/images/gesten/5.png +0 -0
  45. data/public/images/gesten/6.png +0 -0
  46. data/public/images/gesten/7.png +0 -0
  47. data/public/images/gesten/8.png +0 -0
  48. data/public/images/gesten/9.png +0 -0
  49. data/public/images/rails.png +0 -0
  50. data/public/index.html +275 -0
  51. data/public/javascripts/application.js +2 -0
  52. data/public/javascripts/controls.js +963 -0
  53. data/public/javascripts/dragdrop.js +973 -0
  54. data/public/javascripts/effects.js +1128 -0
  55. data/public/javascripts/prototype.js +4320 -0
  56. data/public/robots.txt +5 -0
  57. data/script/about +4 -0
  58. data/script/console +3 -0
  59. data/script/dbconsole +3 -0
  60. data/script/destroy +3 -0
  61. data/script/generate +3 -0
  62. data/script/performance/benchmarker +3 -0
  63. data/script/performance/profiler +3 -0
  64. data/script/plugin +3 -0
  65. data/script/runner +3 -0
  66. data/script/server +3 -0
  67. data/spec/can-controls-gateway/rca_command_spec.rb +31 -0
  68. data/spec/spec.opts +1 -0
  69. data/spec/spec_helper.rb +10 -0
  70. data/test/performance/browsing_test.rb +9 -0
  71. data/test/test_helper.rb +38 -0
  72. metadata +167 -0
@@ -0,0 +1,41 @@
1
+ require 'rubygems'
2
+ require 'socket'
3
+ require 'osc'
4
+ require 'time'
5
+
6
+ ADDR = ['0.0.0.0', 33333] # host, port
7
+ BasicSocket.do_not_reverse_lookup = true
8
+
9
+ UDPSock = UDPSocket.new
10
+ UDPSock.bind(ADDR[0], ADDR[1])
11
+
12
+ lastUpdate = 0
13
+ numPackages = 0
14
+ frequency = 0
15
+
16
+ while true do
17
+ currentUpdate = Time.now
18
+ my_data, my_addr = UDPSock.recvfrom(32768) # if this number is too low it will drop the larger packets and never give them to you
19
+
20
+ decoded = OSC::Packet.decode my_data rescue decoded = nil
21
+
22
+ if decoded.nil?
23
+ my_event = nil
24
+ else
25
+ my_msg = decoded[0][1]
26
+ if my_msg[0].kind_of?(OSC::OSCString) #s
27
+ my_event = my_msg[0]
28
+ elsif my_msg[2].kind_of?(OSC::OSCString) # ffs
29
+ my_event = my_msg[2]
30
+ else
31
+ my_event = nil # something else, e.g. ff
32
+ end
33
+ end
34
+ puts "#{Time.now.iso8601} | From addr: '%s', msg: '%s'" % [my_addr.inspect, my_event]
35
+ puts ""
36
+ frequency = 1 / (currentUpdate - lastUpdate) rescue nil
37
+ lastUpdate = currentUpdate
38
+ numPackages = 0
39
+ #puts "#{frequency} Hz"
40
+ end
41
+ UDPSock.close
@@ -0,0 +1,44 @@
1
+ require 'rubygems'
2
+ require 'socket'
3
+ require 'osc'
4
+ require 'time'
5
+
6
+ ADDR = ['<broadcast>', 6567] # broadcast address
7
+ STATION_ID = 1
8
+ DIMENSIONALITY = 2
9
+ EVENTS = [ "swipeDown", "swipeUp", "swipeLeft", "swipeRight", "zoomIn", "zoomOut",
10
+ "cancel", "mouseDown", 'bigSwipe', "mouseMove", 'mouseUp', 'otherunknown' ]
11
+
12
+ UDPSock = UDPSocket.new
13
+ UDPSock.setsockopt(Socket::SOL_SOCKET, Socket::SO_BROADCAST, true)
14
+
15
+ puts "sending osc packages"
16
+
17
+ while true do
18
+ #case ['cursor', 'event', 'event_and_cursor', 'invalid'].choice
19
+ case ['cursor', 'event', 'event_and_cursor', 'invalid'].choice
20
+ when 'cursor':
21
+ puts 'cursor'
22
+ my_message = OSC::Message.new("/cursor/#{STATION_ID}/1/#{DIMENSIONALITY}",
23
+ 'ff', 0.3, 0.3).encode
24
+ when 'event':
25
+ puts 'event'
26
+ my_message = OSC::Message.new("/cursor/#{STATION_ID}/1/#{DIMENSIONALITY}",'s', EVENTS.choice).encode
27
+ when 'event_and_cursor':
28
+ puts 'event_and_cursor'
29
+ my_message = OSC::Message.new("/cursor/#{STATION_ID}/1/#{DIMENSIONALITY}",
30
+ 'ffs', 0.3, 0.3, EVENTS.choice).encode
31
+ when 'invalid';
32
+ puts 'invalid'
33
+ my_message = 'hallo'
34
+ end
35
+
36
+ puts my_message.inspect
37
+
38
+ UDPSock.send(my_message, 0, ADDR[0], ADDR[1])
39
+ sleep 1.0/2.0 # Hz
40
+ end
41
+
42
+ UDPSock.close
43
+
44
+ puts "good bye"
@@ -0,0 +1,56 @@
1
+ require 'osc'
2
+ require 'socket'
3
+ #require 'ccg_logger'
4
+
5
+ module CanControlsGateway
6
+
7
+ class OscPackage
8
+
9
+ ADDR = ['<broadcast>', OSC_BROADCAST_PORT] # broadcast address
10
+
11
+ def initialize event, station_id
12
+ @event = event
13
+ @station_id = station_id
14
+ end
15
+
16
+ def broadcast
17
+ my_message = prepare_message
18
+ ##
19
+ #CcgLogger::LOGGER.info "#{Time.now.iso8601} | broadcasting osc_package with vector '#{@event.vector}' and event_type '#{@event.event_type}'"
20
+ ##
21
+ my_encoded_message = my_message.encode
22
+ BasicSocket.do_not_reverse_lookup = true
23
+ my_socket = UDPSocket.new
24
+
25
+ my_socket.setsockopt(Socket::SOL_SOCKET, Socket::SO_BROADCAST, true)
26
+ my_socket.send(my_encoded_message, 0, ADDR[0], ADDR[1])
27
+ my_socket.close
28
+
29
+ my_encoded_message.to_s
30
+ end
31
+
32
+ private
33
+
34
+ def prepare_message
35
+ if @event.vector.nil?
36
+ dimensionality = 0
37
+ else
38
+ dimensionality = @event.vector.dimensions
39
+ end
40
+
41
+ if dimensionality == 0
42
+ my_message = OSC::Message.new "/cursor/#{@station_id}/1/#{dimensionality}",
43
+ 's', @event.event_type
44
+ elsif dimensionality == 2
45
+ my_message = OSC::Message.new "/cursor/#{@station_id}/1/#{dimensionality}",
46
+ 'sff', @event.event_type, @event.vector.x, @event.vector.y
47
+ else
48
+ my_message = OSC::Message.new "/cursor/#{@station_id}/1/#{dimensionality}",
49
+ 's', @event.event_type
50
+ end
51
+ my_message
52
+ end
53
+
54
+ end
55
+
56
+ end
@@ -0,0 +1,42 @@
1
+ require 'osc'
2
+ require 'rca_command'
3
+
4
+ module CanControlsGateway
5
+
6
+ class OscToRcaDispatcher
7
+
8
+ attr_reader :event, :raw_data, :osc_packet, :osc_message
9
+
10
+ def initialize data
11
+ @raw_data = data
12
+ @osc_packet = OSC::Packet.decode @raw_data rescue @osc_packet = nil
13
+ @osc_message = @osc_packet[0][1] rescue @osc_message = nil
14
+ @event = extract_event
15
+ end
16
+
17
+ def dispatch_rca
18
+ return true if @event.nil?
19
+ my_args = { 'action' => @event }
20
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} | >> OscToRcaDispatcher: sending command : rci_uri: #{STATION['rci_uri']}, target: #{STATION['target']}, args: #{my_args.inspect}"
21
+ my_command = CanControlsGateway::RcaCommand.new STATION['rci_uri'],
22
+ STATION['target'],
23
+ my_args
24
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} #{my_command.send_command}"
25
+ end
26
+
27
+ private
28
+
29
+ def extract_event
30
+ return nil if @osc_message.nil?
31
+ if @osc_message[0].kind_of?(OSC::OSCString) #s
32
+ return EVENTS[@osc_message[0].to_s]
33
+ elsif @osc_message[2].kind_of?(OSC::OSCString) # ffs
34
+ return EVENTS[@osc_message[2].to_s]
35
+ else
36
+ return nil # something else, e.g. ff
37
+ end
38
+ end
39
+
40
+ end
41
+
42
+ end
data/lib/ping.rb ADDED
@@ -0,0 +1,84 @@
1
+ require 'socket'
2
+ require 'time'
3
+
4
+ SERVER = "localhost"
5
+ PORT = 6567
6
+ STATIONS = 1
7
+ #EVENTS = [ 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove',
8
+ # 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove',
9
+ # 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove', 'mouseMove',
10
+ # 'mouseDown', 'mouseUp', 'mouseDown', 'mouseUp',
11
+ # "swipeDown", "swipeUp", "swipeLeft", "swipeRight", "zoomIn", "zoomOut",
12
+ # "cancel", "mouseDown", 'bigSwipe', "mouseMove", 'mouseUp', 'otherunknown'
13
+ # ]
14
+
15
+ EVENTS = ['mouseMove']
16
+
17
+ XML_EVENT_TEMPLATE = <<-XML
18
+ <?xml version="1.0" encoding="UTF-8"?>
19
+ <trackingdata ts="" station_id="%s">
20
+ <event type="%s">
21
+ <position type="vec3f" coordinate_system="plane">%s, %s, 0</position>
22
+ </event>
23
+ </trackingdata>
24
+ XML
25
+
26
+ XML_MOVE_EVENT_TEMPLATE = <<-XML
27
+ <?xml version="1.0" encoding="UTF-8"?>
28
+ <trackingdata ts="" station_id="%s">
29
+ <event type="mouseMove">
30
+ <position type="vec3f" coordinate_system="plane">%s, %s, 0</position>
31
+ </event>
32
+ <event type="%s"></event>
33
+ </trackingdata>
34
+ XML
35
+
36
+ XML_EVENT_TEMPLATE_NO_DATA = <<-XML
37
+ <?xml version="1.0" encoding="UTF-8"?>
38
+ <trackingdata ts="" station_id="%s">
39
+ <event type="%s">
40
+ </event>
41
+ </trackingdata>
42
+ XML
43
+
44
+ XML_NO_EVENT_TEMPLATE = <<-XML
45
+ <?xml version="1.0" encoding="UTF-8"?>
46
+ <trackingdata ts="" station_id="%s">
47
+ </trackingdata>
48
+ XML
49
+
50
+ def generate_payload
51
+ if [true].choice
52
+ my_event = EVENTS.choice
53
+ puts "event >>>>>> #{my_event}"
54
+ my_now = Time.now
55
+ if ['mouseMove', 'mouseDown', 'mouseUp'].include? my_event
56
+ sprintf(XML_EVENT_TEMPLATE, (rand*STATIONS).to_i, my_event, Math.sin(my_now), Math.cos(my_now))
57
+ else
58
+ sprintf(XML_MOVE_EVENT_TEMPLATE, (rand*STATIONS).to_i, Math.sin(my_now), Math.cos(my_now), my_event)
59
+ end
60
+ else
61
+ puts "no event"
62
+ sprintf(XML_NO_EVENT_TEMPLATE, (rand*STATIONS).to_i)
63
+ end
64
+ end
65
+
66
+ def send_gesture(server_addr, server_port, payload)
67
+ resp, sock = nil, nil
68
+ begin
69
+ sock = UDPSocket.open
70
+ puts payload
71
+ sock.send("#{payload}", 0, server_addr, server_port)
72
+ resp = ["sent"]
73
+ rescue IOError, SystemCallError
74
+ ensure
75
+ sock.close if sock
76
+ end
77
+ resp ? resp[0] : nil
78
+ end
79
+
80
+ (1..30000).each do |i|
81
+ sleep 1.0/40.0 # 40 Hertz
82
+ result = send_gesture(SERVER, PORT, generate_payload)
83
+ puts "#{result} - #{i}"
84
+ end
data/lib/raw_event.rb ADDED
@@ -0,0 +1,33 @@
1
+ require 'rexml/document'
2
+ require 'rexml/xpath'
3
+
4
+ require 'cursor_vector'
5
+
6
+ module CanControlsGateway
7
+
8
+ class RawEvent
9
+
10
+ attr_reader :vector, :event_type
11
+
12
+ def initialize xml_node
13
+ @xml_node = REXML::Document.new(xml_node.to_s)
14
+ @vector = nil
15
+ @event_type = nil
16
+ parse_xml
17
+ end
18
+
19
+ private
20
+
21
+ def parse_xml
22
+ @event_type = REXML::XPath.first(@xml_node, "/event/attribute::type")
23
+ @event_type = @event_type.value if @event_type
24
+
25
+ my_vector_match = REXML::XPath.first(@xml_node, "/event/position")
26
+ if my_vector_match
27
+ @vector = CanControlsGateway::CursorVector.new(my_vector_match)
28
+ end
29
+ end
30
+
31
+ end
32
+
33
+ end
@@ -0,0 +1,42 @@
1
+ require 'net/https'
2
+ require 'cgi'
3
+
4
+ module CanControlsGateway
5
+
6
+ class RcaCommand
7
+
8
+ attr_reader :arguments, :target, :rci_uri
9
+
10
+ def initialize rci_uri, target, arguments={}
11
+ @rci_uri = rci_uri
12
+ @target = target
13
+ @arguments = prepare_command_arguments arguments
14
+ end
15
+
16
+ def send_command
17
+ post_data = "target=#{@target}&arguments=#{@arguments}"
18
+ url = URI.parse(@rci_uri)
19
+ request = Net::HTTP::Post.new(url.path)
20
+ begin
21
+ response = Net::HTTP::start(url.host, url.port) { |http|
22
+ http.request(request, post_data)
23
+ }
24
+ return response.code.to_i, response.body
25
+ rescue Exception => e
26
+ return 500, "#{e}"
27
+ end
28
+ end
29
+
30
+ private
31
+
32
+ def prepare_command_arguments arguments
33
+ my_arguments_list = []
34
+ arguments.keys.sort.each do |key|
35
+ my_arguments_list << "#{key}=#{arguments[key]}"
36
+ end
37
+ CGI::escape(my_arguments_list.join("&"))
38
+ end
39
+
40
+ end
41
+
42
+ end
data/lib/runner.rb ADDED
@@ -0,0 +1,97 @@
1
+ require 'rubygems'
2
+ require 'eventmachine'
3
+
4
+ require 'rest_fs/client'
5
+
6
+ require 'settings'
7
+ require 'server'
8
+
9
+ class CcgRunner < Gom::Remote::Entry
10
+
11
+ Defaults = {
12
+ :logfile => '-',
13
+ :port => nil,
14
+ :valve => :closed,
15
+ }
16
+
17
+ include OAttr
18
+ oattr :incoming_osc_port, :device
19
+
20
+ attr_reader :valve
21
+
22
+ def self.instance
23
+ @@instance
24
+ end
25
+
26
+ def initialize path, options = {}
27
+ @@instance = self
28
+ @path = path
29
+ @options = Defaults.merge(gnode @path).merge(options)
30
+ puts "options: #{@options.inspect}"
31
+
32
+ # FIXIT: legacy! pushing config values from GOM to global variable!!!
33
+ STATION['port'] = Integer(incoming_osc_port)
34
+ STATION['device'] = device
35
+ STATION['rci_uri'] = device_rci_uri
36
+ puts " -- STATION info: #{STATION.inspect}"
37
+
38
+ init_gnp
39
+ end
40
+
41
+ def device_rci_uri
42
+ @device_rci_uri ||= connection.read "#{device}:rci_uri.txt"
43
+ end
44
+
45
+ def run
46
+ #fill_settings
47
+ port = Integer(incoming_osc_port)
48
+ if port.nil?
49
+ raise "NOT Starting servers since port cannot be determined"
50
+ end
51
+
52
+ puts "#{Time.now.iso8601} | ++ Starting servers"
53
+ EventMachine::threadpool_size = 20
54
+ EventMachine::run do
55
+ puts "#{Time.now.iso8601} | ++ * UdpServer (port: #{port}) ..."
56
+ EventMachine::open_datagram_socket('0.0.0.0', port, UdpServer)
57
+ # TODO place http server component for GNP callbacks here...
58
+ end
59
+ end
60
+
61
+ private
62
+ def init_gnp
63
+ @sub = Subscription.new(
64
+ "#{@path}:valve", :name => "ccg", :operations => [:update, :create]
65
+ )
66
+ @sub.callback = lambda { |*args| valve_update(*args) }
67
+ connection.subscribe @sub
68
+ end
69
+
70
+ def valve_update op, attribute
71
+ @valve = attribute["value"].to_sym
72
+ puts " -- can-controls-valve now: #{@valve}"
73
+ end
74
+ end
75
+
76
+ __END__
77
+
78
+ def _fill_settings
79
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} | ++ Initializing settings ..."
80
+ my_gom = RestFs::Client.new GOM_ROOT
81
+
82
+ my_res = my_gom.retrieve("#{STATION['device']}:rci_uri")
83
+ if my_res
84
+ STATION['rci_uri'] = my_res['attribute']['value']
85
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} | ++ setting rci_uri for station #{STATION['device']} => #{STATION['rci_uri'].inspect}"
86
+
87
+ my_port_res = my_gom.retrieve("#{STATION['device']}/hid:port")
88
+ if my_port_res
89
+ STATION['port'] = my_port_res['attribute']['value']
90
+ else
91
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} | ++ device's hid:port #{STATION['device']}/hid:port not found in gom"
92
+ end
93
+ else
94
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} | ++ device's rci_uri #{STATION['device']}:rci_uri not found in gom"
95
+ end
96
+ end
97
+
data/lib/server.rb ADDED
@@ -0,0 +1,45 @@
1
+ require 'rubygems'
2
+ require 'eventmachine'
3
+ require 'socket'
4
+
5
+ require 'osc_to_rca_dispatcher'
6
+
7
+ module UdpServer
8
+
9
+ def post_init
10
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} | ++ ... server started"
11
+ end
12
+
13
+ def receive_data(data)
14
+ puts "1"
15
+ return unless(CcgRunner.instance.valve == :open)
16
+ puts "2"
17
+
18
+ ##
19
+ #CcgLogger::LOGGER.info "#{Time.now.iso8601} | >> raw incoming data: ----------------------"
20
+ #CcgLogger::LOGGER.info data.inspect
21
+ #CcgLogger::LOGGER.info " --------------------------------------------"
22
+ ##
23
+
24
+ #port, ip = Socket.unpack_sockaddr_in(get_peername)
25
+ #CcgLogger::LOGGER.info "#{Time.now.iso8601} | >> UdpServer: sender: #{ip}, #{port}"
26
+
27
+ # RCA
28
+ rca_dispatching = proc {
29
+ my_dispatcher = CanControlsGateway::OscToRcaDispatcher.new data
30
+ #CcgLogger::LOGGER.info my_dispatcher.event.inspect
31
+ my_dispatcher.dispatch_rca
32
+ }
33
+ rca_callback = proc { |result|
34
+ #if result
35
+ # CcgLogger::LOGGER.info "#{Time.now.iso8601} | >> UdpServer: result is: #{result.inspect}"
36
+ #end
37
+ }
38
+ EventMachine::defer rca_dispatching, rca_callback
39
+ end
40
+
41
+ def unbind
42
+ CcgLogger::LOGGER.info "#{Time.now.iso8601} | -- UdpServer stopped"
43
+ end
44
+
45
+ end
data/lib/settings.rb ADDED
@@ -0,0 +1,17 @@
1
+ STATION = {
2
+ 'device' => '/areas/home/tv',
3
+ 'target' => 'input_dispatcher',
4
+ }
5
+
6
+ #GOM_ROOT = "http://gom"
7
+ #GOM_ROOT = "http://localhost:3080"
8
+
9
+ EVENTS = { "swipeDown" => "down",
10
+ "swipeUp" => "up",
11
+ "swipeLeft" => "left",
12
+ "swipeRight" => "right",
13
+ "zoomIn" => "in",
14
+ "zoomOut" => "out",
15
+ "cancel" => "cancel",
16
+ "mouseDown" => "confirm",
17
+ "bigSwipe" => 'start'}
File without changes
File without changes
data/log/server.log ADDED
File without changes
data/log/test.log ADDED
File without changes
data/public/404.html ADDED
@@ -0,0 +1,30 @@
1
+ <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
2
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
3
+
4
+ <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
5
+
6
+ <head>
7
+ <meta http-equiv="content-type" content="text/html; charset=UTF-8" />
8
+ <title>The page you were looking for doesn't exist (404)</title>
9
+ <style type="text/css">
10
+ body { background-color: #fff; color: #666; text-align: center; font-family: arial, sans-serif; }
11
+ div.dialog {
12
+ width: 25em;
13
+ padding: 0 4em;
14
+ margin: 4em auto 0 auto;
15
+ border: 1px solid #ccc;
16
+ border-right-color: #999;
17
+ border-bottom-color: #999;
18
+ }
19
+ h1 { font-size: 100%; color: #f00; line-height: 1.5em; }
20
+ </style>
21
+ </head>
22
+
23
+ <body>
24
+ <!-- This file lives in public/404.html -->
25
+ <div class="dialog">
26
+ <h1>The page you were looking for doesn't exist.</h1>
27
+ <p>You may have mistyped the address or the page may have moved.</p>
28
+ </div>
29
+ </body>
30
+ </html>
data/public/422.html ADDED
@@ -0,0 +1,30 @@
1
+ <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
2
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
3
+
4
+ <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
5
+
6
+ <head>
7
+ <meta http-equiv="content-type" content="text/html; charset=UTF-8" />
8
+ <title>The change you wanted was rejected (422)</title>
9
+ <style type="text/css">
10
+ body { background-color: #fff; color: #666; text-align: center; font-family: arial, sans-serif; }
11
+ div.dialog {
12
+ width: 25em;
13
+ padding: 0 4em;
14
+ margin: 4em auto 0 auto;
15
+ border: 1px solid #ccc;
16
+ border-right-color: #999;
17
+ border-bottom-color: #999;
18
+ }
19
+ h1 { font-size: 100%; color: #f00; line-height: 1.5em; }
20
+ </style>
21
+ </head>
22
+
23
+ <body>
24
+ <!-- This file lives in public/422.html -->
25
+ <div class="dialog">
26
+ <h1>The change you wanted was rejected.</h1>
27
+ <p>Maybe you tried to change something you didn't have access to.</p>
28
+ </div>
29
+ </body>
30
+ </html>
data/public/500.html ADDED
@@ -0,0 +1,30 @@
1
+ <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
2
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
3
+
4
+ <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
5
+
6
+ <head>
7
+ <meta http-equiv="content-type" content="text/html; charset=UTF-8" />
8
+ <title>We're sorry, but something went wrong (500)</title>
9
+ <style type="text/css">
10
+ body { background-color: #fff; color: #666; text-align: center; font-family: arial, sans-serif; }
11
+ div.dialog {
12
+ width: 25em;
13
+ padding: 0 4em;
14
+ margin: 4em auto 0 auto;
15
+ border: 1px solid #ccc;
16
+ border-right-color: #999;
17
+ border-bottom-color: #999;
18
+ }
19
+ h1 { font-size: 100%; color: #f00; line-height: 1.5em; }
20
+ </style>
21
+ </head>
22
+
23
+ <body>
24
+ <!-- This file lives in public/500.html -->
25
+ <div class="dialog">
26
+ <h1>We're sorry, but something went wrong.</h1>
27
+ <p>We've been notified about this issue and we'll take a look at it shortly.</p>
28
+ </div>
29
+ </body>
30
+ </html>
File without changes
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file