Text Parser

Greetings Adam,

This script is excellent. I truly appreciate your continual work. A few items…

  1. start dates are item 4, not 5, as the action field is one item, not two. Also, not all lines in tasks.txt have start dates (item 4), and the script returns an error (Can’t get item 4 of {“errands”, “pickup parcel”}). Can the script simply keep going even if it does not find the item?

  2. start dates for tomorrow are appearing today in current.txt (i.e. 2/8 appears today).

  3. I have several tasks that I would like to recur either weekly or monthly. Example: if the start date for a recurring action is today, could the script change the start date in item 4 (at the end of the day or tomorrow) to one week from today, so that it would would be excluded from current.txt until next Wednesday? Perhaps a symbol could indicate whether it was a weekly or monthly recurring task? Perhaps *2/7 for a weekly recurring task and ^2/7 for a monthly recurring task?

4.Is it possible just to search a few letters of a term, rather than the full word? I.e. ‘int’ rather than ‘internet’?

  1. As for sorting, It would not be necessary for me to search for dates or actions, just contexts and projects, as current.txt acts as an overview for output to GeekTool. For searches on individual items, I would likely search the tasks.txt file itself. Could the script sort lines by the start date (item 4), then by due date (item 5), and then by action (item 2), alphabetically in current.txt? Or if that is too much, simply by dates?

  2. I have a separate list (events.txt) that list events in the following format:

time.event.date

10:00a.appointment1.02/08
12:00p.appointment2.02/08
1:00p.appointment3.02/08
9:00a.appointment4.02/09

How could I have the script take only the lines containing today’s date (in field 3) and then dump them into today.txt and sort them by time (field 1)?

My apologies for all the questions… I am excited to see this script working. I thank-you profusely.

  • David.

See the changes (commented) in the script that follows.

changing ≤ to < in the changed portion should do that.

Sure. You’ll have to figure out how you want to do that - are you suggesting that the entire tasks.txt document be rewritten (because that’s what it would take - load it in, make the changes, put it back).

It’s possible, but the line “if aTD contains srch then” won’t. It would require an entirely different approach and would find anything that contained those 3 letters, such as “pick up mints for Molly”.

We’re not doing anything to the tasks.txt file except reading it. You can sort the results of that read after you’ve broken it down where indicated in the script.

All of those are possible.

Are you talking about the same script, or a new script? Basically the idea is the same as in this script where we set AppleScript’s text item delimiters to “,” here, you’d set them to period there and end up with lists of lists.

You’re welcome. Now here’s hoping that your excitement and motivation will prompt you to try this out for yourself. Next go-around, we’ll help you with a posted script you can’t quite get to work.

Here’s the modified script we were working with:



set srch to text returned of (display dialog "Enter a search term" default answer "")
set ToDo to paragraphs of (read alias ((path to desktop folder as text) & "tasks.txt"))
set TD to {}
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to ","
repeat with P in ToDo
	set TD's end to text items of P
end repeat
set AppleScript's text item delimiters to tid
-- TD now contains all the lines separated into fields that were in tasks.txt
-- Now go thru them:
set tEvents to {}
set tDay to current date
repeat with aTD in TD
	if aTD contains srch then
		-- changes start here
		try
			set SD to date (item 4 of aTD)
			if ((SD - tDay) / days div 1) < 0 then -- the start is before today or today
				set end of tEvents to aTD
			end if
		on error -- nothing in item 4
			set end of tEvents to aTD
		end try
		-- end of changes
	end if
end repeat
-- now you've got the events that contain the search term and meet the date spec in a new list of lists.
-- next you'd sort on the fields (but you don't say on what basis - what if the search term is a date or is an action?
-- Then build a text file from the lists:
set outP to "Current Tasks for " & short date string of tDay & return
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to " *** " -- to separate the fields
repeat with aP in tEvents
	set outP to (outP & (contents of aP) as text) & return
end repeat
set AppleScript's text item delimiters to tid
-- write it out
set CT to open for access ((path to desktop folder as text) & "current.txt") with write permission
try
	set eof of CT to 0 -- erase it if it already exists, leave out line to append it.
	write outP to CT
	close CT
on error
	close CT
end try

Hi Adam,

Thanks for the changes. I had already tried your solution for changing ≤ to <, but the problem is that it now does not show start dates for today (02/08 does not show). I have tried changing the formula in several other ways, but I cannot get it to show start dates up to and including today, without showing start dates for tomorrow also.

