analitics

Pages

Saturday, May 16, 2026

Python 3.10.11 : about the windows embeddable portable Python distributions fix pip.

Let's learn about the windows embeddable portable Python distributions.
  • The Windows embeddable Python distribution is a minimal, self‑contained build of Python designed to run entirely from its own directory without installation.
  • This distribution does not modify system settings, environment variables, or the Windows registry.
  • Its structure makes it suitable for embedding Python inside applications or distributing Python as a portable runtime.
Typical use cases
  • Bundling Python with standalone software that requires a predictable runtime environment.
  • Running Python scripts in isolated environments where system‑wide installations must not be affected.
  • Deploying portable utilities that must operate from removable storage or restricted systems.
When the embeddable distribution is not ideal
  • General development workflows that rely on pip, external packages, or virtual environments.
  • Educational or experimental setups where tutorials assume a standard Python installation.
  • Projects that depend on automatic module discovery and dynamic package management.
The Role of python310._pth
  • The file named python310._pth controls how the embeddable distribution locates and loads Python modules.
  • When this file is present, Python enters an isolated mode in which only the paths explicitly listed inside the file are used.
  • If the file does not include the line import site, the standard site initialization process is disabled, preventing access to site‑packages.
Typical structure of python310._pth
python310.zip
.
import site
Explanation of each entry
  • python310.zip specifies the location of the standard library packaged as a zip archive.
  • . allows Python to import modules from the root directory of the distribution.
  • import site activates the site module, enabling automatic loading of Lib and site‑packages.
Enabling pip and external modules
  • The embeddable distribution does not load external modules unless the appropriate paths are added to python310._pth.
  • To enable pip and other installed packages, the file must include the Lib and Lib\site-packages directories.
Example of a Fully Enabled python310._pth
python310.zip
.
Lib
Lib\site-packages
import site
Testing the updated configuration
python -c "import sys; print(sys.path)"
Installing pip after enabling site‑packages
  • Once the module paths are active, pip can be installed using standard methods.
python get-pip.py
python -m ensurepip
Verifying pip
python -m pip --version
Advantages of the embeddable distribution:
  • Provides a predictable and isolated runtime environment.
  • Does not interfere with system‑wide Python installations.
  • Ideal for packaging Python with standalone applications.
Disadvantages of the embeddable distribution:
  • pip and external modules are disabled by default.
  • Requires manual configuration to behave like a standard installation.
  • Not suitable for typical development workflows.
Clean, Ready‑to‑Use python310._pth File
python310.zip
.
Lib
Lib\site-packages
import site
This will fix the embeddable distribution, let's use this source code to fix the pip tool:
import os
import urllib.request
import zipfile
import shutil

PYTHON_DIR = r"C:\python-3_10_11"
SITE = fr"{PYTHON_DIR}\Lib\site-packages"

print("[INFO] Descarc pip.zip...")
urllib.request.urlretrieve(
    "https://github.com/pypa/pip/archive/refs/heads/main.zip",
    "pip.zip"
)

print("[INFO] Dezarhivez pip.zip...")
with zipfile.ZipFile("pip.zip", "r") as z:
    z.extractall("pip_src")

pip_src = "pip_src/pip-main/src/pip"

print("[INFO] Copiez pip în site-packages...")
target = os.path.join(SITE, "pip")
if os.path.exists(target):
    shutil.rmtree(target)

shutil.copytree(pip_src, target)

print("[INFO] Creez pip.dist-info minimal...")
dist = os.path.join(SITE, "pip.dist-info")
os.makedirs(dist, exist_ok=True)

with open(os.path.join(dist, "METADATA"), "w") as f:
    f.write("Name: pip\nVersion: 0\n")

print("[OK] pip instalat direct în Python.")
print("Rulează acum:")
print("   python -m pip --version")
Let's tun and test with PyQt6:
python fix_pip.py
[INFO] Descarc pip.zip...
[INFO] Dezarhivez pip.zip...
[INFO] Copiez pip în site-packages...
[INFO] Creez pip.dist-info minimal...
[OK] pip instalat direct în Python.
Rulează acum:
   python -m pip --version

