Skip to content

Instantly share code, notes, and snippets.

@lavoiesl
Created August 21, 2012 00:03
Show Gist options
  • Save lavoiesl/3409527 to your computer and use it in GitHub Desktop.
Save lavoiesl/3409527 to your computer and use it in GitHub Desktop.
Download UdeM schedule as iCal
(function(d,s){
var n,b=d.getElementsByTagName(s)[0];
function l(u){
n=d.createElement(s);
n.src=u;
b.parentNode.insertBefore(n,b);
}
l("//ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js");
l("//gist.github.com/raw/3409527/converter.js");
})(document, "script");
(function() {
var $headers = $('table a[href*="index_fiche_cours"]').closest('tr');
var $table = $headers.closest('table');
var $tr = $table.find('tr');
var course, periode;
var courses = {};
var year = $table.text().match(/Date limite.* ([0-9]+)/)[1];
var months = ['janv','févr','mars','avr','mai','juin','juil','août','sept','oct','nov','déc'];
function textOf(el) {
return $.trim(el.text());
}
function parseDate(text) {
if (text === '') return null;
var date = new Date;
var matches = text.match(/([0-9]+)\s+([a-z\u00E0-\u00FC]+)(\s|\.)*$/i);
date.setYear(year);
date.setMonth(months.indexOf(matches[2]));
date.setDate(matches[1]);
date.setHours(0);
date.setMinutes(0);
date.setSeconds(0);
date.setMilliseconds(0);
return date;
}
function parseDateRow(tr) {
var offset = 0;
if ($('td', tr).length == 9) {
offset = 5;
}
var start = textOf($('td:eq('+(offset + 0)+')', tr));
var end = textOf($('td:eq('+(offset + 1)+')', tr));
var date = {
start: parseDate(start),
end: parseDate(end),
local: textOf($('td:eq('+(offset + 2)+')', tr)),
immeuble: textOf($('td:eq('+(offset + 3)+')', tr)),
};
return date;
}
$tr.each(function(){
if ($headers.filter(this).length) {
var $a = $('a[href*="index_fiche_cours"]', this);
course = {
code: $a.text(),
name: textOf($a.closest('td').next()).replace(/\s*\([0-9]+ cr.*/, ''),
classes: []
};
courses[course.code] = course;
} else if ($(this).children('td').length == 9) {
var type = textOf($('td:first', this));
if (type.match(/^(th|tp|ex)/)) {
periode = {
type: type,
jour: textOf($('td:eq(2)',this)),
debut: textOf($('td:eq(3)',this)),
fin: textOf($('td:eq(4)',this)),
dates: []
};
periode.dates.push(parseDateRow(this));
course.classes.push(periode);
}
} else if ($(this).children('td').length == 4) {
periode.dates.push(parseDateRow(this));
} else if ($(this).children('td').length == 1) {
var matches = $(this).text().match(/Professeur.*:\s*(.*)\n/);
course.prof = matches.length > 0 ? matches[1] : "n/d";
}
});
function pad(num) {
return num > 9 ? num : "0" + num;
}
function formatDate(base, hour, min) {
base.setHours(hour);
base.setMinutes(min);
return base.getUTCFullYear() + pad(base.getUTCMonth() + 1) + pad(base.getUTCDate()) + 'T'
+ pad(base.getUTCHours()) + pad(base.getUTCMinutes()) + '00' + 'Z';
}
var ics = "BEGIN:VCALENDAR\nVERSION:2.0\nPRODID:-//hacksw/handcal//NONSGML v1.0//EN\n";
for (var i in courses) {
for (var j in courses[i].classes) {
for (var k in courses[i].classes[j].dates) {
var debut = courses[i].classes[j].debut.match(/^([0-9]+):([0-9]+)$/);
var fin = courses[i].classes[j].fin.match(/^([0-9]+):([0-9]+)$/);
var date = courses[i].classes[j].dates[k];
var current = new Date(date.start);
var end = date.end ? date.end : new Date(date.start);
end.setSeconds(1);
while (current < end) {
// console.log(current, end);
var base = new Date(current);
ics += "BEGIN:VEVENT\n";
ics += "UID:" + courses[i].code + '-' + formatDate(base, debut[1], debut[2]) + "@umontreal.ca\n";
ics += "DTSTAMP:" + formatDate(base, debut[1], debut[2]) + "\n";
ics += "DTSTART:" + formatDate(base, debut[1], debut[2]) + "\n";
ics += "DTEND:" + formatDate(base, fin[1], fin[2]) + "\n";
ics += "SUMMARY:" + courses[i].code + ' - ' + courses[i].classes[j].type.toUpperCase() + ' - ' + courses[i].name + "\n";
ics += "LOCATION:" + date.local + ' - ' + date.immeuble + "\n";
ics += "DESCRIPTION:" + courses[i].prof + "\n";
ics += "END:VEVENT\n";
current.setDate(current.getDate() + 7);
}
}
}
}
ics += "END:VCALENDAR";
// open("data:text/calendar;charset=utf8," + escape(ics));
location.href = "data:text/calendar;charset=utf8," + escape(ics);
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment