Skip to content

Commit

Permalink
Merge pull request #349 from EsupPortail/dev
Browse files Browse the repository at this point in the history
Dev 2.7.0
  • Loading branch information
ptitloup authored Oct 27, 2020
2 parents 8b5694a + fdd65fb commit 8c5d37d
Show file tree
Hide file tree
Showing 90 changed files with 5,146 additions and 1,249 deletions.
25 changes: 25 additions & 0 deletions pod/bbb/admin.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
from django.contrib import admin
from .models import Meeting
from .models import User as BBBUser


class MeetingAdmin(admin.ModelAdmin):
list_display = (
'id', 'session_date', 'meeting_name', 'encoding_step',
'recorded', 'recording_available', 'encoded_by')
list_display_links = ('id', 'meeting_name')
ordering = ('-id', '-session_date')
readonly_fields = []


class BBBUserAdmin(admin.ModelAdmin):
list_display = (
'id', 'full_name', 'role', 'username',
'meeting', 'user')
list_display_links = ('id', 'full_name')
ordering = ('full_name',)
readonly_fields = []


admin.site.register(Meeting, MeetingAdmin)
admin.site.register(BBBUser, BBBUserAdmin)
5 changes: 5 additions & 0 deletions pod/bbb/apps.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
from django.apps import AppConfig


class BbbConfig(AppConfig):
name = 'pod.bbb'
29 changes: 29 additions & 0 deletions pod/bbb/forms.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
from django import forms
from django.conf import settings
from .models import Meeting
from pod.main.forms import add_placeholder_and_asterisk

USE_BBB = getattr(settings, 'USE_BBB', False)


class MeetingForm(forms.ModelForm):

def __init__(self, request, *args, **kwargs):
super(MeetingForm, self).__init__(*args, **kwargs)

# All fields are hidden. This form is like a Confirm prompt
self.fields = add_placeholder_and_asterisk(self.fields)
self.fields['meeting_id'].widget = forms.HiddenInput()
self.fields['internal_meeting_id'].widget = forms.HiddenInput()
self.fields['meeting_name'].widget = forms.HiddenInput()
self.fields['session_date'].widget = forms.HiddenInput()
self.fields['encoding_step'].widget = forms.HiddenInput()
self.fields['recorded'].widget = forms.HiddenInput()
self.fields['recording_available'].widget = forms.HiddenInput()
self.fields['recording_url'].widget = forms.HiddenInput()
self.fields['thumbnail_url'].widget = forms.HiddenInput()
self.fields['encoded_by'].widget = forms.HiddenInput()

class Meta:
model = Meeting
exclude = ()
Empty file added pod/bbb/migrations/__init__.py
Empty file.
142 changes: 142 additions & 0 deletions pod/bbb/models.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,142 @@
import importlib

from django.db import models
from django.conf import settings
from django.utils.translation import ugettext_lazy as _
from django.contrib.auth.models import User
from django.dispatch import receiver
from django.db.models.signals import post_save
from django.utils import timezone
from select2 import fields as select2_fields

USE_BBB = getattr(settings, 'USE_BBB', False)


class Meeting(models.Model):
# Meeting id for the BBB session
meeting_id = models.CharField(
_('Meeting id'), max_length=200,
help_text=_('Id of the BBB meeting.')
)
# Internal meeting id for the BBB session
internal_meeting_id = models.CharField(
_('Internal meeting id'),
max_length=200, help_text=_('Internal id of the BBB meeting.')
)
# Meeting name for the BBB session
meeting_name = models.CharField(
_('Meeting name'),
max_length=200, help_text=_('Name of the BBB meeting.')
)
# Date of the BBB session
session_date = models.DateTimeField(
_('Session date'), default=timezone.now)
# Encoding step / status of the process. Possible values are :
# - 0 : default (Publish is possible)
# - 1 : Waiting for encoding
# - 2 : Encoding in progress
# - 3 : Already published
encoding_step = models.IntegerField(
_('Encoding step'),
help_text=_('Encoding step for conversion of the '
'BBB presentation to video file.'),
default=0)
# Is this meeting was recorded in BigBlueButton ?
recorded = models.BooleanField(
_('Recorded'),
help_text=_('BBB presentation recorded ?'),
default=False)
# Is the recording of the presentation is available in BigBlueButton ?
recording_available = models.BooleanField(
_('Recording available'),
help_text=_('BBB presentation recording is available ?'),
default=False)
# URL of the recording of the BigBlueButton presentation
recording_url = models.CharField(
_('Recording url'),
help_text=_('URL of the recording of the BBB presentation.'),
max_length=200
)
# URL of the recording thumbnail of the BigBlueButton presentation
thumbnail_url = models.CharField(
_('Thumbnail url'),
help_text=_('URL of the recording thumbnail of the BBB presentation.'),
max_length=200
)
# User who converted the BigBlueButton presentation to video file
encoded_by = select2_fields.ForeignKey(
User, on_delete=models.CASCADE,
limit_choices_to={'is_staff': True},
verbose_name=_('User'), null=True, blank=True, help_text=_(
'User who converted the BBB presentation to video file.')
)

def __unicode__(self):
return "%s - %s" % (self.meeting_name, self.meeting_id)

def __str__(self):
return "%s - %s" % (self.meeting_name, self.meeting_id)

def save(self, *args, **kwargs):
super(Meeting, self).save(*args, **kwargs)

class Meta:
verbose_name = _("Meeting")
verbose_name_plural = _("Meetings")
ordering = ['session_date']


