Skip to content

Commit bb056f8

Browse files
committed
- Added Auto and Manual Checking for updates
- Manual Check in About Window - Auto Check happens once when you start the app - Auto Check for updates are enabled by default (Disable from Option menu or Ctrl+U) - This setting is also saved in the config file
1 parent f667ecf commit bb056f8

File tree

1 file changed

+57
-4
lines changed

1 file changed

+57
-4
lines changed

NSE_Option_Chain_Analyzer.py

Lines changed: 57 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@
1919

2020
# noinspection PyAttributeOutsideInit
2121
class Nse:
22+
version: str = '3.7'
23+
2224
def __init__(self, window: Tk) -> None:
2325
self.intervals: List[int] = [1, 2, 3, 5, 10, 15]
2426
self.stdout: TextIO = sys.stdout
@@ -55,6 +57,31 @@ def get_icon_path() -> str:
5557
base_path = os.path.abspath(".")
5658
return os.path.join(base_path, 'nse_logo.ico')
5759

60+
def check_for_updates(self, auto: bool = True) -> None:
61+
release_data: requests.Response = requests.get(
62+
"https://api.github.com/repos/VarunS2002/Python-NSE-Option-Chain-Analyzer/releases/latest")
63+
latest_version: str = release_data.json()['tag_name']
64+
65+
if float(latest_version) > float(Nse.version):
66+
self.info.attributes('-topmost', False) if not auto else None
67+
update: bool = messagebox.askyesno(
68+
title="New Update Available",
69+
message=f"You are running version: {Nse.version}\n"
70+
f"Latest version: {latest_version}\n"
71+
f"Do you want to update now ?\n"
72+
f"{'You can disable auto check for updates from the menu.' if auto and self.update else ''}")
73+
if update:
74+
webbrowser.open_new("https://github.com/VarunS2002/Python-NSE-Option-Chain-Analyzer/releases/latest")
75+
self.info.attributes('-topmost', False) if not auto else None
76+
else:
77+
self.info.attributes('-topmost', True) if not auto else None
78+
else:
79+
if not auto:
80+
self.info.attributes('-topmost', False)
81+
messagebox.showinfo(title="No Updates Available", message=f"You are running the latest version.\n"
82+
f"Version: {Nse.version}")
83+
self.info.attributes('-topmost', True)
84+
5885
def create_config(self, corrupted: bool = False) -> None:
5986
if corrupted:
6087
os.remove('NSE-OCA.ini')
@@ -67,6 +94,7 @@ def create_config(self, corrupted: bool = False) -> None:
6794
self.config_parser.set('main', 'live_export', 'False')
6895
self.config_parser.set('main', 'notifications', 'False')
6996
self.config_parser.set('main', 'auto_stop', 'False')
97+
self.config_parser.set('main', 'update', 'True')
7098
self.config_parser.set('main', 'logging', 'False')
7199

72100
with open('NSE-OCA.ini', 'w') as f:
@@ -80,6 +108,7 @@ def get_config(self) -> None:
80108
self.live_export: bool = self.config_parser.getboolean('main', 'live_export')
81109
self.notifications: bool = self.config_parser.getboolean('main', 'notifications')
82110
self.auto_stop: bool = self.config_parser.getboolean('main', 'auto_stop')
111+
self.update: bool = self.config_parser.getboolean('main', 'update')
83112
self.logging: bool = self.config_parser.getboolean('main', 'logging')
84113
except (configparser.NoOptionError, configparser.NoSectionError, configparser.MissingSectionHeaderError,
85114
configparser.DuplicateSectionError, configparser.DuplicateOptionError) as err:
@@ -386,6 +415,23 @@ def toggle_auto_stop(self, event: Optional[Event] = None) -> None:
386415
with open('NSE-OCA.ini', 'w') as f:
387416
self.config_parser.write(f)
388417

418+
# noinspection PyUnusedLocal
419+
def toggle_updates(self, event: Optional[Event] = None) -> None:
420+
if self.update:
421+
self.update = False
422+
self.options.entryconfig(self.options.index(6), label="Auto Check for Updates: Off")
423+
messagebox.showinfo(title="Auto Checking for Updates Disabled",
424+
message="Program will not check for updates at start.")
425+
else:
426+
self.update = True
427+
self.options.entryconfig(self.options.index(6), label="Auto Check for Updates: On")
428+
messagebox.showinfo(title="Auto Checking for Updates Enabled",
429+
message="Program will check for updates at start.")
430+
431+
self.config_parser.set('main', 'update', f'{self.update}')
432+
with open('NSE-OCA.ini', 'w') as f:
433+
self.config_parser.write(f)
434+
389435
# noinspection PyUnusedLocal
390436
def log(self, event: Optional[Event] = None) -> None:
391437
if self.first_run and self.logging or not self.logging:
@@ -402,7 +448,7 @@ def log(self, event: Optional[Event] = None) -> None:
402448
print('.py version')
403449

