-
Notifications
You must be signed in to change notification settings - Fork 11
Resource discovery rt #9
base: master
Are you sure you want to change the base?
Changes from all commits
367b6e5
8856a90
33de4c1
826ee8e
b6930a5
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,6 +1,9 @@ | ||
| require 'david/server/constants' | ||
|
|
||
| module David | ||
| class ResourceDiscovery | ||
| include Celluloid | ||
| include David::Server::Constants | ||
|
|
||
| def initialize(app) | ||
| @app = app | ||
|
|
@@ -16,11 +19,37 @@ def _call(env) | |
|
|
||
| @env = env | ||
|
|
||
| filtered = routes_hash.select { |link| filter(link) } | ||
| body = filtered.keys.map(&:to_s).join(',') | ||
| queries = @env[QUERY_STRING].split('&') | ||
| body_links = [] | ||
|
|
||
| if queries.length > 0 | ||
| queries.each {|q| | ||
| # XXX do these need to %-unescaped now? | ||
| (item, value) = q.split('=') | ||
|
|
||
| case item | ||
| when 'href' | ||
| # TODO If query end in '*', match on prefix. | ||
| # Otherwise match on whole string. | ||
| # https://tools.ietf.org/html/rfc6690#section-4.1 | ||
| filtered = routes_hash.select { |link| filter(link) } | ||
| body_links = filtered.keys | ||
|
|
||
| when 'rt' | ||
| byebug | ||
| unless resource_links[value].blank? | ||
| body_links << sprintf("<%s>", ERB::Util.html_escape(resource_links[value])) | ||
| end | ||
|
|
||
| else | ||
| false | ||
| end | ||
| } | ||
| end | ||
|
|
||
| # TODO On multicast, do not respond if result set empty. | ||
| body = body_links.map(&:to_s).join(',') | ||
|
|
||
| # TODO On multicast, do not respond if result set empty. | ||
| [ | ||
| 200, | ||
| { | ||
|
|
@@ -54,6 +83,10 @@ def clean_routes | |
| .each { |r| delete_format!(r) } | ||
| end | ||
|
|
||
| def resource_links | ||
| @resource_links ||= Hash[routes.collect { |r| [r[3], r[4]] }] | ||
| end | ||
|
|
||
| def delete_format!(route) | ||
| route[0].gsub!(/\(\.:format\)\z/, '') | ||
| end | ||
|
|
@@ -70,15 +103,19 @@ def filter(link) | |
| end | ||
|
|
||
| def include_route?(route) | ||
| !(route[0] =~ /\A\/(assets|rails)/) | ||
| !(route[0] =~ /\A\/(assets|rails|cable)/) | ||
| end | ||
|
|
||
| def routes | ||
| Rails.application.routes.routes.map do |route| | ||
| Rails.application.routes.routes.select { |route| | ||
| route.defaults[:coap] | ||
|
Owner
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Actually, I am not convinced, it should be necessary to add routes explicitly although it could be helpful in a bigger app that focuses primarily in http. I think, I would like it to be configurable with all routes bring included by default.
Collaborator
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yes, so I didn't want my ActiveScaffold routes showing up in the CoAP interface... I agree that a configuration that includes all routes would be a good thing. Where should I put that configruation?
Owner
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Rails only configuration options are perfectly fine in
Collaborator
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. A configuration option in lib/david/railties/config.rb would apply to all applications... I'm thinking that it belongs in the application's config/routes.rb. (Sorry for coming back to this after such a long time. I've been in OpenSSL DTLS hell. It works now though) |
||
| }.map do |route| | ||
| [ | ||
| route.path.spec.to_s, | ||
| route.defaults[:controller], | ||
| route.defaults[:action] | ||
| route.defaults[:action], | ||
| route.defaults[:rt], | ||
| route.defaults[:short] | ||
| ] | ||
| end | ||
| end | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could the filtering by
rtnot be done in thefiltermethod?There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
At first, I tried to do exactly that. (see: AnimaGUS-minerva@d463c9d) The problem is that one then has complex logic to decide how many times to return a resource which may be duplicated by others, so I changed my mind.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can't we dedup them after filtering?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I thought about dedup, and I tried that, but it just seemed like a backwards way to do things. Can you explain why you think it's better to do this in filter? It seems like really we are doing two different things in this query, and why conflate them?
I also am thinking that if we moved the resource_discovery out of david and somehow into the application, that it would be easier to support Sinatra.