analitics

Pages

Showing posts with label 2026. Show all posts
Showing posts with label 2026. Show all posts

Thursday, October 8, 2026

News : Python 3.15 PEP's.

Python 3.15 brings significant improvements across performance, core features, and developer tools. The startup time is now much faster thanks to explicit lazy imports, and the experimental JIT compiler provides a 7 to 12 percent speed boost depending on your operating system. The update introduces new built-in types like frozendict and sentinel, and officially makes UTF-8 the default text encoding. For developers, the standard library now includes better error messages, more console colors, and a new high-frequency profiling tool called Tachyon to help measure and optimize code performance. The type hinting system is more flexible, and there are major updates to the C API. Most notably, it includes a stable ABI for free-threaded builds, which is a massive step forward for running efficient multi-threaded Python code without the Global Interpreter Lock. Additionally, official macOS installers now include free-threading support by default, Windows 64-bit binaries use a more optimized tail-calling interpreter, and frame pointers are enabled by default for easier system-level debugging. This specific Release Candidate 3 is a surprise extra release added to fix a few last-minute bugs related to the new lazy imports before the final version is launched.
  • PEP 810: Explicit lazy imports for faster startup times
  • PEP 814: Add frozendict built-in type
  • PEP 661: Add sentinel built-in type
  • PEP 798: Unpacking in comprehensions
  • PEP 686: Python now uses UTF-8 as the default encoding
  • PEP 829: Package startup configuration files
  • PEP 799: Tachyon: High frequency statistical sampling profiler / A dedicated profiling package
  • PEP 728: TypedDict with typed extra items
  • PEP 747: Annotating type forms with TypeForm
  • PEP 800: Disjoint bases in the type system
  • PEP 803, 820, 793: Stable ABI for free-threaded builds and related C API
  • PEP 782: A new PyBytesWriter C API to create a Python bytes object
  • PEP 788: Protection against finalization in the C API
  • PEP 831: Frame pointers are enabled by default for improved system-level observability
  • PEP 790: 3.15 release schedule

tkinter : analyze stock market data for a chosen ticker symbol

This Python script creates a mobile-friendly graphical application using Tkinter to analyze stock market data for a chosen ticker symbol, such as NVDA. When you launch the app, it presents a user interface with input fields to type a stock symbol and select a time frame, like one month, six months, or one year. Upon clicking the Load button, the script sends a direct web request to Yahoo Finance. It uses a custom user browser agent header to fetch accurate raw historical market price data, avoiding network blocking or API failures on mobile Python environments. Once the raw data is downloaded, the script converts the response into a structured Pandas dataframe containing daily open, high, low, close, and volume values. It then automatically computes several key technical market indicators. It calculates 20-day and 50-day Simple Moving Averages to show price trends over time. It computes Bollinger Bands to illustrate price volatility boundaries, and it calculates the Relative Strength Index over 14 days to identify overbought or oversold market conditions. At the top of the interface, the app displays text cards showing the latest stock price, current RSI value, and moving averages. Below these metrics, it renders two interactive charts using Matplotlib embedded directly into Tkinter. The upper chart plots the stock closing price alongside the moving averages and Bollinger Bands shading. The lower chart plots the RSI line with dashed horizontal benchmark lines at values 30 and 70. In short, this script serves as a lightweight, real-time stock dashboard that fetches financial market data, calculates essential technical indicators, and visualizes price action clearly on mobile screens.
Let's see the source code:
import tkinter as tk
from tkinter import ttk, messagebox
import pandas as pd
import numpy as np
import requests
from datetime import datetime, timedelta

import matplotlib
matplotlib.use("TkAgg")
from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg
from matplotlib.figure import Figure

