webcalendar

Check-in [7470f6e3bf]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Add a debug startup to "today" so I can play with its function in the CLI. Fix timezone treatment so daylight savings state for the start date of a repeat is calculated correctly. Streamline elems, use a CSS rule instead.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | master | trunk
Files: files | file ages | folders
SHA3-256:7470f6e3bf7818007b121fd06b12af2c8decd22080ee6dd03c9da74a58766673
User & Date: ajv-899-334-8894@vsta.org 2017-05-30 19:45:39
Context
2017-06-01
03:34
Switch from PHP session stuff to basic cookie authen. Implement all the goop to play with the rest of the calendar's cookie management. check-in: d8a95c83d6 user: ajv-899-334-8894@vsta.org tags: master, trunk
2017-05-30
19:45
Add a debug startup to "today" so I can play with its function in the CLI. Fix timezone treatment so daylight savings state for the start date of a repeat is calculated correctly. Streamline elems, use a CSS rule instead. check-in: 7470f6e3bf user: ajv-899-334-8894@vsta.org tags: master, trunk
04:44
Bug report/fix from Mark Blair, = versus ==, incorrectly labeling all-day events. Bug 2720. He also thought the ?: might be backwards, but it looks OK to me. check-in: ffb1667790 user: ajv-899-334-8894@vsta.org tags: master, trunk
Changes
Hide Diffs Unified Diffs Ignore Whitespace Patch

Changes to cgi-bin/today.py.

1
2
3
4
5
6
7
8

9






10
11
12
13
14
15






16
17
18
19
20
21
22
23
24
25

26
27
28
29
30
31
32
33
34
35
36
37



38






39
40
41
42
43
44
45
46
47
48
49
50



51
52
53
54
55
56
57
58
...
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
...
144
145
146
147
148
149
150







#!/usr/bin/python
#
# today.py
#	Display events for today
#
import sys, time, os
import Cookie, webcal, phpsession
from webcal import Today, cmp_time, Today, CALBASE








# Common HTTP response header
print """Content-Type: text/html

<html>
"""







try:
    # Hopefully our PHP session cookie
    cookie = Cookie.SimpleCookie(os.environ["HTTP_COOKIE"])
    sessid = cookie["PHPSESSID"].value
    if ".." in sessid:
	sessid = "XXX"
    f = open("/var/lib/php5/sessions/sess_" + sessid, "r")
    sess = phpsession.load(f)
    uname = sess["webcal_login"]
    f.close()

except:
    print """<head>
    <title>Bad Webcalendar Session</title>
    <meta http-equiv="REFRESH" content="1;url=/webcal" />
   </head>
   <body>
    Redirecting you to Webcalendar for login...
   </body>
</html>
"""
    sys.exit(0)











# Shortcut; we use it a lot
w = sys.stdout.write

# Pixels per line of output
LINEPIX = 25

def filter_today(ev):
    global Today
    res = ev.happens(Today)
    return res

if __name__ == "__main__":



    evs = sorted(webcal.load_user(uname, filter_today),
	cmp=lambda ev1,ev2: cmp_time(ev1.begin, ev2.begin))

    # Assign columns
    rows = {}
    col = {}
    untimed = set()
    for ev in tuple(evs):
................................................................................
    maxcol = int(colpix * 1.2)

    curidx = 0
    for hour in xrange(min(hours), max(hours)+1):
	while (curidx < len(evs)) and (evs[curidx].begin.tm_hour == hour):
	    ev = evs[curidx]
	    w(
	     '<span onclick="view_ev(%d);" class="timedevent"' % (ev.evid,))
	    w(
	     ' style="left: %dvw; top: %dpx; height: %dpx;' %
	     (((col[ev] - 1) * colpix),
	      houridx * LINEPIX, max(ev.dur / 60.0, 0.75) * LINEPIX))
	    w(' max-width: %dvw; z-index: %d;' % (maxcol, col[ev]))
	    if ev.color:
		w(' color: %s;' % (ev.color,))
................................................................................
    w("""</td>
 </tr>
</table>

</body>
</html>
""")













<
|
>

>
>
>
>
>
>






>
>
>
>
>
>
|
|
|
|
|
|
|
|
|
|
>
|
|
|
|
|
|
|
|
|
|
|

>
>
>

>
>
>
>
>
>



|


|
|
|


<
>
>
>
|







 







|







 







>
>
>
>
>
>
>
1
2
3
4
5
6

7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71

72
73
74
75
76
77
78
79
80
81
82
...
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
...
168
169
170
171
172
173
174
175
176
177
178
179
180
181
#!/usr/bin/python
#
# today.py
#	Display events for today
#
import sys, time, os

from webcal import cmp_time
import webcal

# By default, display events for Today
Target = webcal.Today

# Filled in by authen (or debug)
uname = None

# Common HTTP response header
print """Content-Type: text/html

<html>
"""


# Set up, when we're invoked as a CGI under a web server
def init_cgi():
    global uname
    import Cookie, phpsession

    try:
	# Hopefully our PHP session cookie
	cookie = Cookie.SimpleCookie(os.environ["HTTP_COOKIE"])
	sessid = cookie["PHPSESSID"].value
	if ".." in sessid:
	    sessid = "XXX"
	f = open("/var/lib/php5/sessions/sess_" + sessid, "r")
	sess = phpsession.load(f)
	uname = sess["webcal_login"]
	f.close()

    except:
	print """<head>
	<title>Bad Webcalendar Session</title>
	<meta http-equiv="REFRESH" content="1;url=/webcal" />
       </head>
       <body>
	Redirecting you to Webcalendar for login...
       </body>
    </html>
    """
	sys.exit(0)