I have tried to figure out the sorting by myself, by doing some research, and you can see the result of this at the bottom of the script. Unfortunately, it is not sorting current.txt but leaving it in original order.

As for the recurring start dates, I have added the symbols * and ^ to every start date that is applicable in tasks.txt. After searching various date scripts though, I cannot figure out how to have the script rewrite the start dates containing * or ^ to a week or month after the current date. Can you offer any assistance?

Thank-you.


set srch to text returned of (display dialog "Enter a search term" default answer "")
set ToDo to paragraphs of (read alias ((path to desktop folder as text) & "tasks.txt"))
set TD to {}
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to ","
repeat with P in ToDo
	set TD's end to text items of P
end repeat
set AppleScript's text item delimiters to tid
-- TD now contains all the lines separated into fields that were in tasks.txt
-- Now go thru them:
set tEvents to {}
set tDay to current date
repeat with aTD in TD
	if aTD contains srch then
		try
			set SD to date (item 4 of aTD)
			if ((SD - tDay) / days div 1) < 0 then -- PROBLEM: does not show start dates for today
				set end of tEvents to aTD
			end if
		on error -- nothing in item 4
			set end of tEvents to aTD
		end try
	end if
end repeat
-- now you've got the events that contain the search term and meet the date spec in a new list of lists.
-- next you'd sort on the fields (but you don't say on what basis - what if the search term is a date or is an action?
-- Then build a text file from the lists:
set outP to ""
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to " " -- CHANGED to default shell sort delimiter
repeat with aP in tEvents
	set outP to (outP & (contents of aP) as text)  n& return
end repeat
set AppleScript's text item delimiters to tid
--CHANGED: write out and sorting
set sOutput to do shell script "echo " & quoted form of outP & " | sort -n +4 > Users/User/Desktop/current.txt" -- PROBLEM: does not sort by field 4 (start date)

The problem with dates is that current date when you run the script includes the time of day. When you convert 2/8 to a date without a time, the date defaults to one tick after midnight, ie to 12:00:00+ AM. I think you solve the problem by removing the div 1 (which just rounds it to an integer) from the line that does the comparison.

On the sorting, you have to use -t theCharacter to indicate the delimiter (no space between - and t) in the sort command to indicate how you’ve separated the fields. (doesn’t show in the script you posted). The delimiters have to match. You may have to us “as unicode text” as well in setting the delimiter – try that if it doesn’t work without.

sort -t * -n 4 etc. You may have to put the * (or whatever) in single quotes.

Salutations Adam,

The date solution worked perfectly. And after much testing, I was finally able to get the sorting working also. The solution involved reading tasks.txt as unicode text and with a line feed afterwards, instead of a return. Then, employing the unix sort command ‘-k 4’ rather than ‘+4’ and setting the delimiter with ‘-t.’

As for the monthly recurring tasks, I have devised another solution… My monthly tasks always occur on the last specific weekday of a month (for example, there are recurring tasks every last monday of the month. Thus I have created a text file ‘monday.monthly.txt’ that contains these tasks). Now I just need to know how to have the script determine if it is the last respective weekday of a month and if so, read the text file, and to keep going even if it does not find a text file for that specific weekday (as not all weekdays have a file).


set current_date to current date
set current_weekday to weekday of current_date
set current_month to month of current_date

-- here I do not know the commands (error: 'cannot get last weekday of February')...

if current_weekday is the last weekday of current_month then
	set monthly_path to "Macintosh HD:Users:User:Core:Agenda:Tasks:" & current_weekday & ".monthly" & ".txt" as text

-- how can it keep going even if it does not find a file for this particular weekday?

	set monthly_tasks to (read file monthly_path)
end if

-- how do I combine monthly_tasks with the ToDo variable from the original script, so that is is included in the final output?


Thanks Adam.

Nigel Garvey has written a bunch of date scripts, and I’ve played with them too:

Next Thursday:


-- Logic: Work out last Thursday's date and add a week!  8-)