class FinancialDashboardApp:
    def __init__(self, root):
        self.root = root
        self.root.title("Market Indicators Dashboard")
        self.root.geometry("480x800")

        # --- Controls Frame (Top) ---
        control_frame = ttk.LabelFrame(root, text=" Parametrii Simbol ")
        control_frame.pack(fill="x", padx=10, pady=5)

        ttk.Label(control_frame, text="Ticker:").grid(row=0, column=0, padx=5, pady=5)
        self.ticker_entry = ttk.Entry(control_frame, width=8)
        self.ticker_entry.insert(0, "NVDA")
        self.ticker_entry.grid(row=0, column=1, padx=5, pady=5)

        ttk.Label(control_frame, text="Perioadă:").grid(row=0, column=2, padx=5, pady=5)
        self.period_cb = ttk.Combobox(control_frame, values=["1mo", "3mo", "6mo", "1y"], width=6)
        self.period_cb.set("6mo")
        self.period_cb.grid(row=0, column=3, padx=5, pady=5)

        fetch_btn = ttk.Button(control_frame, text="Încarcă", command=self.load_data)
        fetch_btn.grid(row=0, column=4, padx=5, pady=5)

        # --- Info Cards Frame (Middle) ---
        self.info_frame = ttk.LabelFrame(root, text=" Date & Indicatori ")
        self.info_frame.pack(fill="x", padx=10, pady=5)

        self.lbl_price = ttk.Label(self.info_frame, text="Preț: -", font=("Helvetica", 10, "bold"))
        self.lbl_price.grid(row=0, column=0, sticky="w", padx=10, pady=2)

        self.lbl_rsi = ttk.Label(self.info_frame, text="RSI (14): -")
        self.lbl_rsi.grid(row=0, column=1, sticky="w", padx=10, pady=2)

        self.lbl_sma20 = ttk.Label(self.info_frame, text="SMA 20: -")
        self.lbl_sma20.grid(row=1, column=0, sticky="w", padx=10, pady=2)

        self.lbl_sma50 = ttk.Label(self.info_frame, text="SMA 50: -")
        self.lbl_sma50.grid(row=1, column=1, sticky="w", padx=10, pady=2)

        # --- Matplotlib Canvas Frame (Bottom) ---
        self.plot_frame = ttk.Frame(root)
        self.plot_frame.pack(fill="both", expand=True, padx=10, pady=5)

        self.fig = Figure(figsize=(5, 6), dpi=90)
        self.ax1 = self.fig.add_subplot(211) # Subplot Preț + SMA / Bollinger
        self.ax2 = self.fig.add_subplot(212, sharex=self.ax1) # Subplot RSI

        self.canvas = FigureCanvasTkAgg(self.fig, master=self.plot_frame)
        self.canvas.get_tk_widget().pack(fill="both", expand=True)

        self.load_data()

    def fetch_yahoo_data(self, symbol, range_str):
        """Descarcă date brute din Yahoo v8 API simulând un browser desktop."""
        url = f"https://query1.finance.yahoo.com/v8/finance/chart/{symbol}?range={range_str}&interval=1d"
        headers = {
            "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36"
        }
        
        response = requests.get(url, headers=headers, timeout=10)
        if response.status_code != 200:
            return pd.DataFrame()

        data = response.json()
        result = data['chart']['result'][0]
        timestamps = result['timestamp']
        quote = result['indicators']['quote'][0]

        df = pd.DataFrame({
            'Open': quote['open'],
            'High': quote['high'],
            'Low': quote['low'],
            'Close': quote['close'],
            'Volume': quote['volume']
        }, index=pd.to_datetime(timestamps, unit='s'))

        df.dropna(subset=['Close'], inplace=True)
        return df

    def calculate_indicators(self, df):
        # 1. Simple Moving Averages (SMA)
        df['SMA_20'] = df['Close'].rolling(window=20).mean()
        df['SMA_50'] = df['Close'].rolling(window=50).mean()

        # 2. Bollinger Bands
        std20 = df['Close'].rolling(window=20).std()
        df['BB_Upper'] = df['SMA_20'] + (std20 * 2)
        df['BB_Lower'] = df['SMA_20'] - (std20 * 2)

        # 3. RSI (14 zile)
        delta = df['Close'].diff()
        gain = (delta.where(delta > 0, 0)).rolling(window=14).mean()
        loss = (-delta.where(delta < 0, 0)).rolling(window=14).mean()
        rs = gain / loss
        df['RSI'] = 100 - (100 / (1 + rs))

        return df

    def load_data(self):
        ticker_symbol = self.ticker_entry.get().strip().upper()
        period = self.period_cb.get()

        if not ticker_symbol:
            messagebox.showerror("Eroare", "Introduceți un ticker valid.")
            return

        try:
            # Preluare date prin request HTTP direct
            df = self.fetch_yahoo_data(ticker_symbol, period)

            if df.empty:
                messagebox.showwarning("Atenție", f"Nu s-au găsit date pentru tickerul '{ticker_symbol}'. Verificați conexiunea la internet sau simbolul introduse.")
                return

            df = self.calculate_indicators(df)

            curr_price = df['Close'].iloc[-1]
            last_rsi = df['RSI'].iloc[-1] if not pd.isna(df['RSI'].iloc[-1]) else 0.0
            last_sma20 = df['SMA_20'].iloc[-1] if not pd.isna(df['SMA_20'].iloc[-1]) else 0.0
            last_sma50 = df['SMA_50'].iloc[-1] if not pd.isna(df['SMA_50'].iloc[-1]) else 0.0

            # Actualizare etichete UI
            self.lbl_price.config(text=f"Preț: {curr_price:.2f} USD")
            self.lbl_rsi.config(text=f"RSI (14): {last_rsi:.2f}")
            self.lbl_sma20.config(text=f"SMA 20: {last_sma20:.2f}")
            self.lbl_sma50.config(text=f"SMA 50: {last_sma50:.2f}")

            # Generare grafice
            self.plot_charts(df, ticker_symbol)

        except Exception as e:
            messagebox.showerror("Eroare", f"A apărut o eroare la procesare:\n{e}")

    def plot_charts(self, df, ticker_symbol):
        self.ax1.clear()
        self.ax2.clear()

        # Grafic 1: Preț, SMA 20, SMA 50 și Benzi Bollinger
        self.ax1.plot(df.index, df['Close'], label='Close', color='black', linewidth=1.2)
        self.ax1.plot(df.index, df['SMA_20'], label='SMA 20', color='blue', linestyle='--', alpha=0.7)
        self.ax1.plot(df.index, df['SMA_50'], label='SMA 50', color='orange', linestyle='--', alpha=0.7)
        self.ax1.plot(df.index, df['BB_Upper'], label='BB Upper', color='gray', linestyle=':', alpha=0.5)
        self.ax1.plot(df.index, df['BB_Lower'], label='BB Lower', color='gray', linestyle=':', alpha=0.5)
        self.ax1.fill_between(df.index, df['BB_Lower'], df['BB_Upper'], color='gray', alpha=0.1)

        self.ax1.set_title(f"{ticker_symbol} - Preț & Indicatori", fontsize=10)
        self.ax1.legend(loc="upper left", fontsize=7)
        self.ax1.grid(True, linestyle=':', alpha=0.6)

        # Grafic 2: RSI cu nivelurile 30 și 70
        self.ax2.plot(df.index, df['RSI'], label='RSI (14)', color='purple')
        self.ax2.axhline(70, color='red', linestyle='--', alpha=0.6)   # Overbought
        self.ax2.axhline(30, color='green', linestyle='--', alpha=0.6) # Oversold
        self.ax2.set_ylim(0, 100)
        self.ax2.set_title("RSI (14)", fontsize=9)
        self.ax2.grid(True, linestyle=':', alpha=0.6)

        self.fig.autofmt_xdate(rotation=30)
        self.fig.tight_layout()
        self.canvas.draw()

if __name__ == "__main__":
    root = tk.Tk()
    app = FinancialDashboardApp(root)
    root.mainloop()

Tuesday, October 6, 2026

News : How fast is Python 3.15? by Miguel Grinberg.