# Set up when we're manually invoked (for testing)
def init_cli():
    global uname, Target

    if not os.isatty(0):
	raise Exception, "Bad CLI invocation"
    uname = sys.argv[1]
    if len(sys.argv) > 2:
	Target = time.strptime(sys.argv[2], "%m/%d/%Y")

# Shortcut; we use it a lot
w = sys.stdout.write

# CSS pixels per line of output
LINEPIX = 25

def filter_target(ev):
    global Target
    res = ev.happens(Target)
    return res


def run():
    global w, uname

    evs = sorted(webcal.load_user(uname, filter_target),
	cmp=lambda ev1,ev2: cmp_time(ev1.begin, ev2.begin))

    # Assign columns
    rows = {}
    col = {}
    untimed = set()
    for ev in tuple(evs):
................................................................................
    maxcol = int(colpix * 1.2)

    curidx = 0
    for hour in xrange(min(hours), max(hours)+1):
	while (curidx < len(evs)) and (evs[curidx].begin.tm_hour == hour):
	    ev = evs[curidx]
	    w(
	     '<span onclick="view_ev(%d);"' % (ev.evid,))
	    w(
	     ' style="left: %dvw; top: %dpx; height: %dpx;' %
	     (((col[ev] - 1) * colpix),
	      houridx * LINEPIX, max(ev.dur / 60.0, 0.75) * LINEPIX))
	    w(' max-width: %dvw; z-index: %d;' % (maxcol, col[ev]))
	    if ev.color:
		w(' color: %s;' % (ev.color,))
................................................................................
    w("""</td>
 </tr>
</table>

</body>
</html>
""")

if __name__ == "__main__":
    if len(sys.argv) > 1:
	init_cli()
    else:
	init_cgi()
    run()

Changes to cgi-bin/webcal.py.

1
2
3
4
5
6
7
8
9
10
11
12
...
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
...
420
421
422
423
424
425
426










427
428
429
430
431
432
433
#
# today.py
#	Pull all events from a icalendar, display today's
#
import time
import MySQLdb as mysql
import pdb

# Indices into webcal_entry
WE_ID = 0	# Entry's ID
WE_WHEN = 4	# Date (and time at 5)
WE_DUR = 8	# Duration (minutes)
................................................................................

    # HHMMSS
    hour = tmstart / 10000
    min = (tmstart / 100) % 100
    sec = tmstart % 100

    # Convert to system time (everything in the DB is in Zulu)
    tm = time.mktime( (year, month, day, hour, min, sec, 0, 0, -1) )
    return tm-time.timezone

# Tell if these two match to the day level
def daymatch(tm1, tm2):
    return (tm1.tm_year == tm2.tm_year) and \
	    (tm1.tm_mon == tm2.tm_mon) and \
	    (tm1.tm_mday == tm2.tm_mday)

................................................................................

    c.close()

    return res

# Load user's calendar, along with any layers they like to include
def load_user(uname, filter):











    # Get our own entries
    entries = load_cal(uname, filter)
    c = db.cursor()

    # And any layers we desire
    c.execute("""select cal_layeruser,cal_color from webcal_user_layers




|







 







|
|







 







>
>
>
>
>
>
>
>
>
>







1
2
3
4
5
6
7
8
9
10
11
12
...
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
...
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
#
# today.py
#	Pull all events from a icalendar, display today's
#
import time, os, calendar
import MySQLdb as mysql
import pdb

# Indices into webcal_entry
WE_ID = 0	# Entry's ID
WE_WHEN = 4	# Date (and time at 5)
WE_DUR = 8	# Duration (minutes)
................................................................................

    # HHMMSS
    hour = tmstart / 10000
    min = (tmstart / 100) % 100
    sec = tmstart % 100

    # Convert to system time (everything in the DB is in Zulu)
    tm = calendar.timegm( (year, month, day, hour, min, sec, 0, 0, -1) )
    return tm

# Tell if these two match to the day level
def daymatch(tm1, tm2):
    return (tm1.tm_year == tm2.tm_year) and \
	    (tm1.tm_mon == tm2.tm_mon) and \
	    (tm1.tm_mday == tm2.tm_mday)

................................................................................

    c.close()

    return res

# Load user's calendar, along with any layers they like to include
def load_user(uname, filter):

    # If the user has set a timezone, use it
    c = db.cursor()
    c.execute("""select cal_value from webcal_user_pref
	    where cal_login = %s and cal_setting = "TIMEZONE" """,
	(uname,))
    tup = c.fetchone()
    if tup is not None:
	os.environ["TZ"] = tup[0]
	time.tzset()

    # Get our own entries
    entries = load_cal(uname, filter)
    c = db.cursor()

    # And any layers we desire
    c.execute("""select cal_layeruser,cal_color from webcal_user_layers

Changes to includes/css/cal.css.

13
14
15
16
17
18
19
20
21
22
23
24
}
.callist > td:nth-child(2) {
    width: 90vw;
}
.callist span {
    position: absolute;
}
.timedevent {
    /* Just a color I pulled out of a picker... */
    background-color: #d3a5ac;
    border: 1px solid black;
}







|




13
14
15
16
17
18
19
20
21
22
23
24
}
.callist > td:nth-child(2) {
    width: 90vw;
}
.callist span {
    position: absolute;
}
#calevents > span {
    /* Just a color I pulled out of a picker... */
    background-color: #d3a5ac;
    border: 1px solid black;
}