Compare commits
7 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 1a5e32a580 | |||
| 2e79f2b00b | |||
| 891fc73e25 | |||
| 5a5677a994 | |||
| 94fc240086 | |||
| c39071b61a | |||
| 7b35201799 |
@@ -13,10 +13,10 @@ jobs:
|
||||
release-app:
|
||||
runs-on: ubuntu-latest
|
||||
env:
|
||||
RELEASE_TAG: latest
|
||||
ARCHIVE_NAME: shinoa-linux-x86_64.tar.gz
|
||||
CHECKSUM_NAME: shinoa-linux-x86_64.tar.gz.sha256
|
||||
TDLIB_ARCHIVE_URL: ${{ gitea.server_url }}/${{ gitea.repository }}/releases/download/tdlib/tdlib-linux-x86_64.tar.gz
|
||||
TDLIB_RELEASE_TAG: v1.8.63
|
||||
TDLIB_ARCHIVE_URL: https://git.mshq.dev/AxiFisk/shinoa-tdlib/releases/download/${{ env.TDLIB_RELEASE_TAG }}/tdlib-linux-x86_64.tar.gz
|
||||
steps:
|
||||
- name: Check out repository
|
||||
uses: https://github.com/actions/checkout@v4
|
||||
@@ -45,6 +45,20 @@ jobs:
|
||||
pkg-config \
|
||||
zlib1g-dev
|
||||
|
||||
- name: Resolve app version
|
||||
id: app_version
|
||||
run: |
|
||||
set -euo pipefail
|
||||
version="$(sed -n 's/^project(shinoa VERSION \([^ ]*\) LANGUAGES CXX)$/\1/p' CMakeLists.txt)"
|
||||
if [ -z "$version" ]; then
|
||||
echo "Failed to resolve app version from CMakeLists.txt" >&2
|
||||
exit 1
|
||||
fi
|
||||
{
|
||||
echo "version=$version"
|
||||
echo "release_tag=v$version"
|
||||
} >> "$GITHUB_OUTPUT"
|
||||
|
||||
- name: Download prebuilt TDLib
|
||||
run: |
|
||||
set -euo pipefail
|
||||
@@ -54,12 +68,19 @@ jobs:
|
||||
test -f tdlib/lib/libtdjson.so
|
||||
|
||||
- name: Build release bundle
|
||||
env:
|
||||
TELEGRAM_TUI_BUILD_API_ID: ${{ secrets.TELEGRAM_API_ID }}
|
||||
TELEGRAM_TUI_BUILD_API_HASH: ${{ secrets.TELEGRAM_API_HASH }}
|
||||
run: |
|
||||
set -euo pipefail
|
||||
rm -rf build dist
|
||||
|
||||
test -n "${TELEGRAM_TUI_BUILD_API_ID}"
|
||||
test -n "${TELEGRAM_TUI_BUILD_API_HASH}"
|
||||
|
||||
cmake -S . -B build \
|
||||
-DCMAKE_BUILD_TYPE=Release \
|
||||
-DTELEGRAM_TUI_REQUIRE_BUILD_CREDENTIALS=ON \
|
||||
-DTELEGRAM_TUI_TDLIB_ROOT="$PWD/tdlib"
|
||||
cmake --build build -j"$(nproc)"
|
||||
|
||||
@@ -80,18 +101,20 @@ jobs:
|
||||
set -euo pipefail
|
||||
api="${{ gitea.server_url }}/api/v1/repos/${{ gitea.repository }}"
|
||||
commit_sha="${{ github.sha }}"
|
||||
release_tag="${{ steps.app_version.outputs.release_tag }}"
|
||||
version="${{ steps.app_version.outputs.version }}"
|
||||
release_json="$(mktemp)"
|
||||
body_file="$(mktemp)"
|
||||
|
||||
cat > "$body_file" <<EOF
|
||||
Automated rolling release for commit \`${commit_sha}\`.
|
||||
Release ${version} for commit \`${commit_sha}\`.
|
||||
EOF
|
||||
|
||||
status="$(curl --silent --show-error \
|
||||
--output "$release_json" \
|
||||
--write-out "%{http_code}" \
|
||||
-H "Authorization: token ${GITEA_TOKEN}" \
|
||||
"$api/releases/tags/$RELEASE_TAG")"
|
||||
"$api/releases/tags/$release_tag")"
|
||||
|
||||
if [ "$status" = "200" ]; then
|
||||
release_id="$(jq -r '.id' "$release_json")"
|
||||
@@ -105,7 +128,7 @@ jobs:
|
||||
curl --fail-with-body \
|
||||
-H "Authorization: token ${GITEA_TOKEN}" \
|
||||
-X DELETE \
|
||||
"$api/releases/tags/$RELEASE_TAG"
|
||||
"$api/releases/tags/$release_tag"
|
||||
elif [ "$status" != "404" ]; then
|
||||
echo "Failed to query release, HTTP $status" >&2
|
||||
cat "$release_json" >&2
|
||||
@@ -117,11 +140,11 @@ jobs:
|
||||
--write-out "%{http_code}" \
|
||||
-H "Authorization: token ${GITEA_TOKEN}" \
|
||||
-X DELETE \
|
||||
"$api/tags/$RELEASE_TAG")"
|
||||
"$api/tags/$release_tag")"
|
||||
case "$status" in
|
||||
204|404) ;;
|
||||
*)
|
||||
echo "Failed to delete tag $RELEASE_TAG, HTTP $status" >&2
|
||||
echo "Failed to delete tag $release_tag, HTTP $status" >&2
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
@@ -135,9 +158,9 @@ jobs:
|
||||
{
|
||||
"body": $(jq -Rs . < "$body_file"),
|
||||
"draft": false,
|
||||
"name": "latest",
|
||||
"prerelease": true,
|
||||
"tag_name": "$RELEASE_TAG",
|
||||
"name": "v${version}",
|
||||
"prerelease": false,
|
||||
"tag_name": "$release_tag",
|
||||
"target_commitish": "$commit_sha"
|
||||
}
|
||||
EOF
|
||||
|
||||
@@ -7,15 +7,30 @@ set(CMAKE_CXX_STANDARD_REQUIRED ON)
|
||||
set(CMAKE_CXX_EXTENSIONS OFF)
|
||||
|
||||
find_program(CLANG_FORMAT_BIN clang-format)
|
||||
find_package(Git QUIET)
|
||||
|
||||
include(FetchContent)
|
||||
|
||||
option(TELEGRAM_TUI_USE_SYSTEM_TDLIB "Use an installed TDLib package instead of fetching it." OFF)
|
||||
option(TELEGRAM_TUI_REQUIRE_BUILD_CREDENTIALS
|
||||
"Fail configure if build credentials are not provided." OFF)
|
||||
set(TELEGRAM_TUI_TDLIB_ROOT ""
|
||||
CACHE PATH "Path to a prebuilt TDLib root containing include/ and lib/ directories.")
|
||||
|
||||
set(CURSES_NEED_WIDE TRUE)
|
||||
find_package(Curses REQUIRED)
|
||||
find_package(Threads REQUIRED)
|
||||
|
||||
find_package(nlohmann_json QUIET)
|
||||
if(NOT nlohmann_json_FOUND)
|
||||
FetchContent_Declare(
|
||||
nlohmann_json
|
||||
GIT_REPOSITORY https://github.com/nlohmann/json.git
|
||||
GIT_TAG v3.11.3
|
||||
GIT_SHALLOW TRUE
|
||||
)
|
||||
FetchContent_MakeAvailable(nlohmann_json)
|
||||
endif()
|
||||
|
||||
set(TELEGRAM_TUI_APP_CONFIG_PATH "")
|
||||
if(DEFINED ENV{XDG_DATA_HOME} AND NOT "$ENV{XDG_DATA_HOME}" STREQUAL "")
|
||||
@@ -26,21 +41,66 @@ endif()
|
||||
|
||||
set(TELEGRAM_TUI_BUILD_API_ID "")
|
||||
set(TELEGRAM_TUI_BUILD_API_HASH "")
|
||||
if(TELEGRAM_TUI_APP_CONFIG_PATH AND EXISTS "${TELEGRAM_TUI_APP_CONFIG_PATH}")
|
||||
set(TELEGRAM_TUI_BUILD_VERSION "${PROJECT_VERSION}")
|
||||
set(TELEGRAM_TUI_BUILD_COMMIT "")
|
||||
if(GIT_FOUND AND EXISTS "${CMAKE_SOURCE_DIR}/.git")
|
||||
execute_process(
|
||||
COMMAND "${GIT_EXECUTABLE}" rev-parse --short HEAD
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}"
|
||||
OUTPUT_VARIABLE TELEGRAM_TUI_BUILD_COMMIT
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
ERROR_QUIET
|
||||
)
|
||||
execute_process(
|
||||
COMMAND "${GIT_EXECUTABLE}" describe --tags --always --dirty
|
||||
WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}"
|
||||
OUTPUT_VARIABLE TELEGRAM_TUI_GIT_DESCRIBE
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
ERROR_QUIET
|
||||
)
|
||||
if(TELEGRAM_TUI_GIT_DESCRIBE)
|
||||
set(TELEGRAM_TUI_BUILD_VERSION "${PROJECT_VERSION}+${TELEGRAM_TUI_GIT_DESCRIBE}")
|
||||
endif()
|
||||
endif()
|
||||
if(DEFINED ENV{TELEGRAM_TUI_BUILD_API_ID} AND NOT "$ENV{TELEGRAM_TUI_BUILD_API_ID}" STREQUAL "")
|
||||
set(TELEGRAM_TUI_BUILD_API_ID "$ENV{TELEGRAM_TUI_BUILD_API_ID}")
|
||||
elseif(DEFINED ENV{TELEGRAM_API_ID} AND NOT "$ENV{TELEGRAM_API_ID}" STREQUAL "")
|
||||
set(TELEGRAM_TUI_BUILD_API_ID "$ENV{TELEGRAM_API_ID}")
|
||||
endif()
|
||||
|
||||
if(DEFINED ENV{TELEGRAM_TUI_BUILD_API_HASH} AND NOT "$ENV{TELEGRAM_TUI_BUILD_API_HASH}" STREQUAL "")
|
||||
set(TELEGRAM_TUI_BUILD_API_HASH "$ENV{TELEGRAM_TUI_BUILD_API_HASH}")
|
||||
elseif(DEFINED ENV{TELEGRAM_API_HASH} AND NOT "$ENV{TELEGRAM_API_HASH}" STREQUAL "")
|
||||
set(TELEGRAM_TUI_BUILD_API_HASH "$ENV{TELEGRAM_API_HASH}")
|
||||
endif()
|
||||
|
||||
if((TELEGRAM_TUI_BUILD_API_ID STREQUAL "" OR TELEGRAM_TUI_BUILD_API_HASH STREQUAL "") AND
|
||||
TELEGRAM_TUI_APP_CONFIG_PATH AND EXISTS "${TELEGRAM_TUI_APP_CONFIG_PATH}")
|
||||
file(READ "${TELEGRAM_TUI_APP_CONFIG_PATH}" TELEGRAM_TUI_APP_CONFIG_JSON)
|
||||
|
||||
if(TELEGRAM_TUI_BUILD_API_ID STREQUAL "")
|
||||
string(REGEX MATCH "\"api_id\"[ \t\r\n]*:[ \t\r\n]*\"?([0-9]+)\"?"
|
||||
TELEGRAM_TUI_APP_CONFIG_API_ID_MATCH "${TELEGRAM_TUI_APP_CONFIG_JSON}")
|
||||
if(CMAKE_MATCH_1)
|
||||
set(TELEGRAM_TUI_BUILD_API_ID "${CMAKE_MATCH_1}")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(TELEGRAM_TUI_BUILD_API_HASH STREQUAL "")
|
||||
string(REGEX MATCH "\"api_hash\"[ \t\r\n]*:[ \t\r\n]*\"([^\"]+)\""
|
||||
TELEGRAM_TUI_APP_CONFIG_API_HASH_MATCH "${TELEGRAM_TUI_APP_CONFIG_JSON}")
|
||||
if(CMAKE_MATCH_1)
|
||||
set(TELEGRAM_TUI_BUILD_API_HASH "${CMAKE_MATCH_1}")
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(TELEGRAM_TUI_REQUIRE_BUILD_CREDENTIALS AND
|
||||
(TELEGRAM_TUI_BUILD_API_ID STREQUAL "" OR TELEGRAM_TUI_BUILD_API_HASH STREQUAL ""))
|
||||
message(FATAL_ERROR
|
||||
"Build credentials are required. Set TELEGRAM_TUI_BUILD_API_ID and "
|
||||
"TELEGRAM_TUI_BUILD_API_HASH (or TELEGRAM_API_ID/TELEGRAM_API_HASH).")
|
||||
endif()
|
||||
|
||||
configure_file(
|
||||
${CMAKE_SOURCE_DIR}/src/build_config.h.in
|
||||
@@ -119,7 +179,8 @@ if(CLANG_FORMAT_BIN)
|
||||
endif()
|
||||
|
||||
target_include_directories(shinoa PRIVATE ${CURSES_INCLUDE_DIRS} ${CMAKE_CURRENT_BINARY_DIR})
|
||||
target_link_libraries(shinoa PRIVATE ${CURSES_LIBRARIES})
|
||||
target_link_libraries(shinoa PRIVATE ${CURSES_LIBRARIES} Threads::Threads
|
||||
nlohmann_json::nlohmann_json)
|
||||
|
||||
if(TELEGRAM_TUI_USE_SYSTEM_TDLIB)
|
||||
target_link_libraries(shinoa PRIVATE Td::TdJson)
|
||||
|
||||
5
PKGBUILD
5
PKGBUILD
@@ -1,15 +1,16 @@
|
||||
pkgname=shinoa-bin
|
||||
pkgver=latest
|
||||
pkgver=0.1.0
|
||||
pkgrel=1
|
||||
pkgdesc='Minimal Telegram terminal client built with ncurses and bundled TDLib'
|
||||
arch=('x86_64')
|
||||
url='https://git.mshq.dev/AxiFisk/shinoa'
|
||||
license=('custom:unknown')
|
||||
depends=('gcc-libs' 'glibc' 'ncurses' 'openssl' 'zlib')
|
||||
options=(!debug)
|
||||
provides=('shinoa')
|
||||
conflicts=('shinoa')
|
||||
source=(
|
||||
"shinoa-linux-x86_64.tar.gz::${url}/releases/download/latest/shinoa-linux-x86_64.tar.gz"
|
||||
"shinoa-linux-x86_64.tar.gz::${url}/releases/download/v${pkgver}/shinoa-linux-x86_64.tar.gz"
|
||||
)
|
||||
sha256sums=('SKIP')
|
||||
|
||||
|
||||
17
README.md
17
README.md
@@ -31,6 +31,9 @@ cmake --build build -j
|
||||
During configure, CMake also checks the app config at
|
||||
`$XDG_DATA_HOME/telegram-tui/config.json` or `~/.local/share/telegram-tui/config.json`.
|
||||
If that file contains `api_id` and `api_hash`, they are embedded into the build.
|
||||
For CI or release builds, prefer setting `TELEGRAM_TUI_BUILD_API_ID` and
|
||||
`TELEGRAM_TUI_BUILD_API_HASH` in the environment so credentials come from secrets instead of
|
||||
local config.
|
||||
|
||||
## Run
|
||||
|
||||
@@ -64,10 +67,12 @@ archive plus checksum to the Gitea Generic Package Registry under the `tdlib` pa
|
||||
It also refreshes a `latest/tdlib-latest.json` manifest with the newest published version.
|
||||
|
||||
The repository also includes [`.gitea/workflows/release-app.yaml`](.gitea/workflows/release-app.yaml),
|
||||
which downloads a prebuilt TDLib bundle from this repository's `tdlib` release tag, builds a
|
||||
rolling `latest` app release, and publishes an archive containing `usr/bin/shinoa` plus the
|
||||
which downloads a prebuilt TDLib bundle from the `shinoa-tdlib` repository using a pinned
|
||||
version tag such as `v1.8.63`, builds a
|
||||
versioned app release tag such as `v0.1.0`, and publishes an archive containing `usr/bin/shinoa` plus the
|
||||
bundled `usr/lib/libtdjson.so*`. The root `PKGBUILD` installs that prebuilt release as
|
||||
`shinoa-bin`.
|
||||
`shinoa-bin`. The package disables debug splitting with `options=(!debug)`. That workflow expects Gitea secrets named `TELEGRAM_API_ID` and
|
||||
`TELEGRAM_API_HASH`. Release builds are configured to fail if those secrets are missing.
|
||||
|
||||
To prepare the TDLib bundle on your own machine:
|
||||
|
||||
@@ -78,8 +83,10 @@ cmake --install td-build
|
||||
./scripts/package-tdlib.sh td-install tdlib-linux-x86_64.tar.gz
|
||||
```
|
||||
|
||||
Upload `tdlib-linux-x86_64.tar.gz` to a release tagged `tdlib` in this repository. After that,
|
||||
the `Release App` workflow can consume it and publish the app bundle.
|
||||
Publish `tdlib-linux-x86_64.tar.gz` to the `shinoa-tdlib` repository under a versioned tag such
|
||||
as `v1.8.63`. Then update `TDLIB_RELEASE_TAG` in
|
||||
[`.gitea/workflows/release-app.yaml`](.gitea/workflows/release-app.yaml) and run the
|
||||
`Release App` workflow.
|
||||
|
||||
## Keys
|
||||
|
||||
|
||||
99
src/app.cpp
99
src/app.cpp
@@ -1,5 +1,9 @@
|
||||
#include "app.h"
|
||||
|
||||
#include <array>
|
||||
#include <cstdio>
|
||||
#include <future>
|
||||
|
||||
#include <curses.h>
|
||||
|
||||
#include "build_config.h"
|
||||
@@ -9,11 +13,83 @@ namespace telegram_tui {
|
||||
|
||||
namespace {
|
||||
|
||||
std::string trim_release_tag_prefix(const std::string &value) {
|
||||
if (!value.empty() && (value[0] == 'v' || value[0] == 'V')) {
|
||||
return value.substr(1);
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
bool is_truthy_env_value(const std::string &value) {
|
||||
return value == "1" || value == "true" || value == "TRUE" || value == "yes" ||
|
||||
value == "YES" || value == "on" || value == "ON";
|
||||
}
|
||||
|
||||
std::string shell_quote(const std::string &value) {
|
||||
std::string quoted = "'";
|
||||
for (char ch : value) {
|
||||
if (ch == '\'') {
|
||||
quoted += "'\\''";
|
||||
} else {
|
||||
quoted.push_back(ch);
|
||||
}
|
||||
}
|
||||
quoted.push_back('\'');
|
||||
return quoted;
|
||||
}
|
||||
|
||||
std::string run_command_capture(const std::string &command) {
|
||||
FILE *pipe = popen(command.c_str(), "r");
|
||||
if (pipe == nullptr) {
|
||||
return {};
|
||||
}
|
||||
|
||||
std::string output;
|
||||
std::array<char, 4096> buffer{};
|
||||
while (std::fgets(buffer.data(), static_cast<int>(buffer.size()), pipe) != nullptr) {
|
||||
output += buffer.data();
|
||||
}
|
||||
if (pclose(pipe) != 0) {
|
||||
return {};
|
||||
}
|
||||
return output;
|
||||
}
|
||||
|
||||
std::optional<std::string> fetch_update_notice() {
|
||||
static constexpr const char *kLatestReleaseApiUrl =
|
||||
"https://git.mshq.dev/api/v1/repos/AxiFisk/shinoa/releases/latest";
|
||||
|
||||
if (std::string(TELEGRAM_TUI_BUILD_COMMIT).empty()) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
const std::string response =
|
||||
run_command_capture("curl -fsSL " + shell_quote(kLatestReleaseApiUrl) + " 2>/dev/null");
|
||||
if (response.empty()) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
try {
|
||||
const json release = json::parse(response, nullptr, true, true);
|
||||
const std::string latest_tag = trim_release_tag_prefix(safe_string(release, "tag_name"));
|
||||
if (!latest_tag.empty() && latest_tag == TELEGRAM_TUI_PROJECT_VERSION) {
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
const std::string target_commit = safe_string(release, "target_commitish");
|
||||
if (target_commit.empty()) {
|
||||
return std::nullopt;
|
||||
}
|
||||
const std::string current_commit = TELEGRAM_TUI_BUILD_COMMIT;
|
||||
if (target_commit == current_commit || target_commit.rfind(current_commit, 0) == 0) {
|
||||
return std::nullopt;
|
||||
}
|
||||
return std::string("Update available");
|
||||
} catch (const json::exception &) {
|
||||
return std::nullopt;
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
App::App() {
|
||||
@@ -49,6 +125,8 @@ App::App() {
|
||||
if (use_test_dc_) {
|
||||
status_line_ = "Starting TDLib in test DC mode...";
|
||||
}
|
||||
|
||||
start_update_check();
|
||||
}
|
||||
|
||||
int App::run() {
|
||||
@@ -80,6 +158,27 @@ int App::run() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void App::start_update_check() {
|
||||
update_check_future_ =
|
||||
std::async(std::launch::async, []() { return fetch_update_notice(); });
|
||||
}
|
||||
|
||||
bool App::refresh_update_check_result() {
|
||||
if (!update_check_future_.valid()) {
|
||||
return false;
|
||||
}
|
||||
if (update_check_future_.wait_for(std::chrono::seconds(0)) != std::future_status::ready) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const auto notice = update_check_future_.get();
|
||||
if (notice == update_notice_) {
|
||||
return false;
|
||||
}
|
||||
update_notice_ = notice.value_or(std::string());
|
||||
return true;
|
||||
}
|
||||
|
||||
std::optional<std::int64_t> App::highlighted_chat_id() const {
|
||||
if (sorted_chat_ids_.empty()) {
|
||||
return std::nullopt;
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
#include <cstdint>
|
||||
#include <chrono>
|
||||
#include <filesystem>
|
||||
#include <future>
|
||||
#include <map>
|
||||
#include <optional>
|
||||
#include <tuple>
|
||||
@@ -38,6 +39,8 @@ class App {
|
||||
|
||||
void init_curses();
|
||||
void shutdown_curses();
|
||||
void start_update_check();
|
||||
bool refresh_update_check_result();
|
||||
bool process_updates();
|
||||
void handle_td_object(const json &object);
|
||||
void handle_authorization_state();
|
||||
@@ -197,6 +200,7 @@ class App {
|
||||
std::string input_prompt_;
|
||||
std::string input_buffer_;
|
||||
std::string status_line_ = "Starting TDLib...";
|
||||
std::string update_notice_;
|
||||
std::string attachment_preview_graphics_data_;
|
||||
std::string attachment_viewer_title_;
|
||||
std::string attachment_preview_signature_;
|
||||
@@ -217,6 +221,7 @@ class App {
|
||||
std::size_t attachment_viewer_frame_index_ = 0;
|
||||
std::string attachment_viewer_send_caption_;
|
||||
std::vector<std::int64_t> forward_message_ids_;
|
||||
std::future<std::optional<std::string>> update_check_future_;
|
||||
};
|
||||
|
||||
} // namespace telegram_tui
|
||||
|
||||
@@ -9,6 +9,7 @@
|
||||
|
||||
#include <curses.h>
|
||||
|
||||
#include "build_config.h"
|
||||
#include "util.h"
|
||||
|
||||
namespace telegram_tui {
|
||||
@@ -242,7 +243,7 @@ void App::send_tdlib_parameters() {
|
||||
{"system_language_code", "en"},
|
||||
{"device_model", "shinoa"},
|
||||
{"system_version", "Linux"},
|
||||
{"application_version", "0.1.0"},
|
||||
{"application_version", TELEGRAM_TUI_BUILD_VERSION},
|
||||
{"enable_storage_optimizer", true},
|
||||
{"ignore_file_names", false},
|
||||
});
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
#include <curses.h>
|
||||
|
||||
#include "app_ui.h"
|
||||
#include "build_config.h"
|
||||
#include "util.h"
|
||||
|
||||
namespace telegram_tui {
|
||||
@@ -88,10 +89,25 @@ void App::draw() {
|
||||
|
||||
attron(A_REVERSE);
|
||||
mvhline(header_y, 0, ' ', width);
|
||||
const std::string header_label = use_test_dc_ ? "shinoa [TEST DC]" : "shinoa";
|
||||
std::string header_label = std::string("shinoa ") + TELEGRAM_TUI_BUILD_VERSION;
|
||||
if (use_test_dc_) {
|
||||
header_label += " [TEST DC]";
|
||||
}
|
||||
mvprintw(header_y, 1, "%s", header_label.c_str());
|
||||
const std::string auth_label = authorized_ ? "ready" : current_auth_label();
|
||||
const int auth_x = std::max(1, width - static_cast<int>(auth_label.size()) - 2);
|
||||
if (!update_notice_.empty()) {
|
||||
const std::string centered_notice =
|
||||
truncate_to_width(update_notice_, std::max(1, width - 4));
|
||||
const int notice_x =
|
||||
std::max(1, (width - static_cast<int>(centered_notice.size())) / 2);
|
||||
if (notice_x > 1 + static_cast<int>(header_label.size()) &&
|
||||
notice_x + static_cast<int>(centered_notice.size()) < auth_x - 1) {
|
||||
attron(A_BOLD);
|
||||
mvprintw(header_y, notice_x, "%s", centered_notice.c_str());
|
||||
attroff(A_BOLD);
|
||||
}
|
||||
}
|
||||
mvprintw(header_y, auth_x, "%s", auth_label.c_str());
|
||||
attroff(A_REVERSE);
|
||||
|
||||
|
||||
@@ -25,7 +25,7 @@ std::string format_download_progress(std::int64_t downloaded_size, std::int64_t
|
||||
} // namespace
|
||||
|
||||
bool App::process_updates() {
|
||||
bool changed = false;
|
||||
bool changed = refresh_update_check_result();
|
||||
while (true) {
|
||||
auto update = td_.receive(0.0);
|
||||
if (!update.has_value()) {
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#define TELEGRAM_TUI_PROJECT_VERSION "@PROJECT_VERSION@"
|
||||
#define TELEGRAM_TUI_BUILD_COMMIT "@TELEGRAM_TUI_BUILD_COMMIT@"
|
||||
#define TELEGRAM_TUI_BUILD_VERSION "@TELEGRAM_TUI_BUILD_VERSION@"
|
||||
#define TELEGRAM_TUI_BUILD_API_ID "@TELEGRAM_TUI_BUILD_API_ID@"
|
||||
#define TELEGRAM_TUI_BUILD_API_HASH "@TELEGRAM_TUI_BUILD_API_HASH@"
|
||||
|
||||
Reference in New Issue
Block a user