From 0dece2cec96254cc2644ff5478bd87dcf1e5e6cb Mon Sep 17 00:00:00 2001
From: itdominator <1itdominator@gmail.com>
Date: Tue, 4 Oct 2022 02:30:46 -0500
Subject: [PATCH] More searcher plugin updates, added additional file settings
---
plugins/searcher/mixins/grep_search_mixin.py | 3 +-
plugins/searcher/utils/search.py | 69 ++++++++++++++-----
.../searcher/widgets/grep_preview_widget.py | 52 +++++++-------
3 files changed, 78 insertions(+), 46 deletions(-)
diff --git a/plugins/searcher/mixins/grep_search_mixin.py b/plugins/searcher/mixins/grep_search_mixin.py
index 860a346..cdf1c58 100644
--- a/plugins/searcher/mixins/grep_search_mixin.py
+++ b/plugins/searcher/mixins/grep_search_mixin.py
@@ -70,4 +70,5 @@ class GrepSearchMixin:
grep_result = jdata[key]
widget = GrepPreviewWidget(key, sub_keys, grep_result)
- self._grep_list.add(widget)
+ GLib.idle_add(self._grep_list.add, widget)
+ # self._grep_list.add(widget)
diff --git a/plugins/searcher/utils/search.py b/plugins/searcher/utils/search.py
index f06f3fa..1355f1d 100755
--- a/plugins/searcher/utils/search.py
+++ b/plugins/searcher/utils/search.py
@@ -2,7 +2,7 @@
# Python imports
-import os, traceback, argparse, json, base64
+import os, traceback, argparse, threading, json, base64, time
from setproctitle import setproctitle
from multiprocessing.connection import Client
@@ -16,11 +16,20 @@ from multiprocessing.connection import Client
_ipc_address = f'/tmp/solarfm-search_grep-ipc.sock'
_ipc_authkey = b'' + bytes(f'solarfm-search_grep-ipc', 'utf-8')
-filter = (".mkv", ".mp4", ".webm", ".avi", ".mov", ".m4v", ".mpg", ".mpeg", ".wmv", ".flv") + \
- (".png", ".jpg", ".jpeg", ".gif", ".ico", ".tga", ".webp") + \
- (".psf", ".mp3", ".ogg", ".flac", ".m4a")
+filter = (".cpp", ".css", ".c", ".go", ".html", ".htm", ".java", ".js", ".json", ".lua", ".md", ".py", ".rs", ".toml", ".xml", ".pom") + \
+ (".txt", ".text", ".sh", ".cfg", ".conf", ".log")
-file_result_set = []
+# NOTE: Threads WILL NOT die with parent's destruction.
+def threaded(fn):
+ def wrapper(*args, **kwargs):
+ threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=False).start()
+ return wrapper
+
+# NOTE: Threads WILL die with parent's destruction.
+def daemon_threaded(fn):
+ def wrapper(*args, **kwargs):
+ threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=True).start()
+ return wrapper
def send_ipc_message(message) -> None:
@@ -42,7 +51,7 @@ def file_search(path, query):
if os.path.isdir(target):
file_search(target, query)
else:
- if query.lower() in file.lower():
+ if query in file.lower():
data = f"SEARCH|{json.dumps([target, file])}"
send_ipc_message(data)
except Exception as e:
@@ -52,21 +61,40 @@ def file_search(path, query):
def _search_for_string(file, query):
b64_file = base64.urlsafe_b64encode(file.encode('utf-8')).decode('utf-8')
grep_result_set = {}
-
+ padding = 15
with open(file, 'r') as fp:
- for i, line in enumerate(fp):
- if query in line:
- b64_line = base64.urlsafe_b64encode(line.encode('utf-8')).decode('utf-8')
+ # NOTE: I know there's an issue if there's a very large file with content all on one line will lower and dupe it.
+ # And, yes, it will only return one instance from the file.
+ for i, raw in enumerate(fp):
+ line = None
+ llower = raw.lower()
+ if not query in llower:
+ continue
- if f"{b64_file}" in grep_result_set.keys():
- grep_result_set[f"{b64_file}"][f"{i+1}"] = b64_line
- else:
- grep_result_set[f"{b64_file}"] = {}
- grep_result_set[f"{b64_file}"] = {f"{i+1}": b64_line}
+ if len(raw) > 72:
+ start = 0
+ end = len(raw) - 1
+ index = llower.index(query)
+ sindex = llower.index(query) - 15 if index >= 15 else abs(start - index) - index
+ eindex = sindex + 15 if end > (index + 15) else abs(index - end) + index
+ line = raw[sindex:eindex]
+ else:
+ line = raw
+
+ b64_line = base64.urlsafe_b64encode(line.encode('utf-8')).decode('utf-8')
+ if f"{b64_file}" in grep_result_set.keys():
+ grep_result_set[f"{b64_file}"][f"{i+1}"] = b64_line
+ else:
+ grep_result_set[f"{b64_file}"] = {}
+ grep_result_set[f"{b64_file}"] = {f"{i+1}": b64_line}
data = f"GREP|{json.dumps(grep_result_set)}"
send_ipc_message(data)
+@daemon_threaded
+def _search_for_string_threaded(file, query):
+ _search_for_string(file, query)
+
def grep_search(path, query):
try:
@@ -75,18 +103,23 @@ def grep_search(path, query):
if os.path.isdir(target):
grep_search(target, query)
else:
- if not target.lower().endswith(filter):
+ if target.lower().endswith(filter):
+ size = os.path.getsize(target)
+ if size < 5000:
_search_for_string(target, query)
+ else:
+ _search_for_string_threaded(target, query)
+
except Exception as e:
print("Couldn't traverse to path. Might be permissions related...")
traceback.print_exc()
def search(args):
if args.type == "file_search":
- file_search(args.dir, args.query)
+ file_search(args.dir, args.query.lower())
if args.type == "grep_search":
- grep_search(args.dir, args.query)
+ grep_search(args.dir, args.query.lower())
if __name__ == "__main__":
diff --git a/plugins/searcher/widgets/grep_preview_widget.py b/plugins/searcher/widgets/grep_preview_widget.py
index 85aa2f8..899d309 100644
--- a/plugins/searcher/widgets/grep_preview_widget.py
+++ b/plugins/searcher/widgets/grep_preview_widget.py
@@ -10,37 +10,35 @@ from gi.repository import Gtk
class GrepPreviewWidget(Gtk.Box):
- def __init__(self, _path, sub_keys, data):
+ def __init__(self, _path, sub_keys, _data):
super(GrepPreviewWidget, self).__init__()
self.set_orientation(Gtk.Orientation.VERTICAL)
self.line_color = "#e0cc64"
- path = base64.urlsafe_b64decode(_path.encode('utf-8')).decode('utf-8')
- _label = '/'.join( path.split("/")[-3:] )
- title = Gtk.LinkButton.new_with_label(uri=f"file://{path}", label=_label)
+ path = self.decode_str(_path)
+ _label = '/'.join( path.split("/")[-3:] )
+ title = Gtk.LinkButton.new_with_label(uri=f"file://{path}", label=_label)
+
+ text_view = Gtk.TextView()
+ text_view.set_editable(False)
+ text_view.set_wrap_mode(Gtk.WrapMode.NONE)
+ buffer = text_view.get_buffer()
+
+ for i, key in enumerate(sub_keys):
+ line_num = self.make_utf8_line_num(self.line_color, key)
+ text = f"\t\t{ self.decode_str(_data[key]) }"
+
+ itr = buffer.get_end_iter()
+ buffer.insert_markup(itr, line_num, len(line_num))
+ itr = buffer.get_end_iter()
+ buffer.insert(itr, text, length=len(text))
self.add(title)
- for key in sub_keys:
- line_num = key
- text = base64.urlsafe_b64decode(data[key].encode('utf-8')).decode('utf-8')
-
-
- box = Gtk.Box()
- number_label = Gtk.Label()
- text_view = Gtk.Label(label=text[:-1])
- label_text = f"{line_num}"
-
- number_label.set_markup(label_text)
- number_label.set_margin_left(15)
- number_label.set_margin_right(5)
- number_label.set_margin_top(5)
- number_label.set_margin_bottom(5)
- text_view.set_margin_top(5)
- text_view.set_margin_bottom(5)
- text_view.set_line_wrap(True)
-
- box.add(number_label)
- box.add(text_view)
- self.add(box)
-
+ self.add(text_view)
self.show_all()
+
+ def decode_str(self, target):
+ return base64.urlsafe_b64decode(target.encode('utf-8')).decode('utf-8')
+
+ def make_utf8_line_num(self, color, target):
+ return bytes(f"\n{target}", "utf-8").decode("utf-8")