yshalsager's Channel
2.38K subscribers
66 photos
12 videos
4 files
774 links
A channel where you can find @yshalsager's projects and its updates.
https://yshalsager.com/en/
Download Telegram
https://tools.simonwillison.net/colophon

useful collection of web tools
2
Some people live a quiet, private life. No audience and no strangers. Just family, friends, and a small circle that understands them.

Then one day, they decide to go online. They open a social media account and begin speaking to the entire world, sharing opinions, stories, emotions, and personal experiences.

After one or two videos, the comments come in. Criticism, mockery and harsh words are hurled at them, and suddenly, insecurity sets in.

The next video isn’t a message anymore, it’s a defense, then tears, then explanations, then more pain.

And I ask, what for? Islam teaches us that not everything needs to be shared. Not everyone deserves access to your story.

The Quran teaches us the wisdom of selective sharing through the story of Prophet Yusuf عليه السلام.

قالَ يا بُنَيَّ لا تَقصُص رُؤياكَ عَلى إِخوَتِكَ فَيَكيدوا لَكَ كَيدًا إِنَّ الشَّيطانَ لِلإِنسانِ عَدُوٌّ مُبينٌ
“He said, ‘O my son, do not relate your dream to your brothers, or they will plot against you. Indeed, the devil is a clear enemy to man.” (Surah Yusuf: 5)

This wasn’t about hiding the truth, it was about protecting it. Because not everyone who hears your story will make Dua for you. Some will envy you, some will misunderstand you and some will use it against you.

The online world is not built on gentleness. It is not obligated to sympathize with you. And it will not change for your sensitivity. If you are sensitive, and there is nothing wrong with that, then protect yourself.

Not every story, pain and emotion needs an audience and comments. Some things are meant to stay offline, where they are safer, purer, and better cared for.

Keeping things private is not shameful nor is it weakness. And staying offline can sometimes be the wisest decision of all. Choose wisely.

https://quranreflect.com/posts/1766823931107372
8🔥1
Compare and see best LLM model for OCR

https://www.ocrarena.ai/battle
👍4
yshalsager's Channel
Shamela EPUB Exporter A tool to download books from the Shamela Library into EPUB files locally. Available as browser extenstion, desktop app, and Android app. https://github.com/yshalsager/shamela-epub-exporter
Four years ago I worked on a command-line tool and a graphical interface to download books from Shamela (Al-Maktaba Al-Shamela) as EPUB e-books from the official site so I could download the latest books and read them on any device or reader without being tied to the website or the desktop program.

https://github.com/yshalsager/shamela2epub

About six months ago I made a simpler, web-based version of the tool that runs in Google Colab notebooks so anyone can use the tool and download books easily.

https://t.iss.one/ysh_alsager/5970

Then about a month ago I rebuilt the project using web technologies after it had been written in Python.

The result: Chrome and Firefox browser extensions, a desktop app for Windows, Linux, and Mac, and an Android app using the same codebase, available in both Arabic and English!

Technologies used
TypeScript + Svelte 5 (UI)
WXT + Vite (extension tooling)
Tauri (desktop app)
Tailwind CSS (styling)
JSZip (EPUB creation)
Wuchale (localization)

As always, the new software is free and open source; you can view and download it from the code repository

https://github.com/yshalsager/shamela-epub-exporter

And for those who need to run Shamela’s tools on non-Windows desktop operating systems, here is how to run version 4 on:
- Linux
- Mac
7👍2
🚀 New feature on Quran.com!

You can now embed Quran verses anywhere to help share the words of Allah 🌙

The new embed builder lets you:
• choose a surah/ayah (or a verse range)
• select translations
• enable audio, word-by-word, themes, mushaf styles, etc.
• get a ready-to-use embed code in seconds

Perfect for blogs, mosque websites, apps, and community projects.

https://quran.com/embed
6🤩1
E-Book Converter Bot has been updated with new features

Major Features
- Added interactive conversion options flow.
- Added localized format-specific controls and simplified options flow.
- Added EPUB background removal option.
- Added KePub conversion support.
- Added PDF input conversion support.
- Added Shamela .bok input support.

Conversion UX & Behavior
- Made option state updates idempotent.
- Added DOCX float CSS filtering (fixes converting some cases).
- Hardened converter callback state and reply-mode handling.
- Added queue expiration, periodic cleanup, and user-facing expired-request messages.
- Added dynamic supported format counts in /start.

Reliability & Security
- Reworked restart state handling with restart.json.
- Hardened restart notices and shutdown cleanup.
- Added Telegram retry behavior for flood/slow-mode waits.
- Removed shell exec risk and unsafe download path usage.

Broadcast & i18n
- Improved localized broadcast status formatting.
- Switched broadcast completion to built-in localized message source.
- Migrated gettext workflow from Makefile tasks to mise.toml.

Database & Infra
- Switched DB access to per-call SQLAlchemy sessions.
- Added missing analytics format columns.
- Updated Docker localtime mount placement.

Dev/Test Tooling
- Migrated type checking from mypy to ty.
- Added/updated pytest tasks via mise.
- Migrated EPUB OPF tests to pytest.
- General dependency and typing cleanup.

