Add 2011 to FSF/AIST copyright years.
[bpt/emacs.git] / test / icalendar-testsuite.el
CommitLineData
7ec01532
GM
1;; icalendar-testsuite.el --- Test suite for icalendar.el
2
5df4f04c 3;; Copyright (C) 2005, 2008, 2009, 2010, 2011 Free Software Foundation, Inc.
7ec01532
GM
4
5;; Author: Ulf Jasper <ulf.jasper@web.de>
6;; Created: March 2005
7;; Keywords: calendar
8;; Human-Keywords: calendar, diary, iCalendar, vCalendar
9
10;; This file is part of GNU Emacs.
11
4f43e937 12;; GNU Emacs is free software: you can redistribute it and/or modify
7ec01532 13;; it under the terms of the GNU General Public License as published by
4f43e937
GM
14;; the Free Software Foundation, either version 3 of the License, or
15;; (at your option) any later version.
7ec01532
GM
16
17;; GNU Emacs is distributed in the hope that it will be useful,
18;; but WITHOUT ANY WARRANTY; without even the implied warranty of
19;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20;; GNU General Public License for more details.
21
22;; You should have received a copy of the GNU General Public License
4f43e937 23;; along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>.
7ec01532
GM
24
25;;; Commentary:
26
27;; TODO:
28;; - Add more unit tests for functions, timezone etc.
29
a4766629
GM
30;; Note: Watch the trailing blank that is added on import.
31
7ec01532
GM
32;;; Code:
33(defun icalendar-testsuite-run ()
34 "Run icalendar test suite."
35 (interactive)
36 (icalendar-testsuite--run-function-tests)
37 (icalendar-testsuite--run-import-tests)
38 (icalendar-testsuite--run-export-tests)
39 (icalendar-testsuite--run-cycle-tests)
40 (icalendar-testsuite--run-real-world-tests)
41 (message "All icalendar tests finished successfully."))
42
43;; ======================================================================
44;; Test methods for functions
45;; ======================================================================
46(defun icalendar-testsuite--run-function-tests ()
47 "Perform tests for single icalendar functions."
48 (icalendar-testsuite--test-parse-summary-and-rest)
49 (icalendar-testsuite--test-format-ical-event)
50 (icalendar-testsuite--test-import-format-sample)
a4766629
GM
51 (icalendar-testsuite--test-first-weekday-of-year)
52 (icalendar-testsuite--test-datestring-to-isodate)
53 (icalendar-testsuite--test-datetime-to-diary-date)
f052351a 54 (icalendar-testsuite--test-diarytime-to-isotime)
b4340b3f
UJ
55 (icalendar-testsuite--test-convert-ordinary-to-ical)
56 (icalendar-testsuite--test-convert-weekly-to-ical)
57 (icalendar-testsuite--test-convert-yearly-to-ical)
58 (icalendar-testsuite--test-convert-block-to-ical)
59 (icalendar-testsuite--test-convert-cyclic-to-ical)
60 (icalendar-testsuite--test-convert-anniversary-to-ical)
aad81014 61 (icalendar-testsuite--test-calendar-style)
6fe539d2
UJ
62 (icalendar-testsuite--test-create-uid)
63 (icalendar-testsuite--test-parse-vtimezone))
7ec01532
GM
64
65(defun icalendar-testsuite--test-format-ical-event ()
a4766629 66 "Test `icalendar--format-ical-event'."
7ec01532
GM
67 (let ((icalendar-import-format "%s%d%l%o%t%u%c")
68 (icalendar-import-format-summary "SUM %s")
69 (icalendar-import-format-location " LOC %s")
70 (icalendar-import-format-description " DES %s")
71 (icalendar-import-format-organizer " ORG %s")
72 (icalendar-import-format-status " STA %s")
73 (icalendar-import-format-url " URL %s")
74 (icalendar-import-format-class " CLA %s")
7ec01532
GM
75 (event (icalendar-testsuite--get-ical-event "BEGIN:VEVENT
76DTSTAMP:20030509T043439Z
77DTSTART:20030509T103000
78SUMMARY:sum
79ORGANIZER:org
80LOCATION:loc
81DTEND:20030509T153000
82DESCRIPTION:des
83END:VEVENT
84")))
85 (assert (string= (icalendar--format-ical-event event)
86 "SUM sum DES des LOC loc ORG org") t)
87 (setq icalendar-import-format (lambda (&rest ignore)
88 "helloworld"))
89 (assert (string= (icalendar--format-ical-event event)
90 "helloworld") t)
91 (setq icalendar-import-format
92 (lambda (e)
93 (format "-%s-%s-%s-%s-%s-%s-%s-"
94 (icalendar--get-event-property event 'SUMMARY)
95 (icalendar--get-event-property event 'DESCRIPTION)
96 (icalendar--get-event-property event 'LOCATION)
97 (icalendar--get-event-property event 'ORGANIZER)
98 (icalendar--get-event-property event 'STATUS)
99 (icalendar--get-event-property event 'URL)
100 (icalendar--get-event-property event 'CLASS))))
101 (assert (string= (icalendar--format-ical-event event)
102 "-sum-des-loc-org-nil-nil-nil-") t)))
103
104(defun icalendar-testsuite--test-parse-summary-and-rest ()
a4766629 105 "Test `icalendar--parse-summary-and-rest'."
7ec01532
GM
106 (let ((icalendar-import-format "%s%d%l%o%t%u%c")
107 (icalendar-import-format-summary "SUM %s")
108 (icalendar-import-format-location " LOC %s")
109 (icalendar-import-format-description " DES %s")
110 (icalendar-import-format-organizer " ORG %s")
111 (icalendar-import-format-status " STA %s")
112 (icalendar-import-format-url " URL %s")
113 (icalendar-import-format-class " CLA %s")
7ec01532 114 (result))
f052351a 115 (setq result (icalendar--parse-summary-and-rest "SUM sum ORG org"))
7ec01532
GM
116 (assert (string= (cdr (assoc 'org result)) "org"))
117
118 (setq result (icalendar--parse-summary-and-rest
f052351a 119 "SUM sum DES des LOC loc ORG org STA sta URL url CLA cla"))
7ec01532
GM
120 (assert (string= (cdr (assoc 'des result)) "des"))
121 (assert (string= (cdr (assoc 'loc result)) "loc"))
122 (assert (string= (cdr (assoc 'org result)) "org"))
123 (assert (string= (cdr (assoc 'sta result)) "sta"))
124 (assert (string= (cdr (assoc 'cla result)) "cla"))
125
126 (setq icalendar-import-format (lambda () "Hello world"))
127 (setq result (icalendar--parse-summary-and-rest
128 "blah blah "))
129 (assert (not result))
130 ))
131
132(defun icalendar-testsuite--get-ical-event (ical-string)
a4766629
GM
133 "Helper function for testing `icalendar-testsuite--test-format-ical-event'.
134Return icalendar event for ICAL-STRING."
7ec01532
GM
135 (save-excursion
136 (with-temp-buffer
137 (insert ical-string)
138 (goto-char (point-min))
139 (car (icalendar--read-element nil nil)))))
140
141(defun icalendar-testsuite--test-import-format-sample ()
142 "Test method for `icalendar-import-format-sample'."
143 (assert (string= (icalendar-import-format-sample
144 (icalendar-testsuite--get-ical-event "BEGIN:VEVENT
145DTSTAMP:20030509T043439Z
146DTSTART:20030509T103000
147SUMMARY:a
148ORGANIZER:d
149LOCATION:c
150DTEND:20030509T153000
151DESCRIPTION:b
152END:VEVENT
153"))
154 (concat "SUMMARY=`a' DESCRIPTION=`b' LOCATION=`c' "
155 "ORGANIZER=`d' STATUS=`' URL=`' CLASS=`'"))))
156
157(defun icalendar-testsuite--test-first-weekday-of-year ()
a4766629 158 "Test method for `icalendar-first-weekday-of-year'."
7ec01532
GM
159 (assert (eq 1 (icalendar-first-weekday-of-year "TU" 2008)))
160 (assert (eq 3 (icalendar-first-weekday-of-year "WE" 2007)))
161 (assert (eq 5 (icalendar-first-weekday-of-year "TH" 2006)))
162 (assert (eq 7 (icalendar-first-weekday-of-year "FR" 2005)))
163 (assert (eq 3 (icalendar-first-weekday-of-year "SA" 2004)))
164 (assert (eq 5 (icalendar-first-weekday-of-year "SU" 2003)))
165 (assert (eq 7 (icalendar-first-weekday-of-year "MO" 2002)))
166 (assert (eq 3 (icalendar-first-weekday-of-year "MO" 2000)))
167 (assert (eq 1 (icalendar-first-weekday-of-year "TH" 1970))))
168
a4766629
GM
169(defun icalendar-testsuite--test-datestring-to-isodate ()
170 "Test method for `icalendar--datestring-to-isodate'."
171 (let ((calendar-date-style 'iso))
172 ;; numeric iso
173 (assert (string= (icalendar--datestring-to-isodate "2008 05 11")
174 "20080511"))
175 (assert (string= (icalendar--datestring-to-isodate "2008 05 31")
176 "20080531"))
177 (assert (string= (icalendar--datestring-to-isodate "2008 05 31" 2)
178 "20080602"))
179
180 ;; numeric european
181 (setq calendar-date-style 'european)
182 (assert (string= (icalendar--datestring-to-isodate "11 05 2008")
183 "20080511"))
184 (assert (string= (icalendar--datestring-to-isodate "31 05 2008")
185 "20080531"))
186 (assert (string= (icalendar--datestring-to-isodate "31 05 2008" 2)
187 "20080602"))
188
189 ;; numeric american
190 (setq calendar-date-style 'american)
191 (assert (string= (icalendar--datestring-to-isodate "11 05 2008")
192 "20081105"))
193 (assert (string= (icalendar--datestring-to-isodate "12 30 2008")
194 "20081230"))
195 (assert (string= (icalendar--datestring-to-isodate "12 30 2008" 2)
196 "20090101"))
197
198 ;; non-numeric
199 (setq calendar-date-style nil) ;not necessary for conversion
200 (assert (string= (icalendar--datestring-to-isodate "Nov 05 2008")
201 "20081105"))
202 (assert (string= (icalendar--datestring-to-isodate "05 Nov 2008")
203 "20081105"))
204 (assert (string= (icalendar--datestring-to-isodate "2008 Nov 05")
205 "20081105"))))
206
207(defun icalendar-testsuite--test-datetime-to-diary-date ()
208 "Test method for `icalendar--datetime-to-diary-date'."
209 (let* ((datetime '(59 59 23 31 12 2008))
210 (calendar-date-style 'iso))
211 (assert (string= (icalendar--datetime-to-diary-date datetime)
212 "2008 12 31"))
213 (setq calendar-date-style 'european)
214 (assert (string= (icalendar--datetime-to-diary-date datetime)
215 "31 12 2008"))
216 (setq calendar-date-style 'american)
217 (assert (string= (icalendar--datetime-to-diary-date datetime)
218 "12 31 2008"))))
219
f052351a
UJ
220(defun icalendar-testsuite--test-diarytime-to-isotime ()
221 "Test method for `icalendar--diarytime-to-isotime'."
b4340b3f
UJ
222 (assert (string= (icalendar--diarytime-to-isotime "01:15" "")
223 "T011500"))
224 (assert (string= (icalendar--diarytime-to-isotime "1:15" "")
225 "T011500"))
226 (assert (string= (icalendar--diarytime-to-isotime "0:01" "")
227 "T000100"))
f052351a
UJ
228 (assert (string= (icalendar--diarytime-to-isotime "0100" "")
229 "T010000"))
230 (assert (string= (icalendar--diarytime-to-isotime "0100" "am")
231 "T010000"))
232 (assert (string= (icalendar--diarytime-to-isotime "0100" "pm")
233 "T130000"))
234 (assert (string= (icalendar--diarytime-to-isotime "1200" "")
235 "T120000"))
236 (assert (string= (icalendar--diarytime-to-isotime "17:17" "")
237 "T171700"))
238 (assert (string= (icalendar--diarytime-to-isotime "1200" "am")
239 "T000000"))
240 (assert (string= (icalendar--diarytime-to-isotime "1201" "am")
241 "T000100"))
242 (assert (string= (icalendar--diarytime-to-isotime "1259" "am")
243 "T005900"))
244 (assert (string= (icalendar--diarytime-to-isotime "1200" "pm")
245 "T120000"))
246 (assert (string= (icalendar--diarytime-to-isotime "1201" "pm")
247 "T120100"))
248 (assert (string= (icalendar--diarytime-to-isotime "1259" "pm")
249 "T125900")))
250
b4340b3f
UJ
251(defun icalendar-testsuite--test-convert-ordinary-to-ical ()
252 "Test method for `icalendar--convert-ordinary-to-ical'."
253 (let* ((calendar-date-style 'iso)
254 result)
255 ;; without time
256 (setq result (icalendar--convert-ordinary-to-ical "&?" "2010 2 15 subject"))
257 (assert (= 2 (length result)))
258 (assert (string= "\nDTSTART;VALUE=DATE:20100215\nDTEND;VALUE=DATE:20100216"
259 (car result)))
260 (assert (string= "subject" (cadr result)))
261
262 ;; with time
263 (setq result (icalendar--convert-ordinary-to-ical
264 "&?" "&2010 2 15 12:34-23:45 s"))
265 (assert (= 2 (length result)))
266 (assert (string= (concat "\nDTSTART;VALUE=DATE-TIME:20100215T123400"
267 "\nDTEND;VALUE=DATE-TIME:20100215T234500")
268 (car result)))
269 (assert (string= "s" (cadr result)))
270
271 ;; with time, again -- test bug#5549
272 (setq result (icalendar--convert-ordinary-to-ical
273 "x?" "x2010 2 15 0:34-1:45 s"))
274 (assert (= 2 (length result)))
275 (assert (string= (concat "\nDTSTART;VALUE=DATE-TIME:20100215T003400"
276 "\nDTEND;VALUE=DATE-TIME:20100215T014500")
277 (car result)))
278 (assert (string= "s" (cadr result)))))
279
280(defun icalendar-testsuite--test-convert-weekly-to-ical ()
281 "Test method for `icalendar--convert-weekly-to-ical'."
282 (let* ((calendar-date-style 'iso)
283 result
284 (calendar-day-name-array
285 ["Sunday" "Monday" "Tuesday" "Wednesday" "Thursday" "Friday"
286 "Saturday"]))
287 (setq result (icalendar--convert-weekly-to-ical "" "Monday 8:30 subject"))
288 (assert (= 2 (length result)))
289 (assert (string= (concat "\nDTSTART;VALUE=DATE-TIME:20050103T083000"
290 "\nDTEND;VALUE=DATE-TIME:20050103T093000"
291 "\nRRULE:FREQ=WEEKLY;INTERVAL=1;BYDAY=MO")
292 (car result)))
293 (assert (string= "subject" (cadr result)))))
294
295(defun icalendar-testsuite--test-convert-yearly-to-ical ()
296 "Test method for `icalendar--convert-yearly-to-ical'."
297 (let* ((calendar-date-style 'iso)
298 result
299 (calendar-month-name-array
300 ["January" "February" "March" "April" "May" "June" "July" "August"
301 "September" "October" "November" "December"]))
302 (setq result (icalendar--convert-yearly-to-ical "" "May 1 Tag der Arbeit"))
303 (assert (= 2 (length result)))
304 (assert (string= (concat
305 "\nDTSTART;VALUE=DATE:19000501"
306 "\nDTEND;VALUE=DATE:19000502"
307 "\nRRULE:FREQ=YEARLY;INTERVAL=1;BYMONTH=5;BYMONTHDAY=1")
308 (car result)))
309 (assert (string= "Tag der Arbeit" (cadr result)))))
310
311(defun icalendar-testsuite--test-convert-block-to-ical ()
312 "Test method for `icalendar--convert-block-to-ical'."
313 (let* ((calendar-date-style 'iso)
314 result)
315 (setq result (icalendar--convert-block-to-ical
316 "" "%%(diary-block 2004 7 19 2004 8 27) Sommerferien"))
317 (assert (= 2 (length result)))
318 (assert (string= (concat
319 "\nDTSTART;VALUE=DATE:20040719"
320 "\nDTEND;VALUE=DATE:20040828")
321 (car result)))
322 (assert (string= "Sommerferien" (cadr result)))))
323
324(defun icalendar-testsuite--test-convert-cyclic-to-ical ()
325 "Test method for `icalendar--convert-cyclic-to-ical'."
326 (let* ((calendar-date-style 'iso)
327 result)
328 (setq result (icalendar--convert-block-to-ical
329 "" "%%(diary-block 2004 7 19 2004 8 27) Sommerferien"))
330 (assert (= 2 (length result)))
331 (assert (string= (concat
332 "\nDTSTART;VALUE=DATE:20040719"
333 "\nDTEND;VALUE=DATE:20040828")
334 (car result)))
335 (assert (string= "Sommerferien" (cadr result)))))
336
337(defun icalendar-testsuite--test-convert-anniversary-to-ical ()
338 "Test method for `icalendar--convert-anniversary-to-ical'."
339 (let* ((calendar-date-style 'iso)
340 result)
341 (setq result (icalendar--convert-anniversary-to-ical
342 "" "%%(diary-anniversary 1964 6 30) g"))
343 (assert (= 2 (length result)))
344 (assert (string= (concat
345 "\nDTSTART;VALUE=DATE:19640630"
346 "\nDTEND;VALUE=DATE:19640701"
347 "\nRRULE:FREQ=YEARLY;INTERVAL=1;BYMONTH=06;BYMONTHDAY=30")
348 (car result)))
349 (assert (string= "g" (cadr result)))))
350
a4766629
GM
351(defun icalendar-testsuite--test-calendar-style ()
352 "Test method for `icalendar--date-style'."
353 (dolist (calendar-date-style '(iso american european))
354 (assert (eq (icalendar--date-style) calendar-date-style)))
355 (let ((cds calendar-date-style)
356 (european-calendar-style t))
357 (makunbound 'calendar-date-style)
358 (assert (eq (icalendar--date-style) 'european))
359 (with-no-warnings (setq european-calendar-style nil)) ;still get warning!?! FIXME
360 (assert (eq (icalendar--date-style) 'american))
361 (setq calendar-date-style cds)))
362
aad81014
UJ
363(defun icalendar-testsuite--test-create-uid ()
364 "Test method for `icalendar--create-uid'."
f052351a
UJ
365 (let* ((icalendar-uid-format "xxx-%t-%c-%h-%u-%s")
366 t-ct
367 (icalendar--uid-count 77)
368 (entry-full "30.06.1964 07:01 blahblah")
369 (hash (format "%d" (abs (sxhash entry-full))))
370 (contents "DTSTART:19640630T070100\nblahblah")
371 (username (or user-login-name "UNKNOWN_USER"))
372 )
aad81014
UJ
373 ;; FIXME! If a test fails 'current-time is screwed. FIXME!
374 (fset 't-ct (symbol-function 'current-time))
375 (fset 'current-time (lambda () '(1 2 3)))
376 (assert (= 77 icalendar--uid-count))
f052351a
UJ
377 (assert (string= (concat "xxx-123-77-" hash "-" username "-19640630")
378 (icalendar--create-uid entry-full contents)))
aad81014
UJ
379 (assert (= 78 icalendar--uid-count))
380 (fset 'current-time (symbol-function 't-ct))
f052351a
UJ
381
382 (setq contents "blahblah")
383 (setq icalendar-uid-format "yyy%syyy")
384 (assert (string= (concat "yyyDTSTARTyyy")
385 (icalendar--create-uid entry-full contents)))
aad81014
UJ
386 ))
387
6fe539d2
UJ
388(defun icalendar-testsuite--test-parse-vtimezone ()
389 (let (vtimezone result)
390 (setq vtimezone (icalendar-testsuite--get-ical-event "BEGIN:VTIMEZONE
391TZID:thename
392BEGIN:STANDARD
393DTSTART:16010101T040000
394TZOFFSETFROM:+0300
395TZOFFSETTO:+0200
396RRULE:FREQ=YEARLY;INTERVAL=1;BYDAY=-1SU;BYMONTH=10
397END:STANDARD
398BEGIN:DAYLIGHT
399DTSTART:16010101T030000
400TZOFFSETFROM:+0200
401TZOFFSETTO:+0300
402RRULE:FREQ=YEARLY;INTERVAL=1;BYDAY=-1SU;BYMONTH=3
403END:DAYLIGHT
404END:VTIMEZONE
405"))
406 (setq result (icalendar--parse-vtimezone vtimezone))
407 (assert (string= "thename" (car result)))
408 (message (cdr result))
409 (assert (string= "STD-02:00DST-03:00,M3.5.0/03:00:00,M10.5.0/04:00:00" (cdr result)))
410 (setq vtimezone (icalendar-testsuite--get-ical-event "BEGIN:VTIMEZONE
411TZID:anothername
412BEGIN:STANDARD
413DTSTART:16010101T040000
414TZOFFSETFROM:+0300
415TZOFFSETTO:+0200
416RRULE:FREQ=YEARLY;INTERVAL=1;BYDAY=2MO;BYMONTH=10
417END:STANDARD
418BEGIN:DAYLIGHT
419DTSTART:16010101T030000
420TZOFFSETFROM:+0200
421TZOFFSETTO:+0300
422RRULE:FREQ=YEARLY;INTERVAL=1;BYDAY=2MO;BYMONTH=3
423END:DAYLIGHT
424END:VTIMEZONE
425"))
426 (setq result (icalendar--parse-vtimezone vtimezone))
427 (assert (string= "anothername" (car result)))
428 (message (cdr result))
429 (assert (string= "STD-02:00DST-03:00,M3.2.1/03:00:00,M10.2.1/04:00:00" (cdr result)))))
f052351a 430
7ec01532
GM
431;; ======================================================================
432;; Test methods for exporting from diary to icalendar
433;; ======================================================================
434
a4766629
GM
435(defun icalendar-testsuite--test-export (input-iso input-european input-american
436 expected-output)
7ec01532 437 "Perform an export test.
a4766629 438Argument INPUT-ISO iso style diary string.
7ec01532
GM
439Argument INPUT-EUROPEAN european style diary string.
440Argument INPUT-AMERICAN american style diary string.
a4766629
GM
441Argument EXPECTED-OUTPUT expected icalendar result string.
442
443European style input data must use german month names. American
444and ISO style input data must use english month names."
7ec01532 445 (message "--- icalendar-testsuite--test-export ---")
a4766629 446 (let ((calendar-date-style 'iso)
7ec01532
GM
447 (icalendar-recurring-start-year 2000))
448 (set-time-zone-rule "CET") ;;FIXME: reset timezone!
a4766629
GM
449 (when input-iso
450 (let ((calendar-month-name-array
451 ["January" "February" "March" "April" "May" "June" "July" "August"
452 "September" "October" "November" "December"])
453 (calendar-day-name-array
454 ["Sunday" "Monday" "Tuesday" "Wednesday" "Thursday" "Friday"
455 "Saturday"]))
456 (setq calendar-date-style 'iso)
457 (icalendar-testsuite--do-test-export input-iso expected-output)))
7ec01532
GM
458 (when input-european
459 (let ((calendar-month-name-array
460