Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New timetable load #215

Open
wants to merge 12 commits into
base: master
Choose a base branch
from
19 changes: 19 additions & 0 deletions pyconbalkan/core/static/css/components/person.css
Original file line number Diff line number Diff line change
Expand Up @@ -32,12 +32,31 @@

.presentation__talk {
color: #343C3E;

}

.presentation__workshop {
color: #666;
}

.presentation__keynote,
.presentation__talk,
.presentation__workshop {
padding-left: 1em;
}

.cat-session {
border: 1px solid;
border-radius: 2px;
width: 3em;
text-align: center;
color: #3aaee2;
font-size: 14px;
font-weight: 700;
float:left;
margin-top: 1.3em;
}

.speaker,
.organizer,
.sponsor {
Expand Down
56 changes: 56 additions & 0 deletions pyconbalkan/core/static/css/components/timetable.css
Original file line number Diff line number Diff line change
@@ -1,3 +1,59 @@
#dates-wrapper {
text-align: center;
}

.day-select {
border: 1px solid #343C3E;
border-radius: 6px;
background: white;
font-size: 16px;
padding: 6px;
text-decoration: none;
margin: 1em;
}

.day-select:focus {outline:0;}

.day-select:active,
.day-select:hover,
.selected-day {
background: #27aae1;
color: white;
border: 1px solid transparent;
}

/*.room-timeline {*/
/* width: 1800px !important;*/
/* overflow: hidden !important;*/
/*}*/

.timetable .time-entry {
background-color: #27aae1 !important;
border: 1px solid #efefef !important;
text-decoration: none;
font-size: 11px;
}

.timetable .time-entry:hover {
background-color: #343c3e !important;
}

.timetable>section>header li {
width: 115px !important;
}

.timetable ul.room-timeline li:before {
background-image: unset !important;
}

.timetable ul.room-timeline li:after {
background-size: 112px auto !important
}

.timetable ul.room-timeline li .time-entry {
height: 140px;
}

