【问题标题】:Applescript - Organize files into folders according to their namesApplescript - 根据名称将文件组织到文件夹中
【发布时间】:2019-09-14 20:33:12
【问题描述】:

我发现这篇文章:Applescript - Creating folders based on the first word of the filename 经过一些研究寻找类似的东西,但涉及更多的步骤。 首先,我是applescript的新手。我有点能够看到代码并理解它的部分功能,但不是全部。

我有一堆这样命名的 pdf 文件: Category1 Category2 Category3 RestofTheName.pdf 您可以想象,每个类别的名称可能因一堆 pdf 文件而异。

我想将它们组织在文件夹中,就像上面的脚本一样。 然后我想删除每个 pdf 的第一个单词(因为 CategoryX 部分仅出于组织目的而提供给文件名)。我已经用下面的代码完成了:

###################################################
#################### CATEGORY1 #######################
###################################################

###########################################################
# Organize files of a chosen folder using the first word of each file as name of the sub folders #
###########################################################

set chosenFolder to (choose folder)
tell application "Finder" to set fileList to files of chosenFolder

set TID to text item delimiters

set text item delimiters to space
repeat with aFile in fileList
    set fileName to name of aFile
    set textItems to text items of fileName
    if (count textItems) = 1 then
        set fileExtension to name extension of aFile
        set folderName to text 1 thru ((get offset of "." & fileExtension in fileName) - 1) of fileName
    else
        set folderName to first item of textItems
    end if
    set sourceFile to quoted form of POSIX path of (aFile as text)
    set destinationFile to quoted form of (POSIX path of chosenFolder & folderName & "/" & fileName)
    do shell script "ditto " & sourceFile & space & destinationFile
    do shell script "rm " & sourceFile
end repeat

set text item delimiters to TID

#####################################
# Remove first word of if each file inside every sub folder  #
#####################################

set oldDelims to AppleScript's text item delimiters
set AppleScript's text item delimiters to " "

set pFolder to chosenFolder

processThisFolder(pFolder)

on processThisFolder(sourceFolder)
    set the theList to list folder sourceFolder without invisibles
    set sourceFolder to sourceFolder as string

    repeat with i from 1 to number of items in theList
        set thisItem to item i of theList
        set thisItem to (sourceFolder & thisItem) as alias
        set thisItemInfo to info for thisItem
        set isFolder to folder of thisItemInfo

        if isFolder is true then
            processThisFolder(thisItem)

        else
            set thisFileName to name of thisItemInfo
            #set withoutPrefix to text item -last text item) of thisFileName    -- solo deja la ultima palabra
            set withoutPrefix to text from text item 2 to -1 of thisFileName

            tell application "Finder"
                set name of thisItem to withoutPrefix
            end tell
        end if
    end repeat

end processThisFolder
set AppleScript's text item delimiters to oldDelims

到目前为止一切顺利。问题是现在我想继续组织 pdf 文件。我希望脚本遍历第一步创建的每个文件夹,并再次检查每个文件名的第一个单词(最初是第二个单词)并将它们移动到文件夹中。他们有它再次删除第一个单词。

然后再做这一步。所以我最终会得到这个结构:

+ Category1 Folder1
  - Category2 Folder1
    · Category 3 Folder1
       RestofTheName1.pdf
       RestofTheName2.pdf
       RestofTheName3.pdf
       RestofTheName4.pdf
       RestofTheName5.pdf

    · Category 3 Folder2
    · Category 3 Folder3

  - Category2 Folder2
    · Category 3 Folder1
    · Category 3 Folder2

+ Category1 Folder2
  - Category2 Folder1
  - Category2 Folder2
  - Category2 Folder3
  - Category2 Folder4

由于第一部分工作正常,我想这是重复步骤的问题:组织、重命名、组织、重命名。但是随着文件夹结构的每一步都在增长,我似乎无法让脚本作用于正确的文件夹/子文件夹/文件......

这就是我现在的位置:

# CATEGORY1 

# Organize files of a chosen folder using the first word of each file as name of the sub folders 
###########################################################

set chosenFolder to (choose folder)
tell application "Finder" to set fileList to files of chosenFolder

set TID to text item delimiters

set text item delimiters to space
repeat with aFile in fileList
    set fileName to name of aFile
    set textItems to text items of fileName
    if (count textItems) = 1 then
        set fileExtension to name extension of aFile
        set folderName to text 1 thru ((get offset of "." & fileExtension in fileName) - 1) of fileName
    else
        set folderName to first item of textItems
    end if
    set sourceFile to quoted form of POSIX path of (aFile as text)
    set destinationFile to quoted form of (POSIX path of chosenFolder & folderName & "/" & fileName)
    do shell script "ditto " & sourceFile & space & destinationFile
    do shell script "rm " & sourceFile
end repeat

set text item delimiters to TID


# Remove first word of if each file inside every sub folder  #
###########################################################

set oldDelims to AppleScript's text item delimiters
set AppleScript's text item delimiters to " "

set pFolder to chosenFolder

processThisFolder(pFolder)

