* VRFS-1228
This commit is contained in:
parent
89a5f2747e
commit
7a41b74549
|
|
@ -1,6 +1,8 @@
|
|||
module JamRuby
|
||||
class Notification < ActiveRecord::Base
|
||||
|
||||
@@log = Logging.logger[Notification]
|
||||
|
||||
self.primary_key = 'id'
|
||||
|
||||
default_scope order('created_at DESC')
|
||||
|
|
@ -504,7 +506,11 @@ module JamRuby
|
|||
|
||||
# send email notifications
|
||||
unless offline_ff.empty?
|
||||
UserMailer.musician_session_join(offline_ff.map! {|f| f.email}, notification_msg).deliver
|
||||
begin
|
||||
UserMailer.musician_session_join(offline_ff.map! {|f| f.email}, notification_msg).deliver if APP_CONFIG.send_join_session_email_notifications
|
||||
rescue => e
|
||||
@@log.error("unable to send email to offline participants #{e}")
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -105,6 +105,10 @@ def app_config
|
|||
100
|
||||
end
|
||||
|
||||
def send_join_session_email_notifications
|
||||
true
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def audiomixer_workspace_path
|
||||
|
|
|
|||
|
|
@ -456,6 +456,8 @@
|
|||
|
||||
function onHashChange(e, postFunction) {
|
||||
|
||||
if(currentHash == context.location.hash) { return }
|
||||
|
||||
if(resettingHash) {
|
||||
resettingHash = false;
|
||||
e.preventDefault();
|
||||
|
|
@ -474,7 +476,7 @@
|
|||
var accepted = screenEvent(currentScreen, 'beforeLeave', {screen:screen, hash: context.location.hash});
|
||||
if(accepted === false) {
|
||||
console.log("navigation to " + context.location.hash + " rejected by " + currentScreen);
|
||||
resettingHash = true;
|
||||
//resettingHash = true;
|
||||
// reset the hash to where it just was
|
||||
context.location.hash = currentHash;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@
|
|||
var rest = context.JK.Rest();
|
||||
var decrementedFriendCountOnce = false;
|
||||
var sentFriendRequest = false;
|
||||
var profileScreen = null;
|
||||
|
||||
var instrument_logo_map = context.JK.getInstrumentIconMap24();
|
||||
|
||||
|
|
@ -307,6 +308,7 @@
|
|||
}
|
||||
|
||||
function bindAbout() {
|
||||
|
||||
$('#profile-instruments').empty();
|
||||
|
||||
// name
|
||||
|
|
@ -359,61 +361,93 @@
|
|||
$('#profile-favorite-stats').html(user.favorite_count + text);
|
||||
}
|
||||
|
||||
if(isCurrentUser) {
|
||||
renderBio();
|
||||
}
|
||||
|
||||
/** The biography show/edit functionality */
|
||||
function renderBio() {
|
||||
|
||||
|
||||
function initializeBioVisibility() {
|
||||
|
||||
$showBio.hide();
|
||||
$noBio.hide();
|
||||
$biographyEditor.hide();
|
||||
|
||||
$bioTextArea.val(user.biography);
|
||||
|
||||
if(user.biography) {
|
||||
$('#profile-biography').text(user.biography);
|
||||
$showBio.show();
|
||||
if(isCurrentUser()) {
|
||||
$editBiographyButton.show();
|
||||
}
|
||||
$biographyText.text(user.biography).show();
|
||||
}
|
||||
else {
|
||||
var createBio = $(context._.template($('#template-add-user-profile').html(), {}, { variable: 'data' }));
|
||||
$('a.enter-bio', createBio).click(function() {
|
||||
$('.update-biography').show();
|
||||
return false;
|
||||
});
|
||||
|
||||
$('#btn-update-user-biography', createBio).click(function() {
|
||||
var $bio = $('#profile-biography .user-biography');
|
||||
var bio = $bio.val();
|
||||
$bio.closest('div.field').removeClass('error');
|
||||
$('.error-text', $bio.closest('div.field')).remove();
|
||||
rest.updateUser({
|
||||
biography: bio
|
||||
})
|
||||
.done(function(response) {
|
||||
if(response.biography){
|
||||
$('#profile-biography').text(response.biography);
|
||||
} else {
|
||||
$('.update-biography').hide();
|
||||
}
|
||||
})
|
||||
.fail(function(jqXHR) {
|
||||
if(jqXHR.status == 422) {
|
||||
var errors = JSON.parse(jqXHR.responseText)
|
||||
var biography = context.JK.format_errors("biography", errors);
|
||||
if(biography != null) {
|
||||
$bio.closest('div.field').addClass('error').end().after(biography);
|
||||
}
|
||||
else {
|
||||
app.notifyServerError(jqXHR, "Unable to update biography")
|
||||
}
|
||||
}
|
||||
else {
|
||||
app.notifyServerError(jqXHR, "Unable to update biography")
|
||||
}
|
||||
})
|
||||
return false;
|
||||
});
|
||||
|
||||
$('#btn-cancel-user-biography', createBio).click(function() {
|
||||
$('.update-biography').hide();
|
||||
return false;
|
||||
});
|
||||
$('#profile-biography').html(createBio);
|
||||
if(isCurrentUser()) {
|
||||
$noBio.show();
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
$('#profile-biography').text(user.biography);
|
||||
}
|
||||
|
||||
var $bioTextArea = $('.user-biography', profileScreen);
|
||||
var $showBio = $('.have-bio', profileScreen);
|
||||
var $noBio = $('.no-bio', profileScreen);
|
||||
var $biographyEditor = $('.update-biography', profileScreen);
|
||||
var $addBiographyButton = $('a.enter-bio', profileScreen);
|
||||
var $editBiographyButton = $('#profile-edit-biography', profileScreen);
|
||||
var $submitBiographyButton = $('#btn-update-user-biography', profileScreen);
|
||||
var $cancelBiographyButton = $('#btn-cancel-user-biography', profileScreen);
|
||||
var $biographyText = $('#profile-biography', profileScreen);
|
||||
|
||||
initializeBioVisibility();
|
||||
|
||||
$addBiographyButton.unbind('click').click(function() {
|
||||
$biographyEditor.val(user.biography).show();
|
||||
return false;
|
||||
});
|
||||
|
||||
$editBiographyButton.unbind('click').click(function() {
|
||||
$editBiographyButton.hide();
|
||||
$biographyText.hide();
|
||||
$bioTextArea.val(user.biography);
|
||||
$biographyEditor.show();
|
||||
return false;
|
||||
})
|
||||
|
||||
$submitBiographyButton.unbind('click').click(function() {
|
||||
var bio = $bioTextArea.val();
|
||||
$bioTextArea.closest('div.field').removeClass('error');
|
||||
$('.error-text', $bioTextArea.closest('div.field')).remove();
|
||||
userDefer = rest.updateUser({
|
||||
biography: bio
|
||||
})
|
||||
.done(function(response) {
|
||||
user = response;
|
||||
initializeBioVisibility();
|
||||
})
|
||||
.fail(function(jqXHR) {
|
||||
if(jqXHR.status == 422) {
|
||||
var errors = JSON.parse(jqXHR.responseText)
|
||||
var biography = context.JK.format_errors("biography", errors);
|
||||
if(biography != null) {
|
||||
$bioTextArea.closest('div.field').addClass('error').end().after(biography);
|
||||
}
|
||||
else {
|
||||
app.notifyServerError(jqXHR, "Unable to update biography")
|
||||
}
|
||||
}
|
||||
else {
|
||||
app.notifyServerError(jqXHR, "Unable to update biography")
|
||||
}
|
||||
})
|
||||
return false;
|
||||
})
|
||||
|
||||
$cancelBiographyButton.unbind('click').click(function() {
|
||||
initializeBioVisibility();
|
||||
return false;
|
||||
})
|
||||
}
|
||||
|
||||
/****************** SOCIAL TAB *****************/
|
||||
|
|
@ -696,7 +730,7 @@
|
|||
'afterShow': afterShow
|
||||
};
|
||||
app.bindScreen('profile', screenBindings);
|
||||
|
||||
profileScreen = $('#user-profile');
|
||||
events();
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -279,6 +279,10 @@
|
|||
// a client can only be in one session at a time,
|
||||
// and other parts of the code want to know at any certain times
|
||||
// about the current session, if any (for example, reconnect logic)
|
||||
if(context.JK.CurrentSessionModel) {
|
||||
context.JK.CurrentSessionModel.unsubscribe();
|
||||
}
|
||||
|
||||
context.JK.CurrentSessionModel = sessionModel = new context.JK.SessionModel(
|
||||
context.JK.app,
|
||||
context.JK.JamServer,
|
||||
|
|
@ -442,6 +446,7 @@
|
|||
app.layout.showDialog('leave-session-warning');
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
function beforeHide(data) {
|
||||
|
|
|
|||
|
|
@ -100,7 +100,10 @@
|
|||
logger.debug("SessionModel.leaveCurrentSession()");
|
||||
// TODO - sessionChanged will be called with currentSession = null
|
||||
server.unregisterMessageCallback(context.JK.MessageType.MUSICIAN_SESSION_JOIN, refreshCurrentSession);
|
||||
server.unregisterMessageCallback(context.JK.MessageType.MUSICIAN_SESSION_DEPART, refreshCurrentSession);
|
||||
server.unregisterMessageCallback(context.JK.MessageType.SESSION_JOIN, refreshCurrentSession);
|
||||
server.unregisterMessageCallback(context.JK.MessageType.SESSION_DEPART, refreshCurrentSession);
|
||||
|
||||
//server.unregisterMessageCallback(context.JK.MessageType.MUSICIAN_SESSION_DEPART, refreshCurrentSession);
|
||||
// leave the session right away without waiting on REST. Why? If you can't contact the server, or if it takes a long
|
||||
// time, for that entire duration you'll still be sending voice data to the other users.
|
||||
// this may be bad if someone decides to badmouth others in the left-session during this time
|
||||
|
|
@ -143,7 +146,7 @@
|
|||
*/
|
||||
function refreshCurrentSession() {
|
||||
// XXX use backend instead: https://jamkazam.atlassian.net/browse/VRFS-854
|
||||
logger.debug("SessionModel.refreshCurrentSession()");
|
||||
logger.debug("SessionModel.refreshCurrentSession(" + currentSessionId +")");
|
||||
refreshCurrentSessionRest(sessionChanged);
|
||||
}
|
||||
|
||||
|
|
@ -171,6 +174,7 @@
|
|||
if(sessionData != null) {
|
||||
currentOrLastSession = sessionData;
|
||||
}
|
||||
|
||||
currentSession = sessionData;
|
||||
}
|
||||
|
||||
|
|
@ -189,7 +193,6 @@
|
|||
$.ajax({
|
||||
type: "GET",
|
||||
url: url,
|
||||
async: false,
|
||||
success: function(response) {
|
||||
sendClientParticipantChanges(currentSession, response);
|
||||
updateCurrentSession(response);
|
||||
|
|
@ -378,8 +381,7 @@
|
|||
var url = "/api/participants/" + clientId;
|
||||
return $.ajax({
|
||||
type: "DELETE",
|
||||
url: url,
|
||||
async: true
|
||||
url: url
|
||||
});
|
||||
}
|
||||
|
||||
|
|
@ -489,6 +491,12 @@
|
|||
this.getCurrentOrLastSession = function() {
|
||||
return currentOrLastSession;
|
||||
};
|
||||
this.unsubscribe = function() {
|
||||
server.unregisterMessageCallback(context.JK.MessageType.MUSICIAN_SESSION_JOIN, refreshCurrentSession);
|
||||
server.unregisterMessageCallback(context.JK.MessageType.SESSION_JOIN, refreshCurrentSession);
|
||||
server.unregisterMessageCallback(context.JK.MessageType.SESSION_DEPART, refreshCurrentSession);
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
})(window,jQuery);
|
||||
|
|
@ -248,6 +248,7 @@
|
|||
//
|
||||
// use context._.template for something more powerful
|
||||
context.JK.fillTemplate = function(template, vals) {
|
||||
if(template == null) throw 'null template in fillTemplate'
|
||||
for(var val in vals)
|
||||
template=template.replace(new RegExp('{'+val+'}','g'), vals[val]);
|
||||
return template;
|
||||
|
|
|
|||
|
|
@ -1,20 +1,13 @@
|
|||
@import "client/common.css.scss";
|
||||
|
||||
#user-profile {
|
||||
#profile-biography {
|
||||
a.enter-bio {
|
||||
|
||||
}
|
||||
.profile-about-right {
|
||||
|
||||
textarea {
|
||||
width:100%;
|
||||
height:150px;
|
||||
padding:0;
|
||||
}
|
||||
|
||||
.update-biography {
|
||||
display:none;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -61,8 +61,27 @@
|
|||
<span id="profile-recording-stats"></span><br />
|
||||
</div>
|
||||
<div class="profile-about-right">
|
||||
<p id="profile-biography"></p><br />
|
||||
<div id="profile-instruments"></div>
|
||||
<div class="no-bio">
|
||||
<span>You have no bio to describe yourself as a musician. <a href="#" class="enter-bio">Enter one now!</a></span>
|
||||
</div>
|
||||
<div class="have-bio">
|
||||
<p id="profile-biography"></p><a id="profile-edit-biography" class="button-orange right" href="#">Edit Bio</a>
|
||||
</div>
|
||||
<div class="update-biography">
|
||||
<div class="field">
|
||||
<textarea name="biography" class="user-biography"></textarea>
|
||||
</div>
|
||||
<br clear="left" /><br />
|
||||
<div class="right">
|
||||
<a id="btn-update-user-biography" layout-action="close" class="button-orange">OK</a>
|
||||
</div>
|
||||
<div class="right">
|
||||
<a id="btn-cancel-user-biography" layout-action="close" class="button-grey">CANCEL</a>
|
||||
</div>
|
||||
<br clear="all" />
|
||||
</div>
|
||||
<br />
|
||||
<div id="profile-instruments"></div>
|
||||
</div>
|
||||
<br clear="all" />
|
||||
</div>
|
||||
|
|
@ -192,24 +211,3 @@
|
|||
<div class="profile-block-city">{location}</div>
|
||||
</div>
|
||||
</script>
|
||||
|
||||
|
||||
<script type="text/template" id="template-add-user-profile">
|
||||
<div>
|
||||
<span>You have no bio to describe yourself as a musician. <a href="#" class="enter-bio">Enter one now!</a></span>
|
||||
<div class="update-biography">
|
||||
<div class="field">
|
||||
<textarea name="biography" class="user-biography"/>
|
||||
</div>
|
||||
<br clear="left" /><br />
|
||||
<div class="right">
|
||||
<a id="btn-update-user-biography" layout-action="close" class="button-orange">OK</a>
|
||||
</div>
|
||||
<div class="right">
|
||||
<a id="btn-cancel-user-biography" layout-action="close" class="button-grey">CANCEL</a>
|
||||
</div>
|
||||
<br clear="all" />
|
||||
</div>
|
||||
<div>
|
||||
</script>
|
||||
|
||||
|
|
|
|||
|
|
@ -207,5 +207,7 @@ if defined?(Bundler)
|
|||
config.autocheck_create_session_agreement = false
|
||||
|
||||
config.max_audio_downloads = 100
|
||||
|
||||
config.send_join_session_email_notifications = true
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -45,7 +45,7 @@ SampleApp::Application.configure do
|
|||
config.assets.compress = false
|
||||
|
||||
# Expands the lines which load the assets
|
||||
config.assets.debug = false
|
||||
config.assets.debug = true
|
||||
|
||||
# Set the logging destination(s)
|
||||
config.log_to = %w[stdout file]
|
||||
|
|
@ -55,6 +55,7 @@ SampleApp::Application.configure do
|
|||
|
||||
config.websocket_gateway_enable = true
|
||||
|
||||
|
||||
TEST_CONNECT_STATES = false
|
||||
|
||||
# Overloaded value to match production for using cloudfront in dev mode
|
||||
|
|
@ -77,4 +78,6 @@ SampleApp::Application.configure do
|
|||
|
||||
# set CREATE_SESSION_AGREEMENT=0 if you don't want the autoclick behavior
|
||||
config.autocheck_create_session_agreement = ENV['CREATE_SESSION_AGREEMENT'] ? ENV['CREATE_SESSION_AGREEMENT'] == "1" : true
|
||||
|
||||
config.send_join_session_email_notifications = false
|
||||
end
|
||||
|
|
|
|||
Loading…
Reference in New Issue