Commit 2790c99c by Damien Moulard

bdm admin subscribe a member to a shift template

parent fd7f5d1e
......@@ -115,6 +115,9 @@ ENTRANCE_EASY_SHIFT_VALIDATE_MSG = """Si vous faites un service dans un comité,
valider votre présence en cherchant<br/>
votre nom ou numéro ci-dessous
"""
HAS_COMMITTEE_SHIFT = True
# Members space / shifts
UNSUBSCRIBED_FORM_LINK = 'https://docs.google.com/forms/d/e/1FAIpQLScWcpls-ruYIp7HdrjRF1B1TyuzdqhvlUIcUWynbEujfj3dTg/viewform'
UNSUBSCRIBED_MSG = 'Vous êtes désincrit·e, merci de remplir <a href="https://docs.google.com/forms/d/e/1FAIpQLSfPiC2PkSem9x_B5M7LKpoFNLDIz0k0V5I2W3Mra9AnqnQunw/viewform">ce formulaire</a> pour vous réinscrire sur un créneau.<br />Vous pouvez également contacter le Bureau des Membres en remplissant <a href="https://docs.google.com/forms/d/e/1FAIpQLSeZP0m5-EXPVJxEKJk6EjwSyZJtnbiGdYDuAeFI3ENsHAOikg/viewform">ce formulaire</a>'
......
......@@ -5,6 +5,7 @@ from outils.common import OdooAPI
from members.models import CagetteUser
from members.models import CagetteMembers
from members.models import CagetteMember
from members.models import CagetteServices
from shifts.models import CagetteShift
from outils.common import MConfig
from datetime import datetime
......@@ -337,8 +338,18 @@ def manage_attached(request):
def manage_regular_shifts(request):
""" Administration des créneaux des membres """
template = loader.get_template('members/admin/manage_regular_shifts.html')
context = {'title': 'BDM - Créneaux',
'module': 'Membres'}
context = {
'title': 'BDM - Créneaux',
'module': 'Membres',
'couchdb_server': settings.COUCHDB['url'],
'db': settings.COUCHDB['dbs']['member'],
'max_begin_hour': settings.MAX_BEGIN_HOUR,
'mag_place_string': settings.MAG_NAME,
'open_on_sunday': getattr(settings, 'OPEN_ON_SUNDAY', False),
'show_ftop_button': getattr(settings, 'SHOW_FTOP_BUTTON', True),
'has_committe_shift': getattr(settings, 'HAS_COMMITTEE_SHIFT', True),
'ASSOCIATE_MEMBER_SHIFT' : getattr(settings, 'ASSOCIATE_MEMBER_SHIFT', '')
}
return HttpResponse(template.render(context, request))
def get_makeups_members(request):
......@@ -399,6 +410,9 @@ def update_members_makeups(request):
response = JsonResponse(res, status=403)
return response
# --- Gestion des créneaux
def delete_shift_registration(request):
""" From BDM admin, delete (cancel) a member shift registration """
res = {}
......@@ -469,7 +483,41 @@ def delete_shift_template_registration(request):
response = JsonResponse(res, status=403)
return response
# Gestion des binômes
def shift_subscription(request):
""" Inscrit un membre désinscrit à un shift template """
res = {}
if CagetteUser.are_credentials_ok(request):
data = json.loads(request.body.decode())
partner_id = int(data["partner_id"])
shift_type = data["shift_type"]
if shift_type == 1:
# 1 = standard
shift_template_id = data["shift_template_id"]
else:
# 2 = ftop
shift_template_id = CagetteServices.get_committees_shift_id()
m = CagetteMember(partner_id)
m.create_coop_shift_subscription(shift_template_id, shift_type)
# Retrurn necessary data
api = OdooAPI()
c = [['id', '=', shift_template_id]]
f = ['id', 'name']
res["shift_template"] = api.search_read('shift.template', c, f)[0]
c = [['id', '=', partner_id]]
f = ['cooperative_state']
res["cooperative_state"] = api.search_read('res.partner', c, f)[0]['cooperative_state']
response = JsonResponse(res)
else:
response = JsonResponse({"message": "Unauthorized"}, status=403)
return response
# --- Gestion des binômes
def get_member_info(request, id):
"""Retrieve information about a member."""
......
......@@ -75,7 +75,8 @@
}
/* Actions */
#remove_shift_template_button {
#remove_shift_template_button,
#subscribe_to_shift_template_button {
display: none;
margin: 15px;
}
......@@ -86,3 +87,25 @@
#permanent_unsuscribe {
margin-right: 5px;
}
/* Calendar */
#shifts_calendar_area {
display: none;
margin-top: 15px;
}
.shift[data-place="Cleme"], [data-select="Cleme"] {background: #c8deff;}
#subs_cap {width: 200px;}
.lat_menu button {margin-bottom:5px;}
.oddeven_selector {margin-right:25px;}
.main_content .shift {float:left;}
.main_content .shift.full {display:none;}
.shift {margin:2px; padding:2px; cursor: cell;}
.shift.alert,span.alert {border-bottom: 3px #e52121 solid;}
.highlighted {box-shadow: 10px 10px 5px grey;}
.lat_menu.highlighted {border: 2px #fffc07 dotted;}
#coop_list_view td.coop:hover,
#coop_list_view td.c_shift:hover {background:#fffc07; cursor:pointer;}
.b_red {color:#ffffff;}
.shift[data-type="compact"] {border: 1px solid #000000;border-radius: 5px; padding:5px; cursor: pointer;}
.shift_template, .next_shift {font-weight: bold;}
\ No newline at end of file
......@@ -26,13 +26,13 @@ function load_member_infos(divId, memberId) {
traditional: true,
contentType: "application/json; charset=utf-8",
success: function(data) {
console.log(data.member)
console.log(data.member);
if (divId === 'parentInfo') {
parentId = data.member.id;
parentName = data.member.barcode_base + ' ' + data.member.name
parentName = data.member.barcode_base + ' ' + data.member.name;
} else if (divId === 'childInfo') {
childId = data.member.id;
childName = data.member.barcode_base + ' ' + data.member.name
childName = data.member.barcode_base + ' ' + data.member.name;
}
display_member_infos(divId, data.member);
},
......@@ -70,7 +70,7 @@ function display_member_infos(divId, memberData) {
if (parentId != null && childId != null) {
$("#createPair").prop("disabled", false);
$("#createPair").addClass("btn--primary")
$("#createPair").addClass("btn--primary");
}
}
......@@ -223,15 +223,16 @@ function delete_pair(childId) {
function confirmDeletion(childId) {
var modalContent = $('#confirmModal')
modalContent.find("#parentName").text(parentName)
modalContent.find("#childName").text(childName)
var modalContent = $('#confirmModal');
modalContent.find("#parentName").text(parentName);
modalContent.find("#childName").text(childName);
modalContent = modalContent.html();
openModal(modalContent, () => {
if (is_time_to('delete_pair')) {
closeModal();
openModal();
delete_pair(childId)
delete_pair(childId);
}
}, 'Valider', false);
}
......@@ -244,10 +245,9 @@ function create_pair(payload) {
dataType:"json",
contentType: "application/json; charset=utf-8",
data: JSON.stringify(payload),
success: function(data) {
success: function() {
enqueue_message_for_next_loading("Binôme créé.");
location.reload()
location.reload();
},
error: function(data) {
err = {msg: "erreur serveur", ctx: 'create pair'};
......@@ -261,6 +261,8 @@ function create_pair(payload) {
data.responseJSON.errors.map(function(error) {
message += ('\n' + error);
return null;
});
alert(message);
}
......@@ -317,10 +319,10 @@ $(document).ready(function() {
});
},
minLength: 1,
search: function(event, ui) {
search: function() {
$('#spinner1').show();
},
response: function(event, ui) {
response: function() {
$('#spinner1').hide();
},
select: function(event, ui) {
......@@ -331,6 +333,8 @@ $(document).ready(function() {
return false;
}
return null;
}
});
......@@ -367,10 +371,10 @@ $(document).ready(function() {
});
},
minLength: 1,
search: function(event, ui) {
search: function() {
$('#spinner2').show();
},
response: function(event, ui) {
response: function() {
$('#spinner2').hide();
},
select: function(event, ui) {
......@@ -380,6 +384,8 @@ $(document).ready(function() {
return false;
}
return null;
}
});
......@@ -390,15 +396,16 @@ $(document).ready(function() {
"child": {"id": childId}
};
var modalContent = $('#confirmModal')
modalContent.find("#parentName").text(parentName)
modalContent.find("#childName").text(childName)
var modalContent = $('#confirmModal');
modalContent.find("#parentName").text(parentName);
modalContent.find("#childName").text(childName);
modalContent = modalContent.html();
openModal(modalContent, () => {
if (is_time_to('create_pair')) {
closeModal();
openModal(); // Show gears
create_pair(payload)
create_pair(payload);
}
}, 'Valider', false);
}
......@@ -411,6 +418,7 @@ $(document).ready(function() {
$(document).on('click', '.delete_pair', function (event) {
var childId = event.target.id.split('_').slice(-1)[0];
$.ajax({
type: 'GET',
url: "/members/get_member_info/" + childId,
......@@ -418,8 +426,8 @@ $(document).ready(function() {
traditional: true,
contentType: "application/json; charset=utf-8",
success: function(data) {
parentName = data.member.parent_barcode_base + ' - ' + data.member.parent_name
childName = data.member.barcode_base + ' - ' + data.member.name
parentName = data.member.parent_barcode_base + ' - ' + data.member.parent_name;
childName = data.member.barcode_base + ' - ' + data.member.name;
confirmDeletion(childId);
},
error: function(data) {
......
......@@ -75,10 +75,12 @@ function display_makeups_members() {
width: "10%",
render: function (data, type, row) {
if (data == 'ftop') {
return row.display_ftop_points
return row.display_ftop_points;
} else if (data == 'standard') {
return row.display_std_points
return row.display_std_points;
}
return null;
}
},
{
......
......@@ -21,7 +21,7 @@ function remove_from_shift_template() {
partner_id: selected_member.id,
shift_template_id: selected_member.shift_template_id[0],
permanent_unsuscribe: permanent_unsuscribe,
makeups_to_do: selected_member.makeups_to_do,
makeups_to_do: selected_member.makeups_to_do
};
$.ajax({
......@@ -54,25 +54,123 @@ function remove_from_shift_template() {
}
/**
* Send the request to register a member to a shift template
* @param {int} shift_type 1 === standard ; 2 === ftop
* @param {int} shift_template_id null for ftop shift type
*/
function shift_subscrition(shift_type, shift_template_id = null) {
openModal();
let data = {
partner_id: selected_member.id,
shift_type: shift_type,
shift_template_id: shift_template_id
};
$.ajax({
type: 'POST',
url: '/members/shift_subscription',
data: JSON.stringify(data),
dataType:"json",
traditional: true,
contentType: "application/json; charset=utf-8",
success: function(data) {
stdata = data.shift_template;
selected_member.shift_template_id = [
stdata.id,
stdata.name
];
selected_member.cooperative_state = data.cooperative_state;
display_member_info();
$("#shifts_calendar_area").hide();
closeModal();
},
error: function() {
err = {
msg: "erreur serveur lors de l'inscription du membre au créneau",
ctx: 'members.admin.manage_regular_shifts.shift_subscrition'
};
report_JS_error(err, 'members.admin');
closeModal();
$.notify("Une erreur est survenue lors de l'inscription du membre au créneau.", {
globalPosition:"top right",
className: "error"
});
}
});
}
/**
* When a member is selected, display the selected member relevant info
*/
function display_member_info() {
$('.member_name').text(`${selected_member.barcode_base} - ${selected_member.name}`);
$('.member_status').text(possible_cooperative_state[selected_member.cooperative_state]);
$('.member_makeups').text(selected_member.makeups_to_do);
if (selected_member.shift_template_id === undefined || selected_member.shift_template_id === null) {
$('.member_shift').text("");
$('.search_member_results_area').hide();
$("#remove_shift_template_button").hide();
$("#remove_shift_template_button").off();
$("#subscribe_to_shift_template_button").hide();
$("#subscribe_to_shift_template_button").off();
$("#shifts_calendar_area").hide();
if (selected_member.shift_template_id === undefined || selected_member.shift_template_id === null) {
$('.member_shift').text("X");
$("#subscribe_to_shift_template_button").show();
$("#subscribe_to_shift_template_button").on("click", () => {
retrieve_and_draw_shift_tempates();
$("#shifts_calendar_area").show();
// Wait for listeners to be set in common.js
setTimeout(() => {
// Cancel listeners from subscription page & set custom listeners
$("#shifts_calendar_area button[data-select='Volant']").off("click");
$("#shifts_calendar_area button[data-select='Volant']").on("click", function() {
// Subscribe to comitee/ftop shift
msg = (has_committe_shift === "True")
? `Inscrire ${selected_member.name} au service des Comités ?`
: `Inscrire ${selected_member.name} en Volant ?`;
openModal(
msg,
() => {
shift_subscrition(2);
},
"Confirmer",
false
);
});
$(".shift").off("click");
$(".shift").on("click", function() {
// Subscribe to shift template
let shift_template_id = select_shift_among_compact(this, false); // method from common.js
let shift_template_data = shift_templates[shift_template_id].data;// shift_templates: var from common.js
let shift_template_name = get_shift_name(shift_template_data);
openModal(
`Inscrire ${selected_member.name} au créneau ${shift_template_name} ?`,
() => {
shift_subscrition(1, parseInt(shift_template_id));
},
"Confirmer",
false
);
});
}, 500);
});
} else {
$('.member_shift').text(selected_member.shift_template_id[1]);
$("#remove_shift_template_button").show();
$("#remove_shift_template_button").off();
$("#remove_shift_template_button").on("click", () => {
let modal_template = $("#modal_remove_shift_template");
modal_template.find(".shift_template_name").text(selected_member.shift_template_id[1]);
openModal(
......@@ -91,7 +189,7 @@ function display_member_info() {
/**
* Display the members from the search result
*/
function display_possible_members() {
function display_possible_members() {
$('.search_member_results_area').show();
$('.search_member_results').empty();
$('.btn_possible_member').off();
......@@ -140,8 +238,14 @@ function display_member_info() {
$(document).ready(function() {
if (coop_is_connected()) {
$.ajaxSetup({ headers: { "X-CSRFToken": getCookie('csrftoken') } });
dbc = new PouchDB(couchdb_dbname);
$(".page_content").show();
if (has_committe_shift === "True") {
$("#shifts_calendar_area button[data-select='Volant']").text("Comités");
}
// Set action to search for the member
$('#search_member_form').submit(function() {
let search_str = $('#search_member_input').val();
......@@ -179,6 +283,7 @@ $(document).ready(function() {
$('#back_to_admin_index').on('click', function() {
let base_location = window.location.href.split("manage_regular_shifts")[0].slice(0, -1);
window.location.assign(base_location);
});
});
......@@ -94,7 +94,7 @@ function display_member_shifts() {
$(row).addClass("makeup_row");
$(row).prop('title', 'Ce service est un rattrapage');
}
},
}
});
$('#member_shifts_table').on('click', 'tbody td .delete_shift_registration', function () {
......@@ -103,6 +103,7 @@ function display_member_shifts() {
const shift_is_makeup = row_data.is_makeup;
let msg = `<p>Enlever la présence de <b>${member.name}</b> au service du <b>${row_data.shift_id[1]}</b> ?</p>`;
if (shift_is_makeup === true) {
msg += `<p><i class="fas fa-exclamation-triangle"></i> Ce service est un rattrapage. Le supprimer ajoutera un point au compteur de ce.tte membre.</p>`;
}
......
......@@ -63,6 +63,7 @@ urlpatterns = [
url(r'^update_members_makeups$', admin.update_members_makeups),
url(r'^delete_shift_registration$', admin.delete_shift_registration),
url(r'^delete_shift_template_registration$', admin.delete_shift_template_registration),
url(r'^shift_subscription$', admin.shift_subscription),
url(r'^admin/manage_attached$', admin.manage_attached),
url(r'^admin/manage_attached/create_pair$', admin.create_pair),
url(r'^admin/manage_attached/delete_pair$', admin.delete_pair),
......
......@@ -99,8 +99,8 @@ function single_shift_click() {
}
}
function select_shift_among_compact() {
var clicked = $(this);
function select_shift_among_compact(clicked_item = null, subscribe = true) {
var clicked = clicked_item === null ? $(this) : $(clicked_item);
var day = clicked.closest('td').attr('class');
var hour = clicked.closest('tr').data('begin');
var selected = null;
......@@ -129,9 +129,11 @@ function select_shift_among_compact() {
}
}
});
//console.log(worst_score)
if (selected)
if (selected && subscribe === true)
subscribe_shift(selected);
return selected
}
......
......@@ -55,10 +55,18 @@
<button class="btn--primary" id="remove_shift_template_button">
Désinscrire du créneau
</button>
<button class="btn--primary" id="subscribe_to_shift_template_button">
Réinscrire à un créneau
</button>
</div>
</div>
</div>
</div>
<div id="shifts_calendar_area">
{% include "members/shift_template_choice.html" %}
</div>
<div id="templates" style="display:none;">
<div id="modal_remove_shift_template">
<p>Voulez vraiment désinscrire ce membre du créneau <span class="shift_template_name"></span> ?</p>
......@@ -70,7 +78,16 @@
</div>
</div>
<script src="{% static "js/pouchdb.min.js" %}"></script>
<script type="text/javascript">
var type = 2;
var has_committe_shift = '{{has_committe_shift}}'
var max_begin_hour = '{{max_begin_hour}}'
var couchdb_dbname = '{{db}}';
var couchdb_server = '{{couchdb_server}}' + couchdb_dbname;
var ASSOCIATE_MEMBER_SHIFT = '{{ASSOCIATE_MEMBER_SHIFT}}';
</script>
<script src='{% static "js/common.js" %}?v='></script>
<script src='{% static "js/all_common.js" %}?v='></script>
<script src='{% static "js/admin/manage_regular_shifts.js" %}?v='></script>
{% endblock %}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment