diff options
Diffstat (limited to 'paste/webkit/FakeWebware/TaskKit')
18 files changed, 0 insertions, 1661 deletions
diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/GenIndex.css b/paste/webkit/FakeWebware/TaskKit/Docs/GenIndex.css deleted file mode 100644 index a95df2f..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/GenIndex.css +++ /dev/null @@ -1,46 +0,0 @@ -<style type="text/css"> -<!-- - /** - This style sheet is linked to by both Webware's index.html - as well as each component's index.html. - */ - - p { - padding-left: 0; - } - dl { - padding-left: 0; - } - ol { - padding-left: 0; - } - ul { - list-style-type: disc; - padding-left: 0; - } - li { - padding-top: 0; - } - a.BigLink { - font-size: larger; - font-weight: bold; - } - td.InfoLabel { - font-family: Arial, Helvetica, sans-serif; - background-color: #DDD; - } - td.InfoValue { - font-family: Arial, Helvetica, sans-serif; - background-color: #EEE; - } - td.InfoSummary { - font-family: Arial, Helvetica, sans-serif; - font-size: smaller; - background-color: #EEE; - } - td.DocList { - font-family: Arial, Helvetica, sans-serif; - } - ---> -</style> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/QuickStart.html b/paste/webkit/FakeWebware/TaskKit/Docs/QuickStart.html deleted file mode 100644 index 97e81b8..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/QuickStart.html +++ /dev/null @@ -1,408 +0,0 @@ -<HTML> -<HEAD> -<TITLE>TaskKit QuickStart</TITLE> -</HEAD> - -<BODY BGCOLOR="WHITE"> - -<H4>Tom's Webware Documentation</H4> -<H1>Scheduling with Python and Webware</H1> -<a href="mailto:Tom.Schwaller@linux-community.de" style="text-decoration: none; color : #009999;">Tom Schwaller</a> - -<P> -<HR NOSHADE> -<I><FONT COLOR="#0000ff"> -Since version 0.5 the web application framework Webware has a scheduling plug-in called TaskKit. -This QuickStart Guide describes how to use it in your daily work with Webware and also with -normal Python programs. -</FONT></I> -<HR NOSHADE> - -<P> -Scheduling periodic tasks is a very common activity for users of a modern operating system. -System administrators for example know very well how to start new <code>cron</code> jobs or the -corresponding Windows analogues. So, why does a web application server like Webware/WebKit -need its own scheduling framework. The answer is simple: Because it knows better how to -react to a failed job, has access to internal data structures, which otherwise would have -to be exposed to the outside world and last but not least it needs scheduling capabilities -anyway (e.g. for session sweeping and other memory cleaning operations). - -<P> -Webware is developped with the object oriented scripting language Python so it seemed natural -to write a general purpose Python based scheduling framework. One could think that this -problem is already solved (remember the Python slogan: batteries included), but strange -enough there has not much work been done in this area. The two standard Python modules -<code>sched.py</code> and <code>bisect.py</code> are way too simple, not really object oriented -and also not multithreaded. This was the reason to develop a new scheduling framework, which -can not only be used with Webware but also with general purpose Python programs. Unfortunately -scheduling has an annoying side effect. The more you delve into the subject the more it becomes -difficult. - -<P> -After some test implementations I discovered the Java scheduling framework of the -<a href="http://www.arlut.utexas.edu/gash2/">Ganymede</a> network directory management -system and took it as a model for the Python implementation. Like any other Webware Kit -or plug-in the TaskKit is self contained and can be used in other Python projects. -This modularity is one of the real strengths of Webware and in sharp contrast to Zope -where people tend to think in Zope and not in Python terms. In a perfect world one should -be able to use web wrappers (for Zope, Webware, Quixote,..) around clearly designed Python -classes and not be forced to use one framework. Time will tell if this is just a dream -or if people will reinvent the "python wheels" over and over again. - -<h2>Tasks</h2> - -<P> -The TaskKit implements the three classes <code>Scheduler, TaskHandler</code> and <code>Task</code>. -Let's begin with the simplest one, i.e. Task. It's an abstract base class, from which you -have to derive your own task classes by overriding the <code>run()</code>-method like in -the following example: - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<pre> -<FONT COLOR=black><B>from</B></FONT> TaskKit.Task <FONT COLOR=black><B>import</B></FONT> Task -<FONT COLOR=black><B>from</B></FONT> time <FONT COLOR=black><B>import</B></FONT> time, strftime, localtime - -<FONT COLOR=black><B>class</B></FONT><A NAME="SimpleTask"><FONT COLOR=#AA00AA><B> SimpleTask</B></FONT></A>(Task): - <FONT COLOR=black><B>def</B></FONT><A NAME="run"><FONT COLOR=#AA00AA><B> run</B></FONT></A>(self): - <FONT COLOR=black><B>print</B></FONT> self.name(), strftime(<FONT COLOR=#FF0000>"%H:%M:%S"</FONT>, localtime(time())) -</pre> -</td></tr></table> - -<p> -<code>self.name()</code> returns the name under which the task was registered by the scheduler. -It is unique among all tasks and scheduling tasks with the same name will delete the old -task with that name (so beware of that feature!). Another simple example which is used -by WebKit itself is found in <code>WebKit/Tasks/SessionTask.py</code>. - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<pre> -<FONT COLOR=black><B>from</B></FONT> TaskKit.Task <FONT COLOR=black><B>import</B></FONT> Task - -<FONT COLOR=black><B>class</B></FONT><A NAME="SessionTask"><FONT COLOR=#AA00AA><B> SessionTask</B></FONT></A>(Task): - <FONT COLOR=black><B>def</B></FONT><A NAME="__init__"><FONT COLOR=#AA00AA><B> __init__</B></FONT></A>(self, sessions): - Task.__init__(self) - self._sessionstore = sessions - - <FONT COLOR=black><B>def</B></FONT><A NAME="run"><FONT COLOR=#AA00AA><B> run</B></FONT></A>(self): - <FONT COLOR=black><B>if</B></FONT> self.proceed(): - self._sessionstore.cleanStaleSessions(self) -</pre> -</td></tr></table> - -<p> -Here you see the <code>proceed()</code> method in action. It can be used by long running tasks -to check if they should terminate. This is the case when the scheduler or the task itself has been -stoped. The latter is achieved with a <code>stopTask()</code> call which is not recommented though. -It's generally better to let the task finish and use the <code>unregister()</code> and -<code>disable()</code> methods. The first really deletes the task after termination while -the second only disables its rescheduling. You can still use it afterwards. Right now the implementation -of <code>proceed()</code> - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<pre> -<FONT COLOR=black><B>def</B></FONT><A NAME="proceed"><FONT COLOR=#AA00AA><B> proceed</B></FONT></A>(self): - <FONT COLOR=#FF0000>""" - Should this task continue running? Should be called periodically - by long tasks to check if the system wants them to exit. - Returns 1 if its OK to continue, 0 if it's time to quit. - """</FONT> - <FONT COLOR=black><B>return</B></FONT> <FONT COLOR=black><B>not</B></FONT>( self._close.isSet() <FONT COLOR=black><B>or</B></FONT> (<FONT COLOR=black><B>not</B></FONT> self._handle._isRunning) ) -</pre> -</td></tr></table> - -<P> -uses the <code>_close</code> Event variable, which was also available trough the <code>close()</code> method. -Don't count on that in future versions, it will probably be removed. Just use <code>proceed()</code> instead -(take a look at <code>TaskKit/Tests/BasicTest.py</code>). Another API change after version 0.5 of Webware was -the removal of the <code>close</code> variable in <code>run()</code>. If you plan to make serious use of TaskKit -it's better to take the newest CVS snapshot of Webware, otherwise you will have to delete all occurences of -<code>close</code> afterwards. Another thing to remember about tasks is, that they know nothing about -scheduling, how often they will run (periodically or just once) or if they are on hold. All this is managed -by the task wrapper class <code>TaskManager</code>, which will be discussed shortly. Let's look at some more -examples first. - -<h2>Generating static pages</h2> - -<P> -On a high trafic web site (a la <a href="http://slashdot.org">slashdot</a>) it's -common practice to use semistatic page generation techniques. For example -you can generate the entry page as a static page once per minute. During this time -the content will not be completely accurate (e.g. the number of comments will certainly -increase), but nobody really cares about that. The benefit is a dramatic reduction of -database requests. For other pages (like older news with comments attached) it makes -more sense to generate static versions on demand. This is the case when the discussion -has come to an end, but somebody adds a comment afterwards and implicitely changes the -page by this action. Generating a static version will happen very seldom after the -"hot phase" when getting data directly out of the database is more appropriate. So -you need a periodic task which checks if there are new "dead" stories (e.g. no comments -for 2 days) and marks them with a flag for static generation on demand. It should -be clear by now, that an integrated Webware scheduling mechnism is very useful for -this kind of things and the better approach than external <code>cron</code> jobs. -Let's look a litle bit closer at the static generation technique now. First of all we -need a <code>PageGenerator</code> class. To keep the example simple we just -write the actual date into a file. In real life you will assemble much more complex data -into such static pages. - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<pre> -<FONT COLOR=black><B>from</B></FONT> TaskKit.Task <FONT COLOR=black><B>import</B></FONT> Task -<FONT COLOR=black><B>from</B></FONT> time <FONT COLOR=black><B>import</B></FONT> * - -html = <FONT COLOR=#FF0000>'''<html> -<head><title>%s</title></head> -<body bgcolor="white"> -<h1>%s</h1> -</body> -</html> -'''</FONT> - -<FONT COLOR=black><B>class</B></FONT><A NAME="PageGenerator"><FONT COLOR=#AA00AA><B> PageGenerator</B></FONT></A>(Task): - <FONT COLOR=black><B>def</B></FONT><A NAME="__init__"><FONT COLOR=#AA00AA><B> __init__</B></FONT></A>(self, filename): - Task.__init__(self) - self._filename = filename - - <FONT COLOR=black><B>def</B></FONT><A NAME="run"><FONT COLOR=#AA00AA><B> run</B></FONT></A>(self): - f = open(self._filename, <FONT COLOR=#FF0000>'w'</FONT>) - now = asctime(localtime(time())) - f.write( html % (<FONT COLOR=#FF0000>'Static Page'</FONT>, now) ) - f.close() -</pre> -</td></tr></table> - -<h2>Scheduling</h2> - -<P> -That was easy. Now it's time to schedule our task. In the following example you can see how this is -accomplished with TaskKit. As a general recommendation you should put all your tasks in a -separate folder (with an empty <code>__init__.py</code> file to make this folder a Python -package). First of all we create a new <code>Scheduler</code> object, start it as a thread and add -a periodic page generation object (of type <code>PageGenerator</code>) with the -<code>addPeriodicAction</code> method (this will probably be changed in the near future to -the more constitent name <code>addPeriodicTask</code>). The first parameter here is the first -execution time (which can be in the future), the second is the period (in seconds), the third an instance -of our task class and the last parameter is a unique task name which allows us to find the task -later on (e.g. if we want to change the period or put the task on hold). - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<PRE> -<FONT COLOR=black><B>from</B></FONT> TaskKit.Scheduler <FONT COLOR=black><B>import</B></FONT> Scheduler -<FONT COLOR=black><B>from</B></FONT> Tasks.PageGenerator <FONT COLOR=black><B>import</B></FONT> PageGenerator -<FONT COLOR=black><B>from</B></FONT> time <FONT COLOR=black><B>import</B></FONT> * - -<FONT COLOR=black><B>def</B></FONT><A NAME="main"><FONT COLOR=#AA00AA><B> main</B></FONT></A>(): - scheduler = Scheduler() - scheduler.start() - scheduler.addPeriodicAction(time(), 5, PageGenerator(<FONT COLOR=#FF0000>'static.html'</FONT>), <FONT COLOR=#FF0000>'PageGenerator'</FONT>) - sleep(20) - scheduler.stop() - -<FONT COLOR=black><B>if</B></FONT> __name__==<FONT COLOR=#FF0000>'__main__'</FONT>: - main() -</PRE> -</td></tr></table> - -<P> -When you fire up this example you will notice that the timing is not 100% accurate. The reason for this -seems to be an imprecise <code>wait()</code> function in the Python <code>threading</code> module. -Unfortunately this method in indispensible because we need to be able to wake up a sleeping scheduler when -scheduling new tasks with first execution times smaller than <code>scheduler.nextTime()</code>. This is -achieved through the <code>notify()</code> method, which sets the <code>notifyEvent</code> -(<code>scheduler._notifyEvent.set()</code>). On Unix we could use <code>sleep</code> and a <code>signal</code> -to interrupt this system call, but TaskKit has to be plattform independant to be of any use. But don't worry, -this impreciseness is not important for normal usage, because we are talking about scheduling in the minute -(not second) range here. Unix <code>cron</code> jobs have a granularity of one minute, which is a good value -for TaskKit too. Of course nobody can stop you starting tasks with a period of one second (but you have been -warned that this is not a good idea, except for testing purposes). - -<h2>Generating static pages again</h2> - -<P> -Let's refine our example a little bit and plug it into Webware. We will write a Python servlet which loks like this: - -<P> -<center> -<form method="post"> -<input type=submit name=_action_ value=Generate> -<input type=text name=filename value="static.html" size=20> every -<input type=text name=seconds value=60 size=5> seconds</form> - -<table width=50% border=1 cellspacing=0> -<tr bgcolor=00008B><th colspan=2><font color=white>Task List</font></th></tr> -<tr bgcolor=#dddddd><td><b>Task Name</b></td><td><b>Period</b></td></tr> -<tr><td>SessionSweeper</td><td>360</td></tr> -<tr><td>PageGenerator for static3.html</td><td>30</td></tr> -<tr><td>PageGenerator for static1.html</td><td>60</td></tr> -<tr><td>PageGenerator for static2.html</td><td>120</td></tr> -</table> -</center> - -<P> -When you click on the <code>Generate</code> button a new periodic <code>PageGenerator</code> task -will be added to the Webware scheduler. Remember that this will generate a static page <code>static.html</code> -every 60 seconds (if you use the default values). The new task name is <code>"PageGenerator for filename"</code>, -so you can use this servlet to change the settings of already scheduled tasks (by rescheduling) or -add new <code>PageGenerator</code> tasks with different filenames. This is quite useless here, but as -soon as you begin to parametrize your <code>Task</code> classes this approach can become quite powerful -(consider for example a mail reminder form or collecting news from different news channels as periodic tasks -with user defined parameters). In any case, don't be shy and contribute other interesting examples -(the sky's the limit!). - -<P> -Finally we come to the servlet code, which should be more or less self explanatory, except for the -<code>_action_</code> construct which is very well explained in the Webware documentation though (just -in case you forgot that). <code>app.taskManager()</code> gives you the WebKit scheduler, which can be -used to add new tasks. In real life you will have to make the scheduling information persistent -and reschedule all tasks after a WebKit restart because it would be quite annoying to enter this -data again and again. <code>PersistantScheduler</code> is a class which is on the ToDo list for the -next TaskKit version and will probably be implemented with the new MiddleKit from Chuck Esterbrook. -MiddleKit is a new object relational mapping framework for Python and greatly simplyfies this -kind of developments. You'll certainly read more about it in the future. - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<PRE> -<FONT COLOR=black><B>import</B></FONT> os, string, time -<FONT COLOR=black><B>from</B></FONT> ExamplePage <FONT COLOR=black><B>import</B></FONT> ExamplePage -<FONT COLOR=black><B>from</B></FONT> Tasks.PageGenerator <FONT COLOR=black><B>import</B></FONT> PageGenerator - -<FONT COLOR=black><B>class</B></FONT><A NAME="Schedule"><FONT COLOR=#AA00AA><B> Schedule</B></FONT></A>(ExamplePage): - - <FONT COLOR=black><B>def</B></FONT><A NAME="writeContent"><FONT COLOR=#AA00AA><B> writeContent</B></FONT></A>(self): - wr = self.write - wr(<FONT COLOR=#FF0000>'<center><form method="post">'</FONT>) - wr(<FONT COLOR=#FF0000>'<input type=submit name=_action_ value=Generate> '</FONT>) - wr(<FONT COLOR=#FF0000>'<input type=text name=filename value="static.html" size=20> every '</FONT>) - wr(<FONT COLOR=#FF0000>'<input type=text name=seconds value=60 size=5> seconds'</FONT>) - wr(<FONT COLOR=#FF0000>'</form>'</FONT>) - wr(<FONT COLOR=#FF0000>'<table width=50% border=1 cellspacing=0>'</FONT>) - wr(<FONT COLOR=#FF0000>'<tr bgcolor=00008B><th colspan=2><font color=white>Task List</font></th></tr>'</FONT>) - wr(<FONT COLOR=#FF0000>'<tr bgcolor=#dddddd><td><b>Task Name</b></td><td><b>Period</b></td></tr>'</FONT>) - <FONT COLOR=black><B>for</B></FONT> taskname, handler <FONT COLOR=black><B>in</B></FONT> self.application().taskManager().scheduledTasks().items(): - wr(<FONT COLOR=#FF0000>'<tr><td>%s</td><td>%s</td></tr>'</FONT> % (taskname, handler.period())) - wr(<FONT COLOR=#FF0000>'</table></center>'</FONT>) - - <FONT COLOR=black><B>def</B></FONT><A NAME="generate"><FONT COLOR=#AA00AA><B> generate</B></FONT></A>(self, trans): - app = self.application() - tm = app.taskManager() - req = self.request() - <FONT COLOR=black><B>if</B></FONT> req.hasField(<FONT COLOR=#FF0000>'filename'</FONT>) <FONT COLOR=black><B>and</B></FONT> req.hasField(<FONT COLOR=#FF0000>'seconds'</FONT>): - self._filename = req.field(<FONT COLOR=#FF0000>'filename'</FONT>) - self._seconds = string.atoi(req.field(<FONT COLOR=#FF0000>'seconds'</FONT>)) - task = PageGenerator(app.serverSidePath(<FONT COLOR=#FF0000>'Examples/'</FONT> + self._filename)) - taskname = <FONT COLOR=#FF0000>'PageGenerator for '</FONT> + self._filename - tm.addPeriodicAction(time.time(), self._seconds, task, taskname) - self.writeBody() - - <FONT COLOR=black><B>def</B></FONT><A NAME="methodNameForAction"><FONT COLOR=#AA00AA><B> methodNameForAction</B></FONT></A>(self, name): - <FONT COLOR=black><B>return</B></FONT> string.lower(name) - - <FONT COLOR=black><B>def</B></FONT><A NAME="actions"><FONT COLOR=#AA00AA><B> actions</B></FONT></A>(self): - <FONT COLOR=black><B>return</B></FONT> ExamplePage.actions(self) + [<FONT COLOR=#FF0000>'generate'</FONT>] -</PRE> -</td></tr></table> - -<p> -<h2>The Scheduler</h2> - -<P> -Now it's time to take a closer look at the <code>Scheduler</code> class itself. As you have seen in the examples above, -writing tasks is only a matter of overloading the <code>run()</code> method in a derived class and adding it to the -scheduler with <code>addTimedAction, addActionOnDemand, addDailyAction</code> or <code>addPeriodicAction</code>. -The scheduler will wrap the Task in a <code>TaskHandler</code> structure which knows all the scheduling details -and add it to its <code>_scheduled</code> or <code>_onDemand</code> dictionaries. The latter is populated by -<code>addActionOnDemand</code> and contains tasks which can be called any time by -<code>scheduler.runTaskNow('taskname')</code> as you can see in the following example. After that -the task has gone. - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<PRE> -scheduler = Scheduler() -scheduler.start() -scheduler.addActionOnDemand(SimpleTask(), <FONT COLOR=#FF0000>'SimpleTask'</FONT>) -sleep(5) -<FONT COLOR=black><B>print</B></FONT> <FONT COLOR=#FF0000>"Demanding SimpleTask"</FONT> -scheduler.runTaskNow(<FONT COLOR=#FF0000>'SimpleTask'</FONT>) -sleep(5) -scheduler.stop() -</PRE> -</td></tr></table> - -<p> -If you need a task more than one time it's better to start it regularly with one of -the <code>add*Action</code> methods first. It will be added to the <code>_scheduled</code> -dictionary. If you do not need the task for a certain time disable it with -<code>scheduler.disableTask('taskname')</code> and enable it later with -<code>scheduler.enableTask('taskname')</code>. There are some more methods -(e.g. <code>demandTask(), stopTask(), ...</code>) in the <code>Scheduler</code> class -which are all documented by doc strings. Take a look at them and write your own examples -to understand the methods (and maybe find bugs ;-)). - -<P> -When a periodic task is scheduled it is added in a wrapped version to the -<code>_scheduled</code> dictionary first. The (most of the time sleeping) scheduler thread -always knows when to wake up and start the next task whose wrapper is moved to the -<code>_runnning</code> dictionary. After completion of the task thread the handle -reschedules the task by putting it back from <code>_running</code> to <code>_scheduled</code>), -calculating the next execution time <code>nextTime</code> and possibly waking up the scheduler. -It is important to know that you can manipulate the handle while the task is running, eg. change -the period or call <code>runOnCompletion</code> to request that a task be re-run after its -current completion. For normal use you will probably not need the handles at all, but the -more you want to manipulate the task execution, the more you will appreciate the TaskHandler API. -You get all the available handles from the scheduler with the <code>running('taskname), -scheduled('taskname')</code> and <code>onDemand('taskname')</code> methods. - -<P> -In our last example which was contributed by Jay Love, who debugged, stress tested and contributed -a lot of refinements to TaskKit, you see how to write a period modifying Task. This is quite weird -but shows the power of handle manipulations. The last thing to remember is, that the scheduler does -not start a separate thread for each periodic task. It uses a thread for each task run instead and -at any time keeps the number of threads as small as possible. - -<p> -<table border=0 bgcolor="#eeeeee" width="100%"><tr><td> -<PRE> -<FONT COLOR=black><B>class</B></FONT><A NAME="SimpleTask"><FONT COLOR=#AA00AA><B> SimpleTask</B></FONT></A>(Task): - - <FONT COLOR=black><B>def</B></FONT><A NAME="run"><FONT COLOR=#AA00AA><B> run</B></FONT></A>(self): - <FONT COLOR=black><B>if</B></FONT> self.proceed(): - <FONT COLOR=black><B>print</B></FONT> self.name(), time() - <B>print</b> "Increasing period" - self.handle().setPeriod(self.handle().period()+2) - <FONT COLOR=black><B>else</B></FONT>: - <FONT COLOR=black><B>print</B></FONT> <FONT COLOR=#FF0000>"Should not proceed"</FONT>, self.name() -</PRE> -</td></tr></table> - -<p> -As you can see the TaskKit framework is quite sophisticated and will hopefully be used by many people -from the Python community. If you have further question, please feel free to ask them on the Webware -mailing list. (last changes: 2. March 2001) - -<P> -<TABLE BORDER=1 CELLSPACING=0 CELLPADDING=0 WIDTH="100%"> -<TR ALIGN=CENTER BGCOLOR="#DFEFFF"> -<TD ALIGN=CENTER><FONT SIZE=+2>Info</FONT> -</TD> -</TR> -<TR ALIGN=LEFT VALIGN=TOP> -<TD> -<BR> -[1] Webware: <a href="http://webware.sourceforge.net/">http://webware.sourceforge.net/</a> -<br> -[2] Ganymede: <a href="http://www.arlut.utexas.edu/gash2/">http://www.arlut.utexas.edu/gash2/</a> -<br> -</TD> -</TR> -</TABLE> - -<P> -Published under the <a href="http://www.gnu.org/copyleft/fdl.html">GNU Free Documentation License</a>. - -</BODY> -</HTML> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.1.1.html b/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.1.1.html deleted file mode 100644 index f6c71a8..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.1.1.html +++ /dev/null @@ -1,28 +0,0 @@ -<html> - -<head> - <link rel=stylesheet href=StyleSheet.css type=text/css> - <title>TaskKit 0.1.1 Release Notes</title> -</head> - -<body> - -<h1>TaskKit 0.1.1 Release Notes</h1> - - -<a name=ReleaseNotes><h2>Release Notes</h2></a> - -<ul> - <li> Version 0.1.1 was released on 3/@@/2001. -</ul> - -<p> This release is mainly a cleanup of some aspects of the code. The following changes affect the external interface. -<ul> -<li> Removed the <code>close</code> parameter from TaskKit.run(). This parameter was unnecessary. To check if the task should exit, call Task.proceed(), where a non-zero return value indicates that the task should proceed. - -<li> Various other cleanups. None affecting the core functionality. -</ul> - - -</body> -</html> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.7.html b/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.7.html deleted file mode 100644 index 0a91680..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.7.html +++ /dev/null @@ -1,24 +0,0 @@ -<html> - -<head> - <link rel=stylesheet href=StyleSheet.css type=text/css> - <title>TaskKit 0.7 Release Notes</title> -</head> - -<body> - -<h1>TaskKit 0.7 Release Notes</h1> - - -<a name=ReleaseNotes><h2>Release Notes</h2></a> - -<a name=Changes><h2>Changes</h2></a> -<ul> - <li> New versioning strategy: all Webware components will now have their version numbers updated in lock-step. -</ul> - - -<p><hr> - -</body> -</html> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.8.html b/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.8.html deleted file mode 100644 index 5ed9271..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-0.8.html +++ /dev/null @@ -1,24 +0,0 @@ -<html> - -<head> - <link rel=stylesheet href=StyleSheet.css type=text/css> - <title>TaskKit 0.8 Release Notes</title> -</head> - -<body> - -<h1>TaskKit 0.8 Release Notes</h1> - - -<a name=ReleaseNotes><h2>Release Notes</h2></a> - -<a name=Changes><h2>Changes</h2></a> -<ul> - <li> New versioning strategy: all Webware components will now have their version numbers updated in lock-step. -</ul> - - -<p><hr> - -</body> -</html> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-X.Y.html b/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-X.Y.html deleted file mode 100644 index 9b13c30..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/RelNotes-X.Y.html +++ /dev/null @@ -1,75 +0,0 @@ -<html> - -<head> - <link rel=stylesheet href=StyleSheet.css type=text/css> - <style type=text/css> - <!-- - li { padding-bottom: 0.75em; - } - --> - </style> - - <!-- - Auto versioning is handled by Webware/bin/setversion.py. - This will automatically update version and release date - information embedded within HTML comment tags. - - Note however that comment tags within a title block seem to - not be interpreted as comments in Mozilla 1.2.1 - --> - <title>CGIWrapper Release Notes</title> -</head> - -<body> - -<h1>CGIWrapper Release Notes</h1> -Version <!-- version --> X.Y <!-- /version --> <br> -Webware for Python <!-- version --> X.Y <!-- /version --> -Released on <!-- relDate --> @@/@@/@@ <!-- /relDate --> - - -<a name=Introduction<h2>Introduction</h2></a> -<ul> - <li> * -</ul> - -<h2>Major Changes</h2> -<ul> - <li> * -</ul> - - -<h2>New Features</h2> -<ul> - <li> * -</ul> - - -<h2>Improvements and Refinements</h2> -<ul> - <li> * -</ul> - - -<h2>Security</h2> -<ul> - <li> * -</ul> - - -<h2>Minor API Changes</h2> -<ul> - <li> * -</ul> - - -<h2>Bugfixes</h2> -<ul> - <li> * -</ul> - - -<p><hr> - -</body> -</html> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/StyleSheet.css b/paste/webkit/FakeWebware/TaskKit/Docs/StyleSheet.css deleted file mode 100644 index db08e4f..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/StyleSheet.css +++ /dev/null @@ -1,88 +0,0 @@ -<style type="text/css"> -<!-- - h1 { font-family: Tahoma, Arial, Helvetica, sans-serif; - font-size: 18pt; - padding-top: 0; - padding-bottom: 0; - } - h2 { font-family: Arial, Helvetica, sans-serif; - font-size: 12pt; - color: darkblue; - padding-top: 1em; - padding-bottom: 0; - } - h3 { font-family: Arial, Helvetica, sans-serif; - font-size: 11pt; - padding-top: 1em; - padding-bottom: 0; - } - h4 { font-family: Arial, Helvetica, sans-serif; - font-size: 10pt; - padding-top: 1em; - padding-bottom: 0; - } - p { padding-left: 2em; - color: black; - } - dl { padding-left: 2em; - } - ol { padding-left: 0.5em; - } - ul { list-style-type: disc; - padding-left: 0.5em; - } - li { padding-top: 0em; - } - code{ color: darkblue; - } - body{ background-color: #FFFFFF; - } - - .TitleBar { - font-family: Tahoma, Arial, Helvetica, sans-serif; - font-size: 18pt; - padding-top: 0.5ex; - padding-bottom: 0.5ex; - color: white; - background-color: darkblue; - } - .Footer { - font-family: Arial, Helvetica, sans-serif; - font-size: smaller; - } - .ToC { - font-family: Arial, Verdana, Tahoma, Helvetica, sans-serif; - font-size: smaller; - } - span.name { - font-weight: bold; - } - span.filename { - font-family: Verdana, Tahoma, Arial, Helvetica, sans-serif; - font-size: smaller; - } - pre.py { - color: darkblue; - background-color: #EEE; - padding-left: 2.5em; - } - span.typed { - font-weight: bold; - } - - /*** Configuration documentation ***/ - - dl.config { - } - dt.config { - } - dd.config { - } - span.setting { - font-family: Verdana, Tahoma, Arial, Helvetica, sans-serif; - font-size: smaller; - font-weight: bolder; - } - ---> -</style> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/TODO-TaskKit.text b/paste/webkit/FakeWebware/TaskKit/Docs/TODO-TaskKit.text deleted file mode 100644 index 2e5acd0..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/TODO-TaskKit.text +++ /dev/null @@ -1,43 +0,0 @@ -TaskKit -Webware for Python -TO DO - - -<misc> -<tests> -<docs> - - -<misc> - - [ ] Test WebKit with the new changes - - [ ] Task.proceed() questionable name. run() runs and proceed() proceeds, er, no, it inquires? Maybe shouldProceed()? - - [ ] Does a Task's run() really always have to invoke self.proceed()? - -</misc> - - -<tests> - - [ ] make tests that cover all methods and features - -</tests> - - - -<docs> - - [ ] Put this somewhere: - # Based on code from Jonathan Abbey, jonabbey@arlut.utexas.edu - # from the Ganymede Directory Management System - # Python port and enhancements by Tom.Schwaller@linux-community.de - - [ ] Doc strings for all the major methods. - - [ ] User's Guide - - [ ] Properties: Better synopsis - -</docs> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/UsersGuide.html b/paste/webkit/FakeWebware/TaskKit/Docs/UsersGuide.html deleted file mode 100644 index 017c470..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/UsersGuide.html +++ /dev/null @@ -1,54 +0,0 @@ -<html> - -<head> - <link rel=stylesheet href=StyleSheet.css type=text/css> - <title>TaskKit User's Guide</title> -</head> - -<body> - -<h1>TaskKit User's Guide</h1> -Version <!-- version --> X.Y <!-- /version --> -<br>Webware for Python <!-- version --> X.Y <!-- /version --> - - -<!-- -<a name=TOC><h2>Table of Contents</h2></a> - -<p> @@ TO DO ---> - - -<a name=Synopsis><h2>Synopsis</h2></a> - -<p> TaskKit provides a framework for the scheduling and management of tasks which can be triggered periodically or at specific times. Tasks can also be forced to execute immediately, set on hold or rescheduled with a different period (even dynamically). - - -<a name=Feedback><h2>Feedback</h2></a> - -<p> <p> You can e-mail <a href=mailto:webware-discuss@lists.sourceforge.net>webware-discuss@lists.sourceforge.net</a> to give feedback, discuss features and get help using TaskKit. - - -<a name=Introduction><h2>Introduction</h2></a> - -<a name=Overview><h3>Overview</h3></a> - -<p> Task Kit is brand new and does not have a real User's Guide yet. However, there are doc strings in the source code. Also, if you search WebKit for "task" you will find a real world use of this kit. - -<p> <b>The development status of TaskKit is <i>alpha</i>.</b> You can expect API and usage changes in the next version. If you use TaskKit, we highly recommend that you stay in sync with the latest in-development Webware via <a href=https://sourceforge.net/cvs/?group_id=4866>CVS</a>. You should then re-read the latest docs, including this User's Guide and the <a href=TODO-TaskKit.text>TO DO list</a>. - - -<a name=KnownBugs><h2>Known Bugs</h2></a> - -<p> Known bugs and future work in general, are documented in <a href=TODO-TaskKit.text>TO DO</a>. - - -<a name=Credit><h2>Credit</h2></a> - -<p> Authors: Tom Schwaller, Jay Love - - -<p><hr> - -</body> -</html> diff --git a/paste/webkit/FakeWebware/TaskKit/Docs/index.html b/paste/webkit/FakeWebware/TaskKit/Docs/index.html deleted file mode 100644 index bb8da07..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Docs/index.html +++ /dev/null @@ -1,94 +0,0 @@ -<html> -<head> - <title>TaskKit Documentation</title> - <link rel=stylesheet href=StyleSheet.css type=text/css> - <link rel=stylesheet href=GenIndex.css type=text/css> -</head> - -<body> - -<table border=0 align=center width=100%> - <tr> - <td align=center class=TitleBar>TaskKit Documentation</td> - </tr> -</table> -<br> - -<p> -<table align=center border=0 cellpadding=2 cellspacing=2> - -<tr> <td nowrap class=InfoLabel> Name: </td> <td nowrap class=InfoValue> <b>TaskKit</b> </td> - <td valign=top class=InfoLabel> Summary: </td> </tr> -<tr> <td nowrap class=InfoLabel> Version: </td> <td nowrap class=InfoValue> X.Y </td> - <td rowspan=4 valign=top class=InfoSummary> TaskKit provides a framework for the scheduling and management of tasks which can be triggered periodically or at specific times. </td> </tr> -<tr> <td nowrap class=InfoLabel> Status: </td> <td nowrap class=InfoValue> beta </td> </tr> -<tr> <td nowrap class=InfoLabel> Py ver: </td> <td nowrap class=InfoValue> 2.0 </td> </tr> -<tr> <td nowrap class=InfoLabel> Webware: </td> <td nowrap class=InfoValue> X.Y </td> </tr> - -</table> - -<p> - -<table align=center border=0 cellpadding=2 cellspacing=2> - -<tr> - <td nowrap class=InfoLabel> Manuals: </td> - <td nowrap class=InfoLabel> Source: </td> - <td nowrap class=InfoLabel> Release Notes: </td> -</tr> - -<tr> - <td nowrap valign=top class=InfoValue> <a href=QuickStart.html>Quick Start</a> <br> -<a href=UsersGuide.html>User's Guide</a> <br> -<a href=TODO-TaskKit.text>To Do</a> <br> - </td> - <td nowrap valign=top class=InfoValue> - <a href=Source/ClassHier.html class=DocLink>Class hierarchy</a> <br> - <a href=Source/ClassList.html class=DocLink>Class list</a> - </td> - <td nowrap valign=top class=InfoValue> <a href=RelNotes-X.Y.html>X.Y</a> <br> -<a href=RelNotes-0.8.html>0.8</a> <br> -<a href=RelNotes-0.7.html>0.7</a> <br> -<a href=RelNotes-0.1.1.html>0.1.1</a> <br> - </td> -</tr> - -</table> - - -<!-- -<table align=center border=0 cellpadding=4 cellspacing=4> -<tr> - -<td nowrap valign=top class=DocList> -Manuals -<a href=QuickStart.html>Quick Start</a> <br> -<a href=UsersGuide.html>User's Guide</a> <br> -<a href=TODO-TaskKit.text>To Do</a> <br> - -</td> - -<td nowrap valign=top class=DocList> -Source -<br> <a href=Source/ClassHier.html class=DocLink>Class hierarchy</a> -<br> <a href=Source/ClassList.html class=DocLink>Class list</a> -</td> - -<td nowrap valign=top class=DocList> -Release Notes -<a href=RelNotes-X.Y.html>X.Y</a> <br> -<a href=RelNotes-0.8.html>0.8</a> <br> -<a href=RelNotes-0.7.html>0.7</a> <br> -<a href=RelNotes-0.1.1.html>0.1.1</a> <br> - -</td> -</table> - -</td></tr></table> ---> -<hr> -<span class=Footer> -Webware: <a href=http://webware.sourceforge.net>Home</a> <a href=http://sourceforge.net/projects/webware>@ SourceForge</a> -</span> -</body> -</html> diff --git a/paste/webkit/FakeWebware/TaskKit/Properties.py b/paste/webkit/FakeWebware/TaskKit/Properties.py deleted file mode 100644 index 12dfc67..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Properties.py +++ /dev/null @@ -1,15 +0,0 @@ -name = 'TaskKit' - -version = ('X', 'Y', 0) - -docs = [ - {'name': "Quick Start", 'file': 'QuickStart.html'}, - {'name': "User's Guide", 'file': 'UsersGuide.html'}, - {'name': 'To Do', 'file': 'TODO-TaskKit.text'}, -] - -status = 'beta' - -requiredPyVersion = (2, 0, 0) - -synopsis = """TaskKit provides a framework for the scheduling and management of tasks which can be triggered periodically or at specific times.""" diff --git a/paste/webkit/FakeWebware/TaskKit/Scheduler.py b/paste/webkit/FakeWebware/TaskKit/Scheduler.py deleted file mode 100644 index 0e99e1f..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Scheduler.py +++ /dev/null @@ -1,473 +0,0 @@ - -""" -This is the TaskManager python package. It provides a system for running any number of -predefined tasks in separate threads in an organized and controlled manner. - -A task in this package is a class derived from the Task class. The task should have a run -method that, when called, performs some task. - -The Scheduler class is the organizing object. It manages the addition, execution, deletion, -and well being of a number of tasks. Once you have created your task class, you call the Scheduler to -get it added to the tasks to be run. - -""" - - - -from threading import Thread, Event -from TaskHandler import TaskHandler -from time import time, sleep -from exceptions import IOError - -class Scheduler(Thread): - """ - The top level class of the TaskManager system. The Scheduler is a thread that - handles organizing and running tasks. The Sheduler class should be instantiated - to start a TaskManager sessions. It's run method should be called to start the - TaskManager. It's stop method should be called to end the TaskManager session. - """ - - ## Init ## - - def __init__(self, daemon=1): - Thread.__init__(self) - self._notifyEvent = Event() - self._nextTime = None - self._scheduled = {} - self._running = {} - self._onDemand = {} - self._isRunning = 0 - if daemon: self.setDaemon(1) - - - ## Event Methods ## - - def wait(self, seconds=None): - """ - Our own version of wait. - When called, it waits for the specified number of seconds, or until it is - notified that it needs to wake up, through the notify event. - """ - try: - self._notifyEvent.wait(seconds) - except IOError, e: - pass - self._notifyEvent.clear() - - - ## Attributes ## - - def runningTasks(self): - return self._running - - def running(self, name, default=None): - """ - Returns a task with the given name from the "running" list, - if it is present there. - """ - return self._running.get(name, default) - - def hasRunning(self, name): - """ - Check to see if a task with the given name is currently running. - """ - return self._running.has_key(name) - - def setRunning(self, handle): - """ - Add a task to the running dictionary. - Used internally only. - """ - self._running[handle.name()] = handle - - def delRunning(self, name): - """ - Delete a task from the running list. - Used Internally. - """ - try: - handle = self._running[name] - del self._running[name] - return handle - except: - return None - - def scheduledTasks(self): - return self._scheduled - - def scheduled(self, name, default=None): - """ - Returns a task from the scheduled list. - """ - return self._scheduled.get(name, default) - - def hasScheduled(self, name): - """ - Is the task with he given name in the scheduled list? - """ - return self._scheduled.has_key(name) - - def setScheduled(self, handle): - """ - Add the given task to the scheduled list. - """ - self._scheduled[handle.name()] = handle - - def delScheduled(self, name): - """ - Deleted a task with the given name from the scheduled list. - """ - try: - handle = self._scheduled[name] - del self._scheduled[name] - return handle - except: - return None - - def onDemandTasks(self): - return self._onDemand - - def onDemand(self, name, default=None): - """ - Returns a task from the onDemand list. - """ - return self._onDemand.get(name, default) - - def hasOnDemand(self, name): - """ - Is the task with he given name in the onDemand list? - """ - return self._onDemand.has_key(name) - - def setOnDemand(self, handle): - """ - Add the given task to the onDemand list. - """ - self._onDemand[handle.name()] = handle - - def delOnDemand(self, name): - """ - Deleted a task with the given name from the onDemand list. - """ - try: - handle = self._onDemand[name] - del self._onDemand[name] - return handle - except: - return None - - def nextTime(self): - return self._nextTime - - def setNextTime(self, time): - self._nextTime = time - - def isRunning(self): - return self._isRunning - - - ## Adding Tasks ## - - def addTimedAction(self, time, task, name): - """ - This method is used to add an action to be run once, at a specific time. - """ - handle = self.unregisterTask(name) - if not handle: - handle = TaskHandler(self, time, 0, task, name) - else: - handle.reset(time, 0, task, 1) - self.scheduleTask(handle) - - def addActionOnDemand(self, task, name): - """ - This method is used to add a task to the scheduler that will not be scheduled - until specifically requested. - """ - handle = self.unregisterTask(name) - if not handle: - handle = TaskHandler(self, time(), 0, task, name) - else: - handle.reset(time(), 0, task, 1) - self.setOnDemand(handle) - - def addDailyAction(self, hour, minute, task, name): - """ - This method is used to add an action to be run every day at a specific time. - If a task with the given name is already registered with the scheduler, that task - will be removed from the scheduling queue and registered anew as a periodic task. - - Can we make this addCalendarAction? What if we want to run something once a week? - We probably don't need that for Webware, but this is a more generally useful module. - This could be a difficult function, though. Particularly without mxDateTime. - """ - import time - current = time.localtime(time.time()) - currHour = current[3] - currMin = current[4] - - if hour > currHour: - hourDifference = hour - currHour - if minute > currMin: - minuteDifference = minute - currMin - elif minute < currMin: - minuteDifference = 60 - currMin + minute - hourDifference -= 1 - else: - minuteDifference = 0 - elif hour < currHour: - hourDifference = 24 - currHour + hour - if minute > currMin: - minuteDifference = minute - currMin - elif minute < currMin: - minuteDifference = 60 - currMin + minute - hourDifference -= 1 - else: - minuteDifference = 0 - else: - if minute > currMin: - hourDifference = 0 - minuteDifference = minute - currMin - elif minute < currMin: - minuteDifference = 60 - currMin + minute - hourDifference = 23 - else: - hourDifference = 0 - minuteDifference = 0 - - delay = (minuteDifference + (hourDifference * 60)) * 60 - self.addPeriodicAction(time.time()+delay, 24*60*60, task, name) - - - def addPeriodicAction(self, start, period, task, name): - """ - This method is used to add an action to be run at a specific initial time, - and every period thereafter. - - The scheduler will not reschedule a task until the last scheduled instance - of the task has completed. - - If a task with the given name is already registered with the scheduler, - that task will be removed from the scheduling queue and registered - anew as a periodic task. - """ - - handle = self.unregisterTask(name) - if not handle: - handle = TaskHandler(self, start, period, task, name) - else: - handle.reset(start, period, task, 1) - self.scheduleTask(handle) - - - ## Task methods ## - - def unregisterTask(self, name): - """ - This method unregisters the named task so that it can be rescheduled with - different parameters, or simply removed. - """ - handle = None - if self.hasScheduled(name): - handle = self.delScheduled(name) - if self.hasOnDemand(name): - handle = self.delOnDemand(name) - if handle: - handle.unregister() - return handle - - def runTaskNow(self, name): - """ - This method is provided to allow a registered task to be immediately executed. - - Returns 1 if the task is either currently running or was started, or 0 if the - task could not be found in the list of currently registered tasks. - """ - if self.hasRunning(name): - return 1 - handle = self.scheduled(name) - if not handle: - handle = self.onDemand(name) - if not handle: - return 0 - self.runTask(handle) - return 1 - - def demandTask(self, name): - """ - This method is provided to allow the server to request that a task listed as being - registered on-demand be run as soon as possible. - - If the task is currently running, it will be flagged to run again as soon as the - current run completes. - - Returns 0 if the task name could not be found on the on-demand or currently running lists. - """ - if not self.hasRunning(name) and not self.hasOnDemand(name): - return 0 - else: - handle = self.running(name) - if handle: - handle.runOnCompletion() - return 1 - handle = self.onDemand(name) - if not handle: - return 0 - self.runTask(handle) - return 1 - - def stopTask(self, name): - """ - This method is provided to put an immediate halt to a running background task. - - Returns 1 if the task was either not running, or was running and was told to stop. - """ - handle = self.running(name) - if not handle: - return 0 - handle.stop() - return 1 - - - def stopAllTasks(self): - """ - Terminate all running tasks. - """ - for i in self._running.keys(): - print "Stopping ",i - self.stopTask(i) - - def disableTask(self, name): - """ - This method is provided to specify that a task be suspended. Suspended tasks will - not be scheduled until later enabled. If the task is currently running, it will - not be interfered with, but the task will not be scheduled for execution in future - until re-enabled. - - Returns 1 if the task was found and disabled. - """ - handle = self.running(name) - if not handle: - handle = self.scheduled(name) - if not handle: - return 0 - handle.disable() - return 1 - - def enableTask(self, name): - """ - This method is provided to specify that a task be re-enabled after a suspension. - A re-enabled task will be scheduled for execution according to its original schedule, - with any runtimes that would have been issued during the time the task was suspended - simply skipped. - - Returns 1 if the task was found and enabled - """ - - handle = self.running(name) - if not handle: - handle = self.scheduled(name) - if not handle: - return 0 - handle.enable() - return 1 - - def runTask(self, handle): - """ - This method is used by the Scheduler thread's main loop to put a task in - the scheduled hash onto the run hash. - """ - name = handle.name() - if self.delScheduled(name) or self.delOnDemand(name): - self.setRunning(handle) - handle.runTask() - - def scheduleTask(self, handle): - """ - This method takes a task that needs to be scheduled and adds it to the scheduler. - All scheduling additions or changes are handled by this method. This is the only - Scheduler method that can notify the run() method that it may need to wake up early - to handle a newly registered task. - """ - self.setScheduled(handle) - if not self.nextTime() or handle.startTime() < self.nextTime(): - self.setNextTime(handle.startTime()) - self.notify() - - - ## Misc Methods ## - - def notifyCompletion(self, handle): - """ - This method is used by instances of TaskHandler to let the Scheduler thread know - when their tasks have run to completion. - This method is responsible for rescheduling the task if it is a periodic task. - """ - name = handle.name() - if self.hasRunning(name): - self.delRunning(name) - if handle.startTime() and handle.startTime() > time(): - self.scheduleTask(handle) - else: - if handle.reschedule(): - self.scheduleTask(handle) - elif not handle.startTime(): - self.setOnDemand(handle) - if handle.runAgain(): - self.runTask(handle) - - def notify(self): - self._notifyEvent.set() - - def stop(self): - """ - This method terminates the scheduler and its associated tasks. - """ - self._isRunning = 0 - self.notify() - self.stopAllTasks() - self.join() # jdh: wait until the scheduler thread exits; otherwise - # it's possible for the interpreter to exit before this thread - # has a chance to shut down completely, which causes a traceback - - - ## Main Method ## - - def run(self): - """ - This method is responsible for carrying out the scheduling work of this class - on a background thread. The basic logic is to wait until the next action is due to - run, move the task from our scheduled list to our running list, and run it. Other - synchronized methods such as runTask(), scheduleTask(), and notifyCompletion(), may - be called while this method is waiting for something to happen. These methods modify - the data structures that run() uses to determine its scheduling needs. - """ - self._isRunning = 1 - while 1: - if not self._isRunning: - return - if not self.nextTime(): - self.wait() - else: - nextTime = self.nextTime() - currentTime = time() - if currentTime < nextTime: - sleepTime = nextTime - currentTime - self.wait(sleepTime) - if not self._isRunning: return - currentTime = time() - if currentTime >= nextTime: - toRun = [] - nextRun = None - for handle in self._scheduled.values(): - startTime = handle.startTime() - if startTime <= currentTime: - toRun.append(handle) - else: - if not nextRun: - nextRun = startTime - elif startTime < nextRun: - nextRun = startTime - self.setNextTime(nextRun) - for handle in toRun: - self.runTask(handle) diff --git a/paste/webkit/FakeWebware/TaskKit/Task.py b/paste/webkit/FakeWebware/TaskKit/Task.py deleted file mode 100644 index 196dedb..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Task.py +++ /dev/null @@ -1,59 +0,0 @@ -from MiscUtils import AbstractError - - -class Task: - - def __init__(self): - """ Subclasses should invoke super for this method. """ - # Nothing for now, but we might do something in the future. - pass - - def run(self): - """ - Override this method for you own tasks. Long running tasks can periodically - use the proceed() method to check if a task should stop. - """ - raise AbstractError, self.__class__ - - - ## Utility method ## - - def proceed(self): - """ - Should this task continue running? - Should be called periodically by long tasks to check if the system wants them to exit. - Returns 1 if its OK to continue, 0 if its time to quit - """ - return self._handle._isRunning - - - ## Attributes ## - - def handle(self): - """ - A task is scheduled by wrapping a handler around it. It knows - everything about the scheduling (periodicity and the like). - Under normal circumstances you should not need the handler, - but if you want to write period modifying run() methods, - it is useful to have access to the handler. Use it with care. - """ - return self._handle - - def name(self): - """ - Returns the unique name under which the task was scheduled. - """ - return self._name - - - ## Private method ## - - def _run(self, handle): - """ - This is the actual run method for the Task thread. It is a private method which - should not be overriden. - """ - self._name = handle.name() - self._handle = handle - self.run() - handle.notifyCompletion() diff --git a/paste/webkit/FakeWebware/TaskKit/TaskHandler.py b/paste/webkit/FakeWebware/TaskKit/TaskHandler.py deleted file mode 100644 index 51f5f98..0000000 --- a/paste/webkit/FakeWebware/TaskKit/TaskHandler.py +++ /dev/null @@ -1,138 +0,0 @@ - -from time import time, sleep -from threading import Event, Thread - - -class TaskHandler: - """ - While the Task class only knows what task to perform with the run()-method, - the TaskHandler has all the knowledge about the periodicity of the task. - Instances of this class are managed by the Scheduler in the - scheduled, running and onDemand dictionaries. - """ - - ## Init ## - - def __init__(self, scheduler, start, period, task, name): - self._scheduler = scheduler - self._task = task - self._name = name - self._thread = None - self._isRunning = 0 - self._suspend = 0 - self._lastTime = None - self._startTime = start - self._registerTime = time() - self._reregister = 1 - self._rerun = 0 - self._period = abs(period) - - - ## Scheduling ## - - def reset(self, start, period, task, reregister): - self._startTime = start - self._period = abs(period) - self._task = task - self._reregister = reregister - - def runTask(self): - """ - Runs this task in a background thread. - """ - if self._suspend: - self._scheduler.notifyCompletion(self) - return - self._rerun = 0 - self._thread = Thread(None, self._task._run, self.name(), (self,)) - self._isRunning = 1 - self._thread.start() - - def reschedule(self): - """ - Method to determine whether this task should be rescheduled. Increments the - startTime and returns true if this is a periodically executed task. - """ - if self._period == 0: - return 0 - else: - if self._lastTime - self._startTime > self._period: #if the time taken to run the task exceeds the period - self._startTime = self._lastTime + self._period - else: - self._startTime = self._startTime + self._period - return 1 - - def notifyCompletion(self): - self._isRunning = 0 - self._lastTime = time() - self._scheduler.notifyCompletion(self) - - - ## Attributes ## - - def isRunning(self): - return self._isRunning - - def runAgain(self): - """ - This method lets the Scheduler check to see whether this task should be - re-run when it terminates - """ - return self._rerun - - def isOnDemand(self): - """ - Returns true if this task is not scheduled for periodic execution. - """ - return self._period == 1 - - def runOnCompletion(self): - """ - Method to request that this task be re-run after its current completion. - Intended for on-demand tasks that are requested by the Scheduler while - they are already running. - """ - self._rerun = 1 - - def unregister(self): - """ - Method to request that this task not be kept after its current completion. - Used to remove a task from the scheduler - """ - self._reregister = 0 - self._rerun = 0 - - def disable(self): - """ - Method to disable future invocations of this task. - """ - self._suspend = 1 - - def enable(self): - """ - Method to enable future invocations of this task. - """ - self._suspend = 0 - - def period(self): - """ - Returns the period of this task. - """ - return self._period - - def setPeriod(self, period): - """ - Mmethod to change the period for this task. - """ - self._period = period - - def stop(self): - self._isRunning = 0 - - def name(self): - return self._name - - def startTime(self, newTime=None): - if newTime: - self._startTime = newTime - return self._startTime diff --git a/paste/webkit/FakeWebware/TaskKit/Tests/BasicTest.py b/paste/webkit/FakeWebware/TaskKit/Tests/BasicTest.py deleted file mode 100644 index 235be23..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Tests/BasicTest.py +++ /dev/null @@ -1,58 +0,0 @@ -import os, sys -sys.path.insert(1, os.path.abspath('../..')) -import TaskKit - -from TaskKit.Scheduler import Scheduler -from TaskKit.Task import Task -from time import time, sleep - - -class SimpleTask(Task): - - def run(self): - if self.proceed(): - print self.name(), time() -## print "Increasing period" -## self.handle().setPeriod(self.handle().period()+2) - else: - print "Should not proceed", self.name() - print "proceed for %s=%s, isRunning=%s" % (self.name(), self.proceed(), self._handle._isRunning) - - -class LongTask(Task): - def run(self): - while 1: - sleep(2) - print "proceed for %s=%s, isRunning=%s" % (self.name(), self.proceed(), self._handle._isRunning) - if self.proceed(): - print ">>",self.name(), time() - else: - print "Should not proceed:", self.name() - return - -def main(): - from time import localtime - scheduler = Scheduler() - scheduler.start() - scheduler.addPeriodicAction(time(), 1, SimpleTask(), 'SimpleTask1') - scheduler.addTimedAction(time()+3, SimpleTask(), 'SimpleTask2') - scheduler.addActionOnDemand(LongTask(), 'LongTask') - scheduler.addDailyAction(localtime(time())[3], localtime(time())[4]+1, SimpleTask(), "DailyTask") - sleep(5) - print "Demanding LongTask" - scheduler.runTaskNow('LongTask') - sleep(1) -# print "Stopping LongTask" -# scheduler.stopTask("LongTask") - sleep(2) -# print "Deleting 'SimpleTask1'" -# scheduler.unregisterTask("SimpleTask1") - sleep(4) - print "Calling stop" - scheduler.stop() -## sleep(2) - print "Test Complete" - - -if __name__=='__main__': - main() diff --git a/paste/webkit/FakeWebware/TaskKit/Tests/Test.py b/paste/webkit/FakeWebware/TaskKit/Tests/Test.py deleted file mode 100644 index b45d3f6..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Tests/Test.py +++ /dev/null @@ -1,30 +0,0 @@ -import os, sys -sys.path.insert(1, os.path.abspath('../..')) -import TaskKit -#from MiscUtils import unittest -import unittest - - -class TaskKitTest(unittest.TestCase): - - def setUp(self): - from TaskKit.Scheduler import Scheduler - self.scheduler = Scheduler() - - def checkBasics(self): - sched = self.scheduler - sched.start() - - def tearDown(self): - self.scheduler.stop() - self.scheduler = None - - -def makeTestSuite(): - suite1 = unittest.makeSuite(TaskKitTest, 'check') - return unittest.TestSuite((suite1,)) - - -if __name__=='__main__': - runner = unittest.TextTestRunner(stream=sys.stdout) - unittest.main(defaultTest='makeTestSuite', testRunner=runner) diff --git a/paste/webkit/FakeWebware/TaskKit/Tests/__init__.py b/paste/webkit/FakeWebware/TaskKit/Tests/__init__.py deleted file mode 100644 index 792d600..0000000 --- a/paste/webkit/FakeWebware/TaskKit/Tests/__init__.py +++ /dev/null @@ -1 +0,0 @@ -# diff --git a/paste/webkit/FakeWebware/TaskKit/__init__.py b/paste/webkit/FakeWebware/TaskKit/__init__.py deleted file mode 100644 index cffb062..0000000 --- a/paste/webkit/FakeWebware/TaskKit/__init__.py +++ /dev/null @@ -1,3 +0,0 @@ - -def InstallInWebKit(appserver): - pass |