on processThisFolder(sourceFolder)
    set the theList to list folder sourceFolder without invisibles
    set sourceFolder to sourceFolder as string

    repeat with i from 1 to number of items in theList
        set thisItem to item i of theList
        set thisItem to (sourceFolder & thisItem) as alias
        set thisItemInfo to info for thisItem
        set isFolder to folder of thisItemInfo

        if isFolder is true then
            processThisFolder(thisItem)

        else
            set thisFileName to name of thisItemInfo
            set withoutPrefix to text from text item 2 to -1 of thisFileName

            tell application "Finder"
                set name of thisItem to withoutPrefix
            end tell
        end if
    end repeat

end processThisFolder
set AppleScript's text item delimiters to oldDelims



# CATEGORY2

# Organize files inside every subfolder using the first word of each file name (which used to be the second word) as name of the sub sub folders 
###########################################################################################



tell application "Finder" to set subFoldersLevel1 to every folder of (entire contents of (chosenFolder))

set TID to text item delimiters

set text item delimiters to space
repeat with aFile in fileList
    set fileName to name of aFile
    set textItems to text items of fileName
    if (count textItems) = 1 then
        set fileExtension to name extension of aFile
        set folderName to text 1 thru ((get offset of "." & fileExtension in fileName) - 1) of fileName
    else
        set folderName to first item of textItems
    end if
    set sourceFile to quoted form of POSIX path of (aFile as text)
    set destinationFile to quoted form of (POSIX path of chosenFolder & folderName & "/" & fileName)
    do shell script "ditto " & sourceFile & space & destinationFile
    do shell script "rm " & sourceFile
end repeat

set text item delimiters to TID

欢迎任何帮助!

【问题讨论】:

  • 您如何确定名称与类别?是否有固定数量的类别名称或某种分隔符?
  • 好的,我是一名平面设计师,文件的名称因工作而异。假设每个 pdf 将是一个传单。他们每个人都会有一些使他们与其他人不同的东西。如果工作是关于动物的,名称可能是这样的:``` FourLegs BigOnes Horses NameOfHorse.pdf FourLegs SmallOnes Cats NameOfCat.pdf TwoLegs SmallOnes Birds NameOfBird.pdf ``` 所以类别和名称将取决于工作本身的性质.并且没有类别限制,每个工作可以有不同的数量。我希望我理解正确。
  • 我主要是问您如何确定“名称”与类别,例如,您将使用什么来确定FourLegs BigOnes Horses Italian Heavy Draft 的名称?每个文件名是否由空格分隔的单个(大写/小写驼峰式)单词组成,最后一个是您要保留的名称?
  • 好的。在我的示例中,我使用了 3 个类别级别,前 3 个单词之后的所有内容都是文件名,无论是一个单词还是多个单词。但是根据工作的不同,我可以有更多或更少的类别,即使我认为我不需要超过 5 或 6 个类别级别。事实上,我认为让脚本询问您该工作有多少类别会很棒,因此它适用于每种情况。
  • 关于小写和大写,我使用的是大写/小写驼峰式系统,但如果更容易的话,我可以使用 under scores,我的意思是将两个单词的类别保持为一个字符串,没有空格。导出 pdf 时,如果更容易,我可以选择全部小写的类别,但我宁愿将它们作为第一个字符,大写,其余小写。

标签: applescript


【解决方案1】:

您不必对文本分隔符、递归处理程序或其他任何东西过于疯狂。如果原始文件名的组成部分是由空格分隔的单词,您可以使用这些空格来确定类别。在以下示例中,我获取文件名的 words(由空格和各种标点符号分隔的文本)并使用 shell 脚本从中创建目录结构:

on run -- example
    set chosenFolder to (choose folder)
    tell application "Finder" to set fileList to files of chosenFolder as alias list
    set skippedItems to ""
    repeat with anItem in fileList
        set theResult to process(anItem)
        if theResult is not "" then set skippedItems to skippedItems & theResult
    end repeat
    if skippedItems is not "" then display alert "Items were skipped:" message skippedItems
end run

# Create a directory structure from words of the file name and move/rename last item.
to process(theFile)
    set {folderPath, fileName, extension} to getNamePieces from theFile
    try -- guard
        set theWords to words 1 thru -2 of fileName
        set subdirectories to ""
        repeat with anItem in theWords -- build a directory tree from the words
            set subdirectories to subdirectories & anItem & "/"
        end repeat
        do shell script "cd " & quoted form of folderPath & "; mkdir -p " & subdirectories
        tell application "System Events" to set name of (move theFile to disk item (folderPath & "/" & subdirectories)) to (last word of fileName) & extension
    on error errmess -- skip it (no words - underscore separator, etc)
        log errmess
        return (fileName & extension & return)
    end try
    return ""
end process

#  Get posix path of the containing folder, the file name, and the extension.
to getNamePieces from someItem
    tell application "System Events" to tell disk item (someItem as text)
        set theContainer to POSIX path of container
        set {theName, theExtension} to {name, name extension}
    end tell
    if theExtension is not "" then
        set theName to text 1 thru -((count theExtension) + 2) of theName -- the name part
        set theExtension to "." & theExtension
    end if
    return {theContainer, theName, theExtension}
end getNamePieces

【讨论】:

  • 我要到星期一才能试一试。我会让你知道情况如何。非常感谢您的帮助。
  • 非常感谢!我昨天在测试,效果很好。我真的很感激。
猜你喜欢
  • 1970-01-01
  • 2017-06-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-21
  • 1970-01-01
  • 2020-11-02
相关资源
最近更新 更多