Apply tdlight patch
- Memory manager - TD_SKIP_TEST/TD_SKIP_BENCHMARK/TD_SKIP_TG_CLI - Rebranding - github workflow - .gitignore - Add crypt32 to windows - Fatal crash log handler - optionally unencrypted database - malloc_trim support - getMemoryStatistics Options: - disable_document_filenames - disable_minithumbnails - disable_notifications - disable_group_calls - disable_auto_download - ignore_server_deletes_and_reads - ignore_update_chat_last_message - ignore_update_chat_read_inbox - ignore_update_user_chat_action - receive_access_hashes - message_unload_delay modification
This commit is contained in:
parent
0d3a1552ed
commit
b6c5bd07bb
50
.github/workflows/build.yaml
vendored
Normal file
50
.github/workflows/build.yaml
vendored
Normal file
@ -0,0 +1,50 @@
|
||||
name: Build TDLib
|
||||
|
||||
on:
|
||||
push:
|
||||
pull_request:
|
||||
schedule:
|
||||
- cron: '0 0 * * 0' # weekly
|
||||
|
||||
jobs:
|
||||
build:
|
||||
runs-on: ubuntu-20.04
|
||||
strategy:
|
||||
matrix:
|
||||
arch: [linux/386, linux/amd64, linux/arm/v6, linux/arm/v7, linux/arm64, linux/ppc64le]
|
||||
|
||||
steps:
|
||||
- name: Setup variables
|
||||
run: |
|
||||
ARCH=${{ matrix.arch }}
|
||||
SAFE_ARCH=$(echo $ARCH | sed 's/\//\-/g')
|
||||
echo "SAFE_ARCH=$SAFE_ARCH" >> $GITHUB_ENV
|
||||
- name: Install sudo package
|
||||
run: |
|
||||
(apt-get update || true) 2>/dev/null
|
||||
(apt-get install -y sudo || true) 2>/dev/null
|
||||
sudo apt update
|
||||
- uses: actions/checkout@v2
|
||||
with:
|
||||
submodules: "recursive"
|
||||
- name: Cache ccache
|
||||
id: cache-ccache
|
||||
uses: actions/cache@v2
|
||||
with:
|
||||
path: ~/.ccache
|
||||
key: ${{ runner.os }}-${{ env.SAFE_ARCH }}-ccache-all
|
||||
restore-keys: |
|
||||
${{ runner.os }}-${{ env.SAFE_ARCH }}-ccache-
|
||||
- name: Install build tools
|
||||
run: sudo apt-get install -y make git zlib1g-dev libssl-dev gperf php-cli cmake clang-6.0 libc++-dev libc++abi-dev ccache
|
||||
- name: Build
|
||||
run: |
|
||||
mkdir build
|
||||
cd build
|
||||
CXXFLAGS="-stdlib=libc++" CC=/usr/bin/clang-10 CXX=/usr/bin/clang++-10 cmake -DCMAKE_BUILD_TYPE=Release -DCMAKE_INSTALL_PREFIX:PATH=../tdlib ..
|
||||
cmake --build . --target install -- -j4
|
||||
- uses: actions/upload-artifact@v2
|
||||
with:
|
||||
name: tdlight-${{ env.SAFE_ARCH }}
|
||||
path: tdlib/lib
|
||||
|
2
.gitignore
vendored
2
.gitignore
vendored
@ -4,7 +4,9 @@
|
||||
**/auto/
|
||||
docs/
|
||||
/tdlib/
|
||||
.idea/
|
||||
vcpkg/
|
||||
*.tlo
|
||||
|
||||
td.binlog
|
||||
|
||||
|
@ -1024,7 +1024,7 @@ Changes in 1.5.0 (9 Sep 2019):
|
||||
* Added the class `chatEventPollStopped` representing the closing of a poll in a message in the chat event log.
|
||||
* Added ability to specify the exact types of problems with a call in the method `sendCallRating` and
|
||||
the new class `CallProblem`.
|
||||
* Changes in [tdweb](https://github.com/tdlib/td/blob/master/example/web/):
|
||||
* Changes in [tdweb](https://github.com/tdlight-team/tdlight/blob/master/example/web/):
|
||||
- Supported non-zero `offset` and `limit` in `readFilePart`.
|
||||
|
||||
-----------------------------------------------------------------------------------------------------------------------
|
||||
@ -1034,7 +1034,7 @@ Changes in 1.4.0 (1 May 2019):
|
||||
* Added a [TDLib build instructions generator](https://tdlib.github.io/td/build.html), covering in details
|
||||
TDLib building on the most popular operating systems.
|
||||
* Added an example of TDLib building and usage from a browser.
|
||||
See https://github.com/tdlib/td/blob/master/example/web/ for more details.
|
||||
See https://github.com/tdlight-team/tdlight/blob/master/example/web/ for more details.
|
||||
* Allowed to pass NULL pointer to `td_json_client_execute` instead of a previously created JSON client.
|
||||
Now you can use synchronous TDLib methods through a JSON interface before creating a TDLib JSON client.
|
||||
* Added support for media streaming by allowing to download any part of a file:
|
||||
@ -1285,7 +1285,7 @@ Changes in 1.4.0 (1 May 2019):
|
||||
|
||||
Changes in 1.3.0 (5 Sep 2018):
|
||||
|
||||
* Added a review of existing TDLib based [frameworks](https://github.com/tdlib/td/blob/master/example/README.md)
|
||||
* Added a review of existing TDLib based [frameworks](https://github.com/tdlight-team/tdlight/blob/master/example/README.md)
|
||||
in different programming languages.
|
||||
* Added a [Getting started](https://core.telegram.org/tdlib/getting-started) guide describing the main TDLib concepts
|
||||
and basic principles required for library usage.
|
||||
|
@ -207,9 +207,13 @@ add_subdirectory(sqlite)
|
||||
|
||||
add_subdirectory(tddb)
|
||||
|
||||
add_subdirectory(test)
|
||||
option(TD_SKIP_TEST "Use \"ON\" to skip building/running the test harness.")
|
||||
if (NOT TD_SKIP_TEST)
|
||||
add_subdirectory(test)
|
||||
endif()
|
||||
|
||||
if (NOT CMAKE_CROSSCOMPILING)
|
||||
option(TD_SKIP_BENCHMARK "Use \"ON\" to skip building/running the benchmarks.")
|
||||
if (NOT CMAKE_CROSSCOMPILING AND NOT TD_SKIP_BENCHMARK)
|
||||
add_subdirectory(benchmark)
|
||||
endif()
|
||||
|
||||
@ -569,6 +573,7 @@ set(TDLIB_SOURCE_PART2
|
||||
td/telegram/StickersManager.cpp
|
||||
td/telegram/StickerType.cpp
|
||||
td/telegram/StorageManager.cpp
|
||||
td/telegram/MemoryManager.cpp
|
||||
td/telegram/StoryContent.cpp
|
||||
td/telegram/StoryContentType.cpp
|
||||
td/telegram/StoryDb.cpp
|
||||
@ -918,6 +923,7 @@ set(TDLIB_SOURCE_PART2
|
||||
td/telegram/StickersManager.h
|
||||
td/telegram/StickerType.h
|
||||
td/telegram/StorageManager.h
|
||||
td/telegram/MemoryManager.h
|
||||
td/telegram/StoryContent.h
|
||||
td/telegram/StoryContentType.h
|
||||
td/telegram/StoryDb.h
|
||||
@ -1241,6 +1247,8 @@ if (EMSCRIPTEN)
|
||||
endif()
|
||||
|
||||
if (NOT CMAKE_CROSSCOMPILING)
|
||||
option(TD_SKIP_TG_CLI "Use \"ON\" to skip building tg_cli.")
|
||||
if (NOT CMAKE_CROSSCOMPILING AND NOT TD_SKIP_TG_CLI)
|
||||
add_executable(tg_cli td/telegram/cli.cpp ${TL_TD_JSON_SOURCE})
|
||||
|
||||
if (NOT READLINE_FOUND)
|
||||
@ -1269,6 +1277,7 @@ if (NOT CMAKE_CROSSCOMPILING)
|
||||
target_link_libraries(tg_cli PRIVATE memprof tdclient tdcore)
|
||||
add_dependencies(tg_cli tl_generate_json)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# Exported libraries
|
||||
add_library(TdStatic INTERFACE)
|
||||
|
54
README.md
54
README.md
@ -1,9 +1,12 @@
|
||||
# TDLib
|
||||
# TDLight
|
||||
|
||||
TDLib (Telegram Database library) is a cross-platform library for building [Telegram](https://telegram.org) clients. It can be easily used from almost any programming language.
|
||||
TDLight is a fork of TDLib, a cross-platform library for building [Telegram](https://telegram.org) clients. It can be easily used from almost any programming language.
|
||||
|
||||
## Table of Contents
|
||||
- [Features](#features)
|
||||
- [TDLight extra features](#tdlight-extra-features)
|
||||
- [TDLight extra API functions](#tdlight-extra-api-functions)
|
||||
- [TDLight recommended options](#tdlight-recommended-options)
|
||||
- [Examples and documentation](#usage)
|
||||
- [Dependencies](#dependencies)
|
||||
- [Building](#building)
|
||||
@ -28,17 +31,42 @@ TDLib (Telegram Database library) is a cross-platform library for building [Tele
|
||||
* **Secure**: all local data is encrypted using a user-provided encryption key.
|
||||
* **Fully-asynchronous**: requests to `TDLib` don't block each other or anything else, responses are sent when they are available.
|
||||
|
||||
<a name="tdlight-extra-features"></a>
|
||||
### TDLight extra features
|
||||
#### TDLight extra options
|
||||
* **disable_minithumbnails** (true/**false**) This setting removes minithumbnails everywhere. It reduces memory usage because tdlib keeps them in RAM
|
||||
* **disable_document_filenames** (true/**false**) If you don't care about having the original filenames of every file stored in RAM, you can disable them using this option. It reduces memory usage
|
||||
* **disable_notifications** (true/**false**) In TDLib pending notification updates are stored in ram until you "read" them. This option disables completely notifications and keeps the pending notifications queue empty, reducing memory usage
|
||||
* **ignore_update_chat_last_message** (true/**false**) If you don't care about have updateChatLastMessage updates enable this
|
||||
* **ignore_update_chat_read_inbox** (true/**false**) If you don't care about have updateChatReadInbox updates enable this
|
||||
* **ignore_update_user_chat_action** (true/**false**) If you don't care about have updateUserChatAction updates enable this
|
||||
* **ignore_server_deletes_and_reads** (true/**false**) If you don't care about receiving read receipts and remote deletes from other users, enable this, it will reduce memory usage
|
||||
* **receive_access_hashes** (true/**false**) Receive chats and users access hash as updates
|
||||
* **disable_auto_download** (true/**false**) Forcefully ignore auto download settings of all sessions
|
||||
<a name="tdlight-extra-api-functions"></a>
|
||||
### TDLight extra API functions
|
||||
#### TdApi.GetMemoryStatistics
|
||||
This method is used to read the size of all the internal TDLib data structures.
|
||||
The output contains a string that can be parsed as a JSON.
|
||||
<a name="tdlight-recommended-options"></a>
|
||||
## TDLight recommended options
|
||||
* Options:
|
||||
* ignore_inline_thumbnails: true
|
||||
* disable_top_chats: true
|
||||
* ignore_platform_restrictions: true
|
||||
* ignore_sensitive_content_restrictions: true
|
||||
* Disable all the databases (messages_db, users_db, files_db)
|
||||
<a name="usage"></a>
|
||||
## Examples and documentation
|
||||
See our [Getting Started](https://core.telegram.org/tdlib/getting-started) tutorial for a description of basic TDLib concepts.
|
||||
|
||||
Take a look at our [examples](https://github.com/tdlib/td/blob/master/example/README.md#tdlib-usage-and-build-examples).
|
||||
Take a look at our [examples](https://github.com/tdlight-team/tdlight/blob/master/example/README.md#tdlib-usage-and-build-examples).
|
||||
|
||||
See a [TDLib build instructions generator](https://tdlib.github.io/td/build.html) for detailed instructions on how to build TDLib.
|
||||
See a [TDLight build instructions generator](https://tdlight-team.github.io/tdlight/build.html) for detailed instructions on how to build TDLib.
|
||||
|
||||
See description of our [JSON](#using-json), [C++](#using-cxx), [Java](#using-java) and [.NET](#using-dotnet) interfaces.
|
||||
|
||||
See the [td_api.tl](https://github.com/tdlib/td/blob/master/td/generate/scheme/td_api.tl) scheme or the automatically generated [HTML documentation](https://core.telegram.org/tdlib/docs/td__api_8h.html)
|
||||
See the [td_api.tl](https://github.com/tdlight-team/tdlight/blob/master/td/generate/scheme/td_api.tl) scheme or the automatically generated [HTML documentation](https://core.telegram.org/tdlib/docs/td__api_8h.html)
|
||||
for a list of all available `TDLib` [methods](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_function.html) and [classes](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_object.html).
|
||||
|
||||
<a name="dependencies"></a>
|
||||
@ -55,7 +83,7 @@ for a list of all available `TDLib` [methods](https://core.telegram.org/tdlib/do
|
||||
<a name="building"></a>
|
||||
## Building
|
||||
|
||||
The simplest way to build `TDLib` is to use our [TDLib build instructions generator](https://tdlib.github.io/td/build.html).
|
||||
The simplest way to build `TDLight` is to use our [TDLight build instructions generator](https://tdlight-team.github.io/tdlight/build.html).
|
||||
You need only to choose your programming language and target operating system to receive complete build instructions.
|
||||
|
||||
In general, you need to install all `TDLib` [dependencies](#dependencies), enter directory containing `TDLib` sources and compile them using CMake:
|
||||
@ -67,7 +95,7 @@ cmake -DCMAKE_BUILD_TYPE=Release ..
|
||||
cmake --build .
|
||||
```
|
||||
|
||||
To build `TDLib` on low memory devices you can run [SplitSource.php](https://github.com/tdlib/td/blob/master/SplitSource.php) script
|
||||
To build `TDLib` on low memory devices you can run [SplitSource.php](https://github.com/tdlight-team/tdlight/blob/master/SplitSource.php) script
|
||||
before compiling main `TDLib` source code and compile only needed targets:
|
||||
```
|
||||
mkdir build
|
||||
@ -106,21 +134,21 @@ Or you could install `TDLib` and then reference it in your CMakeLists.txt like t
|
||||
find_package(Td 1.8.35 REQUIRED)
|
||||
target_link_libraries(YourTarget PRIVATE Td::TdStatic)
|
||||
```
|
||||
See [example/cpp/CMakeLists.txt](https://github.com/tdlib/td/blob/master/example/cpp/CMakeLists.txt).
|
||||
See [example/cpp/CMakeLists.txt](https://github.com/tdlight-team/tdlight/blob/master/example/cpp/CMakeLists.txt).
|
||||
|
||||
<a name="using-java"></a>
|
||||
## Using in Java projects
|
||||
`TDLib` provides native Java interface through JNI. To enable it, specify option `-DTD_ENABLE_JNI=ON` to CMake.
|
||||
|
||||
See [example/java](https://github.com/tdlib/td/tree/master/example/java) for example of using `TDLib` from Java and detailed build and usage instructions.
|
||||
See [example/java](https://github.com/tdlight-team/tdlight/tree/master/example/java) for example of using `TDLib` from Java and detailed build and usage instructions.
|
||||
|
||||
<a name="using-dotnet"></a>
|
||||
## Using in .NET projects
|
||||
`TDLib` provides native .NET interface through `C++/CLI` and `C++/CX`. To enable it, specify option `-DTD_ENABLE_DOTNET=ON` to CMake.
|
||||
.NET Core supports `C++/CLI` only since version 3.1 and only on Windows, so if older .NET Core is used or portability is needed, then `TDLib` JSON interface should be used through P/Invoke instead.
|
||||
|
||||
See [example/csharp](https://github.com/tdlib/td/tree/master/example/csharp) for example of using `TDLib` from C# and detailed build and usage instructions.
|
||||
See [example/uwp](https://github.com/tdlib/td/tree/master/example/uwp) for example of using `TDLib` from C# UWP application and detailed build and usage instructions for Visual Studio Extension "TDLib for Universal Windows Platform".
|
||||
See [example/csharp](https://github.com/tdlight-team/tdlight/tree/master/example/csharp) for example of using `TDLib` from C# and detailed build and usage instructions.
|
||||
See [example/uwp](https://github.com/tdlight-team/tdlight/tree/master/example/uwp) for example of using `TDLib` from C# UWP application and detailed build and usage instructions for Visual Studio Extension "TDLib for Universal Windows Platform".
|
||||
|
||||
When `TDLib` is built with `TD_ENABLE_DOTNET` option enabled, `C++` documentation is removed from some files. You need to checkout these files to return `C++` documentation back:
|
||||
```
|
||||
@ -132,13 +160,13 @@ git checkout td/telegram/Client.h td/telegram/Log.h td/tl/TlObject.h
|
||||
`TDLib` provides efficient native C++, Java, and .NET interfaces.
|
||||
But for most use cases we suggest to use the JSON interface, which can be easily used with any programming language that is able to execute C functions.
|
||||
See [td_json_client](https://core.telegram.org/tdlib/docs/td__json__client_8h.html) documentation for detailed JSON interface description,
|
||||
the [td_api.tl](https://github.com/tdlib/td/blob/master/td/generate/scheme/td_api.tl) scheme or the automatically generated [HTML documentation](https://core.telegram.org/tdlib/docs/td__api_8h.html) for a list of
|
||||
the [td_api.tl](https://github.com/tdlight-team/tdlight/blob/master/td/generate/scheme/td_api.tl) scheme or the automatically generated [HTML documentation](https://core.telegram.org/tdlib/docs/td__api_8h.html) for a list of
|
||||
all available `TDLib` [methods](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_function.html) and [classes](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_object.html).
|
||||
|
||||
`TDLib` JSON interface adheres to semantic versioning and versions with the same major version number are binary and backward compatible, but the underlying `TDLib` API can be different for different minor and even patch versions.
|
||||
If you need to support different `TDLib` versions, then you can use a value of the `version` option to find exact `TDLib` version to use appropriate API methods.
|
||||
|
||||
See [example/python/tdjson_example.py](https://github.com/tdlib/td/blob/master/example/python/tdjson_example.py) for an example of such usage.
|
||||
See [example/python/tdjson_example.py](https://github.com/tdlight-team/tdlight/tree/master/example/python/tdjson_example.py) for an example of such usage.
|
||||
|
||||
<a name="license"></a>
|
||||
## License
|
||||
|
381
UpdateMemoryManager.javash
Executable file
381
UpdateMemoryManager.javash
Executable file
@ -0,0 +1,381 @@
|
||||
#!/usr/bin/java --source 21
|
||||
import java.io.IOException;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.nio.file.FileVisitOption;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
import java.util.SequencedSet;
|
||||
import java.util.Set;
|
||||
import java.util.regex.Pattern;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.IntStream;
|
||||
|
||||
public class UpdateMemoryManager {
|
||||
|
||||
static final Set<String> EXCLUDED_MANAGERS = Set.of("Memory",
|
||||
"Call",
|
||||
"DeviceToken",
|
||||
"LanguagePack",
|
||||
"Pts",
|
||||
"Password",
|
||||
"SecretChats",
|
||||
"Secure",
|
||||
"Config",
|
||||
"Storage",
|
||||
"FileLoad",
|
||||
"Parts",
|
||||
"FileGenerate",
|
||||
"Resource",
|
||||
"NetStats",
|
||||
"DcAuth",
|
||||
"State",
|
||||
"PhoneNumber",
|
||||
"FileDownload",
|
||||
"FileUpload",
|
||||
"Alarm"
|
||||
);
|
||||
|
||||
record Manager(Path directory, String name) {
|
||||
String includePath() {
|
||||
return directory.toString().substring(2) + "/" + name + "Manager.h";
|
||||
}
|
||||
}
|
||||
|
||||
public static void main(String[] args) throws Exception {
|
||||
if (args.length == 0) {
|
||||
System.err.println("Arguments: PATH");
|
||||
System.exit(1);
|
||||
}
|
||||
|
||||
var path = Path.of(args[0]);
|
||||
var telegramPath = path.resolve("td/telegram");
|
||||
|
||||
var memoryManager = new Manager(telegramPath, "Memory");
|
||||
SequencedSet<Manager> managers;
|
||||
try (var stream = Files.walk(telegramPath, 16)) {
|
||||
var endNamePattern = "Manager.h";
|
||||
managers = stream
|
||||
.filter(Files::isRegularFile)
|
||||
.filter(p -> p.getFileName().toString().endsWith(endNamePattern))
|
||||
.map(p -> new Manager(p.getParent(), p.getFileName().toString().substring(0, p.getFileName().toString().length() - endNamePattern.length())))
|
||||
.filter(name -> !EXCLUDED_MANAGERS.contains(name.name))
|
||||
.collect(Collectors.toCollection(LinkedHashSet::new));
|
||||
}
|
||||
|
||||
System.out.printf("Found %d managers%n", managers.size());
|
||||
|
||||
int fieldsFound = 0;
|
||||
int updatedManagers = 0;
|
||||
int totalManagers = 0;
|
||||
List<Manager> invalidManagers = new ArrayList<>();
|
||||
for (Manager manager : managers) {
|
||||
totalManagers++;
|
||||
var result = updateManagerJson(manager);
|
||||
if (result != null) {
|
||||
fieldsFound += result.fieldsFound();
|
||||
if (result.changed) {
|
||||
updatedManagers++;
|
||||
}
|
||||
} else {
|
||||
invalidManagers.add(manager);
|
||||
}
|
||||
}
|
||||
|
||||
updateMemoryManagerJson(memoryManager, managers);
|
||||
|
||||
System.out.printf("%n%nDone.%n");
|
||||
|
||||
if (!invalidManagers.isEmpty()) {
|
||||
System.out.printf("%d invalid managers found:%n%s",
|
||||
invalidManagers.size(),
|
||||
invalidManagers.stream()
|
||||
.map(x -> "\t\"" + x.directory + "\": " + x.name + "\n")
|
||||
.collect(Collectors.joining(", ")));
|
||||
}
|
||||
System.out.printf("%d/%d managers updated, %d total fields%n", updatedManagers, totalManagers, fieldsFound);
|
||||
}
|
||||
|
||||
enum FieldType {
|
||||
WaitFreeHashMap("WaitFreeHashMap", "calc_size"),
|
||||
WaitFreeHashSet("WaitFreeHashSet", "calc_size"),
|
||||
Vector("vector", "size"),
|
||||
FlatHashMap("FlatHashMap", "size"),
|
||||
FlatHashSet("FlatHashSet", "size")
|
||||
;
|
||||
|
||||
private final String fieldName;
|
||||
private final String sizeMethodName;
|
||||
public final Pattern pattern;
|
||||
|
||||
FieldType(String fieldName, String sizeMethodName) {
|
||||
this.fieldName = fieldName;
|
||||
this.sizeMethodName = sizeMethodName;
|
||||
this.pattern = Pattern.compile("^ {2}(mutable )?" + fieldName + "(<([^ ]|, )+>)? +(?<field>[a-zA-Z_]+);?[ \t/]*$");
|
||||
}
|
||||
|
||||
Pattern getPattern() {
|
||||
return pattern;
|
||||
}
|
||||
}
|
||||
|
||||
record FoundField(FieldType type, String name) {}
|
||||
record UpdateResult(boolean changed, int fieldsFound) {}
|
||||
|
||||
private static UpdateResult updateManagerJson(Manager manager) throws IOException {
|
||||
Path hFile = manager.directory.resolve(manager.name + "Manager.h");
|
||||
Path cppFile = manager.directory.resolve(manager.name + "Manager.cpp");
|
||||
|
||||
System.out.printf("Updating manager \"%s\" files: [\"%s\", \"%s\"]%n", manager.name, hFile, cppFile);
|
||||
|
||||
if (Files.notExists(hFile)) {
|
||||
System.out.printf("File not found, ignoring manager \"%s\": \"%s\"%n", manager.name, hFile);
|
||||
return null;
|
||||
}
|
||||
if (Files.notExists(cppFile)) {
|
||||
System.out.printf("File not found, ignoring manager \"%s\": \"%s\"%n", manager.name, cppFile);
|
||||
return null;
|
||||
}
|
||||
|
||||
List<FoundField> fields = new ArrayList<>();
|
||||
|
||||
var hLines = normalizeSourceFile(readSourceFile(hFile));
|
||||
|
||||
boolean currentClass = false;
|
||||
for (String hLine : hLines) {
|
||||
FoundField field = null;
|
||||
if (hLine.startsWith("class ")) {
|
||||
currentClass = hLine.contains(" " + manager.name + "Manager");
|
||||
}
|
||||
|
||||
if (currentClass) {
|
||||
for (FieldType possibleFieldType : FieldType.values()) {
|
||||
var m = possibleFieldType.getPattern().matcher(hLine);
|
||||
if (m.matches()) {
|
||||
var fieldName = m.group("field");
|
||||
field = new FoundField(possibleFieldType, fieldName);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (field != null) {
|
||||
System.out.println("\tFound field: (%s) %s".formatted(field.type, field.name));
|
||||
fields.add(field);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
StringBuilder memoryStatsMethod = new StringBuilder();
|
||||
|
||||
memoryStatsMethod.append("void %sManager::memory_stats(vector<string> &output) {\n".formatted(manager.name));
|
||||
memoryStatsMethod.append(fields.stream()
|
||||
.map(field -> " output.push_back(\"\\\"%s\\\":\"); output.push_back(std::to_string(this->%s.%s()));\n".formatted(field.name, field.name, field.type.sizeMethodName))
|
||||
.collect(Collectors.joining(" output.push_back(\",\");\n")));
|
||||
memoryStatsMethod.append("}\n");
|
||||
|
||||
List<String> memoryStatsMethodLines = Arrays.asList(memoryStatsMethod.toString().split("\n"));
|
||||
|
||||
var cppLines = readSourceFile(cppFile);
|
||||
var inputCppLines = new ArrayList<>(cppLines);
|
||||
|
||||
// Remove the old memory_stats method
|
||||
var indexOfMemoryStatsStart = -1;
|
||||
var indexOfMemoryStatsEnd = -1;
|
||||
for (int i = 0; i < cppLines.size(); i++) {
|
||||
if (cppLines.get(i).contains("::memory_stats(")) {
|
||||
indexOfMemoryStatsStart = i;
|
||||
for (int j = i - 1; j >= 0; j--) {
|
||||
if (cppLines.get(j).isBlank()) {
|
||||
indexOfMemoryStatsStart = j;
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (indexOfMemoryStatsStart != -1) {
|
||||
for (int i = indexOfMemoryStatsStart + 1; i < cppLines.size(); i++) {
|
||||
if (cppLines.get(i).trim().equals("}")) {
|
||||
indexOfMemoryStatsEnd = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (indexOfMemoryStatsEnd == -1) {
|
||||
throw new IllegalStateException("memory_stats method end not found");
|
||||
}
|
||||
cppLines.subList(indexOfMemoryStatsStart, indexOfMemoryStatsEnd + 1).clear();
|
||||
}
|
||||
|
||||
var last = cppLines.removeLast();
|
||||
cppLines.addAll(memoryStatsMethodLines);
|
||||
cppLines.add("");
|
||||
cppLines.addLast(last);
|
||||
|
||||
boolean changed = !Objects.equals(inputCppLines, cppLines);
|
||||
|
||||
if (changed) {
|
||||
System.out.printf("\tDone: %s.cpp file has been updated!%n", manager.name);
|
||||
Files.write(cppFile, cppLines, StandardCharsets.UTF_8);
|
||||
} else {
|
||||
System.out.printf("\tDone: %s.cpp file did not change.%n", manager.name);
|
||||
}
|
||||
|
||||
return new UpdateResult(changed, fields.size());
|
||||
}
|
||||
|
||||
private static void updateMemoryManagerJson(Manager manager, SequencedSet<Manager> managers) throws IOException {
|
||||
Path hFile = manager.directory.resolve(manager.name + "Manager.h");
|
||||
Path cppFile = manager.directory.resolve(manager.name + "Manager.cpp");
|
||||
|
||||
System.out.printf("Updating memory manager \"%s\" files: [\"%s\", \"%s\"]%n", manager.name, hFile, cppFile);
|
||||
|
||||
if (Files.notExists(hFile)) {
|
||||
System.out.printf("File not found for manager \"%s\": \"%s\"%n", manager.name, hFile);
|
||||
System.exit(1);
|
||||
return;
|
||||
}
|
||||
if (Files.notExists(cppFile)) {
|
||||
System.out.printf("File not found for manager \"%s\": \"%s\"%n", manager.name, cppFile);
|
||||
System.exit(1);
|
||||
return;
|
||||
}
|
||||
|
||||
StringBuilder memoryStatsMethod = new StringBuilder();
|
||||
|
||||
memoryStatsMethod.append("void %sManager::print_managers_memory_stats(vector<string> &output) const {\n".formatted(manager.name));
|
||||
memoryStatsMethod.append(managers.stream()
|
||||
.map(m -> """
|
||||
output.push_back("\\"%s_manager_\\":{"); td_->%s_manager_->memory_stats(output); output.push_back("}");
|
||||
""".formatted(toSnakeCase(m.name), toSnakeCase(m.name)))
|
||||
.collect(Collectors.joining(" output.push_back(\",\");\n")));
|
||||
memoryStatsMethod.append("}\n");
|
||||
|
||||
List<String> memoryStatsMethodLines = Arrays.asList(memoryStatsMethod.toString().split("\n"));
|
||||
|
||||
var cppLines = readSourceFile(cppFile);
|
||||
var inputCppLines = new ArrayList<>(cppLines);
|
||||
|
||||
// Remove the old memory_stats method
|
||||
var indexOfMemoryStatsStart = -1;
|
||||
var indexOfMemoryStatsEnd = -1;
|
||||
for (int i = 0; i < cppLines.size(); i++) {
|
||||
if (cppLines.get(i).contains("::print_managers_memory_stats(")) {
|
||||
indexOfMemoryStatsStart = i;
|
||||
for (int j = i - 1; j >= 0; j--) {
|
||||
if (cppLines.get(j).isBlank()) {
|
||||
indexOfMemoryStatsStart = j;
|
||||
} else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (indexOfMemoryStatsStart != -1) {
|
||||
for (int i = indexOfMemoryStatsStart + 1; i < cppLines.size(); i++) {
|
||||
if (cppLines.get(i).trim().equals("}")) {
|
||||
indexOfMemoryStatsEnd = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (indexOfMemoryStatsEnd == -1) {
|
||||
throw new IllegalStateException("print_managers_memory_stats method end not found");
|
||||
}
|
||||
cppLines.subList(indexOfMemoryStatsStart, indexOfMemoryStatsEnd + 1).clear();
|
||||
}
|
||||
|
||||
var last = cppLines.removeLast();
|
||||
cppLines.addAll(memoryStatsMethodLines);
|
||||
cppLines.add("");
|
||||
cppLines.addLast(last);
|
||||
|
||||
for (Manager m : managers) {
|
||||
var mInclude = "#include \"%s\"".formatted(m.includePath());
|
||||
if (!cppLines.contains(mInclude)) {
|
||||
System.out.printf("\tMissing include, adding \"" + m.includePath() + "\"%n");
|
||||
int includeInsertIndex = -1;
|
||||
for (int i = 0; i < cppLines.size(); i++) {
|
||||
if (cppLines.get(i).startsWith("#include")) {
|
||||
includeInsertIndex = i;
|
||||
}
|
||||
}
|
||||
if (includeInsertIndex == -1) {
|
||||
throw new IllegalStateException("Cannot find a place to put the include");
|
||||
}
|
||||
cppLines.add(includeInsertIndex + 1, mInclude);
|
||||
}
|
||||
}
|
||||
|
||||
boolean changed = !Objects.equals(inputCppLines, cppLines);
|
||||
|
||||
if (changed) {
|
||||
System.out.printf("\tDone: %s.cpp file has been updated!%n", manager.name);
|
||||
Files.write(cppFile, cppLines, StandardCharsets.UTF_8);
|
||||
} else {
|
||||
System.out.printf("\tDone: %s.cpp file did not change.%n", manager.name);
|
||||
}
|
||||
}
|
||||
|
||||
private static String toSnakeCase(String name) {
|
||||
var initialChar = name.codePoints()
|
||||
.limit(1)
|
||||
.map(Character::toLowerCase);
|
||||
var restOfString = name.codePoints()
|
||||
.skip(1)
|
||||
.flatMap(codePoint -> {
|
||||
if (Character.isUpperCase(codePoint)) {
|
||||
return IntStream.of('_', Character.toLowerCase(codePoint));
|
||||
} else {
|
||||
return IntStream.of(codePoint);
|
||||
}
|
||||
});
|
||||
var resultStream = IntStream.concat(initialChar, restOfString);
|
||||
return resultStream.collect(StringBuilder::new, StringBuilder::appendCodePoint, StringBuilder::append).toString();
|
||||
}
|
||||
|
||||
private static List<String> readSourceFile(Path path) throws IOException {
|
||||
return Files.readAllLines(path, StandardCharsets.UTF_8);
|
||||
}
|
||||
|
||||
private static List<String> normalizeSourceFile(List<String> lines) throws IOException {
|
||||
List<String> srcLines = new ArrayList<>(lines);
|
||||
|
||||
// Remove empty lines
|
||||
srcLines.removeIf(String::isBlank);
|
||||
|
||||
// Remove unexpected newlines
|
||||
List<String> srcLinesWithoutNewlines = new ArrayList<>();
|
||||
StringBuilder buf = new StringBuilder();
|
||||
for (String srcLine : srcLines) {
|
||||
if (!buf.isEmpty()) {
|
||||
buf.append(" ");
|
||||
}
|
||||
buf.append(srcLine);
|
||||
var trimmedLine = srcLine.trim();
|
||||
if (!trimmedLine.endsWith(">")) {
|
||||
srcLinesWithoutNewlines.add(buf.toString());
|
||||
buf.setLength(0);
|
||||
}
|
||||
}
|
||||
if (!buf.isEmpty()) {
|
||||
srcLinesWithoutNewlines.add(buf.toString());
|
||||
}
|
||||
|
||||
srcLinesWithoutNewlines.replaceAll(p -> {
|
||||
var commentStart = p.indexOf("//");
|
||||
if (commentStart >= 0) {
|
||||
return p.substring(0, commentStart);
|
||||
} else {
|
||||
return p;
|
||||
}
|
||||
});
|
||||
|
||||
return srcLinesWithoutNewlines;
|
||||
}
|
||||
}
|
40
build.html
40
build.html
@ -2,7 +2,7 @@
|
||||
<html>
|
||||
|
||||
<head>
|
||||
<title>TDLib build instructions</title>
|
||||
<title>TDLight build instructions</title>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<style>
|
||||
:root {
|
||||
@ -193,7 +193,7 @@
|
||||
|
||||
<div class="main">
|
||||
<div id="languageSelectDiv">
|
||||
<p>Choose a programming language from which you want to use TDLib:</p>
|
||||
<p>Choose a programming language from which you want to use TDLight:</p>
|
||||
<select id="languageSelect" onchange="onLanguageChanged(false)" autofocus class="large">
|
||||
<option>Choose a programming language:</option>
|
||||
<option>Python</option>
|
||||
@ -226,7 +226,7 @@
|
||||
</div>
|
||||
|
||||
<div id="osSelectDiv" class="hide">
|
||||
<p>Choose an operating system on which you want to use TDLib:</p>
|
||||
<p>Choose an operating system on which you want to use TDLight:</p>
|
||||
<select id="osSelect" onchange="onOsChanged()" class="large">
|
||||
<option>Choose an operating system:</option>
|
||||
</select>
|
||||
@ -234,7 +234,7 @@
|
||||
</div>
|
||||
|
||||
<div id="linuxSelectDiv" class="hide">
|
||||
<p>Choose a Linux distro on which you want to use TDLib:</p>
|
||||
<p>Choose a Linux distro on which you want to use TDLight:</p>
|
||||
<select id="linuxSelect" onchange="onOsChanged()" class="large">
|
||||
<option>Choose a Linux distro:</option>
|
||||
<option>Alpine</option>
|
||||
@ -265,13 +265,13 @@
|
||||
</div>
|
||||
|
||||
<div id="buildInstallLocalDiv" class="hide">
|
||||
<label><input type="checkbox" id="buildInstallLocalCheckbox" onchange="onOptionsChanged()"/>Install built TDLib to /usr/local instead of placing the files to td/tdlib.</label>
|
||||
<label><input type="checkbox" id="buildInstallLocalCheckbox" onchange="onOptionsChanged()"/>Install built TDLight to /usr/local instead of placing the files to td/tdlib.</label>
|
||||
</div>
|
||||
|
||||
<p></p>
|
||||
|
||||
<div id="buildCompilerDiv" class="hide">
|
||||
<span>Choose which compiler you want to use to build TDLib:</span><br>
|
||||
<span>Choose which compiler you want to use to build TDLight:</span><br>
|
||||
<label><input type="radio" id="buildCompilerRadioGcc" name="buildCompilerRadio" onchange="onOptionsChanged()" checked/>g++</label>
|
||||
<label><input type="radio" id="buildCompilerRadioClang" name="buildCompilerRadio" onchange="onOptionsChanged()"/>clang (recommended)</label>
|
||||
<p></p>
|
||||
@ -307,7 +307,7 @@
|
||||
</div>
|
||||
|
||||
<div id="buildBitnessDiv" class="hide">
|
||||
<span>Choose for which bitness you want to build TDLib:</span><br>
|
||||
<span>Choose for which bitness you want to build TDLight:</span><br>
|
||||
<label><input type="radio" id="buildBitnessRadio32" name="buildBitnessRadio" onchange="onOptionsChanged()" checked/>32</label>
|
||||
<label><input type="radio" id="buildBitnessRadio64" name="buildBitnessRadio" onchange="onOptionsChanged()"/>64</label>
|
||||
<p></p>
|
||||
@ -329,7 +329,7 @@
|
||||
</div>
|
||||
|
||||
<div id="buildCommandsDiv" class="hide">
|
||||
<p id="buildCommandsHeader">Here is complete instruction for TDLib binaries building:</p>
|
||||
<p id="buildCommandsHeader">Here is complete instruction for TDLight binaries building:</p>
|
||||
<p id="buildPre">Hidden text</p>
|
||||
<code id="buildCommands">Empty commands</code>
|
||||
<button id="copyBuildCommandsButton" onclick="copyBuildInstructions()">
|
||||
@ -505,9 +505,9 @@ function getTargetName(target) {
|
||||
return '<a href="https://github.com/tdlib/td#using-cxx">simple and convenient C++11</a>';
|
||||
case 'JNI':
|
||||
case 'Android':
|
||||
return '<a href="https://github.com/tdlib/td#using-java">native ' + target + '</a>';
|
||||
return '<a href="https://github.com/tdlight-team/tdlight#using-java">native ' + target + '</a>';
|
||||
default:
|
||||
return '<a href="https://github.com/tdlib/td#using-dotnet">native ' + target + '</a>';
|
||||
return '<a href="https://github.com/tdlight-team/tdlight#using-dotnet">native ' + target + '</a>';
|
||||
}
|
||||
}
|
||||
|
||||
@ -521,12 +521,12 @@ function onOsChanged() {
|
||||
if (language === 'Other') {
|
||||
language = 'any other programming language';
|
||||
}
|
||||
var text = 'TDLib can be used from ' + language + ' on ' + os + ' through the ' + getTargetName(target) + ' interface.<br>' +
|
||||
'See <a href="https://github.com/tdlib/td/blob/master/example/README.md#' + getExampleAnchor(language) + '">examples</a> of such usage and already available third-party frameworks.<br>';
|
||||
var text = 'TDLight can be used from ' + language + ' on ' + os + ' through the ' + getTargetName(target) + ' interface.<br>' +
|
||||
'See <a href="https://github.com/tdlight-team/tdlight/blob/master/example/README.md#' + getExampleAnchor(language) + '">examples</a> of such usage and already available third-party frameworks.<br>';
|
||||
|
||||
if (target === 'WebAssembly') {
|
||||
text = 'TDLib is available in a prebuilt form as an <a href="https://www.npmjs.com/">NPM</a> package <a href="https://www.npmjs.com/package/tdweb">tdweb</a>.<br>' +
|
||||
'If you want to build it manually, take a look at our <a href="https://github.com/tdlib/td/tree/master/example/web">example</a>.';
|
||||
text = 'TDLight is available in a prebuilt form as an <a href="https://www.npmjs.com/">NPM</a> package <a href="https://www.npmjs.com/package/tdweb">tdweb</a>.<br>' +
|
||||
'If you want to build it manually, take a look at our <a href="https://github.com/tdlight-team/tdlight/tree/master/example/web">example</a>.';
|
||||
target = '';
|
||||
}
|
||||
if (target === 'Android' || target === 'AndroidJson') {
|
||||
@ -757,8 +757,8 @@ function onOptionsChanged() {
|
||||
pre_text.push('Note that the following instruction is for NetBSD 8+ and default SH shell.');
|
||||
}
|
||||
if (os_mac) {
|
||||
pre_text.push('Note that the following instruction will build TDLib only for ' + os_mac_host_name + '.');
|
||||
pre_text.push('If you want to create a universal XCFramework, take a look at our <a href="https://github.com/tdlib/td/tree/master/example/ios">example</a> instead.');
|
||||
pre_text.push('Note that the following instruction will build TDLight only for ' + os_mac_host_name + '.');
|
||||
pre_text.push('If you want to create a universal XCFramework, take a look at our <a href="https://github.com/tdlight-team/tdlight/tree/master/example/ios">example</a> instead.');
|
||||
}
|
||||
|
||||
var terminal_name = (function () {
|
||||
@ -782,12 +782,12 @@ function onOptionsChanged() {
|
||||
if (os_windows) {
|
||||
pre_text.push('Close and re-open ' + terminal_name + ' if the PATH environment variable was changed.');
|
||||
}
|
||||
pre_text.push('Run these commands in ' + terminal_name + ' to build TDLib and to install it to ' + install_dir + ':');
|
||||
pre_text.push('Run these commands in ' + terminal_name + ' to build TDLight and to install it to ' + install_dir + ':');
|
||||
document.getElementById('buildPre').innerHTML = '<ul><li>' + pre_text.join('</li><li>') + '</li></ul>';
|
||||
document.getElementById('buildPre').style.display = 'block';
|
||||
|
||||
if (install_dir && install_dir !== '/usr/local') {
|
||||
install_dir = '../tdlib';
|
||||
install_dir = '../tdlight';
|
||||
if (target === 'JNI' || target === 'C++/CX') {
|
||||
install_dir = '../../' + install_dir;
|
||||
}
|
||||
@ -953,9 +953,9 @@ function onOptionsChanged() {
|
||||
commands.push('exit');
|
||||
}
|
||||
}
|
||||
commands.push('git clone https://github.com/tdlib/td.git');
|
||||
commands.push('git clone https://github.com/tdlight-team/tdlight.git');
|
||||
|
||||
commands.push('cd td');
|
||||
commands.push('cd tdlight');
|
||||
// commands.push('git checkout v1.8.0');
|
||||
|
||||
if (use_vcpkg) {
|
||||
|
@ -1,7 +1,7 @@
|
||||
# TDLib usage and build examples
|
||||
|
||||
This directory contains basic examples of TDLib usage from different programming languages and examples of library building for different platforms.
|
||||
If you are looking for documentation of all available TDLib methods, see the [td_api.tl](https://github.com/tdlib/td/blob/master/td/generate/scheme/td_api.tl) scheme or the
|
||||
If you are looking for documentation of all available TDLib methods, see the [td_api.tl](https://github.com/tdlight-team/tdlight/blob/master/td/generate/scheme/td_api.tl) scheme or the
|
||||
automatically generated [HTML documentation](https://core.telegram.org/tdlib/docs/td__api_8h.html) for a list of all available TDLib
|
||||
[methods](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_function.html) and [classes](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_object.html).
|
||||
Also, take a look at our [Getting Started](https://core.telegram.org/tdlib/getting-started) tutorial for a description of basic TDLib concepts.
|
||||
@ -54,13 +54,13 @@ If you want to use TDLib with asyncio and Python >= 3.9, take a look at [aiotdli
|
||||
For older Python versions you can use [pytdlib](https://github.com/pytdlib/pytdlib).
|
||||
This wrapper contains generator for TDLib API classes and basic interface for interaction with TDLib.
|
||||
|
||||
You can also check out [example/python/tdjson_example.py](https://github.com/tdlib/td/blob/master/example/python/tdjson_example.py),
|
||||
You can also check out [example/python/tdjson_example.py](https://github.com/tdlight-team/tdlight/blob/master/example/python/tdjson_example.py),
|
||||
[tdlib-python](https://github.com/JunaidBabu/tdlib-python), or [Python Wrapper TDLib](https://github.com/alvhix/pywtdlib) for some basic examples of TDLib JSON interface integration with Python.
|
||||
|
||||
<a name="javascript"></a>
|
||||
## Using TDLib in JavaScript projects
|
||||
|
||||
TDLib can be compiled to WebAssembly or asm.js and used in a browser from JavaScript. See [tdweb](https://github.com/tdlib/td/tree/master/example/web) as a convenient wrapper for TDLib in a browser
|
||||
TDLib can be compiled to WebAssembly or asm.js and used in a browser from JavaScript. See [tdweb](https://github.com/tdlight-team/tdlight/tree/master/example/web) as a convenient wrapper for TDLib in a browser
|
||||
and [telegram-react](https://github.com/evgeny-nadymov/telegram-react) as an example of a TDLib-based Telegram client.
|
||||
|
||||
See also [Svelte-tdweb-starter](https://github.com/gennadypolakov/svelte-tdweb-starter) - Svelte wrapper for tdweb, and [Telegram-Photoframe](https://github.com/lukefx/telegram-photoframe) - a web application that displays your preferred group or channel as Photoframe.
|
||||
@ -95,7 +95,7 @@ You can also see [github.com/aliforever/go-tdlib](https://github.com/aliforever/
|
||||
TDLib can be used from the Java programming language through native [JNI](https://github.com/tdlib/td#using-java) binding.
|
||||
|
||||
We provide a generator for JNI bridge methods and Java classes for all TDLib API methods and objects.
|
||||
See [example/java](https://github.com/tdlib/td/tree/master/example/java) for an example of using TDLib from desktop Java along with detailed building and usage instructions.
|
||||
See [example/java](https://github.com/tdlight-team/tdlight/tree/master/example/java) for an example of using TDLib from desktop Java along with detailed building and usage instructions.
|
||||
To use TDLib to create Android Java applications, use our [prebuilt library for Android](https://core.telegram.org/tdlib/tdlib.zip).
|
||||
|
||||
<a name="kotlin"></a>
|
||||
@ -112,8 +112,8 @@ See also [td-ktx](https://github.com/tdlibx/td-ktx) - Kotlin coroutines wrapper
|
||||
|
||||
TDLib provides a native [.NET](https://github.com/tdlib/td#using-dotnet) interface through `C++/CLI` and `C++/CX`.
|
||||
See [tdlib-netcore](https://github.com/dantmnf/tdlib-netcore) for a SWIG-like binding with automatically generated classes for TDLib API.
|
||||
See [example/uwp](https://github.com/tdlib/td/tree/master/example/uwp) for an example of building TDLib SDK for the Universal Windows Platform and an example of its usage from C#.
|
||||
See [example/csharp](https://github.com/tdlib/td/tree/master/example/csharp) for an example of building TDLib with `C++/CLI` support and an example of TDLib usage from C# on Windows.
|
||||
See [example/uwp](https://github.com/tdlight-team/tdlight/tree/master/example/uwp) for an example of building TDLib SDK for the Universal Windows Platform and an example of its usage from C#.
|
||||
See [example/csharp](https://github.com/tdlight-team/tdlight/tree/master/example/csharp) for an example of building TDLib with `C++/CLI` support and an example of TDLib usage from C# on Windows.
|
||||
|
||||
If you want to write a cross-platform C# application using .NET Core, see [tdsharp](https://github.com/egramtel/tdsharp). It uses our [JSON](https://github.com/tdlib/td#using-json) interface,
|
||||
provides an asynchronous interface for interaction with TDLib, automatically generated classes for TDLib API and has some examples.
|
||||
@ -127,8 +127,8 @@ Also, see [Unigram](https://github.com/UnigramDev/Unigram), which is a full-feat
|
||||
|
||||
TDLib has a simple and convenient C++11-interface for sending and receiving requests and can be statically linked to your application.
|
||||
|
||||
See [example/cpp](https://github.com/tdlib/td/tree/master/example/cpp) for an example of TDLib usage from C++.
|
||||
[td_example.cpp](https://github.com/tdlib/td/blob/master/example/cpp/td_example.cpp) contains an example of authorization, processing new incoming messages, getting a list of chats and sending a text message.
|
||||
See [example/cpp](https://github.com/tdlight-team/tdlight/tree/master/example/cpp) for an example of TDLib usage from C++.
|
||||
[td_example.cpp](https://github.com/tdlight-team/tdlight/blob/master/example/cpp/td_example.cpp) contains an example of authorization, processing new incoming messages, getting a list of chats and sending a text message.
|
||||
|
||||
See also the source code of [Fernschreiber](https://github.com/Wunderfitz/harbour-fernschreiber) and [Depecher](https://github.com/blacksailer/depecher) – Telegram apps for Sailfish OS,
|
||||
[TELEports](https://gitlab.com/ubports/development/apps/teleports) – a Qt-client for Ubuntu Touch, [tdlib-purple](https://github.com/ars3niy/tdlib-purple) - Telegram plugin for Pidgin,
|
||||
@ -140,20 +140,20 @@ or [MeeGram](https://github.com/qtinsider/meegram2) - a Telegram client for Noki
|
||||
|
||||
TDLib can be used from the Swift programming language through the [JSON](https://github.com/tdlib/td#using-json) interface and can be linked statically or dynamically.
|
||||
|
||||
See [example/ios](https://github.com/tdlib/td/tree/master/example/ios) for an example of building TDLib for iOS, watchOS, tvOS, visionOS, and macOS.
|
||||
See [example/ios](https://github.com/tdlight-team/tdlight/tree/master/example/ios) for an example of building TDLib for iOS, watchOS, tvOS, visionOS, and macOS.
|
||||
|
||||
See [TDLibKit](https://github.com/Swiftgram/TDLibKit), [tdlib-swift](https://github.com/modestman/tdlib-swift), or [TDLib-iOS](https://github.com/leoMehlig/TDLib-iOS), which provide convenient TDLib clients with automatically generated and fully-documented classes for all TDLib API methods and objects.
|
||||
|
||||
See also the source code of [Moc](https://github.com/mock-foundation/moc) - a native and powerful macOS and iPadOS Telegram client, optimized for moderating large communities and personal use.
|
||||
|
||||
See [example/swift](https://github.com/tdlib/td/tree/master/example/swift) for an example of a macOS Swift application.
|
||||
See [example/swift](https://github.com/tdlight-team/tdlight/tree/master/example/swift) for an example of a macOS Swift application.
|
||||
|
||||
<a name="objective-c"></a>
|
||||
## Using TDLib in Objective-C projects
|
||||
|
||||
TDLib can be used from the Objective-C programming language through [JSON](https://github.com/tdlib/td#using-json) interface and can be linked statically or dynamically.
|
||||
|
||||
See [example/ios](https://github.com/tdlib/td/tree/master/example/ios) for an example of building TDLib for iOS, watchOS, tvOS, visionOS, and macOS.
|
||||
See [example/ios](https://github.com/tdlight-team/tdlight/tree/master/example/ios) for an example of building TDLib for iOS, watchOS, tvOS, visionOS, and macOS.
|
||||
|
||||
<a name="object-pascal"></a>
|
||||
## Using TDLib in Object Pascal projects with Delphi and Lazarus
|
||||
@ -300,7 +300,7 @@ TDLib can be used from the C programming language through the [JSON](https://git
|
||||
|
||||
See [easy-tg](https://github.com/Trumeet/easy-tg) for an example of such usage.
|
||||
|
||||
You can also try to use our [C](https://github.com/tdlib/td/blob/master/td/telegram/td_c_client.h) client, which was used by the private TDLib-based version of [telegram-cli](https://github.com/vysheng/tg).
|
||||
You can also try to use our [C](https://github.com/tdlight-team/tdlight/blob/master/td/telegram/td_c_client.h) client, which was used by the private TDLib-based version of [telegram-cli](https://github.com/vysheng/tg).
|
||||
|
||||
<a name="g"></a>
|
||||
## Using TDLib from G projects
|
||||
|
@ -4,7 +4,7 @@ Below are instructions for building TDLib for iOS, watchOS, tvOS, visionOS, and
|
||||
|
||||
If you need only a macOS build for the current architecture, take a look at [TDLib build instructions generator](https://tdlib.github.io/td/build.html).
|
||||
|
||||
For example of usage take a look at our [Swift example](https://github.com/tdlib/td/tree/master/example/swift).
|
||||
For example of usage take a look at our [Swift example](https://github.com/tdlight-team/tdlight/tree/master/example/swift).
|
||||
|
||||
To compile `TDLib` you will need to:
|
||||
* Install the latest Xcode via `xcode-select --install` or downloading it from [Xcode website](https://developer.apple.com/xcode/).
|
||||
@ -37,7 +37,7 @@ cd <path to TDLib sources>/example/ios
|
||||
```
|
||||
This may take a while, because TDLib will be built about 16 times.
|
||||
Resulting XCFramework will work on any architecture and even on a simulator.
|
||||
We use [CMake/iOS.cmake](https://github.com/tdlib/td/blob/master/CMake/iOS.cmake) toolchain, other toolchains may work too.
|
||||
We use [CMake/iOS.cmake](https://github.com/tdlight-team/tdlight/blob/master/CMake/iOS.cmake) toolchain, other toolchains may work too.
|
||||
|
||||
Built libraries and XCFramework will be stored in `tdjson` directory.
|
||||
|
||||
|
@ -3,7 +3,7 @@
|
||||
To run this example, you will need installed JDK >= 1.6.
|
||||
For Javadoc documentation generation PHP is needed.
|
||||
|
||||
You can find complete build instructions for your operating system at https://tdlib.github.io/td/build.html?language=Java.
|
||||
You can find complete build instructions for your operating system at https://tdlight-team.github.io/tdlight/build.html?language=Java.
|
||||
|
||||
In general, the build process looks as follows.
|
||||
|
||||
|
@ -6,7 +6,7 @@
|
||||
<MoreInfo>https://core.telegram.org/tdlib</MoreInfo>
|
||||
<Tags>Telegram, TDLib, library, client, API</Tags>
|
||||
<License>LICENSE_1_0.txt</License>
|
||||
<ReleaseNotes>https://github.com/tdlib/td/blob/master/CHANGELOG.md</ReleaseNotes>
|
||||
<ReleaseNotes>https://github.com/tdlight-team/tdlight/blob/master/CHANGELOG.md</ReleaseNotes>
|
||||
</Metadata>
|
||||
<Installation Scope="Global">
|
||||
<InstallationTarget Id="Microsoft.ExtensionSDK" TargetPlatformIdentifier="UAP" TargetPlatformVersion="v0.8.0.0" SdkName="Telegram.Td.UWP" SdkVersion="1.0" />
|
||||
|
@ -26,4 +26,4 @@ cd <path to TDLib sources>/example/web
|
||||
|
||||
## Using tdweb NPM package
|
||||
|
||||
See [tdweb](https://www.npmjs.com/package/tdweb) or [README.md](https://github.com/tdlib/td/tree/master/example/web/tdweb/README.md) for package documentation.
|
||||
See [tdweb](https://www.npmjs.com/package/tdweb) or [README.md](https://github.com/tdlight-team/tdlight/tree/master/example/web/tdweb/README.md) for package documentation.
|
||||
|
@ -8,11 +8,11 @@ Once this is done, you can send queries to the TDLib instance using the method `
|
||||
|
||||
See [Getting Started](https://core.telegram.org/tdlib/getting-started) for a description of basic TDLib concepts and a short introduction to TDLib usage.
|
||||
|
||||
See the [td_api.tl](https://github.com/tdlib/td/blob/master/td/generate/scheme/td_api.tl) scheme or
|
||||
See the [td_api.tl](https://github.com/tdlight-team/tdlight/blob/master/td/generate/scheme/td_api.tl) scheme or
|
||||
the automatically generated [HTML documentation](https://core.telegram.org/tdlib/docs/td__api_8h.html) for a list of all available
|
||||
TDLib [methods](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_function.html) and [classes](https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_object.html).
|
||||
The JSON representation of TDLib API objects is straightforward: all API objects are represented as JSON objects with the same keys as the API object field names in the
|
||||
[td_api.tl](https://github.com/tdlib/td/blob/master/td/generate/scheme/td_api.tl) scheme. Note that in the automatically generated C++ documentation all fields have an additional terminating underscore
|
||||
[td_api.tl](https://github.com/tdlight-team/tdlight/blob/master/td/generate/scheme/td_api.tl) scheme. Note that in the automatically generated C++ documentation all fields have an additional terminating underscore
|
||||
which shouldn't be used in the JSON interface. The object type name is stored in the special field '@type' which is optional in places where type is uniquely determined by the context.
|
||||
Fields of Bool type are stored as Boolean, fields of int32, int53, and double types are stored as Number, fields of int64 and string types are stored as String,
|
||||
fields of bytes type are base64 encoded and then stored as String, fields of array type are stored as Array.
|
||||
|
@ -65,7 +65,7 @@ class TdClient {
|
||||
*
|
||||
* If the query contains the field '@extra', the same field will be added into the result.
|
||||
*
|
||||
* @param {Object} query - The query for TDLib. See the [td_api.tl]{@link https://github.com/tdlib/td/blob/master/td/generate/scheme/td_api.tl} scheme or
|
||||
* @param {Object} query - The query for TDLib. See the [td_api.tl]{@link https://github.com/tdlight-team/tdlight/blob/master/td/generate/scheme/td_api.tl} scheme or
|
||||
* the automatically generated [HTML documentation]{@link https://core.telegram.org/tdlib/docs/td__api_8h.html}
|
||||
* for a list of all available TDLib [methods]{@link https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_function.html} and
|
||||
* [classes]{@link https://core.telegram.org/tdlib/docs/classtd_1_1td__api_1_1_object.html}.
|
||||
|
1
td/generate/scheme/.gitignore
vendored
Normal file
1
td/generate/scheme/.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
*.tlo
|
@ -583,6 +583,21 @@ userTypeBot can_be_edited:Bool can_join_groups:Bool can_read_all_group_messages:
|
||||
//@description No information on the user besides the user identifier is available, yet this user has not been deleted. This object is extremely rare and must be handled like a deleted user. It is not possible to perform any actions on users of this type
|
||||
userTypeUnknown = UserType;
|
||||
|
||||
//@class AccessHashType @description Represents the type of an access hash. The following types are possible: user, channel
|
||||
|
||||
//@description An access hash of an user
|
||||
accessHashTypeUser = AccessHashType;
|
||||
|
||||
//@description An access hash of a channel
|
||||
accessHashTypeChannel = AccessHashType;
|
||||
|
||||
|
||||
//@description Access hash
|
||||
//@chat_id Chat identifier
|
||||
//@type Access hash type
|
||||
//@access_hash Access hash
|
||||
accessHash chat_id:int53 type:AccessHashType access_hash:int64 = AccessHash;
|
||||
|
||||
|
||||
//@description Represents a command supported by a bot @command Text of the bot command @param_description Description of the bot command
|
||||
botCommand command:string description:string = BotCommand;
|
||||
@ -6868,6 +6883,10 @@ storageStatisticsFast files_size:int53 file_count:int32 database_size:int53 lang
|
||||
//@statistics Database statistics in an unspecified human-readable format
|
||||
databaseStatistics statistics:string = DatabaseStatistics;
|
||||
|
||||
//@description Contains memory statistics
|
||||
//@statistics Memory statistics in an unspecified human-readable format
|
||||
memoryStatistics statistics:string = MemoryStatistics;
|
||||
|
||||
|
||||
//@class NetworkType @description Represents the type of network
|
||||
|
||||
@ -7637,6 +7656,9 @@ updateUserStatus user_id:int53 status:UserStatus = Update;
|
||||
//@description Some data of a user has changed. This update is guaranteed to come before the user identifier is returned to the application @user New data about the user
|
||||
updateUser user:user = Update;
|
||||
|
||||
//@description Some data of a user or a chat has changed. This update is guaranteed to come before the user or chat identifier is returned to the application @access_hash Access hash
|
||||
updateAccessHash access_hash:accessHash = Update;
|
||||
|
||||
//@description Some data of a basic group has changed. This update is guaranteed to come before the basic group identifier is returned to the application @basic_group New data about the group
|
||||
updateBasicGroup basic_group:basicGroup = Update;
|
||||
|
||||
@ -11284,6 +11306,10 @@ getStorageStatisticsFast = StorageStatisticsFast;
|
||||
//@description Returns database statistics
|
||||
getDatabaseStatistics = DatabaseStatistics;
|
||||
|
||||
//@description Returns memory statistics
|
||||
//@full Full memory statistics calculation
|
||||
getMemoryStatistics full:Bool = MemoryStatistics;
|
||||
|
||||
//@description Optimizes storage usage, i.e. deletes some files and returns new storage usage statistics. Secret thumbnails can't be deleted
|
||||
//@size Limit on the total size of files after deletion, in bytes. Pass -1 to use the default limit
|
||||
//@ttl Limit on the time that has passed since the last time a file was accessed (or creation time for some filesystems). Pass -1 to use the default limit
|
||||
|
@ -1344,4 +1344,7 @@ void AccountManager::get_current_state(vector<td_api::object_ptr<td_api::Update>
|
||||
}
|
||||
}
|
||||
|
||||
void AccountManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -74,6 +74,8 @@ class AccountManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
class UnconfirmedAuthorization;
|
||||
class UnconfirmedAuthorizations;
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include "td/telegram/DialogId.h"
|
||||
#include "td/telegram/Document.h"
|
||||
#include "td/telegram/DocumentsManager.h"
|
||||
#include "td/telegram/MemoryManager.h"
|
||||
#include "td/telegram/FileReferenceManager.h"
|
||||
#include "td/telegram/files/FileManager.h"
|
||||
#include "td/telegram/files/FileType.h"
|
||||
@ -191,9 +192,11 @@ FileId AnimationsManager::on_get_animation(unique_ptr<Animation> new_animation,
|
||||
LOG(DEBUG) << "Animation " << file_id << " duration has changed";
|
||||
a->duration = new_animation->duration;
|
||||
}
|
||||
if (!G()->get_option_boolean("disable_minithumbnails")) {
|
||||
if (a->minithumbnail != new_animation->minithumbnail) {
|
||||
a->minithumbnail = std::move(new_animation->minithumbnail);
|
||||
}
|
||||
}
|
||||
if (a->thumbnail != new_animation->thumbnail) {
|
||||
if (!a->thumbnail.file_id.is_valid()) {
|
||||
LOG(DEBUG) << "Animation " << file_id << " thumbnail has changed";
|
||||
@ -295,9 +298,11 @@ void AnimationsManager::create_animation(FileId file_id, string minithumbnail, P
|
||||
a->mime_type = std::move(mime_type);
|
||||
a->duration = max(duration, 0);
|
||||
a->dimensions = dimensions;
|
||||
if (!G()->get_option_boolean("disable_minithumbnails")) {
|
||||
if (!td_->auth_manager_->is_bot()) {
|
||||
a->minithumbnail = std::move(minithumbnail);
|
||||
}
|
||||
}
|
||||
a->thumbnail = std::move(thumbnail);
|
||||
a->animated_thumbnail = std::move(animated_thumbnail);
|
||||
a->has_stickers = has_stickers;
|
||||
@ -882,4 +887,16 @@ void AnimationsManager::get_current_state(vector<td_api::object_ptr<td_api::Upda
|
||||
}
|
||||
}
|
||||
|
||||
void AnimationsManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"animations_\":"); output.push_back(std::to_string(this->animations_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"saved_animation_ids_\":"); output.push_back(std::to_string(this->saved_animation_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"saved_animation_file_ids_\":"); output.push_back(std::to_string(this->saved_animation_file_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"load_saved_animations_queries_\":"); output.push_back(std::to_string(this->load_saved_animations_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"repair_saved_animations_queries_\":"); output.push_back(std::to_string(this->repair_saved_animations_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -28,6 +28,7 @@ class Td;
|
||||
|
||||
class AnimationsManager final : public Actor {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
AnimationsManager(Td *td, ActorShared<> parent);
|
||||
AnimationsManager(const AnimationsManager &) = delete;
|
||||
AnimationsManager &operator=(const AnimationsManager &) = delete;
|
||||
|
@ -55,10 +55,27 @@ FileId AnimationsManager::parse_animation(ParserT &parser) {
|
||||
parse(animation->duration, parser);
|
||||
}
|
||||
parse(animation->dimensions, parser);
|
||||
parse(animation->file_name, parser);
|
||||
|
||||
string tmp_filename;
|
||||
parse(tmp_filename, parser);
|
||||
|
||||
parse(animation->mime_type, parser);
|
||||
|
||||
if ( G()->get_option_boolean("disable_document_filenames") && (
|
||||
animation->mime_type.rfind("image/") == 0 ||
|
||||
animation->mime_type.rfind("video/") == 0 ||
|
||||
animation->mime_type.rfind("audio/") == 0)) {
|
||||
animation->file_name = "0";
|
||||
} else {
|
||||
animation->file_name = tmp_filename;
|
||||
}
|
||||
|
||||
if (parser.version() >= static_cast<int32>(Version::SupportMinithumbnails)) {
|
||||
parse(animation->minithumbnail, parser);
|
||||
string tmp_minithumbnail;
|
||||
parse(tmp_minithumbnail, parser);
|
||||
if (!G()->get_option_boolean("disable_minithumbnails")) {
|
||||
animation->minithumbnail = tmp_minithumbnail;
|
||||
}
|
||||
}
|
||||
parse(animation->thumbnail, parser);
|
||||
parse(animation->file_id, parser);
|
||||
|
@ -1449,4 +1449,16 @@ void AttachMenuManager::get_current_state(vector<td_api::object_ptr<td_api::Upda
|
||||
updates.push_back(get_update_attachment_menu_bots_object());
|
||||
}
|
||||
|
||||
void AttachMenuManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"attach_menu_bots_\":"); output.push_back(std::to_string(this->attach_menu_bots_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"attach_menu_bot_file_source_ids_\":"); output.push_back(std::to_string(this->attach_menu_bot_file_source_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"reload_attach_menu_bots_queries_\":"); output.push_back(std::to_string(this->reload_attach_menu_bots_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"web_app_file_source_ids_\":"); output.push_back(std::to_string(this->web_app_file_source_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"opened_web_views_\":"); output.push_back(std::to_string(this->opened_web_views_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -79,6 +79,8 @@ class AttachMenuManager final : public Actor {
|
||||
|
||||
static string get_attach_menu_bots_database_key();
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static const int32 PING_WEB_VIEW_TIMEOUT = 60;
|
||||
|
||||
|
@ -309,4 +309,8 @@ tl_object_ptr<telegram_api::InputMedia> AudiosManager::get_input_media(
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void AudiosManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"audios_\":"); output.push_back(std::to_string(this->audios_.calc_size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -22,6 +22,7 @@ class Td;
|
||||
|
||||
class AudiosManager {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
explicit AudiosManager(Td *td);
|
||||
AudiosManager(const AudiosManager &) = delete;
|
||||
AudiosManager &operator=(const AudiosManager &) = delete;
|
||||
|
@ -99,7 +99,13 @@ FileId AudiosManager::parse_audio(ParserT &parser) {
|
||||
has_date = false;
|
||||
}
|
||||
if (has_file_name) {
|
||||
parse(audio->file_name, parser);
|
||||
string tmp_filename;
|
||||
parse(tmp_filename, parser);
|
||||
if (G()->get_option_boolean("disable_document_filenames")) {
|
||||
audio->file_name = "0";
|
||||
} else {
|
||||
audio->file_name = tmp_filename;
|
||||
}
|
||||
}
|
||||
if (has_mime_type) {
|
||||
parse(audio->mime_type, parser);
|
||||
@ -114,7 +120,11 @@ FileId AudiosManager::parse_audio(ParserT &parser) {
|
||||
parse(audio->performer, parser);
|
||||
}
|
||||
if (has_minithumbnail) {
|
||||
parse(audio->minithumbnail, parser);
|
||||
string tmp_minithumbnail;
|
||||
parse(tmp_minithumbnail, parser);
|
||||
if (!G()->get_option_boolean("disable_minithumbnails")) {
|
||||
audio->minithumbnail = tmp_minithumbnail;
|
||||
}
|
||||
}
|
||||
if (has_thumbnail) {
|
||||
parse(audio->thumbnail, parser);
|
||||
|
@ -1493,4 +1493,10 @@ void AuthManager::save_state() {
|
||||
G()->td_db()->get_binlog_pmc()->set("auth_state", log_event_store(db_state).as_slice().str());
|
||||
}
|
||||
|
||||
void AuthManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"other_user_ids_\":"); output.push_back(std::to_string(this->other_user_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_get_authorization_state_requests_\":"); output.push_back(std::to_string(this->pending_get_authorization_state_requests_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -60,6 +60,8 @@ class AuthManager final : public NetActor {
|
||||
void on_authorization_lost(string source);
|
||||
void on_closing(bool destroy_flag);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
// can return nullptr if state isn't initialized yet
|
||||
tl_object_ptr<td_api::AuthorizationState> get_current_authorization_state_object() const;
|
||||
|
||||
|
@ -126,14 +126,27 @@ class SaveAutoDownloadSettingsQuery final : public Td::ResultHandler {
|
||||
AutoDownloadSettings get_auto_download_settings(const td_api::object_ptr<td_api::autoDownloadSettings> &settings) {
|
||||
CHECK(settings != nullptr);
|
||||
AutoDownloadSettings result;
|
||||
if (G()->get_option_boolean("disable_auto_download")) {
|
||||
result.max_photo_file_size = -1;
|
||||
result.max_video_file_size = -1;
|
||||
result.max_other_file_size = -1;
|
||||
} else {
|
||||
result.max_photo_file_size = settings->max_photo_file_size_;
|
||||
result.max_video_file_size = settings->max_video_file_size_;
|
||||
result.max_other_file_size = settings->max_other_file_size_;
|
||||
}
|
||||
result.video_upload_bitrate = settings->video_upload_bitrate_;
|
||||
if (G()->get_option_boolean("disable_auto_download")) {
|
||||
result.is_enabled = false;
|
||||
result.preload_large_videos = false;
|
||||
result.preload_next_audio = false;
|
||||
result.preload_stories = false;
|
||||
} else {
|
||||
result.is_enabled = settings->is_auto_download_enabled_;
|
||||
result.preload_large_videos = settings->preload_large_videos_;
|
||||
result.preload_next_audio = settings->preload_next_audio_;
|
||||
result.preload_stories = settings->preload_stories_;
|
||||
}
|
||||
result.use_less_data_for_calls = settings->use_less_data_for_calls_;
|
||||
return result;
|
||||
}
|
||||
|
@ -547,4 +547,8 @@ void AutosaveManager::get_current_state(vector<td_api::object_ptr<td_api::Update
|
||||
}
|
||||
}
|
||||
|
||||
void AutosaveManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"load_settings_queries_\":"); output.push_back(std::to_string(this->load_settings_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -36,6 +36,8 @@ class AutosaveManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
struct DialogAutosaveSettings {
|
||||
bool are_inited_ = false;
|
||||
|
@ -1508,4 +1508,26 @@ void BackgroundManager::get_current_state(vector<td_api::object_ptr<td_api::Upda
|
||||
updates.push_back(get_update_default_background_object(true));
|
||||
}
|
||||
|
||||
void BackgroundManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"backgrounds_\":"); output.push_back(std::to_string(this->backgrounds_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"background_id_to_file_source_id_\":"); output.push_back(std::to_string(this->background_id_to_file_source_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"name_to_background_id_\":"); output.push_back(std::to_string(this->name_to_background_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"file_id_to_background_id_\":"); output.push_back(std::to_string(this->file_id_to_background_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"loaded_from_database_backgrounds_\":"); output.push_back(std::to_string(this->loaded_from_database_backgrounds_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_loaded_from_database_backgrounds_\":"); output.push_back(std::to_string(this->being_loaded_from_database_backgrounds_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"installed_backgrounds_\":"); output.push_back(std::to_string(this->installed_backgrounds_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_get_backgrounds_queries_\":"); output.push_back(std::to_string(this->pending_get_backgrounds_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_uploaded_files_\":"); output.push_back(std::to_string(this->being_uploaded_files_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"local_backgrounds_\":"); output.push_back(std::to_string(this->local_backgrounds_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -34,6 +34,7 @@ class Td;
|
||||
|
||||
class BackgroundManager final : public Actor {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
BackgroundManager(Td *td, ActorShared<> parent);
|
||||
|
||||
void get_backgrounds(bool for_dark_theme, Promise<td_api::object_ptr<td_api::backgrounds>> &&promise);
|
||||
|
@ -502,4 +502,7 @@ void BoostManager::on_update_dialog_boost(DialogId dialog_id, telegram_api::obje
|
||||
td_->dialog_manager_->get_chat_id_object(dialog_id, "updateChatBoost"), std::move(chat_boost_object)));
|
||||
}
|
||||
|
||||
void BoostManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -55,6 +55,8 @@ class BoostManager final : public Actor {
|
||||
|
||||
void on_update_dialog_boost(DialogId dialog_id, telegram_api::object_ptr<telegram_api::boost> &&boost);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void tear_down() final;
|
||||
|
||||
|
@ -991,4 +991,16 @@ void BotInfoManager::get_bot_info_about(UserId bot_user_id, const string &langua
|
||||
add_pending_get_query(bot_user_id, language_code, 2, std::move(promise));
|
||||
}
|
||||
|
||||
void BotInfoManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"pending_set_bot_info_queries_\":"); output.push_back(std::to_string(this->pending_set_bot_info_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_get_bot_info_queries_\":"); output.push_back(std::to_string(this->pending_get_bot_info_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"bot_media_preview_file_source_ids_\":"); output.push_back(std::to_string(this->bot_media_preview_file_source_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"bot_media_preview_info_file_source_ids_\":"); output.push_back(std::to_string(this->bot_media_preview_info_file_source_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_uploaded_files_\":"); output.push_back(std::to_string(this->being_uploaded_files_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -87,6 +87,8 @@ class BotInfoManager final : public Actor {
|
||||
|
||||
void get_bot_info_about(UserId bot_user_id, const string &language_code, Promise<string> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr double MAX_QUERY_DELAY = 0.01;
|
||||
|
||||
|
@ -1458,4 +1458,14 @@ void BusinessConnectionManager::get_current_state(vector<td_api::object_ptr<td_a
|
||||
});
|
||||
}
|
||||
|
||||
void BusinessConnectionManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"business_connections_\":"); output.push_back(std::to_string(this->business_connections_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"media_group_send_requests_\":"); output.push_back(std::to_string(this->media_group_send_requests_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_uploaded_files_\":"); output.push_back(std::to_string(this->being_uploaded_files_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_uploaded_thumbnails_\":"); output.push_back(std::to_string(this->being_uploaded_thumbnails_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -105,6 +105,8 @@ class BusinessConnectionManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
struct BusinessConnection;
|
||||
struct PendingMessage;
|
||||
|
@ -625,4 +625,7 @@ void BusinessManager::set_business_intro(BusinessIntro &&intro, Promise<Unit> &&
|
||||
td_->create_handler<UpdateBusinessIntroQuery>(std::move(promise))->send(std::move(intro));
|
||||
}
|
||||
|
||||
void BusinessManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -61,6 +61,8 @@ class BusinessManager final : public Actor {
|
||||
|
||||
void set_business_intro(BusinessIntro &&intro, Promise<Unit> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void tear_down() final;
|
||||
|
||||
|
@ -312,4 +312,7 @@ void CallbackQueriesManager::send_get_callback_answer_query(
|
||||
->send(dialog_id, message_full_id.get_message_id(), payload, std::move(password));
|
||||
}
|
||||
|
||||
void CallbackQueriesManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -43,6 +43,8 @@ class CallbackQueriesManager {
|
||||
void send_callback_query(MessageFullId message_full_id, tl_object_ptr<td_api::CallbackQueryPayload> &&payload,
|
||||
Promise<td_api::object_ptr<td_api::callbackQueryAnswer>> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr int32 BOT_CALLBACK_ANSWER_FLAG_HAS_MESSAGE = 1 << 0;
|
||||
static constexpr int32 BOT_CALLBACK_ANSWER_FLAG_NEED_SHOW_ALERT = 1 << 1;
|
||||
|
@ -538,4 +538,12 @@ void ChannelRecommendationManager::open_channel_recommended_channel(DialogId dia
|
||||
telegram_api::make_object<telegram_api::jsonObject>(std::move(data)), std::move(promise));
|
||||
}
|
||||
|
||||
void ChannelRecommendationManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"channel_recommended_dialogs_\":"); output.push_back(std::to_string(this->channel_recommended_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_channel_recommendations_queries_\":"); output.push_back(std::to_string(this->get_channel_recommendations_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_recommended_channels_queries_\":"); output.push_back(std::to_string(this->get_recommended_channels_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -36,6 +36,8 @@ class ChannelRecommendationManager final : public Actor {
|
||||
|
||||
void open_channel_recommended_channel(DialogId dialog_id, DialogId opened_dialog_id, Promise<Unit> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr int32 CHANNEL_RECOMMENDATIONS_CACHE_TIME = 86400; // some reasonable limit
|
||||
|
||||
|
@ -8959,4 +8959,48 @@ void ChatManager::get_current_state(vector<td_api::object_ptr<td_api::Update>> &
|
||||
});
|
||||
}
|
||||
|
||||
void ChatManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"chats_\":"); output.push_back(std::to_string(this->chats_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"chats_full_\":"); output.push_back(std::to_string(this->chats_full_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"unknown_chats_\":"); output.push_back(std::to_string(this->unknown_chats_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"chat_full_file_source_ids_\":"); output.push_back(std::to_string(this->chat_full_file_source_ids_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"min_channels_\":"); output.push_back(std::to_string(this->min_channels_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"channels_\":"); output.push_back(std::to_string(this->channels_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"channels_full_\":"); output.push_back(std::to_string(this->channels_full_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"unknown_channels_\":"); output.push_back(std::to_string(this->unknown_channels_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"invalidated_channels_full_\":"); output.push_back(std::to_string(this->invalidated_channels_full_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"channel_full_file_source_ids_\":"); output.push_back(std::to_string(this->channel_full_file_source_ids_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialogs_for_discussion_\":"); output.push_back(std::to_string(this->dialogs_for_discussion_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"inactive_channel_ids_\":"); output.push_back(std::to_string(this->inactive_channel_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"load_chat_from_database_queries_\":"); output.push_back(std::to_string(this->load_chat_from_database_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"loaded_from_database_chats_\":"); output.push_back(std::to_string(this->loaded_from_database_chats_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"unavailable_chat_fulls_\":"); output.push_back(std::to_string(this->unavailable_chat_fulls_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"load_channel_from_database_queries_\":"); output.push_back(std::to_string(this->load_channel_from_database_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"loaded_from_database_channels_\":"); output.push_back(std::to_string(this->loaded_from_database_channels_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"unavailable_channel_fulls_\":"); output.push_back(std::to_string(this->unavailable_channel_fulls_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"channel_messages_\":"); output.push_back(std::to_string(this->channel_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"linked_channel_ids_\":"); output.push_back(std::to_string(this->linked_channel_ids_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"restricted_channel_ids_\":"); output.push_back(std::to_string(this->restricted_channel_ids_.calc_size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -385,6 +385,8 @@ class ChatManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
struct Chat {
|
||||
string title;
|
||||
|
@ -222,4 +222,8 @@ void CommonDialogManager::on_get_common_dialogs(UserId user_id, int64 offset_cha
|
||||
common_dialogs.total_count = total_count;
|
||||
}
|
||||
|
||||
void CommonDialogManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"found_common_dialogs_\":"); output.push_back(std::to_string(this->found_common_dialogs_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -39,6 +39,8 @@ class CommonDialogManager final : public Actor {
|
||||
std::pair<int32, vector<DialogId>> get_common_dialogs(UserId user_id, DialogId offset_dialog_id, int32 limit,
|
||||
bool force, Promise<Unit> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void tear_down() final;
|
||||
|
||||
|
@ -58,4 +58,7 @@ void ConnectionStateManager::get_current_state(vector<td_api::object_ptr<td_api:
|
||||
updates.push_back(get_update_connection_state_object(connection_state_));
|
||||
}
|
||||
|
||||
void ConnectionStateManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -23,6 +23,8 @@ class ConnectionStateManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void tear_down() final;
|
||||
|
||||
|
@ -610,4 +610,8 @@ FlatHashMap<string, unique_ptr<CountryInfoManager::CountryList>> CountryInfoMana
|
||||
string CountryInfoManager::fragment_prefixes_str_;
|
||||
vector<string> CountryInfoManager::fragment_prefixes_;
|
||||
|
||||
void CountryInfoManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"pending_load_country_queries_\":"); output.push_back(std::to_string(this->pending_load_country_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -47,6 +47,8 @@ class CountryInfoManager final : public Actor {
|
||||
CountryInfoManager &operator=(CountryInfoManager &&) = delete;
|
||||
~CountryInfoManager() final;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void start_up() final;
|
||||
void tear_down() final;
|
||||
|
@ -424,4 +424,10 @@ void DialogActionManager::clear_active_dialog_actions(DialogId dialog_id) {
|
||||
}
|
||||
}
|
||||
|
||||
void DialogActionManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"active_dialog_actions_\":"); output.push_back(std::to_string(this->active_dialog_actions_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"set_typing_query_\":"); output.push_back(std::to_string(this->set_typing_query_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -41,6 +41,8 @@ class DialogActionManager final : public Actor {
|
||||
|
||||
void clear_active_dialog_actions(DialogId dialog_id);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr double DIALOG_ACTION_TIMEOUT = 5.5;
|
||||
|
||||
|
@ -2203,4 +2203,14 @@ void DialogFilterManager::get_current_state(vector<td_api::object_ptr<td_api::Up
|
||||
}
|
||||
}
|
||||
|
||||
void DialogFilterManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"server_dialog_filters_\":"); output.push_back(std::to_string(this->server_dialog_filters_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_filters_\":"); output.push_back(std::to_string(this->dialog_filters_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_filter_reload_queries_\":"); output.push_back(std::to_string(this->dialog_filter_reload_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"recommended_dialog_filters_\":"); output.push_back(std::to_string(this->recommended_dialog_filters_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -128,6 +128,8 @@ class DialogFilterManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr int32 DIALOG_FILTERS_CACHE_TIME = 86400;
|
||||
|
||||
|
@ -1131,4 +1131,10 @@ void DialogInviteLinkManager::delete_all_revoked_dialog_invite_links(DialogId di
|
||||
->send(dialog_id, std::move(input_user));
|
||||
}
|
||||
|
||||
void DialogInviteLinkManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"invite_link_infos_\":"); output.push_back(std::to_string(this->invite_link_infos_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_access_by_invite_link_\":"); output.push_back(std::to_string(this->dialog_access_by_invite_link_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -85,6 +85,8 @@ class DialogInviteLinkManager final : public Actor {
|
||||
|
||||
void delete_all_revoked_dialog_invite_links(DialogId dialog_id, UserId creator_user_id, Promise<Unit> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr size_t MAX_INVITE_LINK_TITLE_LENGTH = 32; // server side limit
|
||||
|
||||
|
@ -2340,4 +2340,20 @@ void DialogManager::on_dismiss_suggested_action(SuggestedAction action, Result<U
|
||||
set_promises(promises);
|
||||
}
|
||||
|
||||
void DialogManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"being_uploaded_dialog_photos_\":"); output.push_back(std::to_string(this->being_uploaded_dialog_photos_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"resolved_usernames_\":"); output.push_back(std::to_string(this->resolved_usernames_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"inaccessible_resolved_usernames_\":"); output.push_back(std::to_string(this->inaccessible_resolved_usernames_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"reload_voice_chat_on_search_usernames_\":"); output.push_back(std::to_string(this->reload_voice_chat_on_search_usernames_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"resolve_dialog_username_queries_\":"); output.push_back(std::to_string(this->resolve_dialog_username_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_suggested_actions_\":"); output.push_back(std::to_string(this->dialog_suggested_actions_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dismiss_suggested_action_queries_\":"); output.push_back(std::to_string(this->dismiss_suggested_action_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -227,6 +227,8 @@ class DialogManager final : public Actor {
|
||||
|
||||
void remove_dialog_suggested_action(SuggestedAction action);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr size_t MAX_TITLE_LENGTH = 128; // server side limit for chat title
|
||||
|
||||
|
@ -3004,4 +3004,18 @@ void DialogParticipantManager::get_current_state(vector<td_api::object_ptr<td_ap
|
||||
}
|
||||
}
|
||||
|
||||
void DialogParticipantManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"dialog_online_member_counts_\":"); output.push_back(std::to_string(this->dialog_online_member_counts_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"user_online_member_dialogs_\":"); output.push_back(std::to_string(this->user_online_member_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_administrators_\":"); output.push_back(std::to_string(this->dialog_administrators_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"channel_participants_\":"); output.push_back(std::to_string(this->channel_participants_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"cached_channel_participants_\":"); output.push_back(std::to_string(this->cached_channel_participants_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"join_channel_queries_\":"); output.push_back(std::to_string(this->join_channel_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -152,6 +152,8 @@ class DialogParticipantManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr int32 ONLINE_MEMBER_COUNT_CACHE_EXPIRE_TIME = 30 * 60;
|
||||
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "td/telegram/Td.h"
|
||||
#include "td/telegram/VideoNotesManager.h"
|
||||
#include "td/telegram/VideosManager.h"
|
||||
#include "td/telegram/Global.h"
|
||||
|
||||
#include "td/utils/algorithm.h"
|
||||
|
||||
@ -36,6 +37,7 @@ void Document::append_file_ids(const Td *td, vector<FileId> &file_ids) const {
|
||||
|
||||
file_ids.push_back(file_id);
|
||||
|
||||
if (!G()->get_option_boolean("disable_minithumbnails")) {
|
||||
FileId thumbnail_file_id = [&] {
|
||||
switch (type) {
|
||||
case Type::Animation:
|
||||
@ -55,6 +57,7 @@ void Document::append_file_ids(const Td *td, vector<FileId> &file_ids) const {
|
||||
if (thumbnail_file_id.is_valid()) {
|
||||
file_ids.push_back(thumbnail_file_id);
|
||||
}
|
||||
}
|
||||
|
||||
FileId animated_thumbnail_file_id = [&] {
|
||||
switch (type) {
|
||||
|
@ -786,4 +786,8 @@ string DocumentsManager::get_document_search_text(FileId file_id) const {
|
||||
return sb.as_cslice().str();
|
||||
}
|
||||
|
||||
void DocumentsManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"documents_\":"); output.push_back(std::to_string(this->documents_.calc_size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -31,6 +31,7 @@ class Td;
|
||||
|
||||
class DocumentsManager {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
explicit DocumentsManager(Td *td);
|
||||
DocumentsManager(const DocumentsManager &) = delete;
|
||||
DocumentsManager &operator=(const DocumentsManager &) = delete;
|
||||
|
@ -14,6 +14,8 @@
|
||||
|
||||
#include "td/utils/tl_helpers.h"
|
||||
|
||||
#include "td/telegram/ConfigManager.h"
|
||||
|
||||
namespace td {
|
||||
|
||||
template <class StorerT>
|
||||
@ -66,13 +68,25 @@ FileId DocumentsManager::parse_document(ParserT &parser) {
|
||||
has_thumbnail = true;
|
||||
}
|
||||
if (has_file_name) {
|
||||
parse(document->file_name, parser);
|
||||
string tmp_filename;
|
||||
parse(tmp_filename, parser);
|
||||
if (G()->get_option_boolean("disable_document_filenames") &&
|
||||
(document->mime_type.rfind("image/") == 0 || document->mime_type.rfind("video/") == 0 ||
|
||||
document->mime_type.rfind("audio/") == 0)) {
|
||||
document->file_name = "0";
|
||||
} else {
|
||||
document->file_name = tmp_filename;
|
||||
}
|
||||
}
|
||||
if (has_mime_type) {
|
||||
parse(document->mime_type, parser);
|
||||
}
|
||||
if (has_minithumbnail) {
|
||||
parse(document->minithumbnail, parser);
|
||||
string tmp_minithumbnail;
|
||||
parse(tmp_minithumbnail, parser);
|
||||
if (!G()->get_option_boolean("disable_minithumbnails")) {
|
||||
document->minithumbnail = tmp_minithumbnail;
|
||||
}
|
||||
}
|
||||
if (has_thumbnail) {
|
||||
parse(document->thumbnail, parser);
|
||||
|
@ -839,4 +839,7 @@ void DownloadManager::Counters::parse(ParserT &parser) {
|
||||
td::parse(downloaded_size, parser);
|
||||
}
|
||||
|
||||
void DownloadManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -107,6 +107,8 @@ class DownloadManager : public Actor {
|
||||
virtual void update_file_download_state(FileId internal_file_id, int64 downloaded_size, int64 size,
|
||||
int64 expected_size, bool is_paused) = 0;
|
||||
virtual void update_file_viewed(FileId file_id, FileSourceId file_source_id) = 0;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
};
|
||||
|
||||
} // namespace td
|
||||
|
@ -542,4 +542,8 @@ td_api::object_ptr<td_api::message> FileReferenceManager::get_message_object(Fil
|
||||
return result;
|
||||
}
|
||||
|
||||
void FileReferenceManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"nodes_\":"); output.push_back(std::to_string(this->nodes_.calc_size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -39,6 +39,7 @@ extern int VERBOSITY_NAME(file_references);
|
||||
|
||||
class FileReferenceManager final : public Actor {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
explicit FileReferenceManager(ActorShared<> parent);
|
||||
FileReferenceManager(const FileReferenceManager &) = delete;
|
||||
FileReferenceManager &operator=(const FileReferenceManager &) = delete;
|
||||
|
@ -1229,4 +1229,8 @@ void ForumTopicManager::on_topic_message_count_changed(DialogId dialog_id, Messa
|
||||
}
|
||||
}
|
||||
|
||||
void ForumTopicManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"dialog_topics_\":"); output.push_back(std::to_string(this->dialog_topics_.calc_size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -115,6 +115,8 @@ class ForumTopicManager final : public Actor {
|
||||
|
||||
void on_topic_message_count_changed(DialogId dialog_id, MessageId top_thread_message_id, int diff);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr size_t MAX_FORUM_TOPIC_TITLE_LENGTH = 128; // server side limit for forum topic title
|
||||
|
||||
|
@ -193,4 +193,7 @@ td_api::object_ptr<td_api::gameHighScores> GameManager::get_game_high_scores_obj
|
||||
return result;
|
||||
}
|
||||
|
||||
void GameManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -38,6 +38,8 @@ class GameManager final : public Actor {
|
||||
td_api::object_ptr<td_api::gameHighScores> get_game_high_scores_object(
|
||||
telegram_api::object_ptr<telegram_api::messages_highScores> &&high_scores);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void tear_down() final;
|
||||
|
||||
|
@ -162,6 +162,10 @@ bool Global::use_message_database() const {
|
||||
return td_db_->use_message_database();
|
||||
}
|
||||
|
||||
bool Global::use_custom_database_format() const {
|
||||
return td_db_->use_custom_database_format();
|
||||
}
|
||||
|
||||
int32 Global::get_retry_after(int32 error_code, Slice error_message) {
|
||||
if (error_code != 429) {
|
||||
return 0;
|
||||
|
@ -78,6 +78,7 @@ class StarManager;
|
||||
class StateManager;
|
||||
class StickersManager;
|
||||
class StorageManager;
|
||||
class MemoryManager;
|
||||
class StoryManager;
|
||||
class Td;
|
||||
class TdDb;
|
||||
@ -116,6 +117,52 @@ class Global final : public ActorContext {
|
||||
|
||||
Status init(ActorId<Td> td, unique_ptr<TdDb> td_db_ptr) TD_WARN_UNUSED_RESULT;
|
||||
|
||||
static bool get_use_custom_database(const std::string &database_directory) {
|
||||
auto s = get_database_directory_opts(database_directory);
|
||||
size_t qmarkpos;
|
||||
std::string token;
|
||||
size_t find_start_index = 0;
|
||||
while ((qmarkpos = s.find_first_of('&'), find_start_index) != std::string::npos) {
|
||||
token = s.substr(find_start_index, qmarkpos - find_start_index);
|
||||
find_start_index = qmarkpos;
|
||||
if ((qmarkpos = token.find_first_of('=')) != std::string::npos) {
|
||||
std::string propkey = token.substr(0, qmarkpos), propval = token.substr(qmarkpos + 1);
|
||||
if (propkey == "use_custom_database_format" && propval == "true") {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static std::string get_database_directory_path(const std::string &database_directory) {
|
||||
if (database_directory.empty()) {
|
||||
return database_directory;
|
||||
}
|
||||
size_t qmarkpos;
|
||||
if ((qmarkpos = database_directory.find_first_of('?')) != std::string::npos) {
|
||||
std::string path = database_directory.substr(0, qmarkpos),
|
||||
opts = database_directory.substr(qmarkpos + 1);
|
||||
return path;
|
||||
} else {
|
||||
return database_directory;
|
||||
}
|
||||
}
|
||||
|
||||
static std::string get_database_directory_opts(const std::string &database_directory) {
|
||||
if (database_directory.empty()) {
|
||||
return database_directory;
|
||||
}
|
||||
size_t qmarkpos;
|
||||
if ((qmarkpos = database_directory.find_first_of('?')) != std::string::npos) {
|
||||
std::string path = database_directory.substr(0, qmarkpos),
|
||||
opts = database_directory.substr(qmarkpos + 1);
|
||||
return opts;
|
||||
} else {
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
Slice get_dir() const;
|
||||
|
||||
Slice get_secure_files_dir() const {
|
||||
@ -498,6 +545,13 @@ class Global final : public ActorContext {
|
||||
storage_manager_ = storage_manager;
|
||||
}
|
||||
|
||||
ActorId<MemoryManager> memory_manager() const {
|
||||
return memory_manager_;
|
||||
}
|
||||
void set_memory_manager(ActorId<MemoryManager> memory_manager) {
|
||||
memory_manager_ = memory_manager;
|
||||
}
|
||||
|
||||
ActorId<StoryManager> story_manager() const {
|
||||
return story_manager_;
|
||||
}
|
||||
@ -574,6 +628,8 @@ class Global final : public ActorContext {
|
||||
|
||||
bool use_message_database() const;
|
||||
|
||||
bool use_custom_database_format() const;
|
||||
|
||||
bool keep_media_order() const {
|
||||
return use_file_database();
|
||||
}
|
||||
@ -718,6 +774,7 @@ class Global final : public ActorContext {
|
||||
ActorId<StarManager> star_manager_;
|
||||
ActorId<StickersManager> stickers_manager_;
|
||||
ActorId<StorageManager> storage_manager_;
|
||||
ActorId<MemoryManager> memory_manager_;
|
||||
ActorId<StoryManager> story_manager_;
|
||||
ActorId<ThemeManager> theme_manager_;
|
||||
ActorId<TimeZoneManager> time_zone_manager_;
|
||||
|
@ -16,6 +16,7 @@
|
||||
#include "td/telegram/DialogParticipantManager.h"
|
||||
#include "td/telegram/Global.h"
|
||||
#include "td/telegram/MessageId.h"
|
||||
#include "td/telegram/MemoryManager.h"
|
||||
#include "td/telegram/MessageSender.h"
|
||||
#include "td/telegram/MessagesManager.h"
|
||||
#include "td/telegram/misc.h"
|
||||
@ -1164,7 +1165,7 @@ bool GroupCallManager::is_group_call_joined(InputGroupCallId input_group_call_id
|
||||
}
|
||||
|
||||
GroupCallId GroupCallManager::get_group_call_id(InputGroupCallId input_group_call_id, DialogId dialog_id) {
|
||||
if (td_->auth_manager_->is_bot() || !input_group_call_id.is_valid()) {
|
||||
if (G()->get_option_boolean("disable_group_calls") || td_->auth_manager_->is_bot() || !input_group_call_id.is_valid()) {
|
||||
return GroupCallId();
|
||||
}
|
||||
return add_group_call(input_group_call_id, dialog_id)->group_call_id;
|
||||
@ -4141,7 +4142,7 @@ void GroupCallManager::on_update_group_call_connection(string &&connection_param
|
||||
}
|
||||
|
||||
void GroupCallManager::on_update_group_call(tl_object_ptr<telegram_api::GroupCall> group_call_ptr, DialogId dialog_id) {
|
||||
if (td_->auth_manager_->is_bot()) {
|
||||
if (G()->get_option_boolean("disable_group_calls") || td_->auth_manager_->is_bot()) {
|
||||
return;
|
||||
}
|
||||
if (dialog_id != DialogId() && !dialog_id.is_valid()) {
|
||||
@ -4849,21 +4850,48 @@ tl_object_ptr<td_api::updateGroupCallParticipant> GroupCallManager::get_update_g
|
||||
|
||||
void GroupCallManager::send_update_group_call(const GroupCall *group_call, const char *source) {
|
||||
LOG(INFO) << "Send update about " << group_call->group_call_id << " from " << source;
|
||||
if (G()->get_option_boolean("disable_group_calls")) {
|
||||
return;
|
||||
}
|
||||
send_closure(G()->td(), &Td::send_update,
|
||||
get_update_group_call_object(group_call, get_recent_speakers(group_call, true)));
|
||||
}
|
||||
|
||||
void GroupCallManager::send_update_group_call_participant(GroupCallId group_call_id,
|
||||
const GroupCallParticipant &participant, const char *source) {
|
||||
if (G()->get_option_boolean("disable_group_calls")) {
|
||||
return;
|
||||
}
|
||||
LOG(INFO) << "Send update about " << participant << " in " << group_call_id << " from " << source;
|
||||
send_closure(G()->td(), &Td::send_update, get_update_group_call_participant_object(group_call_id, participant));
|
||||
}
|
||||
|
||||
void GroupCallManager::send_update_group_call_participant(InputGroupCallId input_group_call_id,
|
||||
const GroupCallParticipant &participant, const char *source) {
|
||||
if (G()->get_option_boolean("disable_group_calls")) {
|
||||
return;
|
||||
}
|
||||
auto group_call = get_group_call(input_group_call_id);
|
||||
CHECK(group_call != nullptr && group_call->is_inited);
|
||||
send_update_group_call_participant(group_call->group_call_id, participant, source);
|
||||
}
|
||||
|
||||
void GroupCallManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"input_group_call_ids_\":"); output.push_back(std::to_string(this->input_group_call_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"group_calls_\":"); output.push_back(std::to_string(this->group_calls_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"group_call_participants_\":"); output.push_back(std::to_string(this->group_call_participants_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"participant_id_to_group_call_id_\":"); output.push_back(std::to_string(this->participant_id_to_group_call_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"group_call_recent_speakers_\":"); output.push_back(std::to_string(this->group_call_recent_speakers_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"load_group_call_queries_\":"); output.push_back(std::to_string(this->load_group_call_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_join_requests_\":"); output.push_back(std::to_string(this->pending_join_requests_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_join_presentation_requests_\":"); output.push_back(std::to_string(this->pending_join_presentation_requests_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -32,6 +32,7 @@ class Td;
|
||||
|
||||
class GroupCallManager final : public Actor {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
GroupCallManager(Td *td, ActorShared<> parent);
|
||||
GroupCallManager(const GroupCallManager &) = delete;
|
||||
GroupCallManager &operator=(const GroupCallManager &) = delete;
|
||||
@ -39,6 +40,8 @@ class GroupCallManager final : public Actor {
|
||||
GroupCallManager &operator=(GroupCallManager &&) = delete;
|
||||
~GroupCallManager() final;
|
||||
|
||||
DialogId get_group_call_participant_id(const td_api::object_ptr<td_api::MessageSender> &message_sender);
|
||||
|
||||
bool is_group_call_being_joined(InputGroupCallId input_group_call_id) const;
|
||||
|
||||
bool is_group_call_joined(InputGroupCallId input_group_call_id) const;
|
||||
|
@ -384,4 +384,7 @@ void InlineMessageManager::get_inline_game_high_scores(const string &inline_mess
|
||||
->send(std::move(input_bot_inline_message_id), std::move(input_user));
|
||||
}
|
||||
|
||||
void InlineMessageManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -51,6 +51,8 @@ class InlineMessageManager final : public Actor {
|
||||
void get_inline_game_high_scores(const string &inline_message_id, UserId user_id,
|
||||
Promise<td_api::object_ptr<td_api::gameHighScores>> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void tear_down() final;
|
||||
|
||||
|
@ -15,6 +15,7 @@
|
||||
#include "td/telegram/Contact.h"
|
||||
#include "td/telegram/DialogManager.h"
|
||||
#include "td/telegram/Document.h"
|
||||
#include "td/telegram/MemoryManager.h"
|
||||
#include "td/telegram/DocumentsManager.h"
|
||||
#include "td/telegram/files/FileManager.h"
|
||||
#include "td/telegram/files/FileType.h"
|
||||
@ -2240,4 +2241,14 @@ void InlineQueriesManager::remove_recent_inline_bot(UserId bot_user_id, Promise<
|
||||
promise.set_value(Unit());
|
||||
}
|
||||
|
||||
void InlineQueriesManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"recently_used_bot_user_ids_\":"); output.push_back(std::to_string(this->recently_used_bot_user_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"inline_query_results_\":"); output.push_back(std::to_string(this->inline_query_results_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"inline_message_contents_\":"); output.push_back(std::to_string(this->inline_message_contents_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"query_id_to_bot_user_id_\":"); output.push_back(std::to_string(this->query_id_to_bot_user_id_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -36,6 +36,7 @@ class Game;
|
||||
|
||||
class InlineQueriesManager final : public Actor {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
InlineQueriesManager(Td *td, ActorShared<> parent);
|
||||
|
||||
void after_get_difference();
|
||||
|
@ -3334,4 +3334,12 @@ Result<MessageLinkInfo> LinkManager::get_message_link_info(Slice url) {
|
||||
return std::move(info);
|
||||
}
|
||||
|
||||
void LinkManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"autologin_domains_\":"); output.push_back(std::to_string(this->autologin_domains_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"url_auth_domains_\":"); output.push_back(std::to_string(this->url_auth_domains_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"whitelisted_domains_\":"); output.push_back(std::to_string(this->whitelisted_domains_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -116,6 +116,8 @@ class LinkManager final : public Actor {
|
||||
|
||||
static Result<MessageLinkInfo> get_message_link_info(Slice url);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void start_up() final;
|
||||
|
||||
|
250
td/telegram/MemoryManager.cpp
Normal file
250
td/telegram/MemoryManager.cpp
Normal file
@ -0,0 +1,250 @@
|
||||
//
|
||||
// Copyright Andrea Cavalli (nospam@warp.ovh) 2020
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
//
|
||||
#include "td/telegram/MemoryManager.h"
|
||||
|
||||
#include "td/telegram/td_api.h"
|
||||
|
||||
#include "td/telegram/AuthManager.h"
|
||||
#include "td/telegram/ConfigManager.h"
|
||||
#include "td/telegram/Td.h"
|
||||
|
||||
#include "td/telegram/AccountManager.h"
|
||||
#include "td/telegram/AttachMenuManager.h"
|
||||
#include "td/telegram/AutosaveManager.h"
|
||||
#include "td/telegram/BoostManager.h"
|
||||
#include "td/telegram/BotInfoManager.h"
|
||||
#include "td/telegram/BusinessConnectionManager.h"
|
||||
#include "td/telegram/BusinessManager.h"
|
||||
#include "td/telegram/CallbackQueriesManager.h"
|
||||
#include "td/telegram/ChannelRecommendationManager.h"
|
||||
#include "td/telegram/ChatManager.h"
|
||||
#include "td/telegram/CommonDialogManager.h"
|
||||
#include "td/telegram/ConnectionStateManager.h"
|
||||
#include "td/telegram/CountryInfoManager.h"
|
||||
#include "td/telegram/DialogActionManager.h"
|
||||
#include "td/telegram/DialogFilterManager.h"
|
||||
#include "td/telegram/DialogInviteLinkManager.h"
|
||||
#include "td/telegram/DialogManager.h"
|
||||
#include "td/telegram/DialogParticipantManager.h"
|
||||
#include "td/telegram/DownloadManager.h"
|
||||
#include "td/telegram/ForumTopicManager.h"
|
||||
#include "td/telegram/GameManager.h"
|
||||
#include "td/telegram/InlineMessageManager.h"
|
||||
#include "td/telegram/LinkManager.h"
|
||||
#include "td/telegram/MessageImportManager.h"
|
||||
#include "td/telegram/NotificationManager.h"
|
||||
#include "td/telegram/NotificationSettingsManager.h"
|
||||
#include "td/telegram/OnlineManager.h"
|
||||
#include "td/telegram/OptionManager.h"
|
||||
#include "td/telegram/PeopleNearbyManager.h"
|
||||
#include "td/telegram/PrivacyManager.h"
|
||||
#include "td/telegram/PromoDataManager.h"
|
||||
#include "td/telegram/QuickReplyManager.h"
|
||||
#include "td/telegram/ReactionManager.h"
|
||||
#include "td/telegram/SavedMessagesManager.h"
|
||||
#include "td/telegram/SponsoredMessageManager.h"
|
||||
#include "td/telegram/StarManager.h"
|
||||
#include "td/telegram/StatisticsManager.h"
|
||||
#include "td/telegram/StoryManager.h"
|
||||
#include "td/telegram/TermsOfServiceManager.h"
|
||||
#include "td/telegram/ThemeManager.h"
|
||||
#include "td/telegram/TimeZoneManager.h"
|
||||
#include "td/telegram/TopDialogManager.h"
|
||||
#include "td/telegram/TranscriptionManager.h"
|
||||
#include "td/telegram/TranslationManager.h"
|
||||
#include "td/telegram/UpdatesManager.h"
|
||||
#include "td/telegram/UserManager.h"
|
||||
#include "td/telegram/VoiceNotesManager.h"
|
||||
#include <algorithm>
|
||||
#include <numeric>
|
||||
|
||||
#include "td/telegram/AnimationsManager.h"
|
||||
#include "td/telegram/AudiosManager.h"
|
||||
#include "td/telegram/BackgroundManager.h"
|
||||
#include "td/telegram/DocumentsManager.h"
|
||||
#include "td/telegram/FileReferenceManager.h"
|
||||
#include "td/telegram/files/FileManager.h"
|
||||
#include "td/telegram/GroupCallManager.h"
|
||||
#include "td/telegram/InlineQueriesManager.h"
|
||||
#include "td/telegram/MessagesManager.h"
|
||||
#include "td/telegram/PollManager.h"
|
||||
#include "td/telegram/StickersManager.h"
|
||||
#include "td/telegram/VideoNotesManager.h"
|
||||
#include "td/telegram/VideosManager.h"
|
||||
#include "td/telegram/WebPagesManager.h"
|
||||
|
||||
namespace td {
|
||||
|
||||
tl_object_ptr<td_api::memoryStatistics> MemoryStats::get_memory_statistics_object() const {
|
||||
return make_tl_object<td_api::memoryStatistics>(debug);
|
||||
}
|
||||
|
||||
MemoryManager::MemoryManager(Td *td, ActorShared<> parent) : td_(td), parent_(std::move(parent)) {
|
||||
}
|
||||
|
||||
void MemoryManager::start_up() {
|
||||
}
|
||||
|
||||
void MemoryManager::tear_down() {
|
||||
parent_.reset();
|
||||
}
|
||||
|
||||
void MemoryManager::get_memory_stats(bool full, Promise<MemoryStats> promise) const {
|
||||
vector<string> output;
|
||||
|
||||
output.push_back("{");
|
||||
|
||||
output.push_back("\"memory_stats\":{");
|
||||
|
||||
this->print_managers_memory_stats(output);
|
||||
|
||||
output.push_back("}");
|
||||
|
||||
output.push_back("}");
|
||||
|
||||
string s;
|
||||
s = accumulate(output.begin(), output.end(), s);
|
||||
auto value = MemoryStats(s);
|
||||
|
||||
promise.set_value(std::move(value));
|
||||
}
|
||||
|
||||
void MemoryManager::get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const {
|
||||
if (td_->auth_manager_->is_bot()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Never return updates
|
||||
}
|
||||
|
||||
void MemoryManager::print_managers_memory_stats(vector<string> &output) const {
|
||||
output.push_back("\"file_manager_\":{"); td_->file_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"business_connection_manager_\":{"); td_->business_connection_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"channel_recommendation_manager_\":{"); td_->channel_recommendation_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"chat_manager_\":{"); td_->chat_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"connection_state_manager_\":{"); td_->connection_state_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"inline_message_manager_\":{"); td_->inline_message_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"online_manager_\":{"); td_->online_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"promo_data_manager_\":{"); td_->promo_data_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"star_manager_\":{"); td_->star_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"terms_of_service_manager_\":{"); td_->terms_of_service_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"user_manager_\":{"); td_->user_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"account_manager_\":{"); td_->account_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"animations_manager_\":{"); td_->animations_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"attach_menu_manager_\":{"); td_->attach_menu_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"audios_manager_\":{"); td_->audios_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"auth_manager_\":{"); td_->auth_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"autosave_manager_\":{"); td_->autosave_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"background_manager_\":{"); td_->background_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"boost_manager_\":{"); td_->boost_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"bot_info_manager_\":{"); td_->bot_info_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"business_manager_\":{"); td_->business_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"callback_queries_manager_\":{"); td_->callback_queries_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"common_dialog_manager_\":{"); td_->common_dialog_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"country_info_manager_\":{"); td_->country_info_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_action_manager_\":{"); td_->dialog_action_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_filter_manager_\":{"); td_->dialog_filter_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_invite_link_manager_\":{"); td_->dialog_invite_link_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_manager_\":{"); td_->dialog_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_participant_manager_\":{"); td_->dialog_participant_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"documents_manager_\":{"); td_->documents_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"download_manager_\":{"); td_->download_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"file_reference_manager_\":{"); td_->file_reference_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"forum_topic_manager_\":{"); td_->forum_topic_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"game_manager_\":{"); td_->game_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"group_call_manager_\":{"); td_->group_call_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"inline_queries_manager_\":{"); td_->inline_queries_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"link_manager_\":{"); td_->link_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"message_import_manager_\":{"); td_->message_import_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"messages_manager_\":{"); td_->messages_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"notification_manager_\":{"); td_->notification_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"notification_settings_manager_\":{"); td_->notification_settings_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"option_manager_\":{"); td_->option_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"people_nearby_manager_\":{"); td_->people_nearby_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"poll_manager_\":{"); td_->poll_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"privacy_manager_\":{"); td_->privacy_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"quick_reply_manager_\":{"); td_->quick_reply_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"reaction_manager_\":{"); td_->reaction_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"saved_messages_manager_\":{"); td_->saved_messages_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"sponsored_message_manager_\":{"); td_->sponsored_message_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"statistics_manager_\":{"); td_->statistics_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"stickers_manager_\":{"); td_->stickers_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"story_manager_\":{"); td_->story_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"theme_manager_\":{"); td_->theme_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"time_zone_manager_\":{"); td_->time_zone_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"top_dialog_manager_\":{"); td_->top_dialog_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"transcription_manager_\":{"); td_->transcription_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"translation_manager_\":{"); td_->translation_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"updates_manager_\":{"); td_->updates_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"video_notes_manager_\":{"); td_->video_notes_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"videos_manager_\":{"); td_->videos_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"voice_notes_manager_\":{"); td_->voice_notes_manager_->memory_stats(output); output.push_back("}");
|
||||
output.push_back(",");
|
||||
output.push_back("\"web_pages_manager_\":{"); td_->web_pages_manager_->memory_stats(output); output.push_back("}");
|
||||
}
|
||||
|
||||
} // namespace td
|
65
td/telegram/MemoryManager.h
Normal file
65
td/telegram/MemoryManager.h
Normal file
@ -0,0 +1,65 @@
|
||||
//
|
||||
// Copyright Andrea Cavalli (nospam@warp.ovh) 2020
|
||||
//
|
||||
// Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
//
|
||||
#pragma once
|
||||
|
||||
#include "td/actor/actor.h"
|
||||
#include "td/actor/MultiPromise.h"
|
||||
#include "td/actor/PromiseFuture.h"
|
||||
#include "td/actor/Timeout.h"
|
||||
|
||||
#include "td/telegram/files/FileId.h"
|
||||
#include "td/telegram/files/FileSourceId.h"
|
||||
#include "td/telegram/Photo.h"
|
||||
#include "td/telegram/SecretInputMedia.h"
|
||||
|
||||
#include "td/utils/buffer.h"
|
||||
#include "td/utils/common.h"
|
||||
#include "td/utils/Hints.h"
|
||||
#include "td/utils/Slice.h"
|
||||
#include "td/utils/Status.h"
|
||||
|
||||
#include "td/telegram/td_api.h"
|
||||
#include "td/telegram/telegram_api.h"
|
||||
|
||||
#include <memory>
|
||||
#include <tuple>
|
||||
#include <unordered_map>
|
||||
#include <unordered_set>
|
||||
#include <utility>
|
||||
|
||||
namespace td {
|
||||
|
||||
class Td;
|
||||
|
||||
struct MemoryStats {
|
||||
string debug;
|
||||
MemoryStats() = default;
|
||||
explicit MemoryStats(string debug) : debug(std::move(debug)) {
|
||||
}
|
||||
tl_object_ptr<td_api::memoryStatistics> get_memory_statistics_object() const;
|
||||
};
|
||||
|
||||
class MemoryManager : public Actor {
|
||||
public:
|
||||
MemoryManager(Td *td, ActorShared<> parent);
|
||||
|
||||
void get_memory_stats(bool full, Promise<MemoryStats> promise) const;
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
private:
|
||||
void start_up() override;
|
||||
|
||||
void tear_down() override;
|
||||
|
||||
void print_managers_memory_stats(vector<string> &output) const;
|
||||
|
||||
Td *td_;
|
||||
ActorShared<> parent_;
|
||||
};
|
||||
|
||||
} // namespace td
|
@ -8282,6 +8282,7 @@ void update_message_content_file_id_remotes(MessageContent *content, const vecto
|
||||
}
|
||||
|
||||
FileId get_message_content_thumbnail_file_id(const MessageContent *content, const Td *td) {
|
||||
if (!G()->get_option_boolean("disable_minithumbnails")) {
|
||||
switch (content->get_type()) {
|
||||
case MessageContentType::Animation:
|
||||
return td->animations_manager_->get_animation_thumbnail_file_id(
|
||||
@ -8311,6 +8312,7 @@ FileId get_message_content_thumbnail_file_id(const MessageContent *content, cons
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
return FileId();
|
||||
}
|
||||
|
||||
|
@ -571,4 +571,12 @@ void MessageImportManager::on_imported_message_attachments_uploaded(int64 random
|
||||
td_->create_handler<StartImportHistoryQuery>(std::move(promise))->send(dialog_id, pending_message_import->import_id);
|
||||
}
|
||||
|
||||
void MessageImportManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"being_uploaded_imported_messages_\":"); output.push_back(std::to_string(this->being_uploaded_imported_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_uploaded_imported_message_attachments_\":"); output.push_back(std::to_string(this->being_uploaded_imported_message_attachments_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_message_imports_\":"); output.push_back(std::to_string(this->pending_message_imports_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -40,6 +40,8 @@ class MessageImportManager final : public Actor {
|
||||
void start_import_messages(DialogId dialog_id, int64 import_id, vector<FileId> &&attached_file_ids,
|
||||
Promise<Unit> &&promise);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void tear_down() final;
|
||||
|
||||
|
@ -46,6 +46,7 @@
|
||||
#include "td/telegram/LinkManager.h"
|
||||
#include "td/telegram/Location.h"
|
||||
#include "td/telegram/logevent/LogEvent.h"
|
||||
#include "td/telegram/MemoryManager.h"
|
||||
#include "td/telegram/MessageContent.h"
|
||||
#include "td/telegram/MessageDb.h"
|
||||
#include "td/telegram/MessageEntity.h"
|
||||
@ -5949,6 +5950,7 @@ void MessagesManager::update_message_reply_count(Dialog *d, MessageId message_id
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool MessagesManager::have_dialog_scheduled_messages_in_memory(const Dialog *d) {
|
||||
return d->scheduled_messages != nullptr && !d->scheduled_messages->scheduled_messages_.empty();
|
||||
}
|
||||
@ -9664,6 +9666,9 @@ void MessagesManager::on_get_recent_locations(DialogId dialog_id, int32 limit, i
|
||||
}
|
||||
|
||||
void MessagesManager::delete_messages_from_updates(const vector<MessageId> &message_ids, bool is_permanent) {
|
||||
if (G()->get_option_boolean("ignore_server_deletes_and_reads", false)) {
|
||||
return;
|
||||
}
|
||||
FlatHashMap<DialogId, vector<int64>, DialogIdHash> deleted_message_ids;
|
||||
FlatHashMap<DialogId, bool, DialogIdHash> need_update_dialog_pos;
|
||||
vector<unique_ptr<Message>> deleted_messages;
|
||||
@ -11252,6 +11257,9 @@ void MessagesManager::read_all_dialog_reactions_on_server(DialogId dialog_id, ui
|
||||
}
|
||||
|
||||
void MessagesManager::read_message_content_from_updates(MessageId message_id, int32 read_date) {
|
||||
if (G()->get_option_boolean("ignore_server_deletes_and_reads", false)) {
|
||||
return;
|
||||
}
|
||||
if (!message_id.is_valid() || !message_id.is_server()) {
|
||||
LOG(ERROR) << "Incoming update tries to read content of " << message_id;
|
||||
return;
|
||||
@ -15023,7 +15031,8 @@ void MessagesManager::on_get_dialogs(FolderId folder_id, vector<tl_object_ptr<te
|
||||
}
|
||||
|
||||
bool MessagesManager::is_message_unload_enabled() const {
|
||||
return G()->use_message_database() || td_->auth_manager_->is_bot();
|
||||
auto has_custom_unload_time = G()->have_option("message_unload_delay");
|
||||
return G()->use_message_database() || td_->auth_manager_->is_bot() || has_custom_unload_time;
|
||||
}
|
||||
|
||||
bool MessagesManager::can_unload_message(const Dialog *d, const Message *m) const {
|
||||
@ -15548,8 +15557,10 @@ void MessagesManager::on_message_deleted(Dialog *d, Message *m, bool is_permanen
|
||||
case DialogType::User:
|
||||
case DialogType::Chat:
|
||||
if (m->message_id.is_server()) {
|
||||
if (!G()->get_option_boolean("ignore_server_deletes_and_reads", false)) {
|
||||
message_id_to_dialog_id_.erase(m->message_id);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case DialogType::Channel:
|
||||
if (m->message_id.is_server() && !td_->auth_manager_->is_bot()) {
|
||||
@ -29072,6 +29083,10 @@ void MessagesManager::send_update_chat_last_message_impl(const Dialog *d, const
|
||||
return;
|
||||
}
|
||||
|
||||
if (G()->get_option_boolean("ignore_update_chat_last_message")) {
|
||||
return;
|
||||
}
|
||||
|
||||
CHECK(d != nullptr);
|
||||
LOG_CHECK(d->is_update_new_chat_sent) << "Wrong " << d->dialog_id << " in send_update_chat_last_message from "
|
||||
<< source;
|
||||
@ -29216,11 +29231,13 @@ void MessagesManager::send_update_chat_read_inbox(const Dialog *d, bool force, c
|
||||
LOG(INFO) << "Send updateChatReadInbox in " << d->dialog_id << "("
|
||||
<< td_->dialog_manager_->get_dialog_title(d->dialog_id) << ") to " << d->server_unread_count << " + "
|
||||
<< d->local_unread_count << " from " << source;
|
||||
if (!G()->get_option_boolean("ignore_update_chat_read_inbox")) {
|
||||
send_closure(G()->td(), &Td::send_update,
|
||||
td_api::make_object<td_api::updateChatReadInbox>(
|
||||
get_chat_id_object(d->dialog_id, "updateChatReadInbox"), d->last_read_inbox_message_id.get(),
|
||||
d->server_unread_count + d->local_unread_count));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void MessagesManager::send_update_chat_read_outbox(const Dialog *d) {
|
||||
@ -38526,6 +38543,10 @@ void MessagesManager::suffix_load_query_ready(DialogId dialog_id) {
|
||||
|
||||
LOG(INFO) << "Finished suffix load query in " << dialog_id;
|
||||
auto *d = get_dialog(dialog_id);
|
||||
if (d == nullptr) {
|
||||
LOG(ERROR) << "Unknown dialog " << dialog_id;
|
||||
return;
|
||||
}
|
||||
bool is_unchanged = queries->suffix_load_first_message_id_ == queries->suffix_load_query_message_id_;
|
||||
suffix_load_update_first_message_id(d, queries);
|
||||
if (is_unchanged && queries->suffix_load_first_message_id_ == queries->suffix_load_query_message_id_) {
|
||||
@ -38800,7 +38821,10 @@ void MessagesManager::set_sponsored_dialog(DialogId dialog_id, DialogSource sour
|
||||
CHECK(sponsored_dialog_id_.is_valid());
|
||||
sponsored_dialog_source_ = std::move(source);
|
||||
const Dialog *d = get_dialog(sponsored_dialog_id_);
|
||||
CHECK(d != nullptr);
|
||||
if (d == nullptr) {
|
||||
LOG(ERROR) << "Unknown dialog " << dialog_id;
|
||||
return;
|
||||
}
|
||||
send_update_chat_position(DialogListId(FolderId::main()), d, "set_sponsored_dialog");
|
||||
save_sponsored_dialog();
|
||||
}
|
||||
@ -38810,7 +38834,10 @@ void MessagesManager::set_sponsored_dialog(DialogId dialog_id, DialogSource sour
|
||||
bool need_update_total_chat_count = false;
|
||||
if (sponsored_dialog_id_.is_valid()) {
|
||||
const Dialog *d = get_dialog(sponsored_dialog_id_);
|
||||
CHECK(d != nullptr);
|
||||
if (d == nullptr) {
|
||||
LOG(ERROR) << "Unknown dialog " << dialog_id;
|
||||
return;
|
||||
}
|
||||
bool was_sponsored = is_dialog_sponsored(d);
|
||||
sponsored_dialog_id_ = DialogId();
|
||||
sponsored_dialog_source_ = DialogSource();
|
||||
@ -38823,7 +38850,10 @@ void MessagesManager::set_sponsored_dialog(DialogId dialog_id, DialogSource sour
|
||||
if (dialog_id.is_valid()) {
|
||||
force_create_dialog(dialog_id, "set_sponsored_dialog_id");
|
||||
const Dialog *d = get_dialog(dialog_id);
|
||||
CHECK(d != nullptr);
|
||||
if (d == nullptr) {
|
||||
LOG(ERROR) << "Unknown dialog " << dialog_id;
|
||||
return;
|
||||
}
|
||||
add_sponsored_dialog(d, std::move(source));
|
||||
if (is_dialog_sponsored(d)) {
|
||||
need_update_total_chat_count = !need_update_total_chat_count;
|
||||
@ -38952,4 +38982,146 @@ void MessagesManager::get_message_file_search_text(MessageFullId message_full_id
|
||||
return promise.set_error(Status::Error(200, "File not found"));
|
||||
}
|
||||
|
||||
void MessagesManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"being_uploaded_files_\":"); output.push_back(std::to_string(this->being_uploaded_files_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_uploaded_thumbnails_\":"); output.push_back(std::to_string(this->being_uploaded_thumbnails_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_loaded_secret_thumbnails_\":"); output.push_back(std::to_string(this->being_loaded_secret_thumbnails_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_sent_messages_\":"); output.push_back(std::to_string(this->being_sent_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"update_message_ids_\":"); output.push_back(std::to_string(this->update_message_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_message_group_sends_\":"); output.push_back(std::to_string(this->pending_message_group_sends_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_paid_media_group_sends_\":"); output.push_back(std::to_string(this->pending_paid_media_group_sends_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"message_id_to_dialog_id_\":"); output.push_back(std::to_string(this->message_id_to_dialog_id_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"last_clear_history_message_id_to_dialog_id_\":"); output.push_back(std::to_string(this->last_clear_history_message_id_to_dialog_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_created_dialogs_\":"); output.push_back(std::to_string(this->pending_created_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialogs_\":"); output.push_back(std::to_string(this->dialogs_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"loaded_dialogs_\":"); output.push_back(std::to_string(this->loaded_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"failed_to_load_dialogs_\":"); output.push_back(std::to_string(this->failed_to_load_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"postponed_chat_read_inbox_updates_\":"); output.push_back(std::to_string(this->postponed_chat_read_inbox_updates_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"search_public_dialogs_queries_\":"); output.push_back(std::to_string(this->search_public_dialogs_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"found_public_dialogs_\":"); output.push_back(std::to_string(this->found_public_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"found_on_server_dialogs_\":"); output.push_back(std::to_string(this->found_on_server_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"found_dialog_messages_\":"); output.push_back(std::to_string(this->found_dialog_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"found_dialog_messages_dialog_id_\":"); output.push_back(std::to_string(this->found_dialog_messages_dialog_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_dialog_queries_\":"); output.push_back(std::to_string(this->get_dialog_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_dialog_query_log_event_id_\":"); output.push_back(std::to_string(this->get_dialog_query_log_event_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"replied_by_yet_unsent_messages_\":"); output.push_back(std::to_string(this->replied_by_yet_unsent_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"replied_yet_unsent_messages_\":"); output.push_back(std::to_string(this->replied_yet_unsent_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"message_to_replied_media_timestamp_messages_\":"); output.push_back(std::to_string(this->message_to_replied_media_timestamp_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"story_to_replied_media_timestamp_messages_\":"); output.push_back(std::to_string(this->story_to_replied_media_timestamp_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"notification_group_id_to_dialog_id_\":"); output.push_back(std::to_string(this->notification_group_id_to_dialog_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"active_get_channel_differences_\":"); output.push_back(std::to_string(this->active_get_channel_differences_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_channel_difference_to_log_event_id_\":"); output.push_back(std::to_string(this->get_channel_difference_to_log_event_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"channel_get_difference_retry_timeouts_\":"); output.push_back(std::to_string(this->channel_get_difference_retry_timeouts_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"postponed_channel_updates_\":"); output.push_back(std::to_string(this->postponed_channel_updates_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"is_channel_difference_finished_\":"); output.push_back(std::to_string(this->is_channel_difference_finished_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"expected_channel_pts_\":"); output.push_back(std::to_string(this->expected_channel_pts_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"expected_channel_max_message_id_\":"); output.push_back(std::to_string(this->expected_channel_max_message_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"active_live_location_message_full_ids_\":"); output.push_back(std::to_string(this->active_live_location_message_full_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"load_active_live_location_messages_queries_\":"); output.push_back(std::to_string(this->load_active_live_location_messages_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"load_scheduled_messages_from_database_queries_\":"); output.push_back(std::to_string(this->load_scheduled_messages_from_database_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_dialogs_tasks_\":"); output.push_back(std::to_string(this->get_dialogs_tasks_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_on_get_dialogs_\":"); output.push_back(std::to_string(this->pending_on_get_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_channel_on_get_dialogs_\":"); output.push_back(std::to_string(this->pending_channel_on_get_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"run_after_get_channel_difference_\":"); output.push_back(std::to_string(this->run_after_get_channel_difference_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_secret_message_ids_\":"); output.push_back(std::to_string(this->pending_secret_message_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_add_dialog_dependent_dialogs_\":"); output.push_back(std::to_string(this->pending_add_dialog_dependent_dialogs_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_add_dialog_data_\":"); output.push_back(std::to_string(this->pending_add_dialog_data_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_add_default_join_group_call_as_dialog_id_\":"); output.push_back(std::to_string(this->pending_add_default_join_group_call_as_dialog_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_add_default_send_message_as_dialog_id_\":"); output.push_back(std::to_string(this->pending_add_default_send_message_as_dialog_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_bot_command_message_ids_\":"); output.push_back(std::to_string(this->dialog_bot_command_message_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"viewed_live_location_tasks_\":"); output.push_back(std::to_string(this->viewed_live_location_tasks_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_viewed_live_locations_\":"); output.push_back(std::to_string(this->pending_viewed_live_locations_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"yet_unsent_media_queues_\":"); output.push_back(std::to_string(this->yet_unsent_media_queues_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"message_full_id_to_file_source_id_\":"); output.push_back(std::to_string(this->message_full_id_to_file_source_id_.calc_size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"last_outgoing_forwarded_message_date_\":"); output.push_back(std::to_string(this->last_outgoing_forwarded_message_date_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_viewed_messages_\":"); output.push_back(std::to_string(this->dialog_viewed_messages_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_reloaded_reactions_\":"); output.push_back(std::to_string(this->being_reloaded_reactions_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_reloaded_fact_checks_\":"); output.push_back(std::to_string(this->being_reloaded_fact_checks_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_dialog_group_call_updates_\":"); output.push_back(std::to_string(this->pending_dialog_group_call_updates_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"auth_notification_id_date_\":"); output.push_back(std::to_string(this->auth_notification_id_date_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"previous_repaired_read_inbox_max_message_id_\":"); output.push_back(std::to_string(this->previous_repaired_read_inbox_max_message_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"yet_unsent_message_full_id_to_persistent_message_id_\":"); output.push_back(std::to_string(this->yet_unsent_message_full_id_to_persistent_message_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"yet_unsent_thread_message_ids_\":"); output.push_back(std::to_string(this->yet_unsent_thread_message_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_suffix_load_queries_\":"); output.push_back(std::to_string(this->dialog_suffix_load_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_message_views_\":"); output.push_back(std::to_string(this->pending_message_views_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"read_history_log_event_ids_\":"); output.push_back(std::to_string(this->read_history_log_event_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"updated_read_history_message_ids_\":"); output.push_back(std::to_string(this->updated_read_history_message_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_reactions_\":"); output.push_back(std::to_string(this->pending_reactions_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"paid_reaction_task_ids_\":"); output.push_back(std::to_string(this->paid_reaction_task_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"paid_reaction_tasks_\":"); output.push_back(std::to_string(this->paid_reaction_tasks_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_read_reactions_\":"); output.push_back(std::to_string(this->pending_read_reactions_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"active_reaction_types_\":"); output.push_back(std::to_string(this->active_reaction_types_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"active_reaction_pos_\":"); output.push_back(std::to_string(this->active_reaction_pos_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_history_queries_\":"); output.push_back(std::to_string(this->get_history_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -126,6 +126,7 @@ class Usernames;
|
||||
|
||||
class MessagesManager final : public Actor {
|
||||
public:
|
||||
void memory_stats(vector<string> &output);
|
||||
static constexpr int32 SEND_MESSAGE_FLAG_DISABLE_WEB_PAGE_PREVIEW = 1 << 1;
|
||||
static constexpr int32 SEND_MESSAGE_FLAG_HAS_REPLY_MARKUP = 1 << 2;
|
||||
static constexpr int32 SEND_MESSAGE_FLAG_HAS_ENTITIES = 1 << 3;
|
||||
|
@ -167,7 +167,11 @@ void NotificationManager::on_flush_pending_updates_timeout_callback(void *notifi
|
||||
}
|
||||
|
||||
bool NotificationManager::is_disabled() const {
|
||||
if ( G()->get_option_boolean("disable_notifications")) {
|
||||
return true;
|
||||
} else {
|
||||
return G()->close_flag() || !td_->auth_manager_->is_authorized() || td_->auth_manager_->is_bot();
|
||||
}
|
||||
}
|
||||
|
||||
StringBuilder &operator<<(StringBuilder &string_builder, const NotificationManager::ActiveNotificationsUpdate &update) {
|
||||
@ -4382,4 +4386,32 @@ void NotificationManager::on_binlog_events(vector<BinlogEvent> &&events) {
|
||||
VLOG(notifications) << "Finish processing binlog events";
|
||||
}
|
||||
|
||||
void NotificationManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"running_get_chat_difference_\":"); output.push_back(std::to_string(this->running_get_chat_difference_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"group_keys_\":"); output.push_back(std::to_string(this->group_keys_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"pending_updates_\":"); output.push_back(std::to_string(this->pending_updates_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"call_notification_group_ids_\":"); output.push_back(std::to_string(this->call_notification_group_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"available_call_notification_group_ids_\":"); output.push_back(std::to_string(this->available_call_notification_group_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"dialog_id_to_call_notification_group_id_\":"); output.push_back(std::to_string(this->dialog_id_to_call_notification_group_id_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"temporary_notification_log_event_ids_\":"); output.push_back(std::to_string(this->temporary_notification_log_event_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"temporary_edit_notification_log_event_ids_\":"); output.push_back(std::to_string(this->temporary_edit_notification_log_event_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"temporary_notifications_\":"); output.push_back(std::to_string(this->temporary_notifications_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"temporary_notification_object_ids_\":"); output.push_back(std::to_string(this->temporary_notification_object_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"push_notification_promises_\":"); output.push_back(std::to_string(this->push_notification_promises_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"active_call_notifications_\":"); output.push_back(std::to_string(this->active_call_notifications_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"announcement_id_date_\":"); output.push_back(std::to_string(this->announcement_id_date_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -135,6 +135,8 @@ class NotificationManager final : public Actor {
|
||||
|
||||
void on_binlog_events(vector<BinlogEvent> &&events);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr int32 DEFAULT_GROUP_COUNT_MAX = 0;
|
||||
static constexpr int32 DEFAULT_GROUP_SIZE_MAX = 10;
|
||||
|
@ -1756,4 +1756,18 @@ void NotificationSettingsManager::get_current_state(vector<td_api::object_ptr<td
|
||||
}
|
||||
}
|
||||
|
||||
void NotificationSettingsManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"saved_ringtone_file_ids_\":"); output.push_back(std::to_string(this->saved_ringtone_file_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"sorted_saved_ringtone_file_ids_\":"); output.push_back(std::to_string(this->sorted_saved_ringtone_file_ids_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"being_uploaded_ringtones_\":"); output.push_back(std::to_string(this->being_uploaded_ringtones_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"reload_saved_ringtones_queries_\":"); output.push_back(std::to_string(this->reload_saved_ringtones_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"repair_saved_ringtones_queries_\":"); output.push_back(std::to_string(this->repair_saved_ringtones_queries_.size()));
|
||||
output.push_back(",");
|
||||
output.push_back("\"get_dialog_notification_settings_queries_\":"); output.push_back(std::to_string(this->get_dialog_notification_settings_queries_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -124,6 +124,8 @@ class NotificationSettingsManager final : public Actor {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
class UpdateScopeNotificationSettingsOnServerLogEvent;
|
||||
class UpdateReactionNotificationSettingsOnServerLogEvent;
|
||||
|
@ -161,4 +161,7 @@ void OnlineManager::on_ping_server_timeout() {
|
||||
set_is_bot_online(false);
|
||||
}
|
||||
|
||||
void OnlineManager::memory_stats(vector<string> &output) {
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -33,6 +33,8 @@ class OnlineManager final : public Actor {
|
||||
|
||||
void set_is_bot_online(bool is_bot_online);
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
static constexpr int32 PING_SERVER_TIMEOUT = 300;
|
||||
|
||||
|
@ -844,6 +844,26 @@ void OptionManager::set_option(const string &name, td_api::object_ptr<td_api::Op
|
||||
if (set_boolean_option("disable_time_adjustment_protection")) {
|
||||
return;
|
||||
}
|
||||
// Start TDLight options
|
||||
if (set_boolean_option("disable_document_filenames")) {
|
||||
return;
|
||||
}
|
||||
if (set_boolean_option("disable_minithumbnails")) {
|
||||
return;
|
||||
}
|
||||
if (set_boolean_option("disable_notifications")) {
|
||||
return;
|
||||
}
|
||||
if (set_boolean_option("disable_group_calls")) {
|
||||
return;
|
||||
}
|
||||
if (set_boolean_option("disable_auto_download")) {
|
||||
return;
|
||||
}
|
||||
// End TDLight options
|
||||
if (set_boolean_option("disable_persistent_network_statistics")) {
|
||||
return;
|
||||
}
|
||||
if (!is_bot && set_boolean_option("disable_top_chats")) {
|
||||
return;
|
||||
}
|
||||
@ -869,6 +889,20 @@ void OptionManager::set_option(const string &name, td_api::object_ptr<td_api::Op
|
||||
if (set_boolean_option("ignore_platform_restrictions")) {
|
||||
return;
|
||||
}
|
||||
// Start TDLight options
|
||||
if (set_boolean_option("ignore_server_deletes_and_reads")) {
|
||||
return;
|
||||
}
|
||||
if (set_boolean_option("ignore_update_chat_last_message")) {
|
||||
return;
|
||||
}
|
||||
if (set_boolean_option("ignore_update_chat_read_inbox")) {
|
||||
return;
|
||||
}
|
||||
if (set_boolean_option("ignore_update_user_chat_action")) {
|
||||
return;
|
||||
}
|
||||
// End TDLight options
|
||||
if (set_boolean_option("is_emulator")) {
|
||||
return;
|
||||
}
|
||||
@ -952,6 +986,11 @@ void OptionManager::set_option(const string &name, td_api::object_ptr<td_api::Op
|
||||
if (set_boolean_option("reuse_uploaded_photos_by_hash")) {
|
||||
return;
|
||||
}
|
||||
// Start TDLight options
|
||||
if (set_boolean_option("receive_access_hashes")) {
|
||||
return;
|
||||
}
|
||||
// End TDLight options
|
||||
break;
|
||||
case 's':
|
||||
if (set_integer_option("storage_max_files_size")) {
|
||||
@ -1070,4 +1109,8 @@ void OptionManager::get_current_state(vector<td_api::object_ptr<td_api::Update>>
|
||||
}
|
||||
}
|
||||
|
||||
void OptionManager::memory_stats(vector<string> &output) {
|
||||
output.push_back("\"pending_get_options_\":"); output.push_back(std::to_string(this->pending_get_options_.size()));
|
||||
}
|
||||
|
||||
} // namespace td
|
||||
|
@ -65,6 +65,8 @@ class OptionManager {
|
||||
|
||||
void get_current_state(vector<td_api::object_ptr<td_api::Update>> &updates) const;
|
||||
|
||||
void memory_stats(vector<string> &output);
|
||||
|
||||
private:
|
||||
void set_option(Slice name, Slice value);
|
||||
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user