python -m pip --version
pip 26.2.dev0 from C:\python-3_10_11\Lib\site-packages\pip (python 3.10)

python -m pip install PyQt6
Collecting PyQt6
  Downloading pyqt6-6.11.0-cp310-abi3-win_amd64.whl.metadata (2.2 kB)
...
Installing collected packages: PyQt6-Qt6, PyQt6-sip, PyQt6
Successfully installed PyQt6-6.11.0 PyQt6-Qt6-6.11.1 PyQt6-sip-13.11.1

Thursday, May 14, 2026

News : Good news from the Python Software Foundation 14.05.2026

Good news from the Python Software Foundation official blogger.
  • May 13, 2026 – The Python Software Foundation (PSF) is excited to announce that Hudson River Trading (HRT), a global leader in quantitative trading, has made a commitment to support Python and the PSF as a Visionary Sponsor.
  • May 12, 2026 - Announcing PSF Community Service Award Recipients!
  • May 11, 2026 - Strategic Planning at the PSF
  • May 10, 2026 - Python 3.14.5 is out!
  • May 7, 2026 - Python 3.15.0 beta 1 is here!
  • May 4, 2026 - Python 3.14.5 release candidate

Thursday, May 7, 2026

Python Qt : simple tiktok downloader.

Today, simple example with PyQt6 and yt_dlp.
Get the link from tiktok browser and use it to download the video for your storage.
I used the Copilot tool. It seems to know the Romanian language. For a developer, comments and source code are not an impediment, because it is very simplistic.
Let's see the source code:
import sys
import os
import yt_dlp
from PyQt6.QtWidgets import (
    QApplication, QWidget, QVBoxLayout, QHBoxLayout, QPushButton,
    QLineEdit, QLabel, QFileDialog, QListWidget, QListWidgetItem,
    QProgressBar, QMessageBox
)
from PyQt6.QtCore import Qt

class TikTokDownloader(QWidget):
    def __init__(self):
        super().__init__()
        self.setWindowTitle("TikTok Downloader (yt-dlp)")
        self.setMinimumWidth(600)

        self.url_input = QLineEdit()
        self.url_input.setPlaceholderText("Introdu URL TikTok...")

        self.folder_input = QLineEdit()
        self.folder_input.setPlaceholderText("Folder download...")

        browse_btn = QPushButton("Selectează folder")
        browse_btn.clicked.connect(self.select_folder)

        fetch_btn = QPushButton("Caută stream-uri")
        fetch_btn.clicked.connect(self.fetch_streams)

        self.stream_list = QListWidget()

        download_btn = QPushButton("Descarcă")
        download_btn.clicked.connect(self.download_selected)

        self.progress = QProgressBar()
        self.progress.setValue(0)

        layout = QVBoxLayout()
        layout.addWidget(QLabel("URL TikTok:"))
        layout.addWidget(self.url_input)

        folder_layout = QHBoxLayout()
        folder_layout.addWidget(self.folder_input)
        folder_layout.addWidget(browse_btn)
        layout.addLayout(folder_layout)

        layout.addWidget(fetch_btn)
        layout.addWidget(QLabel("Stream-uri găsite:"))
        layout.addWidget(self.stream_list)
        layout.addWidget(download_btn)
        layout.addWidget(self.progress)

        self.setLayout(layout)

        self.streams = []
        self.selected_format = None

    def select_folder(self):
        folder = QFileDialog.getExistingDirectory(self, "Selectează folder")
        if folder:
            self.folder_input.setText(folder)

    def fetch_streams(self):
        url = self.url_input.text().strip()
        if not url:
            QMessageBox.warning(self, "Eroare", "Introdu URL TikTok")
            return

        self.stream_list.clear()
        self.streams = []

        ydl_opts = {
            "quiet": True,
            "skip_download": True,
            "forcejson": True,
        }

        try:
            with yt_dlp.YoutubeDL(ydl_opts) as ydl:
                info = ydl.extract_info(url, download=False)

            formats = info.get("formats", [])

            for f in formats:
                desc = f"{f.get('format_id')} | {f.get('ext')} | {f.get('resolution', '')} | {f.get('filesize', 'N/A')}"
                item = QListWidgetItem(desc)
                self.stream_list.addItem(item)
                self.streams.append(f)

        except Exception as e:
            QMessageBox.critical(self, "Eroare", str(e))

    def progress_hook(self, d):
        if d["status"] == "downloading":
            if d.get("total_bytes"):
                pct = int(d["downloaded_bytes"] * 100 / d["total_bytes"])
                self.progress.setValue(pct)

        if d["status"] == "finished":
            self.progress.setValue(100)

    def download_selected(self):
        folder = self.folder_input.text().strip()
        if not folder:
            QMessageBox.warning(self, "Eroare", "Selectează folderul de download")
            return

        selected = self.stream_list.currentRow()
        if selected < 0:
            QMessageBox.warning(self, "Eroare", "Selectează un stream din listă")
            return

        fmt = self.streams[selected]
        url = self.url_input.text().strip()

        ydl_opts = {
            "outtmpl": os.path.join(folder, "%(id)s.%(ext)s"),
            "format": fmt["format_id"],
            "progress_hooks": [self.progress_hook],
        }

        try:
            with yt_dlp.YoutubeDL(ydl_opts) as ydl:
                ydl.download([url])

            QMessageBox.information(self, "Succes", "Download complet!")

        except Exception as e:
            QMessageBox.critical(self, "Eroare", str(e))