.presentation {
display: flex;
margin: 15px 0;
Expand Down
1 change: 1 addition & 0 deletions pyconbalkan/core/static/css/timetablejs.css

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

8 changes: 1 addition & 7 deletions pyconbalkan/core/static/js/timetable.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

5 changes: 5 additions & 0 deletions pyconbalkan/speaker/models.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
from django.db import models
from django.db.models import CASCADE
from embed_video.fields import EmbedVideoField
from slugify import slugify

from pyconbalkan.conference.models import AbstractConference
from pyconbalkan.core.models import Person, ActiveModel
Expand All @@ -10,6 +11,10 @@ class Speaker(Person):
def __str__(self):
return self.name

@property
def slugify(self):
return slugify(self.name)

@property
def preffered_talk_type(self):
return self.presentations.order_by("type").first().get_type_display().lower()
Expand Down
11 changes: 8 additions & 3 deletions pyconbalkan/speaker/templates/speaker.html
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,14 @@ <h4 class="speaker__job"> {{ speaker.job }} {% if speaker.company %}- {{ speaker
<h2>PyCon Balkan {{ conference }} Talks</h2>
{% for presentation in presentations %}
<div class="{{ presentation.get_type_display|lower }}__wrapper">
MaliRobot marked this conversation as resolved.
Show resolved Hide resolved
<a style="text-decoration: none" href="#talk-{{ presentation.slugify }}" name="talk-{{ presentation.slugify }}">
<h3 class="speaker__presentation presentation__{{ speaker.preffered_talk_type }}">{{ presentation.title }}</h3>
</a>
<div class="cat__wrapper">
<p class="cat-session tooltip">{{ presentation.get_type_short }}
<span class="tooltiptext">PyCon {{ presentation.get_type_display }}</span>
</p>
<a style="text-decoration: none" href="#talk-{{ presentation.slugify }}" id="talk-{{ presentation.slugify }}">
<h3 class="speaker__presentation presentation__{{ speaker.preffered_talk_type }}">{{ presentation.title }}</h3>
</a>
</div>
<p>{{ presentation.description|markdownify }}</p>
</div>
<div class="speaker__tags">
Expand Down
97 changes: 47 additions & 50 deletions pyconbalkan/timetable/management/commands/load_timetable.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,13 @@
from pyconbalkan.speaker.models import Speaker
from pyconbalkan.timetable.models import Presentation, Room, Slot

from django.core.exceptions import ObjectDoesNotExist

ALL_DATA_URL = "https://sessionize.com/api/v2/fwv5aino/view/All"


class Command(BaseCommand):
help = 'Closes the specified poll for voting'
help = 'Import data from sessionize'

def add_arguments(self, parser):
pass
Expand All @@ -24,79 +26,74 @@ def add_arguments(self, parser):

def handle(self, *args, **options):
conference = Conference.objects.get(year=options['year'])
_cant_find = []

data = requests.get(options['data_url']).json()

questions = data['questions']
categories = data['categories']
rooms = data['rooms']
sessions = data['sessions']
speakers = data['speakers']

# Sync rooms
types = categories[0]['items']
types = {x['id']:x['name'] for x in types}

Presentation.objects.filter(conference=conference).delete()
Room.objects.filter(conference=conference).delete()
Slot.objects.filter(conference=conference).delete()
all_presentations_this_year = list(Presentation.objects.filter(conference=conference).values_list("id", "title"))

for room in rooms:
Room.objects.create(
Room.objects.get_or_create(
pk=room['id'],
conference=conference,
name=room['name'],
sort_order=room['sort']
)


# Make speaker dict
speakers = {}
for _ in data['speakers']:
first_name = _.pop('firstName')
last_name = _.pop('lastName')
speakers[f"{first_name} {last_name}"] = _

for speaker in speakers.values():
for i, session in enumerate(speaker['sessions']):
speaker['sessions'][i] = list(filter(lambda _: int(_['id']) == session, data['sessions']))[0]
for session in sessions:
speaker_id = session['speakers'][0]
speaker = self.get_speaker(speaker_id, speakers)

# Attach Speaker obj from DB
speakers_qs = Speaker.objects.all().prefetch_related(
Prefetch(
"presentations",
queryset=Presentation.objects.filter(active=True, conference=conference).order_by("type")
if speaker == None:
print(speaker_id, 'Not found')
else:
speaker = speaker.id

presentation, created = Presentation.objects.get_or_create(
pk=session['id'],
active=False,
title=session['title'],
description=session['description'],
type=Presentation.PRESENTATION_TYPE_REVERSE[types[session['categoryItems'][0]]],
speaker_id=speaker,
conference_id=conference.id,
)
)

_cant_find = []
for speaker in speakers_qs:
if not any(speaker.presentations.all()):
continue

r = list(fuzzyfinder(speaker.full_name, speakers.keys()))
if not any(r):
_cant_find.append(speaker)
continue
speakers[r[0]]["model_speaker"] = speaker
speaker = speakers[r[0]]

for _ in speaker['sessions']:
r = list(fuzzyfinder(_['title'], list(zip(*all_presentations_this_year))[1]))
if not any(r):
_cant_find.append(_)


try:
presentation = Presentation.objects.get(title__icontains=_['title'])
except Presentation.DoesNotExist:
_cant_find.append(_)
# TODO NEXT YEAR MAYBE, GET TZ FROM CONFERENCE OBJECT ?!
Slot.objects.create(
from_date=timezone.make_aware(datetime.strptime(_['startsAt'], "%Y-%m-%dT%H:%M:%S")),
to_date=timezone.make_aware(datetime.strptime(_['endsAt'], "%Y-%m-%dT%H:%M:%S")),
talk=presentation,
room=Room.objects.get(pk=_['roomId']),
conference=conference
)
start = timezone.make_aware(datetime.strptime(session['startsAt'], "%Y-%m-%dT%H:%M:%S"))
end = timezone.make_aware(datetime.strptime(session['endsAt'], "%Y-%m-%dT%H:%M:%S"))
Slot.objects.get_or_create(
active=False,
from_date=start,
to_date=end,
room_id=session['roomId'],
talk_id=presentation.id,
conference_id=conference.id,
)

if any(_cant_find):
if options['force']:
print(_cant_find)
else:
raise Exception("Had problems with the following", _cant_find)

def get_speaker(self, speaker_id, speakers):
for speaker in speakers:
if speaker['id'] == speaker_id:
full_name = " ".join(speaker['fullName'].split())
try:
return Speaker.objects.get(full_name=full_name)
except ObjectDoesNotExist:
return None
return None
6 changes: 6 additions & 0 deletions pyconbalkan/timetable/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,12 @@ class Presentation(AbstractConference, ActiveModel):
(KEYNOTE, 'Keynote'),
)

PRESENTATION_TYPE_REVERSE = {
'Talk': TALK,
'Workshop': WORKSHOP,
'Keynote': KEYNOTE
}

title = models.CharField(null=True, blank=True, max_length=100)
description = MarkdownxField(null=True, blank=True)
type = models.IntegerField(choices=PRESENTATION_TYPE, default=TALK)
Expand Down
Loading