Commit 6f15c634910c660e6b8e40a3eb6ed37283f9168f
1 parent
f8418da0
Exists in
master
and in
2 other branches
Websocket-rails
Move js files to right path Videos#delete
Showing
22 changed files
with
195 additions
and
61 deletions
Show diff stats
Gemfile
Gemfile.lock
| ... | ... | @@ -117,6 +117,8 @@ GEM |
| 117 | 117 | warden (~> 1.2.3) |
| 118 | 118 | diff-lcs (1.2.5) |
| 119 | 119 | dotenv (0.7.0) |
| 120 | + em-synchrony (1.0.3) | |
| 121 | + eventmachine (>= 1.0.0.beta.1) | |
| 120 | 122 | em-websocket (0.5.1) |
| 121 | 123 | eventmachine (>= 0.12.9) |
| 122 | 124 | http_parser.rb (~> 0.6.0) |
| ... | ... | @@ -130,6 +132,9 @@ GEM |
| 130 | 132 | railties (>= 3.0.0) |
| 131 | 133 | faker (1.3.0) |
| 132 | 134 | i18n (~> 0.5) |
| 135 | + faye-websocket (0.7.3) | |
| 136 | + eventmachine (>= 0.12.0) | |
| 137 | + websocket-driver (>= 0.3.1) | |
| 133 | 138 | ffi (1.9.3) |
| 134 | 139 | foreman (0.66.0) |
| 135 | 140 | dotenv (~> 0.7.0) |
| ... | ... | @@ -166,6 +171,7 @@ GEM |
| 166 | 171 | actionpack (>= 3.2, < 5) |
| 167 | 172 | activesupport (>= 3.2, < 5) |
| 168 | 173 | hike (1.2.3) |
| 174 | + hiredis (0.5.2) | |
| 169 | 175 | hpricot (0.8.6) |
| 170 | 176 | html2haml (1.0.1) |
| 171 | 177 | erubis (~> 2.7.0) |
| ... | ... | @@ -276,6 +282,9 @@ GEM |
| 276 | 282 | rb-fsevent (0.9.4) |
| 277 | 283 | rb-inotify (0.9.4) |
| 278 | 284 | ffi (>= 0.5.0) |
| 285 | + redis (3.0.7) | |
| 286 | + redis-objects (0.9.1) | |
| 287 | + redis (>= 3.0.2) | |
| 279 | 288 | responders (1.0.0) |
| 280 | 289 | railties (>= 3.2, < 5) |
| 281 | 290 | rolify (3.4.0) |
| ... | ... | @@ -363,6 +372,16 @@ GEM |
| 363 | 372 | warden (1.2.3) |
| 364 | 373 | rack (>= 1.0) |
| 365 | 374 | websocket (1.0.7) |
| 375 | + websocket-driver (0.3.3) | |
| 376 | + websocket-rails (0.7.0) | |
| 377 | + em-synchrony | |
| 378 | + faye-websocket | |
| 379 | + hiredis | |
| 380 | + rack | |
| 381 | + rails | |
| 382 | + redis | |
| 383 | + redis-objects | |
| 384 | + thin | |
| 366 | 385 | xpath (2.0.0) |
| 367 | 386 | nokogiri (~> 1.3) |
| 368 | 387 | |
| ... | ... | @@ -419,3 +438,4 @@ DEPENDENCIES |
| 419 | 438 | thin |
| 420 | 439 | twitter-bootstrap-rails |
| 421 | 440 | uglifier (>= 1.3.0) |
| 441 | + websocket-rails | ... | ... |
app/admin/v_libras_video.rb
| 1 | 1 | ActiveAdmin.register VLibras::Video do |
| 2 | 2 | menu :priority => 15 |
| 3 | - | |
| 4 | - # See permitted parameters documentation: | |
| 5 | - # https://github.com/gregbell/active_admin/blob/master/docs/2-resource-customization.md#setting-up-strong-parameters | |
| 6 | - # | |
| 7 | - # permit_params :list, :of, :attributes, :on, :model | |
| 8 | - # | |
| 9 | - # or | |
| 10 | - # | |
| 11 | - # permit_params do | |
| 12 | - # permitted = [:permitted, :attributes] | |
| 13 | - # permitted << :other if resource.something? | |
| 14 | - # permitted | |
| 15 | - # end | |
| 16 | - | |
| 3 | + | |
| 4 | + permit_params :url, :request_id | |
| 17 | 5 | end | ... | ... |
app/assets/javascripts/application.js
app/assets/javascripts/static/v_libras/rapid.js
| ... | ... | @@ -1,26 +0,0 @@ |
| 1 | -$(function() { | |
| 2 | - $("#service-video").click(function() { | |
| 3 | - console.log($(this).prop('defaultChecked')); | |
| 4 | - | |
| 5 | - $("#url").show('slow'); | |
| 6 | - $("#legend").hide('slow'); | |
| 7 | - }); | |
| 8 | - | |
| 9 | - $("#service-video-subtitle").click(function() { | |
| 10 | - console.log($(this).prop('defaultChecked')); | |
| 11 | - | |
| 12 | - $("#url").show('slow'); | |
| 13 | - $("#legend").show('slow'); | |
| 14 | - }); | |
| 15 | - | |
| 16 | - /* When user press "Back" on the browser */ | |
| 17 | - if ($("#service-video-subtitle")[0].checked) { | |
| 18 | - console.log('b'); | |
| 19 | - $("#service-video-subtitle").click(); | |
| 20 | - } | |
| 21 | - | |
| 22 | - if ($("#service-video")[0].checked) { | |
| 23 | - console.log('a'); | |
| 24 | - $("#service-video").click(); | |
| 25 | - } | |
| 26 | -}); | |
| 27 | 0 | \ No newline at end of file |
| ... | ... | @@ -0,0 +1,20 @@ |
| 1 | +$(function() { | |
| 2 | + $("#service-video").click(function() { | |
| 3 | + $("#url").show('slow'); | |
| 4 | + $("#legend").hide('slow'); | |
| 5 | + }); | |
| 6 | + | |
| 7 | + $("#service-video-subtitle").click(function() { | |
| 8 | + $("#url").show('slow'); | |
| 9 | + $("#legend").show('slow'); | |
| 10 | + }); | |
| 11 | + | |
| 12 | + /* When user press "Back" on the browser */ | |
| 13 | + if ($("#service-video-subtitle")[0].checked) { | |
| 14 | + $("#service-video-subtitle").click(); | |
| 15 | + } | |
| 16 | + | |
| 17 | + if ($("#service-video")[0].checked) { | |
| 18 | + $("#service-video").click(); | |
| 19 | + } | |
| 20 | +}); | |
| 0 | 21 | \ No newline at end of file | ... | ... |
| ... | ... | @@ -0,0 +1,16 @@ |
| 1 | +$(function() { | |
| 2 | + $("a.badge").tooltip(); | |
| 3 | + | |
| 4 | + // connect to server like normal | |
| 5 | + // FIXME: how to get the right address | |
| 6 | + var dispatcher = new WebSocketRails('localhost:3000/websocket'); | |
| 7 | + | |
| 8 | + // subscribe to the channel | |
| 9 | + var channel = dispatcher.subscribe('requests_update'); | |
| 10 | + | |
| 11 | + // bind to a channel event | |
| 12 | + channel.bind('update', function(data) { | |
| 13 | + alert("channel updated"); | |
| 14 | + location.reload(); | |
| 15 | + }); | |
| 16 | +}); | |
| 0 | 17 | \ No newline at end of file | ... | ... |
app/assets/stylesheets/bootstrap_overrides.css.scss
app/controllers/v_libras/videos_controller.rb
| 1 | -class VLibras::VideosController < ApplicationController | |
| 1 | +class VLibras::VideosController < InheritedResources::Base | |
| 2 | + actions :destroy | |
| 3 | + | |
| 2 | 4 | before_filter :check_vlibras_api_status, :only => [ :index ] |
| 3 | 5 | |
| 4 | 6 | def index |
| 5 | 7 | @videos = current_user.videos |
| 6 | - @requests = current_user.requests.limit(10) | |
| 8 | + @requests = current_user.requests.limit(6) | |
| 7 | 9 | end |
| 8 | 10 | end | ... | ... |
app/helpers/application_helper.rb
| ... | ... | @@ -27,20 +27,23 @@ module ApplicationHelper |
| 27 | 27 | end |
| 28 | 28 | end |
| 29 | 29 | |
| 30 | - def request_status_label(status) | |
| 31 | - classes = [ 'label' ] | |
| 30 | + def request_status_label(request) | |
| 31 | + classes = [ 'badge' ] | |
| 32 | + | |
| 33 | + status = request.status | |
| 32 | 34 | |
| 33 | 35 | case status |
| 34 | 36 | when 'created' |
| 35 | 37 | when 'processing' |
| 36 | - classes << 'label-warning' | |
| 38 | + classes << 'badge-warning' | |
| 37 | 39 | when 'error' |
| 38 | - classes << 'label-important' | |
| 40 | + classes << 'badge-important' | |
| 39 | 41 | when 'success' |
| 40 | - classes << 'label-success' | |
| 42 | + classes << 'badge-success' | |
| 41 | 43 | end |
| 42 | 44 | |
| 43 | - content_tag(:div, t(status, scope: 'status'), :class => classes) | |
| 45 | + content_tag(:a, t(status, scope: 'status'), :class => classes, | |
| 46 | + :data => { 'toggle' => "tooltip" }, :title => request.response) | |
| 44 | 47 | end |
| 45 | 48 | |
| 46 | 49 | end | ... | ... |
app/models/v_libras/request.rb
| ... | ... | @@ -19,7 +19,7 @@ class VLibras::Request < ActiveRecord::Base |
| 19 | 19 | |
| 20 | 20 | belongs_to :owner, :class => User |
| 21 | 21 | |
| 22 | - has_one :video, :class => VLibras::Video | |
| 22 | + has_one :video, :class => VLibras::Video, :dependent => :destroy | |
| 23 | 23 | |
| 24 | 24 | validates :service_type, |
| 25 | 25 | presence: true, | ... | ... |
app/models/v_libras/video.rb
app/views/layouts/application.html.erb
app/views/v_libras/requests/rapid.haml
app/views/v_libras/videos/index.haml
| 1 | +- content_for :js do | |
| 2 | + = javascript_include_tag "v_libras/videos/index" | |
| 3 | + | |
| 1 | 4 | .breadcrumb |
| 2 | 5 | %h3= t('videos.list') |
| 3 | 6 | |
| ... | ... | @@ -7,7 +10,8 @@ |
| 7 | 10 | = link_to image_tag("avatar.png"), video.url |
| 8 | 11 | %p |
| 9 | 12 | = link_to t('videos.show'), video_path(video), class: "btn btn-success" |
| 10 | - = link_to t('videos.delete'), video_path(video), confirm: t('shared.confirm_delete'), method: :delete, class: "btn btn-danger" | |
| 13 | + = link_to t('videos.delete'), v_libras_video_path(video), method: :delete, | |
| 14 | + class: "btn btn-danger", data: { confirm: t('shared.confirm_delete') } | |
| 11 | 15 | |
| 12 | 16 | .breadcrumb.requests |
| 13 | 17 | %h4= t('requests.list') |
| ... | ... | @@ -22,7 +26,7 @@ |
| 22 | 26 | |
| 23 | 27 | - @requests.each do |request| |
| 24 | 28 | %tr |
| 25 | - %td.span2= request_status_label(request.status) | |
| 29 | + %td.span2= request_status_label(request) | |
| 26 | 30 | %td.span5= request.video_filename |
| 27 | 31 | %td.span5= time_ago_in_words(request.created_at) |
| 28 | 32 | ... | ... |
config/environments/development.rb
| ... | ... | @@ -0,0 +1,14 @@ |
| 1 | +WebsocketRails::EventMap.describe do | |
| 2 | + # You can use this file to map incoming events to controller actions. | |
| 3 | + # One event can be mapped to any number of controller actions. The | |
| 4 | + # actions will be executed in the order they were subscribed. | |
| 5 | + # | |
| 6 | + # Uncomment and edit the next line to handle the client connected event: | |
| 7 | + # subscribe :client_connected, :to => Controller, :with_method => :method_name | |
| 8 | + # | |
| 9 | + # Here is an example of mapping namespaced events: | |
| 10 | + # namespace :product do | |
| 11 | + # subscribe :new, :to => ProductController, :with_method => :new_product | |
| 12 | + # end | |
| 13 | + # The above will handle an event triggered on the client like `product.new`. | |
| 14 | +end | ... | ... |
config/initializers/assets.rb
| 1 | -Rails.application.config.assets.precompile += %w( static/v_libras/rapid.js ) | |
| 2 | 1 | \ No newline at end of file |
| 2 | +Rails.application.config.assets.precompile += %w( v_libras/requests/rapid.js ) | |
| 3 | +Rails.application.config.assets.precompile += %w( v_libras/videos/index.js ) | |
| 3 | 4 | \ No newline at end of file | ... | ... |
| ... | ... | @@ -0,0 +1,63 @@ |
| 1 | +WebsocketRails.setup do |config| | |
| 2 | + | |
| 3 | + # Uncomment to override the default log level. The log level can be | |
| 4 | + # any of the standard Logger log levels. By default it will mirror the | |
| 5 | + # current Rails environment log level. | |
| 6 | + config.log_level = :debug | |
| 7 | + | |
| 8 | + # Uncomment to change the default log file path. | |
| 9 | + # config.log_path = "#{Rails.root}/log/websocket_rails.log" | |
| 10 | + | |
| 11 | + # Set to true if you wish to log the internal websocket_rails events | |
| 12 | + # such as the keepalive `websocket_rails.ping` event. | |
| 13 | + # config.log_internal_events = false | |
| 14 | + | |
| 15 | + # Change to true to enable standalone server mode | |
| 16 | + # Start the standalone server with rake websocket_rails:start_server | |
| 17 | + # * Requires Redis | |
| 18 | + config.standalone = false | |
| 19 | + | |
| 20 | + # Change to true to enable channel synchronization between | |
| 21 | + # multiple server instances. | |
| 22 | + # * Requires Redis. | |
| 23 | + config.synchronize = false | |
| 24 | + | |
| 25 | + # Prevent Thin from daemonizing (default is true) | |
| 26 | + # config.daemonize = false | |
| 27 | + | |
| 28 | + # Uncomment and edit to point to a different redis instance. | |
| 29 | + # Will not be used unless standalone or synchronization mode | |
| 30 | + # is enabled. | |
| 31 | + # config.redis_options = {:host => 'localhost', :port => '6379'} | |
| 32 | + | |
| 33 | + # By default, all subscribers in to a channel will be removed | |
| 34 | + # when that channel is made private. If you don't wish active | |
| 35 | + # subscribers to be removed from a previously public channel | |
| 36 | + # when making it private, set the following to true. | |
| 37 | + # config.keep_subscribers_when_private = false | |
| 38 | + | |
| 39 | + # Set to true if you wish to broadcast channel subscriber_join and | |
| 40 | + # subscriber_part events. All subscribers of a channel will be | |
| 41 | + # notified when other clients join and part the channel. If you are | |
| 42 | + # using the UserManager, the current_user object will be sent along | |
| 43 | + # with the event. | |
| 44 | + # config.broadcast_subscriber_events = true | |
| 45 | + | |
| 46 | + # Used as the key for the WebsocketRails.users Hash. This method | |
| 47 | + # will be called on the `current_user` object in your controller | |
| 48 | + # if one exists. If `current_user` does not exist or does not | |
| 49 | + # respond to the identifier, the key will default to `connection.id` | |
| 50 | + # config.user_identifier = :id | |
| 51 | + | |
| 52 | + # Uncomment and change this option to override the class associated | |
| 53 | + # with your `current_user` object. This class will be used when | |
| 54 | + # synchronization is enabled and you trigger events from background | |
| 55 | + # jobs using the WebsocketRails.users UserManager. | |
| 56 | + # config.user_class = User | |
| 57 | + | |
| 58 | + # Supporting HTTP streaming on Internet Explorer versions 8 & 9 | |
| 59 | + # requires CORS to be enabled for GET "/websocket" request. | |
| 60 | + # List here the origin domains allowed to perform the request. | |
| 61 | + # config.allowed_origins = ['http://localhost:3000'] | |
| 62 | + | |
| 63 | +end | ... | ... |
config/routes.rb
lib/api_client/callback_processor.rb
| 1 | 1 | class ApiClient::CallbackProcessor |
| 2 | 2 | def self.process(params) |
| 3 | 3 | request = VLibras::Request.find(params[:request_id]) |
| 4 | - request.update(:status => 'success') | |
| 5 | - request.create_video(:url => params['response']) | |
| 4 | + | |
| 5 | + if params['error'] | |
| 6 | + Rails.logger.debug "[VLibras::Callback]: Error #{params}" | |
| 7 | + | |
| 8 | + request.update!(:status => 'error', :response => params['error']) | |
| 9 | + else | |
| 10 | + Rails.logger.debug "[VLibras::Callback] OK: #{params}" | |
| 11 | + | |
| 12 | + request.update!(:status => 'success') | |
| 13 | + request.create_video(:url => params['response']) | |
| 14 | + end | |
| 15 | + | |
| 16 | + Rails.logger.debug "[VLibras::Callback] Notifying websocket channel" | |
| 17 | + WebsocketRails[:requests_update].trigger(:update, {a: :b, c: :d}) | |
| 6 | 18 | end |
| 7 | 19 | end |
| 8 | 20 | \ No newline at end of file | ... | ... |
lib/api_client/client.rb
| ... | ... | @@ -7,7 +7,7 @@ module ApiClient::Client |
| 7 | 7 | def self.submit(request, files) |
| 8 | 8 | o = { query: request.params.clone } |
| 9 | 9 | o[:query].merge!({ :servico => request.service_type }) |
| 10 | - o[:query].merge!({ :callback => "http://150.165.205.192:3000/v_libras/requests/callback?request_id=#{request.id}" }) | |
| 10 | + o[:query].merge!({ :callback => "http://150.165.205.166:3000/v_libras/requests/callback?request_id=#{request.id}" }) | |
| 11 | 11 | |
| 12 | 12 | o[:query].merge!({ :video => files[:video].file.to_file }) |
| 13 | 13 | |
| ... | ... | @@ -27,8 +27,12 @@ module ApiClient::Client |
| 27 | 27 | else |
| 28 | 28 | request.update!(:response => response.body, :status => 'error') |
| 29 | 29 | end |
| 30 | - rescue | |
| 31 | - | |
| 30 | + rescue => e | |
| 31 | + request.update!(:status => 'error', :response => e) | |
| 32 | + ensure | |
| 33 | + # FIXME: Running on another thread. Websocket not working :( | |
| 34 | + Delayed::Worker.logger.debug "[VLibras::Request] Sending message to websocket channel" | |
| 35 | + WebsocketRails[:requests_update].trigger(:update, {a: :b, c: :d}) | |
| 32 | 36 | end |
| 33 | 37 | |
| 34 | 38 | private | ... | ... |