if __name__ == "__main__":
    app = QApplication(sys.argv)
    win = TikTokDownloader()
    win.show()
    sys.exit(app.exec())

Wednesday, May 6, 2026

Python 3.13.0 : another tool with PyQt6 to build an NPC database.

... another tool for game development, see more on my youtube channel.

Python 3.13.0 : mimesis python example.

Mimesis is a powerful data generator for Python that can produce a wide range of fake data in multiple languages. This tool is useful for populating testing databases, creating fake API endpoints, generating custom structures in JSON and XML files, and anonymizing production data, among other things. With Mimesis, developers can obtain realistic, randomized data easily to facilitate development and testing.
This python module can be install with pip tool easy.
See this simple example:
from mimesis import Person, Address, Text, Datetime
from mimesis.enums import Gender
def test_mimesis(locale: str, sex: str):
    person = Person(locale)
    address = Address(locale)
    text = Text(locale)
    dt = Datetime()
    gender = Gender.MALE if sex == "male" else Gender.FEMALE
    data = {
        "first_name": person.first_name(gender=gender),
        "last_name": person.last_name(),
        "full_name": person.full_name(gender=gender),
        "email": person.email(),
        "telephone": person.telephone(),
        "occupation": person.occupation(),
        "address": address.address().replace("\n", ", "),
        "city": address.city(),
        "postal_code": address.postal_code(),
        "country": address.country(),
        "birth_date": dt.date(start=1970, end=2005),
        "bio": text.text(quantity=2),
    }
    return data
if __name__ == "__main__":
    npc = test_mimesis("en", "female")
    for k, v in npc.items():
        print(f"{k}: {v}")
The result is:
python_313 test_mimesis.py
first_name: Nisha
last_name: Rocha
full_name: Hertha Wynn
email: stakeholders2063@protonmail.com
telephone: +14172413972
occupation: Medical Physicist
address: 865 Cooper Highway
city: Elkhart
postal_code: 69168
country: France
birth_date: 2004-06-11
bio: It is also a garbage-collected runtime system. Do you come here often?

Tuesday, May 5, 2026

News : Pythono and nuitka best optimization.

Nuitka is the optimizing Python compiler written in Python that creates executables that run without a separate installer. Data files can both be included or put alongside.
You can read more on the official website.
The install is easy with pip tool, then you can use this command.
python -m nuitka --help
Usage: python.exe -m nuitka [--mode=compilation_mode] [--run] [options] main_module.py

    Note: For general plugin help (they often have their own
    command line options too), consider the output of
    '--help-plugins'.

Options:
  --help                show this help message and exit
  --version             Show version information and important details for bug
                        reports, then exit. Defaults to off.