The article “How fast is Python 3.15?” provides a detailed performance analysis of the upcoming CPython release, focusing on benchmark‑driven comparisons across standard CPython, the new JIT compiler, and the free‑threaded (no‑GIL) build. Using two deterministic workloads—recursive Fibonacci and bubble sort—the author evaluates Python 3.15 in both single‑threaded and multi‑threaded execution modes, generating a clear performance profile relevant for developers, performance engineers, and technical SEO audiences researching Python speed improvements.
In single‑threaded Fibonacci, Python 3.15 shows incremental gains over Python 3.14, continuing the trend of small but consistent optimizations introduced after the major jump in Python 3.11. The standout result is the Python 3.15 JIT, which delivers a 1.20× speedup over standard CPython. This marks the first release where the JIT consistently outperforms the interpreter in this benchmark. PyPy remains significantly faster, achieving 5.5× the speed of CPython 3.15, while Rust demonstrates extreme performance at 77× faster, reinforcing the gap between dynamic and compiled languages.
The single‑threaded bubble‑sort benchmark confirms the same pattern: Python 3.15 is slightly faster than 3.14, but the JIT build provides a substantial 1.28× improvement. Node.js surpasses PyPy in this specific workload, highlighting how algorithmic characteristics influence interpreter performance. Free‑threaded CPython remains slower in single‑thread mode due to concurrency‑related overhead, which is expected.
The multi‑threaded benchmarks reveal the most important performance evolution. Standard CPython continues to scale poorly because of the Global Interpreter Lock (GIL), and Python 3.15 is marginally slower than 3.14 in multi‑threaded Fibonacci. PyPy also suffers from GIL‑related limitations.
However, free‑threaded Python 3.15 demonstrates a major breakthrough: in multi‑threaded Fibonacci, it achieves a 4.5× speedup compared to standard CPython, matching and stabilizing the gains introduced in Python 3.14 FT. This confirms that the no‑GIL architecture is maturing and becoming a viable option for CPU‑bound parallel workloads. The JIT build maintains its advantage even under multi‑threading, showing consistent performance improvements across all categories.
From a technical SEO perspective, the article positions Python 3.15 as a release focused on predictable single‑threaded optimizations, significant JIT compiler progress, and high‑impact concurrency improvements through the free‑threaded runtime. These advancements make Python 3.15 a strategically important version for developers targeting performance‑critical applications, parallel computing, and future no‑GIL migration paths.
See the full article on the official blog.

thinter : manage python scripts !!!

Today, this simple manager for python scripts with autodetect python modules and add to description for each script with Claude AI.
See the source code:
# -*- coding: utf-8 -*-
import os
import re
import ast
import sys
import json
import hashlib
import subprocess
import tkinter as tk
from tkinter import ttk, messagebox
import tkinter.font as tkfont
DEFAULT_ROOT = "/storage/emulated/0/Download"
CATALOG_NAME = ".scripts_catalog.json"
FONT_SIZE = 10
try:
    BASE_DIR = os.path.dirname(os.path.abspath(__file__))
except NameError:
    BASE_DIR = os.getcwd()
STD = getattr(sys, "stdlib_module_names", None)
if STD is None:
    STD = set((
        "__future__ abc argparse array ast asyncio base64 bisect bz2 calendar cmd code codecs collections "
        "configparser contextlib copy csv ctypes curses dataclasses datetime decimal difflib email enum "
        "fnmatch fractions ftplib functools gc getopt getpass gettext glob gzip hashlib heapq hmac html http "
        "imaplib importlib inspect io itertools json locale logging lzma math mimetypes msvcrt multiprocessing "
        "operator optparse os pathlib pdb pickle platform pprint profile queue random re readline sched secrets "
        "select shelve shutil signal smtplib socket sqlite3 ssl stat statistics string struct subprocess sys "
        "tarfile telnetlib tempfile textwrap threading time timeit tkinter traceback turtle types typing "
        "unittest urllib uuid warnings weakref webbrowser winreg xml zipfile zlib"
    ).split())
ALIASES = {
    "PIL": "Pillow", "cv2": "opencv-python", "yt_dlp": "yt-dlp", "bs4": "beautifulsoup4",
    "sklearn": "scikit-learn", "yaml": "PyYAML", "dotenv": "python-dotenv", "serial": "pyserial",
    "win32api": "pywin32", "win32com": "pywin32", "Crypto": "pycryptodome", "skimage": "scikit-image",
    "dateutil": "python-dateutil", "OpenGL": "PyOpenGL", "bpy": "bpy (Blender)",
}
def safe(text):
    return str(text).encode("utf-8", "replace").decode("utf-8")
def read_json(path):
    try:
        with open(path, "r", encoding="utf-8") as f:
            return json.load(f)
    except Exception:
        return None
def is_local(mod, full, root_folder):
    root_n = os.path.normpath(root_folder)
    cur = os.path.normpath(os.path.dirname(full))
    while True:
        is_root = (cur == root_n)
        if os.path.isfile(os.path.join(cur, mod + ".py")):
            return True
        if not is_root and os.path.isdir(os.path.join(cur, mod)):
            return True
        if is_root or len(cur) <= len(root_n):
            return False
        cur = os.path.dirname(cur)
def analyze(full, root_folder):
    try:
        with open(full, "r", encoding="utf-8", errors="replace") as f:
            text = f.read(300000)
    except OSError:
        return "Libs: nu pot citi fișierul"
    mods = []
    try:
        for node in ast.walk(ast.parse(text)):
            if isinstance(node, ast.Import):
                for a in node.names:
                    mods.append(a.name.split(".")[0])
            elif isinstance(node, ast.ImportFrom):
                if node.module and node.level == 0:
                    mods.append(node.module.split(".")[0])
    except (SyntaxError, ValueError):
        pattern = r"^\s*(?:from\s+([A-Za-z_]\w*)[\w.]*\s+import\s|import\s+([A-Za-z_]\w*))"
        for m in re.finditer(pattern, text, re.M):
            mods.append(m.group(1) or m.group(2))
    libs = []
    for m in mods:
        if m in STD or is_local(m, full, root_folder):
            continue
        name = ALIASES.get(m, m)
        if name not in libs:
            libs.append(name)
    libs.sort(key=str.lower)
    return "Libs: " + (", ".join(libs) if libs else "doar biblioteca standard")