@receiver(post_save, sender=Meeting)
def process_recording(sender, instance, created, **kwargs):
# Convert the BBB presentation only one time
# Be careful : this is the condition to create a video of the
# BigBlueButton presentation only one time.
if instance.encoding_step == 1 and instance.encoded_by is not None:
mod = importlib.import_module(
'%s.plugins.type_%s' % (__package__, 'bbb'))
mod.process(instance)


# Management of the BigBlueButton users,
# with role = MODERATOR in BigBlueButton
class User(models.Model):
# User who performed the session in BigBlueButton
meeting = models.ForeignKey(Meeting,
on_delete=models.CASCADE,
verbose_name=_('Meeting'))
# Full name (First_name Last_name) of the user from BigBlueButton
full_name = models.CharField(_('Full name'), max_length=200, help_text=_(
'Full name of the user from BBB.')
)
# Role of this user (only MODERATOR for the moment)
role = models.CharField(_('User role'), max_length=200, help_text=_(
'Role of the user from BBB.')
)
# Username of this user, if the BBB user was translated with a Pod user
# Redundant information with user, but can be useful.
username = models.CharField(_('Username / User id'),
max_length=150, help_text=_(
'Username / User id, if the BBB user was matching a Pod user.')
)

# Pod user, if the BBB user was translated with a Pod user
user = select2_fields.ForeignKey(
User, on_delete=models.CASCADE,
limit_choices_to={'is_staff': True},
verbose_name=_('User'), null=True, blank=True, help_text=_(
'User from the Pod database, if user found.')
)

def __unicode__(self):
return "%s - %s" % (self.full_name, self.role)

def __str__(self):
return "%s - %s" % (self.full_name, self.role)

def save(self, *args, **kwargs):
super(User, self).save(*args, **kwargs)

class Meta:
verbose_name = _("User")
verbose_name_plural = _("Users")
ordering = ['full_name']
Empty file added pod/bbb/plugins/__init__.py
Empty file.
24 changes: 24 additions & 0 deletions pod/bbb/plugins/type_bbb.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import threading
import logging

from django.conf import settings
from pod.video.bbb import start_bbb_encode

BBB_ENCODE_MEETING = getattr(settings, 'BBB_ENCODE_MEETING', start_bbb_encode)

log = logging.getLogger(__name__)


# Process that allows to create a video file
# from a BigBlueButton presentation
def process(recording):
log.info("START PROCESS OF RECORDING %s" % recording)
t = threading.Thread(target=bbb_encode_recording,
args=[recording])
t.setDaemon(True)
t.start()


# Create a video file from a BigBlueButton presentation
def bbb_encode_recording(recording):
BBB_ENCODE_MEETING(recording.id)
29 changes: 29 additions & 0 deletions pod/bbb/rest_views.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
from rest_framework import serializers, viewsets
from .models import Meeting
from .models import User as BBBUser


class MeetingModelSerializer(
serializers.HyperlinkedModelSerializer):

class Meta:
model = Meeting
fields = ('id',)


class MeetingModelViewSet(viewsets.ModelViewSet):
queryset = Meeting.objects.all()
serializer_class = MeetingModelSerializer


class BBBUserModelSerializer(
serializers.HyperlinkedModelSerializer):

class Meta:
model = BBBUser
fields = ('id',)


class BBBUserModelViewSet(viewsets.ModelViewSet):
queryset = BBBUser.objects.all()
serializer_class = BBBUserModelSerializer
54 changes: 54 additions & 0 deletions pod/bbb/templates/bbb/card.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
{% load i18n %}
{% spaceless %}

{% block page_extra_head %}
<style>
.card-body {
padding-top: 4em !important;
padding-bottom: 4em !important;
text-align: center;
}
/*** CARD ***/
.infinite-item .card-body {
height: 13rem;
}
</style>
{% endblock page_extra_head %}

<div class="card mb-4 box-shadow border-secondary">
<div class="card-header" style="">
<div class="d-flex justify-content-between align-items-center" style="min-height: 2.4rem;">
<small class="text-muted time">{{record.meeting_name}} ({{ record.session_date }})</small>
</div>
</div>
<div class="card-body">
<div class="d-flex align-items-center">
<a class="previewBtn link-center-pod" href="" title="{% trans "BigBlueButton presentation preview"%}" data-toggle="modal" data-recid="{{record.recording_url}}" data-target="#previewModal">
<img class="card-img-top" src="{{record.thumbnail_url}}" alt="{% trans "BigBlueButton presentation preview"%}">
</a>
</div>
<footer class="card-footer p-0 m-1">
{% if record.encoding_step == 0 %}
<a href="{% url 'bbb:publish_meeting' id=record.id %}" title="{% trans "Publish the BigBlueButton presentation on this platform"%}" class="p-0 m-0 btn btn-primary btn-sm pl-1">
{% trans "Publish this presentation"%}
</a>
{% endif %}
{% if record.encoding_step == 1 %}
<small class="form-text text-muted">{% trans "Waiting for encoding"%}</small>
{% endif %}
{% if record.encoding_step == 2 %}
<small class="form-text text-muted">{% trans "Encoding in progress"%}</small>
{% endif %}
{% if record.encoding_step == 3 %}
<small class="form-text text-muted">
{% trans "Already published"%}
{% if request.user != record.encoded_by %}
{% trans "by"%} {{ record.encoded_by.first_name }} {{ record.encoded_by.last_name }} ({{ record.encoded_by.email }})
{% endif %}
</small>
{% endif %}
</footer>

</div>
</div>
{% endspaceless %}
Loading

0 comments on commit 8c5d37d

Please sign in to comment.