This python package need to have the Visual Studio Build Tools 2022 and need to use:
  • Desktop development with C++
  • MSVC v143 build tools
  • Windows 10/11 SDK
  • C++ CMake tools
  • C++ ATL/MFC (optional but useful)
Let's install it.
I used this simple example:
import sys
from PyQt6.QtWidgets import QApplication, QLabel, QWidget, QVBoxLayout

def main():
    app = QApplication(sys.argv)

    window = QWidget()
    window.setWindowTitle("PyQt6 + Nuitka Demo")

    layout = QVBoxLayout()
    label = QLabel("Hello! This is a PyQt6 application compiled with Nuitka.")
    layout.addWidget(label)

    window.setLayout(layout)
    window.show()

    sys.exit(app.exec())

if __name__ == "__main__":
    main()
Use this command to see all plugins:
nuitka --plugin-list
                 The following plugins are available in Nuitka
--------------------------------------------------------------------------------
 delvewheel        Required by 'delvewheel' using packages. (core)
 implicit-imports  Provide implicit imports of package as per package configuration files. (core) [auto-enabled]
 data-files        Include data files specified by package configuration files. (core, feature)
 dll-files         Include DLLs as per package configuration files. (core, feature)
 anti-bloat        Patch stupid imports out of widely used library modules source codes. (core, feature, package-support) [auto-enabled]
 options-nanny     Inform user about potential problems as per package configuration files. (core, package-support) [auto-enabled]
 pylint-warnings   Support PyLint / PyDev linting source markers. (feature)
 upx               Compress created binaries with UPX automatically. (integration)
 dill-compat       Required by 'dill' and 'cloudpickle' packages. (package-support) [has detector]
 eventlet          Required by 'eventlet' package. (package-support) [auto-enabled]
 gevent            Required by 'gevent' package. (package-support)
 gi                Required by 'gi' package. (package-support) [auto-enabled]
 glfw              Required by 'glfw' and 'PyOpenGL' packages. (package-support)
 kivy              Required by 'kivy' package. (package-support)
 matplotlib        Required by 'matplotlib' package. (package-support)
 multiprocessing   Required by 'multiprocessing' package. (package-support) [auto-enabled]
 no-qt             Disable inclusion of all Qt bindings. (package-support)
 pbr-compat        Required by 'pbr' package. (package-support)
 pkg-resources     Required by 'pkg_resources' package. (package-support) [auto-enabled]
 playwright        Required by 'playwright' package. (package-support)
 pmw-freezer       Required by 'Pmw' package. (package-support) [has detector]
 pywebview         Required by 'webview' package. (package-support)
 spacy             Required by 'spacy' package. (package-support)
 tk-inter          Required by 'tkinter' package. (package-support) [has detector]
 transformers      Required by 'transformers' package. (package-support) [auto-enabled]
 enum-compat       Required by 'enum' package on Python2. (package-support, python2)
 pyqt5             Required by 'PyQt5' package. (package-support, qt-binding) [has detector]
 pyqt6             Required by 'PyQt6' package. (package-support, qt-binding) [has detector]
 pyside2           Required by 'PySide2' package. (package-support, qt-binding) [has detector]
 pyside6           Required by 'PySide6' package. (package-support, qt-binding) [has detector]
... and standalone build process:
nuitka --standalone --enable-plugin=pyqt6 test_app.py
Nuitka-Options: Used command line options:
Nuitka-Options:   --standalone --enable-plugin=pyqt6 test_app.py
Nuitka-Plugins:pyqt6: Support for PyQt6 is not perfect, e.g. Qt threading does not work, so prefer
Nuitka-Plugins:pyqt6: PySide6 if you can.
Nuitka: Starting Python compilation with:
Nuitka:   Version '4.0.8' on Python 3.10 (flavor 'CPython Official')
Nuitka:   commercial grade 'not installed'.
Nuitka-Plugins:pyqt6: Including Qt plugins 'iconengines,imageformats,platforms,styles,tls' below
Nuitka-Plugins:pyqt6: 'PyQt6\Qt6\plugins'.
Nuitka: Completed Python level compilation and optimization.
Nuitka: Generating source code for C backend compiler.
Nuitka: Running data composer tool for optimal constant value handling.
Nuitka: Running C compilation via Scons.
Nuitka will use gcc from MinGW64 of winlibs to compile on Windows.