All commits

Try the bot new update: @ebook_converter_bot

If you like my work, you may consider supporting it via a donation. A donation was never necessary, but It's making life easier for me and guarantees paying server costs as well as keeping projects active and without annoying ads. My works are free and open-source, that cost money, time, and many efforts. You can do this using GitHub Sponsors, LibrePay, or PayPal.

Stay tuned for new updates!
2
Compiling https://github.com/BurntSushi/ripgrep/ for android


#!/usr/bin/env bash
set -euo pipefail
target='aarch64-linux-android'
if [[ $# -gt 0 && "$1" != -* ]]; then
target="$1"
shift
fi
api="${RG_ANDROID_API:-21}"
if [[ -n "${RG_ANDROID_NDK_HOME:-}" ]]; then
ndk_home="$RG_ANDROID_NDK_HOME"
elif [[ -n "${ANDROID_NDK_HOME:-}" ]]; then
ndk_home="$ANDROID_NDK_HOME"
elif [[ -n "${ANDROID_NDK_ROOT:-}" ]]; then
ndk_home="$ANDROID_NDK_ROOT"
else
ndk_home="$(ls -d "$HOME"/Library/Android/sdk/ndk/* 2>/dev/null | sort -V | tail -n1)"
fi
if [[ -z "${ndk_home:-}" || ! -d "$ndk_home" ]]; then
echo 'error: Android NDK not found. Set RG_ANDROID_NDK_HOME, ANDROID_NDK_HOME or ANDROID_NDK_ROOT.' >&2
exit 1
fi
ndk_prebuilt="$(ls -d "$ndk_home"/toolchains/llvm/prebuilt/* 2>/dev/null | head -n1)"
if [[ -z "${ndk_prebuilt:-}" || ! -d "$ndk_prebuilt" ]]; then
echo "error: NDK LLVM prebuilt toolchain not found in $ndk_home." >&2
exit 1
fi
case "$target" in
aarch64-linux-android) clang_triple='aarch64-linux-android' ;;
x86_64-linux-android) clang_triple='x86_64-linux-android' ;;
i686-linux-android) clang_triple='i686-linux-android' ;;
armv7-linux-androideabi|arm-linux-androideabi) clang_triple='armv7a-linux-androideabi' ;;
*)
echo "error: unsupported Android target '$target'." >&2
exit 1
;;
esac
linker="$ndk_prebuilt/bin/${clang_triple}${api}-clang"
ar="$ndk_prebuilt/bin/llvm-ar"
if [[ ! -x "$linker" ]]; then
echo "error: linker not found: $linker" >&2
exit 1
fi
if [[ ! -x "$ar" ]]; then
echo "error: archiver not found: $ar" >&2
exit 1
fi
target_upper="${target//-/_}"
target_upper="$(printf '%s' "$target_upper" | tr '[:lower:]' '[:upper:]')"
target_lower="${target//-/_}"
export ANDROID_NDK_HOME="$ndk_home"
export "CARGO_TARGET_${target_upper}_LINKER=$linker"
export "CARGO_TARGET_${target_upper}_AR=$ar"
export "CC_${target_lower}=$linker"
export "AR_${target_lower}=$ar"
rustup target add "$target"
cargo build --release --target "$target" --bin rg "$@"
🔥41
Release notes from calibre-with-kfx:

This update adds the ability to pass KFX Input / Output's CLI options.

e.g. Convert to KFX with approximate page numbers (auto): docker run --rm -it -v "$(pwd):/app:rw" yshalsager/calibre-with-kfx book.epub book.kfx --pages 0

When converting to KFX, extra args are passed to the KFX Output plugin (`calibre-debug -r "KFX Output" -- ...`). Useful flags include:

- --pages N create approximate page numbers if missing (`0` = auto)
- --book mark as EBOK (vs default PDOC)
- --asin BXXXXXXXXX set an ASIN
- --logs include Kindle Previewer conversion logs
- --quality include Kindle Previewer quality report
- --timeout stop conversions lasting over ~15 minutes

When converting from KFX to other formats, this image uses ebook-convert normally. Any ebook-convert CLI options can be passed as extra args.

The KFX Input plugin also provides a separate CLI (useful for print replica PDF extraction, CBZ creation, resource unpacking, etc):


docker run --rm -it -v "$(pwd):/app:rw" --entrypoint calibre-debug yshalsager/calibre-with-kfx \
-r "KFX Input" -- /app/book.kfx --help


Common KFX Input CLI flags:

- --epub (default), --epub2
- --pdf extract/produce PDF (print replica, comics/children's)
- --cbz create CBZ (print replica, comics/children's)
- --unpack extract resources to a ZIP
- --json-content create JSON content/position file
- --cover force a generic EPUB cover if missing

KFX Input has one calibre "Convert Books" option: allow_conversion_with_errors (default off). It also has plugin preferences used by its CLI/From-KFX UI (for example splitting landscape comic images when creating PDF).

https://github.com/yshalsager/calibre-with-kfx/releases/tag/20260220-2041