class App:
    def __init__(self, root):
        self.root = root
        root.title("Python Scripts Manager")
        root.geometry("900x600")
        self.scripts = []
        self.files = {}
        self.root_folder = ""
        self.font = tkfont.Font(family="Arial", size=FONT_SIZE)
        style = ttk.Style()
        style.configure("Treeview", font=self.font, rowheight=self.font.metrics("linespace") + 14)
        style.configure("Treeview.Heading", font=(self.font.actual("family"), FONT_SIZE, "bold"))
        top = tk.Frame(root)
        top.pack(fill="x", padx=6, pady=4)
        tk.Label(top, text="Folder:").pack(side="left")
        self.path_var = tk.StringVar(value=DEFAULT_ROOT)
        tk.Entry(top, textvariable=self.path_var, font=self.font).pack(side="left", fill="x", expand=True, padx=4)
        tk.Button(top, text="Scan", command=self.load_scripts).pack(side="left")
        search = tk.Frame(root)
        search.pack(fill="x", padx=6)
        tk.Label(search, text="Caută:").pack(side="left")
        self.search_var = tk.StringVar()
        self.search_var.trace_add("write", lambda *a: self.refresh_table())
        tk.Entry(search, textvariable=self.search_var, font=self.font).pack(side="left", fill="x", expand=True, padx=4)
        frame = tk.Frame(root)
        frame.pack(fill="both", expand=True, padx=6, pady=4)
        self.tree = ttk.Treeview(frame, columns=("name", "rel", "desc"), show="headings", selectmode="browse")
        self.tree.heading("name", text="Script")
        self.tree.heading("rel", text="Path relativ")
        self.tree.heading("desc", text="Descriere")
        self.tree.column("name", width=180)
        self.tree.column("rel", width=300)
        self.tree.column("desc", width=300)
        self.tree.tag_configure("auto", foreground="gray")
        vsb = ttk.Scrollbar(frame, orient="vertical", command=self.tree.yview)
        hsb = ttk.Scrollbar(frame, orient="horizontal", command=self.tree.xview)
        self.tree.configure(yscrollcommand=vsb.set, xscrollcommand=hsb.set)
        self.tree.grid(row=0, column=0, sticky="nsew")
        vsb.grid(row=0, column=1, sticky="ns")
        hsb.grid(row=1, column=0, sticky="ew")
        frame.rowconfigure(0, weight=1)
        frame.columnconfigure(0, weight=1)
        self.tree.bind("", lambda e: self.open_detail())
        btns = tk.Frame(root)
        btns.pack(fill="x", padx=6, pady=4)
        tk.Button(btns, text="Run", command=self.run_script, bg="#2196F3", fg="white", width=8).pack(side="left", padx=2)
        tk.Button(btns, text="Copy path", command=self.copy_path, width=8).pack(side="left", padx=2)
        tk.Button(btns, text="Detalii", command=self.open_detail, width=8).pack(side="left", padx=2)
        tk.Button(btns, text="Auto toate", command=self.auto_all, width=8).pack(side="left", padx=2)
        self.status = tk.Label(root, text="Ready", anchor="w")
        self.status.pack(fill="x", padx=6, pady=2)
        self.load_scripts()
    def primary_file(self):
        return os.path.join(self.root_folder, CATALOG_NAME)
    def fallback_file(self):
        h = hashlib.md5(self.root_folder.encode("utf-8", "replace")).hexdigest()[:8]
        return os.path.join(BASE_DIR, "catalog_" + h + ".json")
    def save_catalog(self):
        payload = {"version": 1, "root": self.root_folder, "files": self.files}
        for path in (self.primary_file(), self.fallback_file()):
            try:
                with open(path, "w", encoding="utf-8") as f:
                    json.dump(payload, f, indent=2, ensure_ascii=False)
                return path
            except OSError:
                continue
        messagebox.showerror("Eroare", "Nu pot salva catalogul.")
        return None
    def load_scripts(self):
        folder = self.path_var.get().strip()
        if not os.path.isdir(folder):
            messagebox.showerror("Eroare", "Folder inexistent:\n" + safe(folder))
            return
        self.root_folder = folder
        data = read_json(self.primary_file()) or read_json(self.fallback_file()) or {}
        old = data.get("files", {})
        found = []
        for dirpath, dirs, files in os.walk(folder):
            dirs[:] = [d for d in dirs if d != "__pycache__"]
            for file in files:
                if file.endswith(".py"):
                    full = os.path.join(dirpath, file)
                    rel = os.path.relpath(full, folder).replace("\\", "/")
                    found.append((file, rel, full))
        found.sort(key=lambda s: s[1].lower())
        found_rels = set(s[1] for s in found)
        orphans = {r: e for r, e in old.items() if r not in found_rels and e.get("desc")}
        new_files = {}
        for name, rel, full in found:
            try:
                st = os.stat(full)
                size, mtime = st.st_size, int(st.st_mtime)
            except OSError:
                size, mtime = 0, 0
            entry = old.get(rel)
            if entry is None:
                entry = {"desc": ""}
                for orel, oe in list(orphans.items()):
                    if os.path.basename(orel) == name and oe.get("size") == size:
                        entry = {"desc": oe.get("desc", ""), "auto": oe.get("auto", "")}
                        del orphans[orel]
                        break
            entry = dict(entry)
            entry["size"] = size
            entry["mtime"] = mtime
            new_files[rel] = entry
        new_files.update(orphans)
        self.files = new_files
        self.scripts = found
        saved = self.save_catalog()
        self.refresh_table()
        if saved:
            self.status.config(text=str(len(found)) + " scripturi | catalog: " + safe(saved))
    def refresh_table(self):
        q = self.search_var.get().strip().lower()
        self.tree.delete(*self.tree.get_children())
        shown = 0
        for i, (name, rel, full) in enumerate(self.scripts):
            entry = self.files.get(rel, {})
            desc = entry.get("desc", "")
            auto = entry.get("auto", "")
            text = desc if desc else ("~ " + auto if auto else "")
            if q and q not in name.lower() and q not in rel.lower() and q not in text.lower():
                continue
            tags = ("auto",) if (not desc and auto) else ()
            self.tree.insert("", "end", iid=str(i), values=(safe(name), safe(rel), safe(text)), tags=tags)
            shown += 1
        if q:
            self.status.config(text=str(shown) + " din " + str(len(self.scripts)) + " scripturi")
    def selected(self):
        sel = self.tree.selection()
        if not sel:
            messagebox.showinfo("Info", "Selectează un script din listă.")
            return None
        return int(sel[0])
    def open_detail(self):
        idx = self.selected()
        if idx is None:
            return
        name, rel, full = self.scripts[idx]
        entry = self.files.setdefault(rel, {})
        win = tk.Toplevel(self.root)
        win.title("Detalii")
        win.transient(self.root)
        w = max(self.root.winfo_width(), 320)
        win.geometry(str(w) + "x" + str(max(self.root.winfo_height() // 2, 280)))
        tk.Label(win, text=safe(rel), wraplength=w - 20, justify="left", anchor="w").pack(fill="x", padx=8, pady=4)
        bar = tk.Frame(win)
        bar.pack(fill="x", padx=8)
        box = tk.Text(win, wrap="word", height=8, font=self.font)
        box.pack(fill="both", expand=True, padx=8, pady=6)
        box.insert("1.0", entry.get("desc") or entry.get("auto", ""))
        def do_auto():
            if box.get("1.0", "end").strip():
                if not messagebox.askyesno("Auto detect", "Înlocuiesc textul din câmp?", parent=win):
                    return
            info = analyze(full, self.root_folder)
            entry["auto"] = info
            box.delete("1.0", "end")
            box.insert("1.0", info)
        def do_update():
            entry["desc"] = box.get("1.0", "end").strip()
            self.save_catalog()
            self.refresh_table()
            win.destroy()
        tk.Button(bar, text="Auto detect", command=do_auto, width=10).pack(side="left", padx=2)
        tk.Button(bar, text="Update", command=do_update, bg="#4CAF50", fg="white", width=8).pack(side="left", padx=2)
        tk.Button(bar, text="Închide", command=win.destroy, width=8).pack(side="left", padx=2)
        win.grab_set()
    def auto_all(self):
        total = len(self.scripts)
        if not total:
            return
        if not messagebox.askyesno("Auto toate", "Regenerez Libs pentru " + str(total) + " scripturi?\nDescrierile tale nu se modifică."):
            return
        for n, (name, rel, full) in enumerate(self.scripts, 1):
            self.files.setdefault(rel, {})["auto"] = analyze(full, self.root_folder)
            if n % 5 == 0:
                self.status.config(text="Analiză " + str(n) + "/" + str(total))
                self.root.update_idletasks()
        self.save_catalog()
        self.refresh_table()
        self.status.config(text="Libs generat pentru " + str(total) + " scripturi")
    def run_script(self):
        idx = self.selected()
        if idx is None:
            return
        full = self.scripts[idx][2]
        try:
            subprocess.Popen([sys.executable, full], cwd=os.path.dirname(full))
            self.status.config(text="Rulat: " + safe(os.path.basename(full)))
        except Exception as e:
            messagebox.showerror("Eroare", "Eroare la rulare:\n" + safe(e))
    def copy_path(self):
        idx = self.selected()
        if idx is None:
            return
        full = self.scripts[idx][2]
        self.root.clipboard_clear()
        self.root.clipboard_append(full)
        self.status.config(text="Copiat: " + safe(full))
if __name__ == "__main__":
    root = tk.Tk()
    App(root)
    root.mainloop()

Python 3.13.13 : Exemple with random and string.

See this source code:
import random
import string

# Generate a random password of length 10
def generate_password(length):
    characters = string.ascii_letters + string.digits + string.punctuation
    return ''.join(random.choices(characters, k=length))


password = generate_password(10)
print(password)

Sunday, October 4, 2026

tkinter : PyTorch and Keras on pydroid3.

Today, simple python script with pytorch and keras on android pydroid application.
This script is a Tkinter graphical application designed to test and verify PyTorch and Keras packages in Pydroid 3. Right at launch, it tracks execution time down to milliseconds and displays the installed package versions in a status panel. All diagnostics run on a background thread to keep the user interface responsive. For PyTorch, the script tests matrix inversion, automatic gradient calculations using Autograd, data processing through a neural network linear layer, and eigenvalue decomposition. For Keras, the script verifies building a Sequential model with dense layers, compiling and training it on synthetic data for 3 epochs, and running a final prediction to confirm end-to-end execution.
This is the result of the running python script:
Let's see the source code:
import os
import time
import threading
import tkinter as tk
from tkinter import ttk, scrolledtext

# Set Keras backend to torch
os.environ["KERAS_BACKEND"] = "torch"

class AppCheck(tk.Tk):
    def __init__(self):
        self.start_time = time.time()
        
        super().__init__()
        self.title("PyTorch & Keras Inspector")
        self.geometry("480x600")
        
        self.style = ttk.Style(self)
        self.style.theme_use('clam')
        
        self.create_widgets()
        
        # Log UI startup time
        ui_ready = self.get_elapsed_str()
        self.log(f"{ui_ready} Tkinter UI initialized")
        
        # Initial package check
        self.check_initial_imports()

    def get_elapsed_str(self):
        """Returns elapsed time in MM:SS.mmm format without brackets."""
        elapsed = time.time() - self.start_time
        minutes = int(elapsed // 60)
        seconds = int(elapsed % 60)
        millis = int((elapsed - int(elapsed)) * 1000)
        return f"+{minutes:02d}:{seconds:02d}.{millis:03d}"

    def create_widgets(self):
        # Status Frame
        self.info_frame = ttk.LabelFrame(self, text=" Package Status ")
        self.info_frame.pack(fill="x", padx=8, pady=4)

        self.lbl_torch = ttk.Label(self.info_frame, text="PyTorch: Checking...", font=("Helvetica", 9))
        self.lbl_torch.pack(anchor="w", padx=8, pady=2)

        self.lbl_keras = ttk.Label(self.info_frame, text="Keras: Checking...", font=("Helvetica", 9))
        self.lbl_keras.pack(anchor="w", padx=8, pady=2)

        # Run Tests Button
        self.btn_run = ttk.Button(self, text="Run Full Test Suite", command=self.start_tests_thread)
        self.btn_run.pack(pady=6)

        # Console Log Header
        ttk.Label(self, text="Execution Log:", font=("Helvetica", 9, "bold")).pack(anchor="w", padx=8)
        
        # Font size reduced to 7 to fit ~10% more content line-by-line
        self.txt_log = scrolledtext.ScrolledText(self, height=25, font=("Courier", 7))
        self.txt_log.pack(fill="both", expand=True, padx=8, pady=4)

    def log(self, message):
        """Helper to append text to the log window."""
        self.txt_log.insert(tk.END, message + "\n")
        self.txt_log.see(tk.END)

    def check_initial_imports(self):
        t_str = self.get_elapsed_str()
        self.log(f"{t_str} Checking imports...")
        
        # Check PyTorch
        try:
            import torch
            self.lbl_torch.config(text=f"PyTorch: v{torch.__version__}", foreground="green")
            self.log(f"{self.get_elapsed_str()} PyTorch v{torch.__version__} loaded successfully")
        except ImportError as e:
            self.lbl_torch.config(text="PyTorch: Not installed", foreground="red")
            self.log(f"{self.get_elapsed_str()} PyTorch import error: {e}")

        # Check Keras
        try:
            import keras
            self.lbl_keras.config(text=f"Keras: v{keras.__version__}", foreground="green")
            self.log(f"{self.get_elapsed_str()} Keras v{keras.__version__} loaded successfully")
        except ImportError as e:
            self.lbl_keras.config(text="Keras: Not installed", foreground="red")
            self.log(f"{self.get_elapsed_str()} Keras import error: {e}")

    def start_tests_thread(self):
        self.btn_run.config(state="disabled")
        threading.Thread(target=self.run_tests, daemon=True).start()

    def run_tests(self):
        self.log(f"\n{self.get_elapsed_str()} STARTING FULL TEST SUITE")

        # PYTORCH TESTS
        try:
            import torch
            
            # Test 1: Matrix Inverse
            self.log(f"{self.get_elapsed_str()} PyTorch Test 1/4 Matrix Operations")
            A = torch.tensor([[2.0, 1.0], [1.0, 4.0]])
            A_inv = torch.inverse(A)
            self.log(f"   Inverted matrix output:")
            for row in A_inv.numpy():
                self.log(f"   {row}")

            # Test 2: Autograd
            self.log(f"{self.get_elapsed_str()} PyTorch Test 2/4 Autograd Gradient Calculation")
            x = torch.tensor([3.0], requires_grad=True)
            y = x**3 + 2*x
            y.backward()
            self.log(f"   dy/dx at x=3 (expected 29.0): {x.grad.item()}")

            # Test 3: Linear Layer
            self.log(f"{self.get_elapsed_str()} PyTorch Test 3/4 Neural Network Linear Layer")
            lin = torch.nn.Linear(3, 1)
            inp = torch.randn(2, 3)
            out = lin(inp)
            self.log(f"   Output tensor shape: {out.shape}")

            # Test 4: Eigenvalues
            self.log(f"{self.get_elapsed_str()} PyTorch Test 4/4 Eigenvalue Decomposition")
            e_vals = torch.linalg.eigvals(A)
            self.log(f"   Eigenvalues: {e_vals.numpy()}")

        except Exception as e:
            self.log(f"{self.get_elapsed_str()} PyTorch Test Failed: {str(e)}")
            
        # KERAS TESTS
        try:
            import keras
            import numpy as np
            
            # Test 1: Sequential Model Creation
            self.log(f"{self.get_elapsed_str()} Keras Test 1/3 Building Sequential Model")
            model = keras.Sequential([
                keras.layers.Input(shape=(4,)),
                keras.layers.Dense(8, activation="relu"),
                keras.layers.Dense(1, activation="sigmoid")
            ])
            self.log(f"   Model created successfully with {model.count_params()} parameters")

            # Test 2: Model Compilation & Training
            self.log(f"{self.get_elapsed_str()} Keras Test 2/3 Model Compilation and Training")
            model.compile(optimizer="adam", loss="binary_crossentropy")
            
            X_train = np.random.random((32, 4))
            y_train = np.random.randint(2, size=(32, 1))
            
            history = model.fit(X_train, y_train, epochs=3, batch_size=16, verbose=0)
            final_loss = history.history['loss'][-1]
            self.log(f"   3 epochs training completed. Final loss: {final_loss:.4f}")

            # Test 3: Inference / Prediction
            self.log(f"{self.get_elapsed_str()} Keras Test 3/3 Model Prediction")
            X_test = np.random.random((2, 4))
            preds = model.predict(X_test, verbose=0)
            self.log(f"   Prediction results shape: {preds.shape}")
            for pred in preds:
                self.log(f"   Output probabilities: {pred}")

        except Exception as e:
            self.log(f"{self.get_elapsed_str()} Keras Test Failed: {str(e)}")

        self.log(f"\n{self.get_elapsed_str()} TEST SUITE COMPLETED SUCCESSFULLY")
        self.btn_run.config(state="normal")

if __name__ == "__main__":
    app = AppCheck()
    app.mainloop()

Friday, October 2, 2026

Python 3.13.16 : React frontend and python on Reflex Cloud.

Today, this simple test with artificial intelligence from reflex chat bot show how good and fast can be with one simple task.
Reflex compiles to a React frontend and a Starlette backend—the ASGI server that powers FastAPI. A familiar web stack, accessible to every Python developer. pandas, SQLAlchemy, scikit-learn, ...
After I ask to create a simple G.U.I. interface with all features from reflex, the chat bot result is this:
I built a one-page interactive playground that shows how a React-powered interface responds to Python state. Visitors can try five demos: a counter with event history, live preview controls, form validation, a searchable collection, and a dialog and toast.
Size: about 1,150 lines of Python across the page, four component modules, and four state modules. The integration section describes possibilities; it does not claim that external services are connected.
The interaction tests passed, and the page renders in the browser. I don’t have a reliable elapsed-time measurement for the build, so I can’t give an accurate creation time.
... the time of build was 4 minutes ...
Reflex comes with free features:
  • Publish 1 app on Reflex Cloud
  • Limited free usage for AI generation and hosting
  • Refills periodically
  • Public apps and public GitHub repos
  • App code download and file editing
  • Public sign-in with Reflex Auth
  • Managed database
See the result online : this webpage.

Tuesday, September 29, 2026

Python 3.13.13 : using webz.io with python.

The webz.io can be used with python:
import requests

response = requests.get(
    "https://api.webz.io/api/news?token=YOUR-TOKEN&q=%28category%3A%22economy%2C+business+and+finance%22+OR+category
    %3A%22war%2C+conflict+and+unrest%22+OR+category%3A%22science+and+technology%22+OR+category%3A%22disaster+and+accident%22
    +OR+category%3A%22environment%22+
    OR+category%3A%22labor%22%29&sort=crawled&ts=1790410006113&format=json&size=10&
    webz_reporter=true&includeSyndicated=false&allowNewsHistory=false",
    headers={"Accept": "application/json"},
)
print(response.json())

Monday, September 28, 2026

tkinter : testing RapidFuzz.

RapidFuzz is a fast and powerful Python library used for fuzzy string matching and similarity scoring. It is designed as a drop-in, high-performance alternative to the popular fuzzywuzzy library, offering significantly faster execution speeds because its core algorithms are implemented in C++ (via pybind11).
​What Can RapidFuzz Do?
​Calculate String Similarity:
It measures how similar two strings are using various mathematical distances (such as Levenshtein distance, Hamming distance, Jaro-Winkler, and Normalized Similarity metrics), returning a score typically ranging from 0 (completely different) to 100 (exact match).
​Smart Search & Extraction (process module):
You can query a list of items (such as filenames, database records, or user inputs) and instantly extract the best matches, even if the user query contains typos, misspellings, or partial words.
​Data Cleaning & Deduplication:
It helps clean messy datasets by grouping entries that represent the same entity despite slight spelling variations (e.g., matching "John Smith" with "Jon Smith").
​Lightweight & Efficient:
Unlike heavy deep learning frameworks, RapidFuzz has minimal dependencies and runs smoothly across different environments—making it ideal for desktop applications, servers, and mobile development environments like Pydroid 3.

Sunday, September 27, 2026

tkinter : fast image tool on pydroid3.

Today, one simple example fast tool for images:
Let's see this start source code:
# -*- coding: utf-8 -*-
"""Image Editor - consistent GUI sizes (Pydroid / Android)"""
import os
import shutil
import zipfile
from datetime import datetime
import tkinter as tk
from tkinter import ttk, filedialog, messagebox, font as tkfont
from PIL import Image, ImageTk, ImageOps, ImageEnhance
VALID_EXTS = (".png", ".jpg", ".jpeg", ".bmp", ".webp", ".gif", ".tiff", ".tif")
def get_android_start_dir():
    candidates = [
        "/storage/emulated/0", "/sdcard",
        "/storage/emulated/0/Download", "/sdcard/Download",
        "/storage/emulated/0/DCIM", "/sdcard/DCIM",
        "/storage/emulated/0/Pictures", "/sdcard/Pictures",
        os.path.expanduser("\~"), "/",
    ]
    for path in candidates:
        if os.path.isdir(path) and os.access(path, os.R_OK):
            return path
    return os.getcwd()
...

Saturday, September 26, 2026

tkinter : basic portfolio for market with simulations ...

Today, one simple script tool for market. this allow to set one portofolio and use with simulations.
Let'see some screenshots:
The basic intro source code ...
import datetime
import json
import threading
import urllib.request
import tkinter as tk
from tkinter import ttk, messagebox

import matplotlib
matplotlib.use("TkAgg")
from matplotlib.figure import Figure
from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg


def fetch_yahoo_history(symbol, period_years=1):
    """Descarcă istoricul zilnic de pe Yahoo Finance."""
    end_date = int(datetime.datetime.now().timestamp())
    start_date = int((datetime.datetime.now() - datetime.timedelta(days=365 * period_years)).timestamp())
    
    url = f"https://query1.finance.yahoo.com/v8/finance/chart/{symbol}?period1={start_date}&period2={end_date}&interval=1d"
    req = urllib.request.Request(url, headers={"User-Agent": "Mozilla/5.0"})
    
    try:
        with urllib.request.urlopen(req, timeout=10) as resp:
            data = json.loads(resp.read().decode("utf-8"))
            result = data["chart"]["result"][0]
            timestamps = result["timestamp"]
            closes = result["indicators"]["quote"][0]["close"]
            
            history = []
            for ts, cl in zip(timestamps, closes):
                if cl is not None:
                    dt = datetime.datetime.fromtimestamp(ts)
                    history.append((dt, float(cl)))
            return history
    except Exception as e:
        print(f"Eroare la descărcare {symbol}: {e}")
        return []
        ...

Thursday, September 24, 2026

News : OpenAI python library released.

The OpenAI Python library provides convenient access to the OpenAI REST API from any Python 3.10+ application. The library includes type definitions for all request params and response fields, and offers both synchronous and asynchronous clients powered by HTTPX2.

Tuesday, September 22, 2026

News : PyPy new 8.0.0 version.

The PyPy team is proud to release version 8.0.0 of PyPy after the previous release on May 26, 2026. This is a major new version, hence the bump to 8.0.0. It is our first release of Python 3.12, which may still have some bugs so we are calling it "beta" quality.
PyPy is written in RPython, and has code generation to translate RPython into C as part of the VM build process. We have made some improvements to code generation in attempts to speed up the base interpreter.

Monday, September 21, 2026

tkinter : simple marshmallow demo.

About the marshmallow package
  • It checks if your data has the correct fields.
  • It verifies that each field has the right type.
  • It helps you validate JSON before using it.
  • It can convert Python data into clean JSON.
About your this source code:
  • It loads the marshmallow package when the app starts.
  • It reads the JSON you type in the input box.
  • It tries to convert that text into Python data.
  • It validates the data using your marshmallow schema.
  • It shows the result or the error directly in the output box.
  • It does not use print or message boxes.
Why this tool is useful
  • You can test JSON visually.
  • You can see validation errors instantly.
  • You avoid console output.
  • You keep everything inside the GUI.
Let's see the sourve code:
import json
import tkinter as tk
from tkinter import ttk

# ------------------ Package Load Test ------------------

try:
    from marshmallow import Schema, fields, ValidationError
    package_status = "Package marshmallow loaded successfully."
except Exception as e:
    package_status = "PACKAGE LOAD ERROR: " + str(e)


# ------------------ Marshmallow Schema ------------------

class PersonSchema(Schema):
    full_name = fields.Str(required=True)
    city = fields.Str(required=True)
    birth_date = fields.Date(required=True)
    nicknames = fields.List(fields.Str(), required=True)


schema = PersonSchema()


# ------------------ Tkinter UI ------------------

def process_json():
    raw = editor.get("1.0", tk.END).strip()

    output.delete("1.0", tk.END)

    # Step 1: package status
    output.insert(tk.END, package_status + "\n\n")

    # Step 2: show raw JSON
    output.insert(tk.END, "RAW JSON RECEIVED:\n" + raw + "\n\n")

    # Step 3: JSON parsing
    try:
        data = json.loads(raw)
        output.insert(tk.END, "JSON PARSED OK.\n\n")
    except Exception as e:
        output.insert(tk.END, "JSON ERROR:\n" + str(e))
        return

    # Step 4: Marshmallow validation
    try:
        result = schema.dump(data)
        output.insert(tk.END, "SCHEMA VALIDATION OK.\n\n")
    except ValidationError as e:
        output.insert(tk.END, "SCHEMA ERROR:\n" + json.dumps(e.messages, indent=2))
        return

    # Step 5: Final result
    output.insert(tk.END, "FINAL RESULT:\n" + json.dumps(result, indent=2))


root = tk.Tk()
root.title("Marshmallow Diagnostic Full Output")
root.geometry("750x550")

frm = ttk.Frame(root, padding=10)
frm.pack(fill="both", expand=True)

ttk.Label(frm, text="JSON Input:").pack(anchor="w")

editor = tk.Text(frm, height=14, width=90)
editor.pack(fill="x")

editor.insert(
    tk.END,
    json.dumps(
        {
            "full_name": "Catalin George Festila",
            "city": "Falticeni",
            "birth_date": "1976-03-07",
            "nicknames": ["catafest", "mythcat"]
        },
        indent=2
    )
)

ttk.Button(frm, text="Run", command=process_json).pack(pady=10)

ttk.Label(frm, text="Output:").pack(anchor="w")

output = tk.Text(frm, height=14, width=90)
output.pack(fill="both", expand=True)

root.mainloop()

Saturday, September 12, 2026

News : Real-Time Stock & ETF Analyzer in using tvscreener and Tkinter and pydroid3.

The tvscreener is a lightweight Python library designed to extract and analyze real-time financial data directly from TradingView's API without requiring paid API keys or complex authentication. It provides quick access to technical indicators, fundamental metrics, historical performance, and volume data for international stocks and ETFs. Explore the source code and documentation on the official tvscreener GitHub repository. The script provides a desktop interface (Tkinter GUI) powered by tvscreener logic to query market data on demand. This allow to choose a ticker symbol from the dropdown list (such as GOOGL, NVDA, AAPL, or ETFs like VUAA). Clicking Check triggers a background HTTP request without freezing the user interface, while displaying real-time progress via the progress bar. The script formats the API response into four core metric categories: Performance, Technical Indicators, Fundamentals, and Volume and Liquidity. Clicking Copy transfers the complete output directly to your system clipboard for quick sharing or note-taking.

Tuesday, September 1, 2026

News : Inkscape MCP coding agent python module.

With Inkscape MCP, your coding agent can do everything a designer does in Inkscape — sketch and reshape paths, apply effects and filters, render LaTeX equations, generate barcodes and QR codes, convert between formats, query and rewrite document structure — through plain conversation instead of menu clicks.

Tuesday, August 25, 2026

News : win a Golden Ticket with Google Cloud: All-Access Pass to NVIDIA GTC Berlin 2026..

The Google Cloud and NVIDIA teams are excited to announce an opportunity for you to win the ultimate developer experience! We are sending one lucky member from our developer community to NVIDIA GTC Berlin 2026 in Berlin, Germany (Oct 20-22). This is a unique opportunity for our developer community, and we hope you will participate in the contest! Be sure to read all the details below to learn how to enter your submission before the deadline on September 10, 2026.
The "Golden Ticket" winner will receive a premier experience:
✈️ Travel & Pass: One complimentary NVIDIA GTC Berlin Conference Pass to attend in person, including a round-trip travel to Berlin and accommodations. Winners must be able to travel to this event in person to accept the prize.
💻 NVIDIA merchandise gift bag.
⭐ VIP Access: VIP seating for NVIDIA CEO Jensen Huang’s keynote on October 21, 2026.
🧠 Access to NVIDIA community special events.

tkinter : three algorithms for yahoo market with pydroid 3.

The script retrieves historical closing-price data for NVDA and VUAA.AS directly from Yahoo Finance.
First tab displays a candlestick chart for the selected time range. Two Simple Moving Averages are calculated automatically; their periods adapt to the chosen interval (for example SMA 5/10 on short ranges and SMA 50/200 on longer ones) and are shown in the legend. Clear dates appear on the horizontal axis.
Its second tab, ML Predictions, focuses on statistical modelling. The downloaded series is fitted with three algorithms: ordinary linear regression, polynomial regression (degree adjustable by the user), and a Random Forest regressor. All four lines—the original prices plus the three model outputs—are plotted on a single chart. Clear calendar dates appear on the horizontal axis, and an enlarged legend identifies each curve. Loading feedback is shown while data are fetched. The tab therefore converts raw Yahoo price history into immediate visual comparisons of linear, non-linear and ensemble trend estimates.