Is it OK to download and put it in local user cache.

Fully automatic, cached. Proceed and download? [Yes]/No :
Nuitka: Downloading
Nuitka: 'https://github.com/brechtsanders/winlibs_mingw/releases/download/14.2.0posix-19.1.1-12.0.0-msvcrt-r2/winlibs-x86_64-posix-seh-gcc-14.2.0-llvm-19.1.1-mingw-w64msvcrt-12.0.0-r2.zip'.
Nuitka: Extracting to
Nuitka: 'C:\Users\CATALI~1\AppData\Local\Nuitka\Nuitka\Cache\DOWNLO~1\gcc\x86_64\14.2.0posix-19.1.1-12.0.0-msvcrt-r2\mingw64\bin\gcc.exe'
Nuitka-Scons: Backend C compiler: gcc (gcc 14.2.0).
Nuitka-Scons: Backend C linking with 9 files (no progress information available for this stage).
Nuitka-Scons: Compiled 9 C files using ccache.
Nuitka-Scons: Cached C files (using ccache) with result 'cache miss': 9
Nuitka: Keeping build directory 'test_app.build'.
Nuitka: Successfully created 'C:\lucru\PyQt6\test_nuitka\test_app.dist\test_app.exe'.

Python Qt : python alias manager tool.

This script allow you to add alias commands on each python install.
NOTE : If this script find some python.exe and not works, it means that this python.exe is not a full Python installation, but only a launcher or an embedded runtime that is designed to run inside a virtual environment or a complete Python directory structure.
I used artificial intelligence, tested and works well, lets see the source code:
import sys
import os
import json
import subprocess
from PyQt6.QtWidgets import (
    QApplication, QWidget, QVBoxLayout, QPushButton,
    QTableWidget, QTableWidgetItem, QFileDialog, QMessageBox
)
from PyQt6.QtCore import Qt

CONFIG_FILE = "python_aliases.json"
ALIAS_DIR = os.path.join(os.environ["LOCALAPPDATA"], "Microsoft", "WindowsApps")

# ------------------------------
# Persistență JSON
# ------------------------------

def load_aliases():
    if os.path.isfile(CONFIG_FILE):
        try:
            with open(CONFIG_FILE, "r") as f:
                return json.load(f)
        except:
            return []
    return []

def save_aliases(data):
    with open(CONFIG_FILE, "w") as f:
        json.dump(data, f, indent=4)


# ------------------------------
# Detectare Python
# ------------------------------

def detect_where_python():
    """Detectează instalările Python folosind 'where python'."""
    found = []
    try:
        out = subprocess.check_output(["where", "python"], stderr=subprocess.STDOUT)
        lines = out.decode().splitlines()
        for line in lines:
            if line.lower().endswith("python.exe"):
                found.append(line.strip())
    except:
        pass
    return found


def search_python_in_folder_recursive(folder):
    """Caută python.exe în folder și în toate subfolderele recursiv."""
    found = []
    for root, dirs, files in os.walk(folder):
        if "python.exe" in files:
            found.append(os.path.join(root, "python.exe"))
    return found

# ------------------------------
# Detectare aliasuri existente
# ------------------------------

def detect_existing_aliases():
    """Caută aliasuri existente (*.cmd) în WindowsApps."""
    aliases = {}
    if not os.path.isdir(ALIAS_DIR):
        return aliases

    for file in os.listdir(ALIAS_DIR):
        if file.endswith(".cmd"):
            alias_name = file[:-4]
            cmd_path = os.path.join(ALIAS_DIR, file)

            try:
                with open(cmd_path, "r") as f:
                    line = f.readline().strip()
                    if line.startswith("@\"") and line.endswith("%*"):
                        python_path = line[2:-3].strip('"')
                        aliases[alias_name] = python_path
            except:
                pass

    return aliases

# ------------------------------
# Creare alias
# ------------------------------

