Script: Create tag and assign it to matching records based on content and name

This script creates a tag, searches for records whose content or name contains the tag and assigns it.

It

  • asks for a tag name
  • creates the tag (if it doesn’t exist)
  • asks in which group to search
  • assigns the tag to all matching records.

If property useGroupSelector is set to false then the current database is used.

If property includeNameInSearch is set to false then only text is searched.

Tag aliases are always included.

The script derived from Script: Assign selected tag to matching records based on content and name.

-- Create tag and assign it to matching records based on content and name

property useGroupSelector : true -- if false the current database is used
property includeNameInSearch : true -- if false only text is searched
property openWindow : true
property theIconPath : (((path to application id "DNtp") & "Contents:Resources:DEVONthink 3.icns:") as string) as alias

tell application id "DNtp"
	try
		try
			set selectedText to selected text of window 1 & "" as string
			set defaultAnswer to selectedText
		on error
			set defaultAnswer to ""
		end try
		set theTag to my displayDialog(defaultAnswer)
		set theTag_escaped to my replace_String(theTag, "/", "\\/")
		
		if useGroupSelector = true then
			set theSearchScope to display group selector "Search records in:" for current database
		else
			set theSearchScope to root of current database
		end if
		
		show progress indicator "Tagging... " as string with cancel button
		
		set theTagRecord to create location "/Tags/" & theTag_escaped in database of theSearchScope
		
		set theTagRecord_Name to name of theTagRecord
		set theTagRecord_Aliases to aliases of theTagRecord
		set theNames to {theTagRecord_Name} & my tid(theTagRecord_Aliases, {", ", "; ", ",", ";"})
		set theNames_readyForQuery to "\"" & my tid(theNames, "\" OR \"") & "\""
		if includeNameInSearch = true then
			set theQuery to "tags!=" & theTagRecord_Name & " kind:any {any: name:" & theNames_readyForQuery & " text:" & theNames_readyForQuery & "}"
		else
			set theQuery to "tags!=" & theTagRecord_Name & " kind:any text:" & theNames_readyForQuery
		end if
		set theResults to search theQuery in theSearchScope
		repeat with thisResult in theResults
			set tags of thisResult to (tags of thisResult) & theTagRecord_Name
		end repeat
		
		if openWindow = true then
			open window for record theTagRecord
			activate
		end if
		
		hide progress indicator
		
	on error error_message number error_number
		hide progress indicator
		if the error_number is not -128 then display alert "DEVONthink" message error_message as warning
		return
	end try
end tell

on tid(theInput, theDelimiter)
	set d to AppleScript's text item delimiters
	set AppleScript's text item delimiters to theDelimiter
	if class of theInput = text then
		set theOutput to text items of theInput
	else if class of theInput = list then
		set theOutput to theInput as text
	end if
	set AppleScript's text item delimiters to d
	return theOutput
end tid

on displayDialog(defaultAnswer)
	tell application id "DNtp"
		try
			set dialogButtons to {"Cancel", "OK"}
			set theDialog to display dialog "Tag:" default answer defaultAnswer buttons dialogButtons default button 2 with title "Create and assign tag:" with icon theIconPath
			set {theButton, theTag} to {button returned, text returned} of theDialog
			if theButton = item 1 of dialogButtons then
				error number -128
			else if theButton = item 2 of dialogButtons then
				if theTag = "" then
					error number -128
				end if
			end if
			return theTag
		on error error_message number error_number
			error number -128
		end try
	end tell
end displayDialog

on replace_String(theText, oldString, newString)
	local ASTID, theText, oldString, newString, lst
	set ASTID to AppleScript's text item delimiters
	try
		considering case
			set AppleScript's text item delimiters to oldString
			set lst to every text item of theText
			set AppleScript's text item delimiters to newString
			set theText to lst as string
		end considering
		set AppleScript's text item delimiters to ASTID
		return theText
	on error eMsg number eNum
		set AppleScript's text item delimiters to ASTID
		error "Can't replaceString: " & eMsg number eNum
	end try
end replace_String

1 Like