-- OK. Subtract the start of a known Thursday in the past from the date being
-- tested. The result modulo 'weeks' is the time that's passed since the start of
-- the most recent Thursday (which is the test date itself, if it's a Thursday).
-- Subtract that time from the test date to get the recent Thursday's date, then
-- add a week for the following Thursday's date.

on nextThursday from theDate -- returns a date
	theDate - (theDate - (date "Thursday, January 2, 1000 12:00:00 AM")) mod weeks + weeks
end nextThursday

nextThursday from current date

Some coming Mondays:


on getComingMondays(theDate, howMany)
	set dt to {}
	repeat with k from 1 to howMany
		set {year:y, month:m, day:D} to (theDate - (theDate - (date "Monday, January 3, 2000 12:00:00 AM")) mod weeks + k * weeks)
		tell ((10000 * y + 100 * m + D) as text) to set end of dt to text 3 thru 4 & "/" & text 5 thru 6 & "/" & text 7 thru 8
	end repeat
	return dt
end getComingMondays

getComingMondays(current date, 6)

To find next of any day from text containing a weekday:


property tDays : {Wednesday, Thursday, Friday, Saturday, Sunday, Monday, Tuesday} -- no quotes
property astid : AppleScript's text item delimiters

set emText to "Hi, John;
Sure, next Thursday at 2 is fine with me.
Regards;
Jim"

repeat with aWD in tDays
	if (aWD as text) is in emText then
		set AppleScript's text item delimiters to aWD as text
		if last word of text item 1 of emText is "next" then
			set theWkDay to getNextWkDay(aWD as text, current date)
			set AppleScript's text item delimiters to astid
			exit repeat
		end if
	end if
	set AppleScript's text item delimiters to astid
end repeat

to getNextWkDay(wkDay, theDate) -- adapted from a script by Nigel Garvey
	set keyDate to date "Wednesday, January 1, 1000 12:00:00 AM"
	repeat with k from 1 to 7
		if item k of tDays as string = wkDay then
			set wkd to item k of tDays
			exit repeat
		end if
	end repeat
	set tWD to keyDate + (k - 1) * days
	return theDate - (theDate - tWD) mod weeks + weeks
end getNextWkDay

For past and future instances of a weekday:


-- This was written at the suggestion of, and in collaboration with, Arthur Knapp.
-- Its purpose is similar to that of 'Next Thursday's date', but it's far more
-- flexible. It returns the date of *any* instance of *any* weekday before or after
-- the input date - eg. the 2nd Saturday after the date. Its parameters are the
-- reference date, the weekday required, and the number of the instance. Positive
-- instance parameters refer to the future; negatives to the past. An instance
-- parameter of 0 returns the given weekday that occurs in the same Sunday-to-
-- Saturday week as the reference date. If you find this handler useful, you're
-- more than welcome to think up a more convenient name for it. ;-)

-- Next Thursday's date (the date of the first Thursday after today)
DateOfThisInstanceOfThisWeekdayBeforeOrAfterThisDate(current date, Thursday, 1)

-- Last Thursday but one's date (the date of the second Thursday before today)
DateOfThisInstanceOfThisWeekdayBeforeOrAfterThisDate(current date, Thursday, -2)

