Page 1 of 1

Script that tags parent folder with tags located in a json file

Posted: 16 Jul 2024 20:43
by o7blue
I finished writing/modifying this script to look for files named folder.json, and tag the folder containing that file with the tags present in that file. Figured I'd post here since this is my first time working with the language, and I might have done something stupid. Also, a huge thank you to highend who wrote the original script I based this off some 4 years ago (viewtopic.php?p=183757#p183757).

The tag format in the json is this:

Code: Select all

{
    "tags": {
        "category 1": [
            "item 1",
            "item 2",
            "item 3",
            "item 4"
        ],
        "category 2": [
            "item 1",
            "item 2"
        ],
        "category 3": [
            "item 1",
            "item 2",
            "item 3",
            "item 4",
            "item 5"
        ]
    }
}
And this is how that should be translated into the Tags field in XY:

Code: Select all

category 1: item 1, category 1: item 2, category 1: item 3, category 1: item 4, category 2: item 1, category 2: item 2, category 3: item 1, category 3: item 2, category 3: item 3, category 3: item 4, category 3: item 5
The script:

Code: Select all

    $json_list = quicksearch("folder.json /af", , , "s");

    // Only process files where "folder.json" itself is not part of the file name
    $json_list = regexmatches($json_list, "^.+\\folder\.json$", <crlf>);
    end (!$json_list), "No folder.json file(s) found, aborted!";

    showstatus 0;
    foreach($json, $json_list, <crlf>) {
        $working_dir = gpc($json, "path");
        $tag_categories = runret('cmd /c jq -r -c ".tags | keys_unsorted[]" folder.json', $working_dir);
        $tag_lists = runret('cmd /c jq -r -c ".tags[]" folder.json', $working_dir);

        if ($json_tags) {
            $tags = "";

            $i = 0;
            foreach($list, $tag_lists, <crlf>, "e") {
                $list = replacelist($list, "[]", "");
                $tag_array[$i] = $list;
                $i = $i + 1;
            }

            $i = 0;
            foreach($category, $tag_categories, <crlf>, "e") {
                foreach($tag, $tag_array[$i], ",", "e") {
                    $tag = replacelist($tag, '"', "");
                    $tag = replacelist($tag, "|", "|");
                    $tags .= " " . $category . ": " . $tag . ",";
                }
                $i = $i + 1;
            }

            if ($tags) {
                $tags = formatlist(trim(trim($tags, , "L"), ",", "R"), "s", ", ");
                $old_tags = tagitems("tags", , $working_dir);
                if ($old_tags != $tags) {
                    tagitems("tags", $tags, $working_dir);
                    status "Tagged folder " . quote(gpc($working_dir, "file")) . " ...";
                }
            }
        }
    }
    #893; // refresh tag list
    status "Done!";
Overall the script does what it's supposed to, but I'm curious:
- I'm relying on runret() to call jq to do most of the json processing, but I'm wondering if it comes with a performance penalty?
- After the quicksearch is done and the tagging begins, XY will become unresponsive (as in, the application has stopped responding) if there are sufficiently many items to be tagged. It's not a showstopper since I just have to wait for it to finish, but it would be nice to see the status bar update as the tagging happens. As it stands I have no idea how long I have to wait after XY stops responding.

Re: Script that tags parent folder with tags located in a json file

Posted: 16 Jul 2024 21:01
by highend
1. Depends on the number of json files to process
Thousands? Maybe, hundreds, probably not

2. Add a wait 1; at the beginning of the foreach loop

Re: Script that tags parent folder with tags located in a json file

Posted: 17 Jul 2024 09:23
by o7blue
Thank you for the tip, that will help out a lot!

Also, is it possible to pass in a filename to runret()? It works out here because the json name is static, but I have other cases where the name changes. When I tried passing in a variable to runret() it didn't expand. Did I just pass it in wrong? Something like runret('cmd /c jq -r -c ".tags | keys_unsorted[]" $json');

Re: Script that tags parent folder with tags located in a json file

Posted: 17 Jul 2024 09:32
by highend
Variables in strings that are enclosed in '' will not be expanded, use (the correct amount) of ""

Re: Script that tags parent folder with tags located in a json file

Posted: 17 Jul 2024 10:21
by o7blue
Ah, just like bash then. Thanks again highend!

Re: Script that tags parent folder with tags located in a json file

Posted: 22 Jul 2024 03:50
by o7blue
quicksearch() returns a list of paths, but how can I get the number of elements in that list?

I tried count() but that works only on arrays. Is there a list equivalent? It would be great for tracking progress in the foreach loop.

Re: Script that tags parent folder with tags located in a json file

Posted: 22 Jul 2024 07:43
by highend
gettoken() can do this

Re: Script that tags parent folder with tags located in a json file

Posted: 22 Jul 2024 17:59
by o7blue
Thanks highend! Was able to get the desired result with gettoken($json_list, "count", ".json") - 1