-
-
Notifications
You must be signed in to change notification settings - Fork 1.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Extremely Improved Bookmarks (Search + Strip URL + More) #1312
base: master
Are you sure you want to change the base?
Conversation
The inspiration: (Luke Smith's Video): "Bookmarking for Unix Chads" Instructions & Justifications & Very Detailed Explanation for Everything can be found below. Short Summary - Allows users to manage and navigate bookmarks using dmenu. - The user can perform actions such as adding, deleting, and editing bookmarks. The script also handles searching within specific websites if the bookmarked URL has the word "search" in it. Such as the SearxNG Instance: "paulgo.io/search?q=". - One more interesting feature of it is that it modifies the order of bookmarks by their popularity (how frequently visited by you). - It can work with Dash and it has no bashisms. Execution Time: Instant Required Programs: dash (or bash) | jq | echo | grep | dmenu | notification daemon | browser | xclip (or "wl-paste" on Wayland) Instructions: These directories should exist: ~/.local/share/larbs/ 1. pacman -s jq (it's a very small program (I.E. 690kb) 2. Open a browser and highlight (xclip -o users) or copy (Wayland users) a website's URL (starting with "http") such as "https://github.com" 2. Run the script with a shortcut you created for the window manager that is used. 3. Write "@@" inside the terminal then enter (@@ can be changed of course). This opens the "Action Menu". 4. Select "Add a New Bookmark" option then enter. 5. The bookmark will be added inside the bookmarks menu. It can be edited or deleted later from the action menu that can be opened with "@@". 6. If a website that has the word "search" in it is added inside bookmarks such as a SearxNG instance "paulgo.io/search?q=" , its search function can be used. When selected, it will offer for a new prompt for the desired keywords. Justification: 1. The script uses jq for parsing and modifying JSON data, which is a lightweight and powerful command-line JSON processor. This choice allows for easy manipulation of the JSON file that stores bookmarks. 2. The use of the while loop with the dmenu interface ensures that the user can perform multiple actions (adding, deleting, or editing bookmarks) in a single session without needing to restart the script. 3. The script checks for an existing URLQUERY_FILE and initializes it with an empty JSON array "[]" if it doesn't exist or is empty. This ensures that the file is always in a valid state for the script to operate. 4. The script sorts bookmarks by popularity, allowing users to quickly access their most frequently visited bookmarks. This is achieved by incrementing a popularity value each time a bookmark is opened. 5. The script supports searching within specific websites by checking if the word "search" is in the URL (More words can be added). This feature provides a convenient way to search within bookmarked websites directly from the script. 6. The use of the dash shell (#!/bin/sh) as the interpreter provides a lightweight and fast shell environment for the script, improving performance. Since the script is efficient enough so this performance difference is not huge, so it can also be used with bash. Detailed Explanation 1. URLQUERY_FILE="~/.local/share/larbs/urlquery": Sets the path for the JSON file that will store the bookmarks. 2. The following block checks if the URLQUERY_FILE exists and if it's empty. If either condition is met, it initializes the file with an empty JSON array "[]". If there is no JSON array present, then no bookmark can be added. `if [ ! -f "$URLQUERY_FILE" ] || [ ! -s "$URLQUERY_FILE" ]; then echo "[]" > "$URLQUERY_FILE" fi` 3. ACTION_MENU='@@': Sets a special string for the action menu. 4. The read_bookmarks function reads the contents of the URLQUERY_FILE using jq. The write_bookmarks function writes the contents passed as an argument to a temporary file and then moves it to the URLQUERY_FILE. The update_bookmark_popularity function updates the popularity value of a bookmark, given its name. 5. The contains_search function checks if a given string contains the word "search". It returns 0 if it does, 1 otherwise. 6. bookmarks=$(read_bookmarks): Reads the bookmarks from the file and stores them in a variable. 7. touch "$URLQUERY_FILE": Ensures the URLQUERY_FILE exists by creating it if it doesn't. 8. The following while loop presents a menu to the user for choosing an action (Add, Delete, or Edit bookmark) or a bookmark to open. It continues until the user selects a bookmark to open or provides an empty input. `while true; do SELECTION=$(echo "$bookmarks" | jq -r '. | sort_by(.[2]) | reverse | .[] | .[0]' | rofi -dmenu -p "Bookmark") if [ -z "$SELECTION" ] || [ "$SELECTION" != "$ACTION_MENU" ]; then write_bookmarks "$bookmarks" break fi ACTION=$(echo "Add a New Bookmark\nDelete a Bookmark\nEdit a Bookmark" | rofi -dmenu -p "Action") #... done` 9. The case block inside the while loop performs the selected action (Add, Delete, or Edit) based on the user's input. 10. After the loop, the script checks if a valid bookmark is selected. If so, it updates the popularity value, writes the changes to the file, and opens the bookmark in Firefox or any browser. If the bookmark contains the word "search", it prompts the user for a search query before opening the URL in Firefox. 11. Creating and moving temporary files are for data integrity and safety. It ensures 0 file corruptions. Has no negative effect in terms of performance.
1- Used logical operators instead of if statements. 2- Improved indentations and blocks for better readibility. 3- Simplified in general.
The idea got me hyped enough to try it. I would recommend renaming the script to sth like It requires As for usability, I suggest somehow not requiring the The main problem is that the script is currently broken. Upon adding a bookmark, it doesn't prompt for 'Name' dmenu at all. This is true when running it from .local/bin and also from dwm shortcut So when I copy a url at clipboard, then press My mind got to the I don't know what the format of Even if it all worked, if on the above packages url, you cannot search directly (as displayed in the video above with paulgo searx engine), I suggest against it imo. Because even if it worked, there is also the problem with local URL bookmarks which I assume will always be desynced to the browser's bookmarks (nothing this script can do against that, browsers are the bane of modern computers) |
Thanks for trying. Yes it requires a POSIX shell. Dash is very lightweight and the fastest shell so I chose Dash for most of my scripts. It's also portable. The file format (urlquery) is very simple. Your format is wrong. We use "=" as a separator: I have been using this for a very long time I don't think it's broken. You don't have to change the file yourself. FYI: xclip -o works with selected (highlighted) text; not copied. I am on Wayland and use a different command but it should work the same. Here below is a newer showcase. I can help you fix it if you can't fix it. By the way your last sentence is technically not correct. I have been using this script for a very long time and search function on all sites work. If a website changes its URL, you can change the URL too. It's not something that frequently happens. showcase.webm |
Here is your example site. Arch Linux website use this format. So you will highlight the link below. You don't need to copy. You need to highlight it (I don't do it on the video because I use another command that works with copying that is wl-copy. x-clip also has an equivalent but in that video Luke uses xclip -o so I kept the same): https://archlinux.org/packages/?sort=&q= So we will use this format in our file (the script does this automatically): Let me walk you through it with a video. I will back-up all of my current files and delete everything then start from 0. I just add another keyword for this site because it doesn't have search in it. Then I add it into my bookmarks and try to search in it. showcase_arch.webm |
I added some QOL and non-important improvements. These directories should exist: Remove the file beforehand just in case 1- Highlight this link by choosing every character of it with your mouse: https://github.com 2- Run the script with a shortcut you created for the window manager that is used. On Luke's DWM setup you will have a line like this. I use grave key you can use anything you want: When you run this script. The script automatically creates the urlquery file. 3- Then you need to prompt "@@" then enter; action menu opens. Select "Add" and it will prompt you asking a name. Enter "GitHub" for example and enter. When you do that, the "urlquery" file will have this line exactly: Now you can open your bookmark menu and select GitHub. You can see the similar showcases on newer videos I posted after your message. So the next time you open the bookmark script, the script will use the program "cut" with the "=" as a delimeter and will give you -f1 on Dmenu which is GitHub and -f2 to the browser which is https://github.com Basically:
This line fills the URL variable. We search for our selection inside the file, then we find it. Then we have a line like this: So in this repo, it means entering this command on the terminal: |
Thank you very much for the detailed reply. Not even in stack overflow would I find such an explanation, reminds me of forums :) I am especially surprised to see it working with custom searches (arch packages demonstration). That's extremely useful as I can query into whatever database from my command line, and for this reason alone, if fixed, I would suggest it gets merged. Though I would still suggest a name like ==================
There is a misunderstanding. Assuming this script works as showcased, these URL bookmarks are local, and do not sync with the browser's bookmarks. If you highlight a text in the browser, then click the star icon to the right, you add a bookmark to the browser. But this newly bookmarked URL is not bookmarked on the local bookmark manager. So if you bookmark a URL with your bookmark manager, it does not display on the browser as a bookmarked URL (as in, being clickable, icon and all). And vice versa if you bookmark a URL in the browser, it doesn't bookmark in the local bookmark manager. Now in a better world where browsers at least had local config files (in a txt or json or xml or whatever), it would be quite easy to sync them, where the browser writing on its config bookmark file would also write it in Since that is not possible because of the anti-user nature of browsers, the best alternative is to open the browser, export bookmarks as html, then manually paste them into Regardless of the above problem, this local bookmark manager is still superior to the browser's bookmarks, for 2 main reasons:
For the above reasons, I would definitely use this over the browser's bookmarks, even though they don't sync. ======== I used the script of the latest commit but I am still having issues making it work. I attach both use-cases. First being trying to add a script, and second being having added a url to I assume it has something to do with failed-to-add-url-bookmark.mp4pressing-enter-on-bookmarked-script.mp4 |
Oh of course. The browser bookmarks would be desynced. I misunderstood that. I haven't used in-browser bookmarks for years since I started using shell scripts. I guess I realized the problem. Since I use Rofi, it can be a little bit different than Dmenu. I guess dmenu can't show 0 lined entries. Can you change -l 0 with another number such as 2. That's why you probably don't see the newer dmenu prompt. For example you can do this to change all 0 line entries with 2 just for trying; and try running the script again later: Additionally FYI: Brave browser has a problem. I mean not a problem but a difference. It adds / at the end of URLs if you copy directly from the address bar on Brave (or any chromium browsers). Firefox and Librewolf don't do this. For example: https://www.github.com becomes https://www.github.com/ so it can break some URLs especially the ones with a search function. I could remove that in the script but then some websites would be broken because some sites use a search with a forward slash such as: https://www.wikiwand.com/en/{yourkeyword} -- so I can't remove that myself. This is an easy fix :) You can work this out. |
I run the above Also pressing edit, then Arch, I have 2 prompts (Edit/Delete), but pressing enter on either doesn't show anything afterwards. I will try to debug it, will post anything new
I use librefox atm, but you are right, even if I changed browser, its just a character swap. Regardless, thanks for notifying me for this, because if I didn't use librefox it would bug and I wouldn't understand why |
In this function, when I am prompted to Add, and press Enter, it prints "test3" on terminal, but it doesn't continue from there (e.g. continuing on dmenu) and also doesn't show "test4" add_bookmark() {
URL=$($CLIPBOARD) ;
is_valid_url "$URL" || error_notify "The clipboard content is not a valid URL." ;
grep -q "=$URL$" "$URLQUERY_FILE" && notify-send "The URL is already in the list." && return ;
echo "test3";
dmenu -i -l 2 -p "Name"
#NAME=$(DMENU 0 "Name")
echo "test4";
[ -n "$NAME" ] && echo "${NAME}=${URL}" >> "$URLQUERY_FILE" && notify-send "'$NAME' is bookmarked."
echo "test5";
} Specifically, I found the problem. I am currently looking into how to implement this cleanly everywhere |
Thanks for detailed analysis. I can fix this in batch form and inform you again. The problem is indeed how dmenu works compared to Rofi. |
I fixed it here (remove the debug messages 😅 ) eea4bc1 I tried to branch on your fork, but since me and you both have Regardless, thank you for creating this useful script and for the assistance. The script works as expected now. I suggest replacing the above parts of the code and it should work for everyone. As for author status, don't include me, it was a simple fix |
Can you test the latest version again? I will also change the name. By the way there is a patch for dmenu to make it centered if you want. Center Patch for Dmenu |
That works too. I confirmed it just now. It has the same minor aesthetics problem as mentioned however. Ah also, I heavily suggest changing the name to |
I renamed it. For aesthetics, you can search dmenu patches, just like the one I shared for Centered menu. Offtopic: @TheYellowArchitect You must be greek with "xaxaxa" laugh? In Turkey, random characters are used for that purpose: "dfglksdfk" known as keysmashing :) The case conditions for searching should be optional though? What do you think? I think a user should add any keyword there according to their usecase just like you adding "packages". Wiki and search would be intuitive for users that's why I used them. |
Nice, the name is great as it distincts from local bookmarks
Thank you for sharing me that list of patches. The aesthetics problem is minor anyway, it only lasts while you don't type any character, and when there are no choices, so it's not worth a patch, this script is worth a visual inconvenience which I won't even notice in practice
Unexpected observation but accurate xaxaxa
I understand that some keywords should be optional, but I cannot think of a url containing packages and not having searchable packages, hence my suggestion to include it, because i remember having seen it before with java, and I assume one can see it with NuGet packages (C#) and javascript Anyway, as long you place a comment above that line on what triggers the search, it's great imo. My use-case is covered personally, so idk about what URLs others save with the keyword packages inside, a comment above is good enough |
Open to more suggestions :) FYI you can also use Arch Wiki or Gentoo Wiki with their search URLs: |
Aside of the above, literally nothing can be suggested at this moment, you have added so much in a single day, that I would feel greedy if I requested anything else (since it would be optional, this script works great as it is atm) |
The inspiration: (Luke Smith's Video): "Bookmarking for Unix Chads"
Instructions & Justifications & Very Detailed Explanation for Everything can be found below.
Short Summary
Video Presentation Under a Minute (Notification Support Added Later):
bookmark.mp4
Execution Time: Instant
Required Programs: dash | sed | echo | grep | dmenu | notification daemon | browser | xclip (or "wl-paste --primary" on Wayland)
Instructions
These directories should exist:
~/.local/share/
Justification
The script uses jq for parsing and modifying JSON data, which is a lightweight and powerful command-line JSON processor. This choice allows for easy manipulation of the JSON file that stores bookmarks.The script now uses tools like sed, grep, cut. The logic is also simplified.
The script checks for an existing URLQUERY_FILE and initializes it if it doesn't exist or is empty. This ensures that the file is always in a valid state for the script to operate.
The script supports searching within specific websites by checking if the word "search" is in the URL (More words can be added). This feature provides a convenient way to search within bookmarked websites directly from the script.
The use of the dash shell (#!/bin/sh) as the interpreter provides a lightweight and fast shell environment for the script, improving performance. Since the script is efficient enough, this performance difference is not huge, so it can also be used with bash with some modifications.
Detailed Explanation
FUNCTIONS:
URLQUERY_FILE: The file where bookmarks are saved.
CLIPBOARD: Command to fetch content from the clipboard.
ACTION_MENU: A unique string that triggers the action menu when selected.
DMENU(): This is a function wrapper around the dmenu command to simplify its usage in the script.
error_notify(): Displays an error notification and exits the script if an error occurs.
ensure_file_exists(): Checks if the bookmark file exists. If it doesn’t, it creates it.
get_selection(): Retrieves a selection from the bookmark file using dmenu.
update_file(): A utility function to modify the bookmark file.
is_valid_url(): Validates if string in clipboard is a valid URL.
add_bookmark(): Adds a new bookmark to the file.
delete_bookmark(): Deletes a selected bookmark from the file.
edit_name() and edit_url(): Functions for editing the name or URL of an existing bookmark.
edit_bookmark(): Allows the user to choose to edit either the name or the URL of a bookmark.
open_bookmark(): Opens a selected bookmark in the default web browser. If the bookmarked URL has search, it prompts you for an extra query.
FLOW:
The script first ensures the bookmark file exists.
The user makes a selection using dmenu. If the special @@ string is selected, an action menu is shown with options like "Add", "Delete", and "Edit". Otherwise, the selected bookmark is opened.
Based on the user's choice, different functions are executed, and bookmarks can be added, deleted, edited, or opened.