404450
try:
405-
self.options.entryconfig(self.options.index(6), label="Debug Logging: On")
451+
self.options.entryconfig(self.options.index(7), label="Debug Logging: On")
406452
messagebox.showinfo(title="Debug Logging Enabled",
407453
message="Errors will be logged to NSE-OCA.log.")
408454
except AttributeError:
@@ -413,7 +459,7 @@ def log(self, event: Optional[Event] = None) -> None:
413459
sys.stderr = self.stderr
414460
streamtologger._is_redirected = False
415461
self.logging = False
416-
self.options.entryconfig(self.options.index(6), label="Debug Logging: Off")
462+
self.options.entryconfig(self.options.index(7), label="Debug Logging: Off")
417463
messagebox.showinfo(title="Debug Logging Disabled", message="Errors will not be logged.")
418464

419465
self.config_parser.set('main', 'logging', f'{self.logging}')
@@ -468,7 +514,7 @@ def about(self, event: Optional[Event] = None) -> None:
468514
heading.grid(row=0, column=0, columnspan=2, sticky=N + S + W + E)
469515
version_label: Label = Label(self.info, text="Version:", relief=RIDGE)
470516
version_label.grid(row=1, column=0, sticky=N + S + W + E)
471-
version_val: Label = Label(self.info, text="3.7", relief=RIDGE)
517+
version_val: Label = Label(self.info, text=f"{Nse.version}", relief=RIDGE)
472518
version_val.grid(row=1, column=1, sticky=N + S + W + E)
473519
dev_label: Label = Label(self.info, text="Developer:", relief=RIDGE)
474520
dev_label.grid(row=2, column=0, sticky=N + S + W + E)
@@ -487,7 +533,9 @@ def about(self, event: Optional[Event] = None) -> None:
487533
sources: Label = Label(self.info, text="Sources", fg="blue", cursor="hand2", relief=RIDGE)
488534
sources.bind("<Button-1>", lambda click, link="sources": self.links(link, click))
489535
sources.grid(row=4, column=1, sticky=N + S + W + E)
490-
536+
updates: Button = Button(self.info, text="Check for Updates",
537+
command=lambda auto=False: self.check_for_updates(auto))
538+
updates.grid(row=5, column=0, columnspan=2, sticky=N + S + W + E)
491539
self.info.mainloop()
492540

493541
# noinspection PyUnusedLocal
@@ -528,6 +576,8 @@ def main_win(self) -> None:
528576
self.options.add_command(label=f"Stop automatically at 3:30pm: {'On' if self.auto_stop else 'Off'}",
529577
accelerator="(Ctrl+K)", command=self.toggle_auto_stop)
530578
self.options.add_separator()
579+
self.options.add_command(label=f"Auto Check for Updates: {'On' if self.update else 'Off'}",
580+
accelerator="(Ctrl+U)", command=self.toggle_updates)
531581
self.options.add_command(label=f"Debug Logging: {'On' if self.logging else 'Off'}", accelerator="(Ctrl+L)",
532582
command=self.log)
533583
self.options.add_command(label="About", accelerator="(Ctrl+M)", command=self.about)
@@ -540,6 +590,7 @@ def main_win(self) -> None:
540590
self.root.bind('<Control-b>', self.toggle_live_export)
541591
self.root.bind('<Control-n>', self.toggle_notifications)
542592
self.root.bind('<Control-k>', self.toggle_auto_stop)
593+
self.root.bind('<Control-u>', self.toggle_updates)
543594
self.root.bind('<Control-l>', self.log)
544595
self.root.bind('<Control-m>', self.about)
545596
self.root.bind('<Control-q>', self.close)
@@ -1094,6 +1145,8 @@ def main(self) -> None:
10941145
self.set_values()
10951146

10961147
if self.first_run:
1148+
if self.update:
1149+
self.check_for_updates()
10971150
self.first_run = False
10981151
if self.str_current_time == '15:30:00' and not self.stop and self.auto_stop:
10991152
self.stop = True

0 commit comments

Comments
 (0)