<?xml version='1.0' encoding='UTF-8'?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/'><id>tag:blogger.com,1999:blog-6259484853198426929</id><updated>2007-04-17T09:04:34.786-07:00</updated><title type='text'>CIMSU OTS Technical Blog</title><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/index.htm'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default'></link><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://msuconfuciusinstitute.org/scheduler/techblog/atom.xml'></link><author><name>James</name><uri>http://jamessocol.com/</uri></author><generator version='7.00' uri='http://www2.blogger.com'>Blogger</generator><openSearch:totalResults>12</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-124672483519205834</id><published>2007-04-17T08:25:00.000-07:00</published><updated>2007-04-17T09:04:34.896-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='New Feature'></category><category scheme='http://www.blogger.com/atom/ns#' term='Bug Fix'></category><title type='text'>Tutor Time Errors, DST, and Profile Updates</title><content type='html'>Dealing with users is timezones over 12 hours apart has caused all sorts of interesting errors. Most recently, we noticed that adding new availability tended to be 12 hours off. Turns out there was a series of errors that lead to times being added wrong&amp;em;apparently when I fixed it I didn't fix it everywhere.&lt;br /&gt;&lt;br /&gt;So now, theoretically, that's fixed so that all times really are stored in the servers timezone and then converted for each user.&lt;br /&gt;&lt;br /&gt;I also found an easy way to automatically adjust for Daylight Saving Time. Unfortunately, due to PHP's slight bias, it only works with US DST, not with European Summer Time. So, sorry Europeans, but you'll have to go through and adjust your timezone yourself.&lt;br /&gt;&lt;br /&gt;Finally, I added what I always intended to have, but forgot about: immediate profile updates. If you change something on your profile, the update will automatically appear in both the database and the session, so the changes appear everywhere on the site simultaneously.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/04/tutor-time-errors-and-dst.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/124672483519205834'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/124672483519205834'></link><author><name>OTS Development Team</name><uri>http://confucius.msu.edu/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-8797981070223286166</id><published>2007-04-12T11:19:00.000-07:00</published><updated>2007-04-12T11:29:01.455-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='FrameWorks'></category><title type='text'>Bugs</title><content type='html'>A while ago we created our own small bug reporting script to handle, well, bug reporting. That script (&lt;code&gt;http://msuconfuciusinstitute.org/scheduler/bugs/&lt;/code&gt;) is the first live test of FrameWorks 2. It seems to be running well so far.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/04/bugs.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8797981070223286166'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8797981070223286166'></link><author><name>OTS Development Team</name><uri>http://confucius.msu.edu/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-8359028537773255984</id><published>2007-04-12T11:08:00.000-07:00</published><updated>2007-04-12T11:18:37.455-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Bug Fix'></category><title type='text'>IE Fix</title><content type='html'>Because Internet Explorer does not support the &lt;code&gt;display: table-cell;&lt;/code&gt; value in CSS (or any of its related values), apparently all the calendars were appearing as vertical columns in IE. Apparently "We don't support Internet Explorer" wasn't a valid response, so I had to alter the Calendar object a bit to output tables instead of divs.&lt;br /&gt;&lt;br /&gt;Just to make it harder, though, the system wasn't using a new version of Calendar, it was using something along the lines of v0.9. When I altered the file directly, very weird stuff happened. So I tried to upgrade to 1.2 which uses Parser and some templates, but of course I ended up with several conflicting class names and it was more work than it was worth. So I downgraded to Calender 1.1, and modified the output code.&lt;br /&gt;&lt;br /&gt;This all involved breaking the site for maybe half an hour, which is pretty good.&lt;br /&gt;&lt;br /&gt;I haven't had the chance to work on this project lately, but now the plethora other small projects seem to be vanishing so I can really start work on version 2 again.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/04/ie-fix.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8359028537773255984'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8359028537773255984'></link><author><name>OTS Development Team</name><uri>http://confucius.msu.edu/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-4490996571088527711</id><published>2007-03-08T11:29:00.000-08:00</published><updated>2007-03-08T12:02:39.043-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='New Feature'></category><category scheme='http://www.blogger.com/atom/ns#' term='FrameWorks'></category><title type='text'>Parser 1.4.1 , Pages, Request &amp; Ajax</title><content type='html'>&lt;strong&gt;Parser 1.4.1&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;Major updates on the Parser object. Version 1.3 included Parser Extensions. Version 1.4.1 includes Parser Extensions and Link formatting, in 3.5 different flavors.&lt;br /&gt;&lt;br /&gt;First, two FrameWorks-style tags were added, "link" and "url". They do about what you'd expect, ie: "link" generates an internal link and "url" generates an internal URL. Here's the syntax:&lt;br /&gt;{link:page}&lt;br /&gt;{link:page|Link Text}&lt;br /&gt;{url:page}&lt;br /&gt;&lt;br /&gt;These work with the new global $fgLinkStyle. Those familiar with MediaWiki will recognize this, it's essentially the same thing, just a string with $1 in it somewhere that tells the parser how to format links.&lt;br /&gt;&lt;br /&gt;There's also two pseudo-WikiMarkup additions: [[link]] and [http://link], which work exactly as they do in MediaWiki, including the | deliminator.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Pages&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;The way we'll handle pages has finally been worked out. This is fairly intricate, but also entirely encapsulated and modular, so I think it's a fair deal. New pages are stored in their own files (though you could, of course, store multiple pages in the same file). This file calls a function, ffAddPage, which takes 2-4 parameters. First is the "label" for the page, ie: some kind of text name that will appear in the URL or querystring. Second is a unique callback function (I've been starting callbacks with "fc") that actually does the processing for the page. More on this in a minute. The third and fourth parameters are booleans, setting the #3 to &lt;em&gt;true&lt;/em&gt; will make this page the default, setting #4 &lt;em&gt;true&lt;/em&gt; will make it the error page. This is pretty unnecessary, as there's a built-in error page you can use.&lt;br /&gt;&lt;br /&gt;The callback functions need to take four parameters, preferably by reference&amp;mdash;at least for the first three. Here's the format:&lt;br /&gt;&lt;code&gt;fcPageCallback( &amp;$Parser, &amp;$User, &amp;$Request, $Subpage = false ) {...}&lt;/code&gt;&lt;br /&gt;&lt;br /&gt;The $Parser parameter is the global fgParser object. The $User parameter is the global fgUser, and the $Request parameter is the global fgRequest object. The subpage is any part of the parameter after the first '/' character.&lt;br /&gt;&lt;br /&gt;So, calling&lt;br /&gt;&lt;code&gt;index.php?page=page/subpage&lt;/code&gt;&lt;br /&gt;will result in the following: if "page" exists, and the callback is defined, say fcPage, fcPage will be called with the parameters above, including the $Subpage = "subpage". It's the responsibility of the callback fcPage to output material to the browser. This lets pages generate RSS feeds using RSSFeed.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Request &amp; Ajax&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;em&gt;Request&lt;/em&gt; is a new object that handles getting variables from the HTTP request for you, including escaping quotes if magic_quotes is off. Use the method $fgRequest-&gt;getVar('varname'); to get either any request var. Note that POST vars take precedence over GET vars, and that, even if you use the POST method, if there are no POST vars, it will interpret this as essentially GET.&lt;br /&gt;&lt;br /&gt;&lt;em&gt;Ajax&lt;/em&gt; is almost identical to the AjaxDispatcher object in MediaWiki, that is, if $fgUseAjax is set to true, and you pass a request var called "action" set to "ajax", it will call the Ajax object and use a user-defined callback function. (Note you actually need to set "action=ajax", "rs=callback", and "rsargs=functionarguments" in your request. Though, of course, you could always global in the $fgRequest object and access anything that way.) User-defined callback functions have to be added using the &lt;code&gt;void ffAddAjaxFunction( string Callback )&lt;/code&gt; function.&lt;br /&gt;&lt;br /&gt;The Ajax callback has to do two things: 1) accept a string or array as the only parameter, and 2) if necessary, it needs to handle any output to the browser.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/03/parser-141-pages-request-ajax.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/4490996571088527711'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/4490996571088527711'></link><author><name>OTS Development Team</name><uri>http://confucius.msu.edu/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-8281759570162660379</id><published>2007-03-06T13:47:00.000-08:00</published><updated>2007-03-06T13:57:42.135-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='New Feature'></category><title type='text'>Bug Reports</title><content type='html'>There is a new method of bug reporting in town. Basically, I got sick of people e-mailing me directly with problems. Now the OTS uses something called the &lt;a href="http://msuconfuciusinstitute.org/scheduler/bugs/"&gt;Bug Reporting and Tracking Service&lt;/a&gt; to handle bug reports. I always intended to get around to coding this, but didn't get to it until this week.&lt;br /&gt;&lt;br /&gt;It's fairly straightforward. Instead of bothering with logins I just created a password protected directory to allow "admin" access. And each user can create a "bug password," which is stored in plaintext, to limit who can respond to the bug.&lt;br /&gt;&lt;br /&gt;The real point of this new Service is to test some of the FrameWorks components. It uses DB2, Parser1.2, and RSSFeed1.1 to generate RSS feeds tracking the progress of each bug or to see the latest bugs&amp;mdash;which I'm using to keep track of people submitting them. So far, the new components seem to be performing admirably.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/03/bug-reports.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8281759570162660379'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8281759570162660379'></link><author><name>OTS Development Team</name><uri>http://confucius.msu.edu/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-1248408202651330610</id><published>2007-03-06T13:24:00.000-08:00</published><updated>2007-03-06T13:43:30.882-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='FrameWorks'></category><title type='text'>Lots of Small Changes</title><content type='html'>In the past week, there have been several small changes made throughout the FrameWorks system. Let me 'splain. No, there is too much. Let me sum up:&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Parser 1.2.2&lt;/strong&gt;: Parser got a little upgrade, to have a little more in common with &lt;a href="http://smarty.php.net/"&gt;Smarty&lt;/a&gt; and to simplify the code in pages that use it. The "addVariable" method was shortened to "set" (with an alias left for backwards compatibility) and the "setTemplate" method was made private (this may cause scripts to crash) and template selection was limited to the output function, as in Smarty. So now, code should look something like:&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;&lt;br /&gt;$parser = new Parser;&lt;br /&gt;$parser-&gt;set('name', 'value');&lt;br /&gt;echo $parser-&gt;output('default.htm');&lt;br /&gt;&lt;/pre&gt;&lt;/blockquote&gt;&lt;br /&gt;It also now gets the default template directory from LocalSettings.php, which means you must first include LocalSettings.php, which means you must first define the security constant.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Calendar 1.2.1&lt;/strong&gt;: Calendar just got updates to follow the new Parser code formats.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;RSSFeed 1.1&lt;/strong&gt;: RSSFeed got similar updates to Calendar 1.1. It now uses Parser to generate code, instead of encoding raw XML. The "addItem" method was also shortened to "add" (with an alias for backwards compatibility).&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;User 2.0.1&lt;/strong&gt; and &lt;strong&gt;Userdata 1.0.1&lt;/strong&gt;: To streamline the process of accessing user information, the Rights array and associated functions were moved to the Userdata object. The User method "hasRight" is now a reference to the mUserdata object's "getRight" method.&lt;br /&gt;&lt;br /&gt;The only major update planned for any of these at this time is the addition of ParserExtensions to the Parser object. These would use callback functions to allow custom extensions, as in the MediaWiki parser. I am currently undecided about the format for such tags or how data will be passed to the callback.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/03/lots-of-small-changes.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/1248408202651330610'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/1248408202651330610'></link><author><name>OTS Development Team</name><uri>http://confucius.msu.edu/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-8330592222500726210</id><published>2007-02-13T17:10:00.000-08:00</published><updated>2007-02-13T19:03:42.223-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='FrameWorks'></category><title type='text'>Calendar 1.2</title><content type='html'>The next major revision of Calendar is done. Calendar 1.2 simplifies Calendar 1.1, reducing the CSS requirements and overall shortening the code by over 100 lines. It also abstracts the process of generating HTML, which used to be done in the Calendar object itself but now relies on templates with loops&amp;mdash;a feature of Parser 1.2.&lt;br /&gt;&lt;br /&gt;Currently Calendar 1.2 needs three templates. This is due to the inability to nest loops. This does give pretty specific control over how each section will look, though. The only lost functionality is the ability to use completely different CSS for "big days," used to display seven days or less, and "small days," used for two-week and month displays. Practically, the only difference was a height factor, which could easily be changed on a page-by-page basis, or left to float, with a min-height attribute.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;&lt;/span&gt;With these major revisions of Parser and Calendar I am now going back to work on User 2.0. If anyone has advice on the best way to do session-based user login, let me know. Version 1.0 serialized the itself and stored the data in the session. Any new User object would check for the session data, and, if found, copy the data into itself. I can't decide if I want to do something like this again, or store the whole object in the session.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/02/calendar-12.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8330592222500726210'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/8330592222500726210'></link><author><name>James</name><uri>http://jamessocol.com/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-5067397963302915694</id><published>2007-02-12T18:52:00.000-08:00</published><updated>2007-02-12T17:43:41.992-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='FrameWorks'></category><title type='text'>Parser 1.2</title><content type='html'>On the way to Calendar 1.2, which will use Parser to simplify the process of looping through days and make it, yet again, easier to update, I realized my templates were going to be bloody long and fairly ... static, so I had to update to Parser 1.2.&lt;br /&gt;&lt;br /&gt;Parser 1.2 has yet another new feature: foreach loops. This allows you to--OK, here it gets complicated--define as a variable an array, call it $Loop, of associative arrays, say $Data, with tag =&gt; value data. Each $Data has the same array keys (theoretically) and different array values (theoretically). Then you put in the template something like:&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;{foreach:loop}&lt;br /&gt;{name1} likes {name2}&amp;lt;br /&amp;gt;&lt;br /&gt;{endforeach:}&lt;/pre&gt;&lt;/blockquote&gt;This would print, provided the tags name1 and name2 were defined in each member of the variable "loop," one row of who-likes-who for each member of "loop." The structure is something like...&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;$Loop = Array (&lt;br /&gt;0 =&gt; Array (&lt;br /&gt;  "name1" =&gt; "Jessica",&lt;br /&gt;  "name2" =&gt; "Mark"&lt;br /&gt;),&lt;br /&gt;1 =&gt; Array (&lt;br /&gt;  "name1" =&gt; "Stewart",&lt;br /&gt;  "name2" =&gt; "Leslie"&lt;br /&gt;),&lt;br /&gt;);&lt;br /&gt;$parser-&gt;addVariable("loop", $Loop);&lt;br /&gt;&lt;/pre&gt;&lt;/blockquote&gt;And this would print something like, using that template above:&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;Jessica likes Mark&amp;lt;br /&amp;gt;&lt;br /&gt;Stewart likes Leslie&amp;lt;br /&amp;gt;&lt;br /&gt;&lt;/pre&gt;&lt;/blockquote&gt;&lt;br /&gt;The potential here is obvious. It's a little tricky, yes, and not something one would want to do by hand, but it's not too hard to do it automatically, having another loop add arrays to the $Loop array before adding it as a variable. This is exactly what Calendar 1.2 will be doing.&lt;br /&gt;&lt;br /&gt;All I wanted to do was streamline Calendar, and I ended up with a whole new control structure in Parser. Imagine that.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/02/parser-12.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/5067397963302915694'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/5067397963302915694'></link><author><name>OTS Development Team</name><uri>http://confucius.msu.edu/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-74947052166368938</id><published>2007-02-10T16:41:00.000-08:00</published><updated>2007-02-10T16:41:07.073-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Bug Fix'></category><title type='text'>Exterminating</title><content type='html'>There's nothing like trouble-shooting and bug-killing.&lt;br /&gt;&lt;br /&gt;Some minor fixes:&lt;br /&gt;&lt;br /&gt;1) The doLogin script had been modified to use a static redirect some time ago, and I never noticed. Basically, instead of users redirecting to a login page and then back to the page they wanted, everyone went to the homepage after they logged in. Easy to fix.&lt;br /&gt;&lt;br /&gt;2) Through my complete oversight, the system allowed blank usernames. Well, since a blank string will evaluate as false, this was also a pretty easy fix. Now you can neither log in nor register if your username evaluates as false.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/02/exterminating.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/74947052166368938'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/74947052166368938'></link><author><name>James</name><uri>http://jamessocol.com/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-6079613490666728298</id><published>2007-02-10T16:10:00.000-08:00</published><updated>2007-02-10T16:10:19.635-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='FrameWorks'></category><title type='text'>FrameWorks 2.0</title><content type='html'>If nothing else, I'm learning a &lt;span style="font-style: italic;"&gt;lot&lt;/span&gt; about practical programming through this project.&lt;br /&gt;&lt;br /&gt;The original backbone, FrameWorks 1.0CI, had more bugs than your average Microsoft release, and was about as useful as anything before Service Pack 2. It couldn't do much of anything, except handle user authentication and basic data access. The "CI" part of the version also meant it had been rewritten for PHP4, and lost a lot of its performance.&lt;br /&gt;&lt;br /&gt;The first part of the new version, FrameWorks 2.0, was the Calendar object, an abstraction of basic calendar functions, which I talked about in the last post. Calendar is currently in version 1.1.2, but I'm hard at work on version 1.2.&lt;br /&gt;&lt;br /&gt;The Calendar object caused me to build a Math object, which is nothing but a bunch of static functions (I love PHP5) to do basic math that PHP doesn't have built in, like a true modulo function. Math basically augments versions every time I find a new function it needs.&lt;br /&gt;&lt;br /&gt;I also created my own exception class, called Error. Currently in version 1.0.1, Error simply cleans up the messages created by the built in Exception class.&lt;br /&gt;&lt;br /&gt;The next big project was a template parser, called, simply, Parser. Parser is like a slimmed down version of Smarty. It's missing some of the big features, mostly because it works much differently. Smarty, for instance, compiles templates into workable PHP code. It then caches these compiled files. It doesn't have true page-caching. Parser, on the other hand, doesn't compile templates, so it can't cache them, so, summarily, it has no caching system (yet). Since all the pages are dynamic, I'm not too worried about this, either.&lt;br /&gt;&lt;br /&gt;Parser 0.1-1.0 involved a built-in Menu system, which would create automatic variables known to fill in a menu and submenu. Parser 1.1 ditched this (retrospectively dumb) idea for two much more powerful implementations: template inclusion and basic boolean logic. This pretty much eliminated the need for a difficult-to-implement menu system anyway. Now it's much easier to just create a "menu.htm" template with various if/then statements to decide which link to highlight or whatever.&lt;br /&gt;&lt;br /&gt;Parser also uses an internal object called Translator. This is my first real stab at multiple language support. Language files just have an associative array with the text label and translation. This will let the new version of the OTS support users native languages. And through the Translator, the Parser can interact with the Calendar to change the language and date formats there, too.&lt;br /&gt;&lt;br /&gt;Also new is an RSSFeed object, which will be able to automatically generate RSS feeds (either static files, like through cron or publishing script, or dynamic through another script). The idea for the OTS is that users will be able to subscribe to a feed with their next 10 appointments or something.&lt;br /&gt;&lt;br /&gt;Finally, major updates are planned for both the DB and User classes, which should both be in a functional 2.0 by the end of the week.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/02/frameworks-20.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/6079613490666728298'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/6079613490666728298'></link><author><name>James</name><uri>http://jamessocol.com/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-5839269518036409198</id><published>2007-02-10T15:40:00.000-08:00</published><updated>2007-02-10T15:40:38.784-08:00</updated><title type='text'>Background Info</title><content type='html'>As this is supposed to be a partial record of the development of the OTS, I feel some background is in order.&lt;br /&gt;&lt;br /&gt;The system runs in PHP5.1 (previously 4.3) with a MySQL 3.21 backend on Redhat Linux on an IBM Blade Server. The update to PHP5 has allowed me to begin work on a much more advanced backbone which I'm calling OTS2 for now.&lt;br /&gt;&lt;br /&gt;Originally, the OTS ran on an object-oriented backbone, called FrameWorks, I designed as an abstraction of several important functions I'd been using, such as user authentication and database access. But as the needs of the project developed, it became relatively obvious how limited this system was. It was also a huge performance problem, as it relied on an object-inheritance tree. (There was a root object called "Object" which did nothing but figure out the name of the class and generate a microtime stamp.)&lt;br /&gt;&lt;br /&gt;Currently, most of the system still runs on FrameWorks 1.0CI, the original implementation of FrameWorks, adapted for the Confucius Institute (basically downgraded to run in PHP4). However, as I update the functionality of the site, I am slowly transitioning to FrameWorks 2.0beta, a strictly PHP5 update of the previous version. Features of PHP5 that are heavily incorporated in FrameWorks 2 are more advanced error handling via PHP's new Exception structure--user-friendly error messages instead of simple "die();" statements--and the new OOP structures, such as static methods and variables and scope resolution.&lt;br /&gt;&lt;br /&gt;The first part to be rewritten as part of FrameWorks 2 was the Calendar system. Obviously, OTS relies on a lot of calendar functions to schedule appointments. FrameWorks 1 didn't even have a Calendar object, so OTS had several pages creating their own, simple "calendars." This took a &lt;span style="font-weight: bold;"&gt;lot &lt;/span&gt;of code, and changing the calendars involved changing the code in &lt;span style="font-style: italic;"&gt;all&lt;/span&gt; of them. They were also formatted with tables and just generally unpleasant. So I created a new OO system in which a Calendar object stores all sorts of things, including user and server timezone offsets--important when half the users are in China and the other half are in the US--and deals in "Events," which are ordered based on their beginning timestamp. The Calendar can then output a CSS-formatted calendar (all DIVs instead of tables) which can show a day, a week, a month, a work-week, or the next 4 days. Incorporating this reduced some of the code by as much as 80% and unified the system so that changes are now made to one object instead of three or four pages.&lt;br /&gt;&lt;br /&gt;The OTS is built, too heavily, on AJAX. This has caused me nothing but headaches since I made the decision. When I started the system, I had just discovered AJAX and how to make it work... I hadn't yet discovered &lt;span style="font-style: italic;"&gt;when&lt;/span&gt; to make it work. Certain parts of the site benefit from the AJAX framework--the "announcements" system, for instance, which can count down to your next appointment--but the rest suffers. A lot. AJAX is a great methodology for things that actually need to update regularly without page reloads, but it's far too rigid for real page-to-page navigation. Either you end up with hundreds of individual JavaScript functions (like I have) or you simply can't do certain things (also, like I can't), like easily submitting forms. The number of cheap hacks and "workarounds" I've done has made maintenance on the system virtually impossible.&lt;br /&gt;&lt;br /&gt;Finally, the real meat of the OTS is a Flash Communications Server. Honestly, I have almost nothing to do with this. We already had the necessary SWF files and just plugged it in. It allows full-duplex audio conferencing along with both English and Simplified Chinese text chat. In these "rooms," tutors and students get together and the actual learning takes place. Lately the only work I've done on this is try to fix the way sessions end and take users to rating pages (stupid AJAX).&lt;br /&gt;&lt;br /&gt;That's basically where we stand now. I'll post some more info about the changes I'm working on shortly.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/02/background-info.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/5839269518036409198'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/5839269518036409198'></link><author><name>James</name><uri>http://jamessocol.com/</uri></author></entry><entry><id>tag:blogger.com,1999:blog-6259484853198426929.post-5136928664861293224</id><published>2007-02-10T15:26:00.000-08:00</published><updated>2007-02-10T15:26:38.347-08:00</updated><title type='text'>Technical Blog</title><content type='html'>As the lead developer (&lt;span style="font-style: italic;"&gt;only developer&lt;/span&gt; would be more accurate) of the &lt;a href="http://confucius.msu.edu/"&gt;Confucius Institute&lt;/a&gt; at &lt;a href="http://www.msu.edu/"&gt;Michigan State University&lt;/a&gt;'s &lt;a href="http://msuconfuciusinstitute.org/scheduler/"&gt;Online Tutoring System&lt;/a&gt;, I've decided to keep two blogs related to the project. The first is meant for &lt;a href="http://msuconfuciusinstitute.org/scheduler/blog/"&gt;end-users&lt;/a&gt;, and is just a review of how features are changing. This blog, however, will be a more in-depth, technically oriented review of changes, problems, and solutions.&lt;br /&gt;&lt;br /&gt;I'm providing this for those who are interested in the technical side of things, for any developers--veterans or newbies--who want to comment/ask questions, and also as a record of the development of the OTS.&lt;br /&gt;&lt;br /&gt;Enjoy, I have a few background posts to fill in right away.</content><link rel='alternate' type='text/html' href='http://msuconfuciusinstitute.org/scheduler/techblog/2007/02/technical-blog.html'></link><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/5136928664861293224'></link><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6259484853198426929/posts/default/5136928664861293224'></link><author><name>James</name><uri>http://jamessocol.com/</uri></author></entry></feed>