Bläddra i källkod

plugin talks configurabile

boyska 7 år sedan
förälder
incheckning
3d172beb73
2 ändrade filer med 50 tillägg och 35 borttagningar
  1. 49 35
      plugins/talks.py
  2. 1 0
      publishconf.py

+ 49 - 35
plugins/talks.py

@@ -2,6 +2,7 @@
 Manage talks scheduling in a semantic way
 '''
 
+
 from __future__ import print_function
 import os
 import io
@@ -23,11 +24,9 @@ from docutils.parsers.rst import directives, Directive
 from pelican import signals, generators
 import jinja2
 
+pelican = None  # This will be set during register()
+
 
-TALKS_PATH = 'talks'
-TALK_ATTACHMENT_PATH = 'res'
-TALK_ICS = 'schedule.ics'
-GRID_STEP = 30
 
 
 def memoize(function):
@@ -56,7 +55,7 @@ def setlocale(name):
 
 @memoize
 def get_talk_names():
-    return [name for name in os.listdir(TALKS_PATH)
+    return [name for name in os.listdir(pelican.settings['TALKS_PATH'])
             if not name.startswith('_') and
             get_talk_data(name) is not None
             ]
@@ -73,7 +72,7 @@ def unique_attr(iterable, attr):
 
 @memoize
 def get_global_data():
-    fname = os.path.join(TALKS_PATH, 'meta.yaml')
+    fname = os.path.join(pelican.settings['TALKS_PATH'], 'meta.yaml')
     if not os.path.isfile(fname):
         return None
     with io.open(fname, encoding='utf8') as buf:
@@ -92,7 +91,7 @@ def get_global_data():
 
 @memoize
 def get_talk_data(talkname):
-    fname = os.path.join(TALKS_PATH, talkname, 'meta.yaml')
+    fname = os.path.join(pelican.settings['TALKS_PATH'], talkname, 'meta.yaml')
     if not os.path.isfile(fname):
         return None
     with io.open(fname, encoding='utf8') as buf:
@@ -104,6 +103,7 @@ def get_talk_data(talkname):
     if data is None:
         return None
     try:
+        gridstep = pelican.settings['TALKS_GRID_STEP']
         if 'title' not in data:
             logging.warn("Talk <{}> has no `title` field".format(talkname))
             data['title'] = talkname
@@ -115,10 +115,10 @@ def get_talk_data(talkname):
                          .format(talkname))
             data['duration'] = 50
         data['duration'] = int(data['duration'])
-        if data['duration'] < GRID_STEP:
+        if data['duration'] < gridstep:
             logging.info("Talk <{}> lasts only {} minutes; changing to {}"
-                         .format(talkname, data['duration'], GRID_STEP))
-            data['duration'] = GRID_STEP
+                         .format(talkname, data['duration'], gridstep))
+            data['duration'] = gridstep
         if 'links' not in data or not data['links']:
             data['links'] = []
         if 'contacts' not in data or not data['contacts']:
@@ -145,7 +145,8 @@ def get_talk_data(talkname):
             else:
                 logging.error("Talk <%s> has malformed `time`", talkname)
         data['id'] = talkname
-        resdir = os.path.join(TALKS_PATH, talkname, TALK_ATTACHMENT_PATH)
+        resdir = os.path.join(pelican.settings['TALKS_PATH'], talkname,
+                              pelican.settings['TALKS_ATTACHMENT_PATH'])
         if os.path.isdir(resdir) and os.listdir(resdir):
             data['resources'] = resdir
         return data
@@ -154,16 +155,19 @@ def get_talk_data(talkname):
         raise
 
 
-jinja_env = jinja2.Environment(
-    loader=jinja2.FileSystemLoader(os.path.join(TALKS_PATH, '_templates')),
-    autoescape=True,
-)
-jinja_env.filters['markdown'] = lambda text: \
-        jinja2.Markup(markdown.Markdown(extensions=['meta']).
-                      convert(text))
-jinja_env.filters['dateformat'] = format_date
-jinja_env.filters['datetimeformat'] = format_datetime
-jinja_env.filters['timeformat'] = format_time
+@memoize
+def jinja_env():
+    env = jinja2.Environment(
+        loader=jinja2.FileSystemLoader(os.path.join(pelican.settings['TALKS_PATH'], '_templates')),
+        autoescape=True,
+    )
+    env.filters['markdown'] = lambda text: \
+            jinja2.Markup(markdown.Markdown(extensions=['meta']).
+                          convert(text))
+    env.filters['dateformat'] = format_date
+    env.filters['datetimeformat'] = format_datetime
+    env.filters['timeformat'] = format_time
+    return env
 
 
 class TalkListDirective(Directive):
@@ -175,7 +179,7 @@ class TalkListDirective(Directive):
 
     def run(self):
         lang = self.options.get('lang', 'C')
-        tmpl = jinja_env.get_template('talk.html')
+        tmpl = jinja_env().get_template('talk.html')
         return [
             nodes.raw('', tmpl.render(lang=lang, **get_talk_data(n)),
                       format='html')
@@ -193,7 +197,7 @@ class TalkDirective(Directive):
 
     def run(self):
         lang = self.options.get('lang', 'C')
-        tmpl = jinja_env.get_template('talk.html')
+        tmpl = jinja_env().get_template('talk.html')
         data = get_talk_data(self.arguments[0])
         if data is None:
             return []
@@ -213,9 +217,10 @@ class TalkGridDirective(Directive):
 
     def run(self):
         lang = self.options.get('lang', 'C')
-        tmpl = jinja_env.get_template('grid.html')
+        tmpl = jinja_env().get_template('grid.html')
         output = []
         days = unique_attr(all_talks(), 'day')
+        gridstep = pelican.settings['TALKS_GRID_STEP']
         for day in sorted(days):
             talks = {talk['id'] for talk in all_talks()
                      if talk.get('day', None) == day
@@ -231,18 +236,18 @@ class TalkGridDirective(Directive):
                 del rooms[rooms.index('*')]
             mintime = min({talk['time'].hour * 60 +
                            talk['time'].minute
-                           for talk in talks}) // GRID_STEP * GRID_STEP
+                           for talk in talks}) // gridstep * gridstep
             maxtime = max({talk['time'].hour * 60 +
                            talk['time'].minute +
                            talk['duration']
                            for talk in talks})
             times = {}
 
-            for t in range(mintime, maxtime, GRID_STEP):
+            for t in range(mintime, maxtime, gridstep):
                 times[t] = [None] * len(rooms)
             for talk in sorted(talks, key=lambda x: x['time']):
                 talktime = talk['time'].hour * 60 + talk['time'].minute
-                position = talktime // GRID_STEP * GRID_STEP  # round
+                position = talktime // gridstep * gridstep  # round
                 assert position in times
                 if talk['room'] == '*':
                     roomnums = range(len(rooms))
@@ -258,14 +263,14 @@ class TalkGridDirective(Directive):
                         continue
                     times[position][roomnum] = copy(talk)
                     times[position][roomnum]['skip'] = False
-                    for i in range(1, talk['duration'] // GRID_STEP):
-                        times[position + i*GRID_STEP][roomnum] = copy(talk)
-                        times[position + i*GRID_STEP][roomnum]['skip'] = True
+                    for i in range(1, talk['duration'] // gridstep):
+                        times[position + i*gridstep][roomnum] = copy(talk)
+                        times[position + i*gridstep][roomnum]['skip'] = True
 
             render = tmpl.render(times=times,
                                  rooms=rooms,
                                  mintime=mintime, maxtime=maxtime,
-                                 timestep=GRID_STEP,
+                                 timestep=gridstep,
                                  lang=lang,
                                  )
             output.append(nodes.raw(
@@ -321,25 +326,33 @@ class TalksGenerator(generators.Generator):
     def generate_output(self, writer=None):
         for talkname in self.talks:
             if 'resources' in self.talks[talkname]:
-                outdir = os.path.join(self.output_path, TALKS_PATH, talkname,
-                                      TALK_ATTACHMENT_PATH)
+                outdir = os.path.join(self.output_path,
+                                      pelican.settings['TALKS_PATH'], talkname,
+                                      pelican.settings['TALKS_ATTACHMENT_PATH'])
                 if os.path.isdir(outdir):
                     shutil.rmtree(outdir)
                 shutil.copytree(self.talks[talkname]['resources'], outdir)
-        with io.open(os.path.join(self.output_path, TALK_ICS),
+        with io.open(os.path.join(self.output_path, pelican.settings.get('TALKS_ICS')),
                      'w',
                      encoding='utf8') as buf:
             buf.write(talks_to_ics())
 
 
 def add_talks_option_defaults(pelican):
-    pelican.settings.setdefault('TALKS_PATH', TALKS_PATH)
+    pelican.settings.setdefault('TALKS_PATH', 'talks')
+    pelican.settings.setdefault('TALKS_ATTACHMENT_PATH', 'res')
+    pelican.settings.setdefault('TALKS_ICS', 'schedule.ics')
+    pelican.settings.setdefault('TALKS_GRID_STEP', 30)
 
 
 def get_generators(gen):
     return TalksGenerator
 
 
+def pelican_init(pelicanobj):
+    global pelican
+    pelican = pelicanobj
+
 try:
     import yaml
 except ImportError:
@@ -350,6 +363,7 @@ except ImportError:
 else:
 
     def register():
+        signals.initialized.connect(pelican_init)
         signals.get_generators.connect(get_generators)
         signals.initialized.connect(add_talks_option_defaults)
         directives.register_directive('talklist', TalkListDirective)

+ 1 - 0
publishconf.py

@@ -12,6 +12,7 @@ from pelicanconf import *
 
 SITEURL = '/hackit17'
 RELATIVE_URLS = True
+TALKS_GRID_STEP = 30
 
 # DELETE_OUTPUT_DIRECTORY = True