def create_alias(alias_name, python_path):
    """Creează un fișier .cmd în WindowsApps pentru alias."""
    cmd_path = os.path.join(ALIAS_DIR, alias_name + ".cmd")

    try:
        with open(cmd_path, "w") as f:
            f.write(f'@"{python_path}" %*\n')
        return True
    except Exception as e:
        print("Eroare alias:", e)
        return False

# ------------------------------
# Interfață PyQt6
# ------------------------------

class PythonAliasManager(QWidget):
    def __init__(self):
        super().__init__()
        self.setWindowTitle("Python Alias Manager – PyQt6")
        self.resize(800, 550)

        layout = QVBoxLayout(self)

        self.table = QTableWidget(0, 2)
        self.table.setHorizontalHeaderLabels(["Path Python", "Alias (editabil)"])
        self.table.horizontalHeader().setStretchLastSection(True)
        layout.addWidget(self.table)

        btn_detect = QPushButton("Detectează instalări (where python)")
        btn_detect.clicked.connect(self.detect_where)
        layout.addWidget(btn_detect)

        btn_add_folder = QPushButton("Adaugă folder custom (recursiv)")
        btn_add_folder.clicked.connect(self.add_folder)
        layout.addWidget(btn_add_folder)

        btn_search_folder = QPushButton("Caută python.exe recursiv în folder selectat")
        btn_search_folder.clicked.connect(self.search_folder)
        layout.addWidget(btn_search_folder)

        btn_aliases = QPushButton("Afișează aliasuri existente")
        btn_aliases.clicked.connect(self.show_existing_aliases)
        layout.addWidget(btn_aliases)

        btn_apply = QPushButton("Aplică aliasuri în Windows")
        btn_apply.clicked.connect(self.apply_aliases)
        layout.addWidget(btn_apply)

        self.data = load_aliases()
        self.refresh_table()

    # --------------------------
    # Tabel
    # --------------------------

    def refresh_table(self):
        self.table.setRowCount(0)
        for entry in self.data:
            row = self.table.rowCount()
            self.table.insertRow(row)

            self.table.setItem(row, 0, QTableWidgetItem(entry["path"]))

            alias_item = QTableWidgetItem(entry["alias"])
            alias_item.setFlags(alias_item.flags() | Qt.ItemFlag.ItemIsEditable)
            self.table.setItem(row, 1, alias_item)

    # --------------------------
    # Detectare instalări
    # --------------------------

    def detect_where(self):
        paths = detect_where_python()
        for p in paths:
            self.add_entry(p)
        self.refresh_table()
        save_aliases(self.data)

    def add_folder(self):
        folder = QFileDialog.getExistingDirectory(self, "Selectează folder Python")
        if folder:
            paths = search_python_in_folder_recursive(folder)
            for p in paths:
                self.add_entry(p)
            self.refresh_table()
            save_aliases(self.data)

    def search_folder(self):
        folder = QFileDialog.getExistingDirectory(self, "Selectează folder pentru scanare")
        if folder:
            paths = search_python_in_folder_recursive(folder)
            for p in paths:
                self.add_entry(p)
            self.refresh_table()
            save_aliases(self.data)

    # --------------------------
    # Aliasuri existente
    # --------------------------

    def show_existing_aliases(self):
        aliases = detect_existing_aliases()
        if not aliases:
            QMessageBox.information(self, "Aliasuri", "Nu există aliasuri în WindowsApps.")
            return

        msg = "\n".join([f"{a} → {p}" for a, p in aliases.items()])
        QMessageBox.information(self, "Aliasuri existente", msg)

    # --------------------------
    # Adăugare în listă
    # --------------------------

    def add_entry(self, path):
        if not any(e["path"] == path for e in self.data):
            alias = "python_" + os.path.basename(os.path.dirname(path)).replace(".", "_")
            self.data.append({"path": path, "alias": alias})

    # --------------------------
    # Aplicare aliasuri
    # --------------------------

    def apply_aliases(self):
        # actualizează aliasurile din tabel
        for row in range(self.table.rowCount()):
            self.data[row]["path"] = self.table.item(row, 0).text()
            self.data[row]["alias"] = self.table.item(row, 1).text()

        save_aliases(self.data)

        ok = 0
        for entry in self.data:
            if create_alias(entry["alias"], entry["path"]):
                ok += 1

        QMessageBox.information(
            self,
            "Aliasuri aplicate",
            f"Aliasuri create: {ok}\nAcum poți folosi comenzile în CMD/PowerShell."
        )