-- The Thursday of this week (may be before, after, or on today's date)
DateOfThisInstanceOfThisWeekdayBeforeOrAfterThisDate(current date, Thursday, 0)

on DateOfThisInstanceOfThisWeekdayBeforeOrAfterThisDate(d, w, i) -- returns a date
	-- Keep an note of whether the instance value *starts* as zero
	set instanceIsZero to (i is 0)
	-- Increment negative instances to compensate for the following subtraction loop
	if i < 0 and d's weekday is not w then set i to i + 1
	-- Subtract a day at a time until the required weekday is reached
	repeat until d's weekday is w
		set d to d - days
		-- Increment an original zero instance to 1 if subtracting from Sunday into Saturday 
		if instanceIsZero and d's weekday is Saturday then set i to 1
	end repeat
	-- Add (adjusted instance) * weeks to the date just obtained and zero the time
	d + i * weeks - (d's time)
end DateOfThisInstanceOfThisWeekdayBeforeOrAfterThisDate

Adam,

Thanks for the date examples - I was able to compose a solution with some snippets.

When I search for a project, I would like it to show me ALL the lines that contain that project (not just those with a current/past start date, as it does for a context search). I thought of indicating a project (so that the script would know if a search was for a project) with ‘:’ before the project name (i.e. context,action,:project,startdate,duedate)

I tried to code it myself without success, as you can see below. Could you please tell me some code that would work?

Thanks.

set srch to text returned of (display dialog "Enter a search term" default answer "")
set ToDo to paragraphs of (read file ((path to desktop folder as text) & "tasks.txt"))
set TD to {}
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to "."
repeat with P in ToDo
	set TD's end to text items of P
end repeat
set AppleScript's text item delimiters to tid
-- TD now contains all the lines separated into fields that were in tasks.txt
-- Now go thru them:

set tEvents to {}
set tDay to current date
repeat with aTD in TD
	if aTD contains srch then
		try
			set SD to date (item 4 of aTD)
			if ((SD - tDay) / days) < 0 then -- the start is before today or today
				set end of tEvents to aTD
			end if
		on error -- nothing in item 4
			set end of tEvents to aTD
		end try
		-- I NEED HELP HERE...
	else if aTD contains srch and srch contains ":" then
		try
			set end of tEvents to aTD
		end try
	end if
end repeat

set outP to ""
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to "." -- to separate the fields
repeat with aP in tEvents
	set outP to (outP & (contents of aP) as Unicode text) & {ASCII character 10}
end repeat
set AppleScript's text item delimiters to tid
-- write it out
set CT to open for access ((path to desktop folder as text) & "current.txt") with write permission
try
	set eof of CT to 0 -- erase it if it already exists, leave out line to append it.
	write outP to CT
	close access CT
on error
	close access CT
end try
do shell script "sort -t. -k 4,2 Users/User/Desktop/current.txt -o Users/User/Desktop/current.txt"

The problem is in the logic. If projects are to be treated specially, then you don’t want to do the context search you’d do otherwise, you need another. To accomplish that, you have to test whether the search is a project early in the game and key the search accordingly, i.e., if srch contains “:” then do one thing, else do the date stuff. If you want to sort differently, then have two sort calls and choose between them dependent on a flag you set in the logic, that is: set project to true, set project to false in the if logic, then if project then do one search, else do the other.

You’ll get there.:slight_smile:

Hi Adam,

Where in the script should I position this? Is this the correct command? …

else if srch contains ":" then
       try
           -- is this the correct command/variable do to use here?...
set end of tEvents to aTD
       end try

Thank-you kindly.

Something like this, I would think:

set tEvents to {}
set tDay to current date
repeat with aTD in TD
	if aTD contains srch then -- contains the search term
		if srch contains ":" then -- also contains ":"
			set end of tEvents to aTD -- without dating them.
		else -- doesn't contain ":", but does contain search term, so want date checked
			try
				set SD to date (item 4 of aTD)
				if ((SD - tDay) / days) < 0 then -- the start is before today or today
					set end of tEvents to aTD
				end if
			on error -- nothing in item 4; dateless
				set end of tEvents to aTD
			end try
		end if -- for ":"
	end if -- for search term
end repeat

Adam,

Thanks so much for the code - it works excellently.

As you can see below, I am trying to have the script read three text files (irregularActions & weeklyActions & monthlyActions) and set ‘ToDo’ to the paragraphs of all three files. It seems to do this, but in the final output, it does not filter weeklyActions and monthlyActions according to the search term (it simply includes all the lines in these two files, rather then just those that match the search). How do I have the search filter out results from all three files?

Also, I sometimes (but not always) get the following error “«script» doesn’t understand the daysInMonth message.” Why is this?

Thank-you.


-- read weekly actions

try
	set weeklyActions to (read file ("Macintosh HD:Users:User:Core:Agenda:Actions:" & weekday of (current date) & ".weekly" & ".txt"))
on error
	set weeklyActions to ""
end try

-- read monthly actions

on daysInMonth for theDate
	32 - ((theDate + (32 - (theDate's day)) * days)'s day)
end daysInMonth

set daysInMonth to daysInMonth for (current date)
set finalWeek to daysInMonth - 6

if day of (current date) ≥ finalWeek then
	try
		set monthlyActions to (read file ("Macintosh HD:Users:User:Core:Agenda:Actions:" & weekday of (current date) & ".monthly" & ".txt"))
	on error
		set monthlyActions to ""
	end try
else
	set monthlyActions to ""
end if

-- combine with irregular actions and delineate

set search to text returned of (display dialog "Enter a search term" default answer "")
set irregularActions to (read file ("Macintosh HD:Users:User:Core:Agenda:Actions:actions.txt"))
set ToDo to paragraphs of irregularActions & weeklyActions & monthlyActions -- PROBLEM: does not filter weeklyActions or monthlyActions in the search part below
set TD to {}
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to "."
repeat with P in ToDo
	set TD's end to text items of P
end repeat
set AppleScript's text item delimiters to tid

-- filter by search term

set tEvents to {}
set tDay to current date
repeat with aTD in TD
	if aTD contains search then -- contains the search term
		if search contains ":" then -- also contains ":"
			set end of tEvents to aTD -- without dating them.
			set projectSearch to true
		else -- doesn't contain ":", but does contain search term, so want date checked
			try
				set SD to date (item 4 of aTD)
				if ((SD - tDay) / days) < 0 then -- the start is before today or today
					set end of tEvents to aTD
				end if
				set projectSearch to false
			on error -- nothing in item 4; dateless
				set end of tEvents to aTD
			end try
		end if -- for ":"
	else if search contains "all" then
		try
			set SD to date (item 4 of aTD)
			if ((SD - tDay) / days) < 0 then -- the start is before today or today
				set end of tEvents to aTD
				set projectSearch to false
			end if
		on error -- nothing in item 4
			set end of tEvents to aTD
			set projectSearch to false
		end try
	end if -- for search term
end repeat

-- write output and sort

set outP to ""
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to "." -- to separate the fields
repeat with aP in tEvents
	set outP to (outP & (contents of aP) as Unicode text) & {ASCII character 10}
end repeat
set AppleScript's text item delimiters to tid
set CT to open for access "Macintosh HD:Users:User:Core:Agenda:Actions:readactions.txt" with write permission
try
	set eof of CT to 0 -- erase it if it already exists, leave out line to append it.
	write outP to CT
	close access CT
on error
	close access CT
end try
if projectSearch is true then
	do shell script "sort -t. -k 4 Users/User/Core/Agenda/Actions/readactions.txt -o Users/User/Core/Agenda/Actions/readactions.txt"
else if projectSearch is false then
	do shell script "sort -t. -k 2,4 Users/User/Core/Agenda/Actions/readactions.txt -o Users/User/Core/Agenda/Actions/readactions.txt"
end if

Two comments: 1) set tDay to current date once at the top and use tDay everywhere else - it’s much more efficient than repeatedly asking the system for the current date. 2) You don’t need the days in month calculation as a handler. Do this:

set daysInMonth to 32 - ((theDate + (32 - (theDate's day)) * days)'s day) -- no need for handler
set finalWeek to daysInMonth - 6

With respect to the failure to sort, that’s obviously because the tests in the “filter by search term” section are failing somehow and the line set end of tEvents to aTD is executing for every event in the lists that fail. I have no idea why, since I don’t have samples of them. I’m not sure either of the logic you intend by including the else if search contains “all” with a repetition of the date sort because you’ll never get there, the first two for aTD contains search and then aTD contains “:” should grab everything whether “all” is there or not. What do you intend?

Further thoughts, envisage. When doing “if” blocks, it’s essential that the tests are performed in an order that doesn’t leave one of them “blinded” by the “greediness” of the previous tests as you have done with the “all” test (I don’t know how that works because I don’t know where “all” is supposed to appear). Remember that if tests can use boolean algebra; OR, AND, and NOT being available here (but not NAND or NOR). Also, use these relationships when analyzing logical statements:

a OR (b OR c) = (a OR b) OR c
a AND (b AND c) = (a AND b) AND c associativity

a OR b = b OR a
a AND b = b AND a commutativity

a OR (a AND b) = a
a AND (a OR b) = a absorption

a OR (b AND c) = (a OR b) AND (a OR c)
a AND (b OR c) = (a AND b) OR (a AND c) distributivity

a OR (NOT a) = true
a AND (NOT a) = false complements

NOT (a OR b) = (NOT a) AND (NOT b)
NOT (a AND b) = (NOT a) OR (NOT b) de Morgen’s theorem

Hi Adam,

I have applied your comments. Thanks.

In regards to the failure to filter by search term, here is the setup/result:

For consistency’s sake I have placed the same text in all three files:

action.contact
action.contact…02/10
action.contact.:project1.02/01
action.internet
action.internet…02/10
action.internet.:project2.02/10
action.internet.:project2.02/05
action.internet.:project2.02/20

I set my date to Monday Feburary 26, 2007, so that it will read the monthlyActions file. Thus, the three files that the script reads from are:

actions.txt (irregularActions)
monday.weekly.txt (weeklyActions)
monday.monthly.txt (monthylActions)

If I run the script with the search term “contact” the result in readactions.txt is:

action.contact
action.contact
action.contact
action.contact…02/10
action.contact…02/10
action.contact…02/10
action.contact.:project1.02/01
action.contact.:project1.02/01
action.contact.project1.02/01
action.internet
action.internet
action.internet…02/10
action.internet…02/10
action.internet.:project2.02/05
action.internet.:project2.02/05
action.internet.:project2.02/10
action.internet.:project2.02/10
action.internet.:project2.02/20
action.internet.:project2.02/20

It outputs three of every entry that contains ‘contact’, but only two of every entry that contains ‘internet’

If I run the script with the search term “internet” the result in readactions.txt is:

action.contact
action.contact
action.contact…02/10
action.contact…02/10
action.contact.:project1.02/01
action.contact.:project1.02/01
action.internet
action.internet
action.internet
action.internet…02/10
action.internet…02/10
action.internet…02/10
action.internet.:project2.02/05
action.internet.:project2.02/05
action.internet.:project2.02/10
action.internet.:project2.02/10
action.internet.:project2.02/20
action.internet.:project2.02/20
action.internet.project2.02/05
action.internet.project2.02/10
action.internet.project2.02/20

This time, it outputs three of every entry that contains ‘internet’, but only two of every entry that contains ‘contact’

Another thing to note is that if I set ToDo to only read from one file, it works fine, but as soon as there are more than one file to read from, it does not work properly.

The following works fine:
ToDo to paragraphs of irregularActions
So does this:
ToDo to paragraphs of weeklyActions

The following does not workly properly:
set ToDo to paragraphs of irregularActions & weeklyActions


In regards to the ‘else if search contains “all” then’ section, I would like to have the script return all the lines within the start date range (before or on today), as opposed to only those containing the search field and within the date range. Perhaps this is not a good way of going about it (It was all I could think of). What would you suggest?

Aha!

set ToDo to paragraphs of irregularActions & weeklyActions is taking the paragraphs of irregular (a list) and concatinating weekly as a single list item to the end.

You need this: set ToDo to paragraphs of (irregularActions & weeklyActions) to force the concatination to be first and then the paragraphing.

Good-day Adam,

Thanks for figuring out that problem – and the simplicity of it all. I have been making some progress, but have come to another area that is posing some difficulty.

Is there any way to sort according to 12-hr time?

08:30a.text
10:00a.text
12:00p.text
03:00p.text
11:00p.text

How can I sort the above? I have tried “sort -k1.6,1.6” which gives the following:

08:30a.text
10:00a.text
03:00p.text
11:00p.text
12:00p.text

…and “sort -k 1.6,1.6 -k 1.2,1.2” which gives the following:

10:00a.text
08:30a.text
11:00p.text
12:00p.text
03:00p.text

Is there some way to make this work? (whether shell or applescript?)

Well here’s one way:


-- Assuming you mean 24-hour time, that there are always 2 numbers before the colon and 2 after, and that you don't want to change the original list's names but just order them:
set T to paragraphs of "08:30a.text
10:00a.text
12:00p.text
03:00p.text
11:00p.text"
set T24 to {}
repeat with para in T
	tell para
		if character 6 is "p" then
			set N to 12
		else
			set N to 0
		end if
		if (character 1 & character 2) as number = 12 then set N to 0 -- adjust for noon
		set T24's end to N + (character 1 & character 2) -- build new list
	end tell
end repeat
set T to sortDouble(T24, T)
-- put the list back to paragraphs as before
set tid to AppleScript's text item delimiters
set AppleScript's text item delimiters to return
set T to T as text
set AppleScript's text item delimiters to tid
T --> the sorted paragraphs

-- Adapted from a handler by Kai Edwards
to sortDouble(sortList, SecondList) -- the first is the sortby list, the second is kept in sync.
	tell (count sortList) to repeat with i from (it - 1) to 1 by -1
		set s to sortList's item i
		set r to SecondList's item i
		repeat with i from (i + 1) to it
			tell sortList's item i to if s > it then
				set sortList's item (i - 1) to it
				set SecondList's item (i - 1) to SecondList's item i
			else
				set sortList's item (i - 1) to s
				set SecondList's item (i - 1) to r
				exit repeat
			end if
		end repeat
		if it is i and s > sortList's end then
			set sortList's item it to s
			set SecondList's item it to r
		end if
	end repeat
	return SecondList
end sortDouble

Good-day Adam,

Well, after continued efforts, here is the result of what we have been working on. It seems to be functional, but I will have to test it further to know if it works for the longterm. I would like to thank-you for all your knowledge and expertise and excellent assistance. You are a good man, Mr. Bell.


on handle_string(theString)
	my process(theString)
end handle_string

on process(theString)
	
	-- retrieve date
	
	set tDay to current date
	set wDay to weekday of tDay
	
	-- read weekly actions
	
	try
		set weeklyActions to (do shell script "grep -i 'w" & wDay & "' /Users/User/Documents/Agenda/repactions.txt | cut -f1,2 -d. | nl -v101")
	on error
		set weeklyActions to ""
	end try
	
	-- read monthly actions
	
	set daysInMonth to 32 - ((tDay + (32 - (tDay's day)) * days)'s day)
	set finalWeek to daysInMonth - 6
	
	if day of tDay ≥ finalWeek then
		try
			set monthlyActions to (do shell script "grep -i 'm" & wDay & "' /Users/User/Documents/Agenda/repactions.txt | cut -f1,2 -d. | nl -v201")
		on error
			set monthlyActions to ""
		end try
	else
		set monthlyActions to ""
	end if
	
	--read irregular actions
	
	set irregularActions to (do shell script "cat /Users/User/Documents/Agenda/oneactions.txt")
	
	-- combine all three & delineate
	
	set ToDo to paragraphs of (irregularActions & (ASCII character 10) & weeklyActions & (ASCII character 10) & monthlyActions)
	set TD to {}
	set originalDelimiters to AppleScript's text item delimiters
	set AppleScript's text item delimiters to "."
	repeat with P in ToDo
		set TD's end to text items of P
	end repeat
	set AppleScript's text item delimiters to originalDelimiters
	
	-- filter by search term
	
	set search to theString as text
	set tEvents to {}
	repeat with aTD in TD
		if aTD contains search then -- contains the search term
			if search contains ":" then -- also contains ":"
				set projectSearch to true
				set end of tEvents to aTD -- without dating them.
			else -- doesn't contain ":", but does contain search term, so want date checked
				set projectSearch to false
				try
					set SD to date (item 4 of aTD)
					if ((SD - tDay) / days) < 0 then -- the start is before today or today
						set end of tEvents to aTD
					end if
				on error -- nothing in item 4
					set end of tEvents to aTD
				end try
			end if -- for ":"
		else if search is "all" then
			set projectSearch to 0
			try
				set SD to date (item 4 of aTD)
				if ((SD - tDay) / days) < 0 then
					set end of tEvents to aTD
				end if
			on error -- nothing in item 4
				set end of tEvents to aTD
			end try
		end if
	end repeat
	
	-- compile & write/sort output
	
	set outP to (ASCII character 9) & "> " & search & (ASCII character 10)
	set originalDelimiters to AppleScript's text item delimiters
	set AppleScript's text item delimiters to "."
	repeat with aP in tEvents
		set outP to (outP & (contents of aP)) & (ASCII character 10)
	end repeat
	set AppleScript's text item delimiters to originalDelimiters
	
	if projectSearch is true then
		do shell script "echo " & quoted form of outP & " | grep -v '^$' | sort -t. -k 4,4 -k 5,5 -k 2,2 | cut -f1,2,4,5 -d. | cut -f2 -d'	' > /Users/User/Documents/Agenda/getactions.txt"
	else if projectSearch is false then
		do shell script "echo " & quoted form of outP & " | grep -v '^$' | sort -k 1,1 -k 5,5 | cut -f1,3,5 -d. | cut -f2 -d'	' > /Users/User/Documents/Agenda/getactions.txt"
	else
		do shell script "echo " & quoted form of outP & " | grep -v '^$' | sort -t. -k 2,2 -k 4,4 -k 5,5 | cut -f1,2,3,5 -d. | cut -f2 -d'	' > /Users/User/Documents/Agenda/getactions.txt"
	end if
end process

Glad to know that you’ve succeeded. Thanks for the feedback. :cool: