Misha Posted November 24, 2017 Share Posted November 24, 2017 (edited) Hi all, is it possible to create a dynamic script filter, in the sense that the list of options is created on the basis of the contents of a directory? I currently have this code, which seems to work in the terminal, but it doesn't produce the list that I would like: for f in mydirectory/*; do x=$(basename "$f") x1="${x%.*}" x12=$(echo $x | sed 's/_.*//') cat << EOB {"items": [ { "uid": "$x1", "type": "file", "title": "$x1", "subtitle": "", "arg": "mydirectory/$x1", "autocomplete": "$x1", "icon": { "path": "colour_$x12.png" } }, ]} EOB done Edited November 24, 2017 by Misha Link to comment
deanishe Posted November 24, 2017 Share Posted November 24, 2017 (edited) It's wrong in a few ways. First of all, generating valid JSON with bash is tricky. There's a good chance that even when the logic is fixed, it's still going to break on certain filenames. The two big problems are: You must only output one JSON items object. You're outputting one for each file, and {...}{...} is not valid JSON, let alone the correct format for Alfred. You're using a relative filepath (mydirectory/*). Workflows are run with the workflow's own directory as the working directory, so unless you are actually trying to list the files in a subdirectory of the workflow, you'll need an absolute path. Edited November 24, 2017 by deanishe Link to comment
Misha Posted November 25, 2017 Author Share Posted November 25, 2017 Thanks Deanishe for your quick reply. The item point solved the problem! (I changed the directory to "mydirectory" because of privacy reasons). I am sure there are more elegant ways of doing this, but for anyone trying to do the same, this code works for me: cat << EOB {"items": [ EOB for f in /mydirectory/*; do x=$(basename "$f") x1="${x%.*}" x12=$(echo $x | sed 's/_.*//') cat << EOB { "uid": "$x1", "type": "file", "title": "$x1", "subtitle": "", "arg": "/mydirectory/$x1", "autocomplete": "$x1", "icon": { "path": "colour_$x12.png" } }, EOB done cat << EOB ]} EOB Link to comment
deanishe Posted November 25, 2017 Share Posted November 25, 2017 3 minutes ago, Misha said: this code works for me It shouldn't, tbh: the JSON is invalid. If Alfred is accepting it, it must be using a non-standard JSON parser, as trailing commas are not permitted in JSON. Link to comment
Misha Posted November 25, 2017 Author Share Posted November 25, 2017 The script reads files in a folder, and creates a script filter (list) based on the names of each of the files. In that way at least it works fine.... So yes, maybe because of Alfred's parser... Thanks for your help anyway Link to comment
dfay Posted November 25, 2017 Share Posted November 25, 2017 Why wouldn’t you just use a file filter set to that directory? Link to comment
deanishe Posted November 25, 2017 Share Posted November 25, 2017 10 hours ago, dfay said: Why wouldn’t you just use a file filter set to that directory? He's doing funky things with the icons. Link to comment
Misha Posted November 26, 2017 Author Share Posted November 26, 2017 I'm definitely doing funky things. And I'm also sure the things I do could be done differently and better. (I built my own time-clock (checking in and out for certain tasks). For that, this setup works for me because 1. it shows all the options at once, while (I believe) a file filter wouldn't 2. I can adjust the icons (they are dynamic) and 3. I can attach arguments to these options that I use later on in the workflow.) Link to comment
giovanni Posted May 21, 2020 Share Posted May 21, 2020 (edited) On 11/25/2017 at 7:24 AM, deanishe said: It shouldn't, tbh: the JSON is invalid. If Alfred is accepting it, it must be using a non-standard JSON parser, as trailing commas are not permitted in JSON. Hi @deanishe may I ask what the correct syntax should be? I am trying to learn how to replace XML with JSON in my script filters (mostly serving the output of grep commands, typically multiple matches), and this from the OP seems to me similar to what is provided as an example in Alfred. Thanks for educating us newbies! G. Edited May 21, 2020 by giovanni Link to comment
Andrew Posted May 21, 2020 Share Posted May 21, 2020 @giovanni The full syntax for Alfred's JSON is described on this page: https://www.alfredapp.com/help/workflows/inputs/script-filter/json/ And there are some built in examples in Alfred's Workflow editor from the [+] > Examples > Script Filter / Advanced Script Filters Cheers, Andrew giovanni 1 Link to comment
giovanni Posted May 21, 2020 Share Posted May 21, 2020 Thanks! To clarify, I am trying to convert an XML script filter to JSON and I was wondering about the appropriate way to generate dynamically a JSON object containing multiple items (from grep matches), and avoid the trailing comma. thanks again! giovanni Link to comment
deanishe Posted May 22, 2020 Share Posted May 22, 2020 On 5/21/2020 at 6:22 PM, giovanni said: the appropriate way to generate dynamically a JSON object containing multiple items (from grep matches), and avoid the trailing comma TBH, the only safe (and sane) way to do it is to use a real JSON library or tool. You can get away with cat for static (or very, very limited) JSON, but for anything that isn't super simple, you shouldn’t try to generate JSON by smushing strings together. So you should either use a language with support for JSON (essentially anything but shell or AppleScript), or if you simply must use bash even when it’s not up to the job, you can use jq (install it with Homebrew). giovanni 1 Link to comment
Shis1982 Posted May 28, 2020 Share Posted May 28, 2020 (edited) thanks, taking in consideration that i'm having a similar problem but i'm far from professional on main course, i found it all very useful. may i ask you questions if i would have any? thanks Edited June 8, 2020 by Shis1982 grammar Link to comment
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now