# ------------------------------
# Main
# ------------------------------

if __name__ == "__main__":
    app = QApplication(sys.argv)
    win = PythonAliasManager()
    win.show()
    sys.exit(app.exec())

News : the new python 3.15.0a8.

The Python programming language expected the new version 3.15.0a8 to come with this changelog and release date: XXXX-XX-XX.
Major features and changes
1. Interpreter and JIT optimizations
  • Much improved JIT with optimizations for int, float, list, and tuple operations.
  • Reduces redundant reference counting and adds new specializations (for example for enum.Enum and concatenations).
  • Supports unwinding JIT frames in GDB and GNU backtrace, and sets frame pointers for better profiling.
  • Free-threading improvements remove bottlenecks in sys.intern(), PyObject_SetAttr(), PyMutex, and PyDict_Watch(), improving multi-thread scaling.
  • Garbage collector returns to generational GC as the default and exposes new APIs for external GC monitoring.
  • Runtime optimizations reduce stack usage and fix O(N²) behavior in constant folding, and speed up yield from, bytes.replace(), and memoryview.cast().
2. Security hardening
  • Updates bundled cryptography libraries (for example newer OpenSSL versions in some builds).
  • Fixes path traversal issues in shutil.unpack_archive().
  • Hardens remote debugging related code paths.
  • Addresses crashes and recursion issues in xml.parsers.expat.
  • Adds stricter validation in http.cookies, webbrowser, configparser, and related modules.
  • Introduces tighter limits for TOML keys and canonical Base64 handling.
3. Standard library enhancements
  • Command-line tools like argparse, pdb, regrtest, pickletools, tokenize, calendar, timeit, and http.server gain extended colorized output.
  • The inspect command-line interface is significantly improved.
  • timeit adds a --target-time option for more predictable benchmarking.
  • Typing gains support for features such as disjoint base decorators and richer TypeVarTuple options (bound, covariant, contravariant).
  • ForwardRef representations become clearer and easier to read.
  • Regular expression APIs move toward re.prefixmatch() instead of re.match().
  • array and memoryview support complex number formats like Zf and Zd.
  • frozendict is better integrated with dataclasses, plistlib, and dictionary merging.
  • UserDict.popitem() now behaves in a predictable, ordered way.
  • json adds an array_hook for more flexible decoding.
  • email, IDNA, and importlib.metadata receive fixes for Unicode handling and corrupted metadata.
  • asyncio adds TaskGroup.cancel(), improves debugging, shutdown behavior, and event loop performance.
  • The profiling.sampling module gains dump snapshots, --jsonl output, and --diff-flamegraph for visual comparisons.
4. C API and extension changes
  • Implements a unified slot system for types, simplifying extension type definitions.
  • Adds a stable ABI variant for free-threaded builds (abi3t).
  • Introduces new, safer functions for garbage collector traversal.
  • Makes PyCriticalSection part of the Stable ABI.
  • Provides hooks like PyInterpreterState_SetEvalFrameAllowSpecialization for controlling specialization behavior.
5. Build system and platforms
  • Windows builds adopt a new layout and support free-threaded configurations.
  • Updates to toolchains such as WASI SDK and modern compilers.
  • Improves performance on AArch64 and x86_64 architectures.
  • Fixes issues with PGO, Clang, and LLVM-based builds.
  • Adds options like --enable-static-libpython-for-interpreter for more flexible embedding.
6. Developer experience and ergonomics
  • More extensive colorization in command-line tools and error messages.
  • Better suggestions and messages for AttributeError and similar exceptions.
  • More robust REPL behavior and nicer pretty-printing, including support for new string forms.
  • Smarter import-related completions and diagnostics for everyday workflows.

Saturday, May 2, 2026

Python 3.10.x : Install ComfyUI tool with python and Krita.

This is a basic install of ComfyUI tool with python 3.10 version.
git clone https://github.com/comfyanonymous/ComfyUI
cd ComfyUI
python -m pip install -r requirements.txt
...
Successfully installed blake3-1.0.8 comfy-aimdo-0.3.0 comfy-kitchen-0.2.8 comfyui-embedded-docs-0.4.4 comfyui-frontend-package-1.42.15 comfyui-workflow-templates-0.9.66 comfyui-workflow-templates-core-0.3.221 comfyui-workflow-templates-media-api-0.3.73 comfyui-workflow-templates-media-image-0.3.133 comfyui-workflow-templates-media-other-0.3.187 comfyui-workflow-templates-media-video-0.3.83 glfw-2.10.0 kornia-0.8.2 kornia_rs-0.1.10 sentencepiece-0.2.1 simpleeval-1.0.7 spandrel-0.4.2 torchsde-0.2.6 trampoline-0.1.2
python main.py
You don't have all nodes for running, for example if you want to use with Krita then use this:

git clone https://github.com/comfyanonymous/ComfyUI
cd ComfyUI

echo ================================================
echo   Install all need for ComfyUI
echo ================================================
python -m pip install -r requirements.txt

echo ================================================
echo   Install nodes Krita AI Diffusion
echo ================================================
cd custom_nodes

REM --- ControlNet Preprocessors ---
if not exist comfyui_controlnet_aux (
    git clone https://github.com/Fannovel16/comfyui_controlnet_aux
)

REM --- IP-Adapter Plus ---
if not exist ComfyUI_IPAdapter_plus (
    git clone https://github.com/cubiq/ComfyUI_IPAdapter_plus
)

REM --- Tooling Nodes ---
if not exist comfyui-tooling-nodes (
    git clone https://github.com/Acly/comfyui-tooling-nodes
)

REM --- Inpaint Nodes ---
if not exist comfyui-inpaint-nodes (
    git clone https://github.com/Acly/comfyui-inpaint-nodes
)

cd ..

echo ================================================
echo   Install nodes
echo ================================================

REM --- ControlNet Aux ---
if exist custom_nodes\comfyui_controlnet_aux\requirements.txt (
    python -m pip install -r custom_nodes\comfyui_controlnet_aux\requirements.txt
)

REM --- IPAdapter Plus ---
if exist custom_nodes\ComfyUI_IPAdapter_plus\requirements.txt (
    python -m pip install -r custom_nodes\ComfyUI_IPAdapter_plus\requirements.txt
)

REM --- Tooling Nodes ---
if exist custom_nodes\comfyui-tooling-nodes\requirements.txt (
    python -m pip install -r custom_nodes\comfyui-tooling-nodes\requirements.txt
)

REM --- Inpaint Nodes ---
if exist custom_nodes\comfyui-inpaint-nodes\requirements.txt (
    python -m pip install -r custom_nodes\comfyui-inpaint-nodes\requirements.txt
)

echo ================================================
echo   Install packages
echo ================================================
python -m pip install blake3 comfy-aimdo comfy-kitchen comfyui-embedded-docs ^
comfyui-frontend-package comfyui-workflow-templates ^
comfyui-workflow-templates-core comfyui-workflow-templates-media-api ^
comfyui-workflow-templates-media-image comfyui-workflow-templates-media-other ^
comfyui-workflow-templates-media-video glfw kornia kornia_rs sentencepiece ^
simpleeval spandrel torchsde trampoline

echo ================================================
echo   Start ComfyUI
echo ================================================
python main.py

Thursday, April 23, 2026

Tuesday, April 21, 2026

Python Qt : sprites tool idea with ffmpeg.

This is a simple tool created in a minute with artificial intelligence to help me create sprites with a blend effect based on a map for ffmpeg. I used Python version 3.13.0, pyqt6, pygame, ...

Monday, April 20, 2026

Python 3.12.13 : Colab example with Ipywidgets.

Ipywidgets are interactive HTML widgets for Jupyter notebooks and the IPython kernel that allow users to create GUIs (sliders, text boxes, checkboxes) to visualize and control data in real time. They enable dynamic data exploration and parameter tuning, with over 30 built-in, customizable controls for building interactive dashboards directly in Python code.
You can see on my GitHub Colab repo.