├── .commitlintrc.js
├── .cz-config.js
├── .eslintignore
├── .eslintrc.js
├── .flowconfig
├── .github
└── ISSUE_TEMPLATE
│ ├── Bug_report.md
│ └── Feature_request.md
├── .gitignore
├── .travis.yml
├── README.md
├── bin
└── telegram-typings
├── changelog.md
├── flow-typed
└── npm
│ ├── @babel
│ ├── generator_vx.x.x.js
│ └── types_v7.0.x.js
│ ├── cheerio_v1.0.x.js
│ ├── debug_v3.x.x.js
│ ├── node-fetch_v1.x.x.js
│ └── rust-keywords_v1.x.x.js
├── javascript
├── index.d.ts
├── index.js
├── index.js.flow
├── package.json
└── readme.md
├── lib
├── builders
│ ├── abstract-js.js
│ ├── base.js
│ ├── flow.js
│ ├── rust.js
│ └── typescript.js
├── main.js
├── native.js
├── parser.js
└── store.js
├── license
├── package-lock.json
├── package.json
├── rust
├── .gitignore
├── Cargo.toml
├── README.md
└── src
│ └── lib.rs
└── tt.code-workspace
/.commitlintrc.js:
--------------------------------------------------------------------------------
1 | const czConfig = require('./.cz-config');
2 |
3 | module.exports = {
4 | rules: {
5 | 'body-leading-blank': [2, 'always'],
6 | 'footer-leading-blank': [1, 'always'],
7 | 'header-max-length': [1, 'always', 100],
8 | 'scope-enum': [1, 'always', czConfig.scopes.map((scope) => scope.name)],
9 | 'scope-case': [2, 'always', 'lower-case'],
10 | 'subject-case': [0],
11 | 'subject-empty': [2, 'never'],
12 | 'subject-full-stop': [1, 'never', '.'],
13 | 'type-enum': [2, 'always', czConfig.types.map((type) => type.value)],
14 | 'type-case': [2, 'always', 'lower-case'],
15 | }
16 | }
17 |
--------------------------------------------------------------------------------
/.cz-config.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | types: [
3 | { value: 'feat', name: 'feat: A new feature' },
4 | { value: 'fix', name: 'fix: A bug fix' },
5 | { value: 'docs', name: 'docs: Documentation only changes' },
6 | { value: 'style', name: 'style: Changes that do not affect the meaning of the code\n (white-space, formatting, missing semi-colons, etc)' },
7 | { value: 'refactor', name: 'refactor: A code change that neither fixes a bug nor adds a feature' },
8 | { value: 'perf', name: 'perf: A code change that improves performance' },
9 | { value: 'build', name: 'build: Changes that affect the build system or external dependencies' },
10 | { value: 'test', name: 'test: Adding missing tests' },
11 | { value: 'chore', name: 'chore: Changes to the build process or auxiliary tools\n and libraries such as documentation generation' },
12 | { value: 'revert', name: 'revert: Revert to a commit' },
13 | { value: 'WIP', name: 'WIP: Work in progress' },
14 | ],
15 | scopes: [
16 | { name: 'main' },
17 | { name: 'parser' },
18 | { name: 'store' },
19 | { name: 'builders' },
20 | { name: 'builders/base' },
21 | { name: 'builders/rust' },
22 | { name: 'builders/typescript' },
23 | { name: 'builders/flow' },
24 | { name: '@rust' },
25 | { name: '@js' },
26 | { name: '@bin' },
27 | ],
28 | allowCustomScopes: true,
29 | allowBreakingChanges: ['feat', 'fix', 'revert'],
30 | }
31 |
--------------------------------------------------------------------------------
/.eslintignore:
--------------------------------------------------------------------------------
1 | flow-typed
2 | .vscode
3 | javascript
4 | node_modules
5 | rust
6 |
--------------------------------------------------------------------------------
/.eslintrc.js:
--------------------------------------------------------------------------------
1 | module.exports = {
2 | extends: "@atomix/eslint-config",
3 | rules: {
4 | "class-methods-use-this": "off",
5 | "import/no-extraneous-dependencies": ["error", {
6 | "devDependencies": true
7 | }],
8 | "spaced-comment": ["off", "always", { "block": { "balanced": true, "exceptions": [":"] } }],
9 | },
10 | }
11 |
--------------------------------------------------------------------------------
/.flowconfig:
--------------------------------------------------------------------------------
1 | [ignore]
2 | .*/node_modules/.*
3 | .*/vscode/.*
4 | .*/javascript/.*
5 | .*/rust/.*
6 | ./.commitlintrc.js
7 |
8 | [include]
9 | ./lib
10 | ./bin/telegram-typings
11 |
12 | [libs]
13 | ./flow
14 | ./flow-typed
15 |
16 | [lints]
17 |
18 | [options]
19 | all=true
20 | traces=3
21 | emoji=true
22 | suppress_comment=\\(.\\|\n\\)*\\$FlowIssue
23 | suppress_comment=\\(.\\|\n\\)*\\$FlowDisable
24 |
25 | [strict]
26 |
27 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/Bug_report.md:
--------------------------------------------------------------------------------
1 | ---
2 | name: Bug report
3 | about: Create a report to help us improve
4 |
5 | ---
6 |
7 | **Describe the bug**
8 | A clear and concise description of what the bug is.
9 |
10 | **To Reproduce**
11 | Steps to reproduce the behavior:
12 | 1. Go to '...' (sandbox)
13 | 2. Open devtools/console
14 | 3. Scroll down to '....'
15 | 4. See error
16 |
17 | **Expected behavior**
18 | A clear and concise description of what you expected to happen.
19 |
20 | **Screenshots**
21 | If applicable, add screenshots to help explain your problem.
22 |
23 | **Desktop (please complete the following information):**
24 | - OS: [e.g. iOS]
25 | - Browser [e.g. chrome, safari]
26 | - Typescript or Flow version
27 | - Telegram-typings version [e.g. 22]
28 |
29 | **Additional context**
30 | Add any other context about the problem here.
31 |
--------------------------------------------------------------------------------
/.github/ISSUE_TEMPLATE/Feature_request.md:
--------------------------------------------------------------------------------
1 | ---
2 | name: Feature request
3 | about: Suggest an idea for this project
4 |
5 | ---
6 |
7 | **Is your feature request related to a problem? Please describe.**
8 | A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
9 |
10 | **Describe the solution you'd like**
11 | A clear and concise description of what you want to happen.
12 |
13 | **Describe alternatives you've considered**
14 | A clear and concise description of any alternative solutions or features you've considered.
15 |
16 | **Additional context**
17 | Add any other context or screenshots about the feature request here.
18 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 |
2 | # Created by https://www.gitignore.io/api/node,windows,macos,linux
3 |
4 | ### Linux ###
5 | *~
6 |
7 | # temporary files which can be created if a process still has a handle open of a deleted file
8 | .fuse_hidden*
9 |
10 | # KDE directory preferences
11 | .directory
12 |
13 | # Linux trash folder which might appear on any partition or disk
14 | .Trash-*
15 |
16 | # .nfs files are created when an open file is removed but is still being accessed
17 | .nfs*
18 |
19 | ### macOS ###
20 | *.DS_Store
21 | .AppleDouble
22 | .LSOverride
23 |
24 | # Icon must end with two \r
25 | Icon
26 |
27 | # Thumbnails
28 | ._*
29 |
30 | # Files that might appear in the root of a volume
31 | .DocumentRevisions-V100
32 | .fseventsd
33 | .Spotlight-V100
34 | .TemporaryItems
35 | .Trashes
36 | .VolumeIcon.icns
37 | .com.apple.timemachine.donotpresent
38 |
39 | # Directories potentially created on remote AFP share
40 | .AppleDB
41 | .AppleDesktop
42 | Network Trash Folder
43 | Temporary Items
44 | .apdisk
45 |
46 | ### Node ###
47 | # Logs
48 | logs
49 | *.log
50 | npm-debug.log*
51 | yarn-debug.log*
52 | yarn-error.log*
53 |
54 | # Runtime data
55 | pids
56 | *.pid
57 | *.seed
58 | *.pid.lock
59 |
60 | # Directory for instrumented libs generated by jscoverage/JSCover
61 | lib-cov
62 |
63 | # Coverage directory used by tools like istanbul
64 | coverage
65 |
66 | # nyc test coverage
67 | .nyc_output
68 |
69 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files)
70 | .grunt
71 |
72 | # Bower dependency directory (https://bower.io/)
73 | bower_components
74 |
75 | # node-waf configuration
76 | .lock-wscript
77 |
78 | # Compiled binary addons (http://nodejs.org/api/addons.html)
79 | build/Release
80 |
81 | # Dependency directories
82 | node_modules/
83 | jspm_packages/
84 |
85 | # Typescript v1 declaration files
86 | typings/
87 |
88 | # Optional npm cache directory
89 | .npm
90 |
91 | # Optional eslint cache
92 | .eslintcache
93 |
94 | # Optional REPL history
95 | .node_repl_history
96 |
97 | # Output of 'npm pack'
98 | *.tgz
99 |
100 | # Yarn Integrity file
101 | .yarn-integrity
102 |
103 | # dotenv environment variables file
104 | .env
105 |
106 |
107 | ### Windows ###
108 | # Windows thumbnail cache files
109 | Thumbs.db
110 | ehthumbs.db
111 | ehthumbs_vista.db
112 |
113 | # Folder config file
114 | Desktop.ini
115 |
116 | # Recycle Bin used on file shares
117 | $RECYCLE.BIN/
118 |
119 | # Windows Installer files
120 | *.cab
121 | *.msi
122 | *.msm
123 | *.msp
124 |
125 | # Windows shortcuts
126 | *.lnk
127 |
128 | # End of https://www.gitignore.io/api/node,windows,macos,linux
129 |
130 | # Created by https://www.gitignore.io/api/rust
131 |
132 | ### Rust ###
133 | # Generated by Cargo
134 | # will have compiled files and executables
135 | /target/
136 |
137 | # Remove Cargo.lock from gitignore if creating an executable, leave it for libraries
138 | # More information here http://doc.crates.io/guide.html#cargotoml-vs-cargolock
139 | Cargo.lock
140 |
141 | # These are backup files generated by rustfmt
142 | **/*.rs.bk
143 |
144 | # End of https://www.gitignore.io/api/rust
145 |
146 | # Ignore personal .vscode configuration
147 | .vscode
148 |
--------------------------------------------------------------------------------
/.travis.yml:
--------------------------------------------------------------------------------
1 |
2 | language: node_js
3 |
4 | node_js:
5 | - 8
6 |
7 | sudo: false
8 |
9 | script:
10 | - npm test
11 | - npm run build
12 |
13 | # after_success:
14 | # - npm run coverage
15 | # - npm run report
16 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Telegram Bot API typings for Flow, TypeScript and Rust
2 |
3 |    
4 |
5 | This repository contains [Telegram Bot API](https://core.telegram.org/bots/api) typings for [Flow](https://flow.org/), [TypeScript](https://www.typescriptlang.org/) and [Rust](https://www.rust-lang.org/).
6 |
7 | The types are automatically generated for all supported languages from the Telegram Bot API website.
8 |
9 | ## Flow and TypeScript typings
10 |
11 | See [javascript/](javascript/) folder.
12 |
13 | ## Rust typings
14 |
15 | See [rust](rust/) folder.
16 |
17 | ## Contributing
18 |
19 | Source code for the type generation lives under [lib/](lib/) folder.
20 |
21 | ### Setting up local development environment
22 |
23 | To contribute to this project, you will need to have the following tools installed:
24 |
25 | * Rust
26 | * Node v8.x or higher
27 | * npm v5.7.1 or higher
28 |
29 | Once these tools are installed, you can install the required dependencies:
30 |
31 | ```
32 | npm install
33 | cargo install rustfmt --version 0.9.0
34 | ```
35 |
36 | ### Generating new typings
37 |
38 | To generate new types, run the following:
39 |
40 | ```
41 | npm run build
42 | ```
43 |
44 | If the [Telegram Bot API](https://core.telegram.org/bots/api) documentation has not changed, and you haven't done any changes to code, you should not get any diff.
45 |
--------------------------------------------------------------------------------
/bin/telegram-typings:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env node
2 | const run = require('../lib/main')
3 | /* eslint-disable no-console */
4 |
5 | run()
6 | .then(() => console.log('Build success'))
7 | .catch((error) => {
8 | console.error(error)
9 | process.exit(-1)
10 | })
11 |
--------------------------------------------------------------------------------
/changelog.md:
--------------------------------------------------------------------------------
1 |
2 | # [4.0.0-beta](https://github.com/sergeysova/telegram-typings/compare/v3.6.1...v4.0.0-beta) (2018-08-02)
3 |
4 |
5 | ### Bug Fixes
6 |
7 | * Bug in parser, breaking type generation ([ef317f1](https://github.com/sergeysova/telegram-typings/commit/ef317f1))
8 | * Output correct Rust types by skipping method serialization for now ([c0f87e5](https://github.com/sergeysova/telegram-typings/commit/c0f87e5))
9 |
10 |
11 | ### Features
12 |
13 | * Add InputFile manually ([c42fa60](https://github.com/sergeysova/telegram-typings/commit/c42fa60))
14 | * Add missing union types manually ([90b7d82](https://github.com/sergeysova/telegram-typings/commit/90b7d82))
15 | * Add raw support for parsing union types ([fa7cb8b](https://github.com/sergeysova/telegram-typings/commit/fa7cb8b))
16 | * Parse methods as interfaces ([edb35b0](https://github.com/sergeysova/telegram-typings/commit/edb35b0))
17 | * Write method payloads as type aliases for Flowtype ([3b64acf](https://github.com/sergeysova/telegram-typings/commit/3b64acf))
18 | * Write out methods for Flow using function declaration types ([1fb3520](https://github.com/sergeysova/telegram-typings/commit/1fb3520))
19 | * **main:** fetch new version ([756092a](https://github.com/sergeysova/telegram-typings/commit/756092a))
20 |
21 |
22 |
23 |
24 | ## [3.6.1](https://github.com/sergeysova/telegram-typings/compare/v3.6.0...v3.6.1) (2018-05-04)
25 |
26 |
27 | ### Bug Fixes
28 |
29 | * install changelog generation ([e545cd5](https://github.com/sergeysova/telegram-typings/commit/e545cd5))
30 |
31 |
32 | ### Features
33 |
34 | * **main:** upgrade dependencies ([8a2e40c](https://github.com/sergeysova/telegram-typings/commit/8a2e40c))
35 |
36 |
37 |
38 |
39 | # [3.6.0](https://github.com/sergeysova/telegram-typings/compare/v0.3.5-4...v3.6.0) (2018-04-18)
40 |
41 |
42 | ### Features
43 |
44 | * rebuild ([4751295](https://github.com/sergeysova/telegram-typings/commit/4751295))
45 |
46 |
47 |
48 |
49 | ## [0.3.5-4](https://github.com/sergeysova/telegram-typings/compare/v0.3.5-1...v0.3.5-4) (2018-01-26)
50 |
51 |
52 | ### Bug Fixes
53 |
54 | * **@rust:** ignore rust from eslint ([d2bd6d0](https://github.com/sergeysova/telegram-typings/commit/d2bd6d0))
55 | * **builders:** Rust building with enums ([57299d0](https://github.com/sergeysova/telegram-typings/commit/57299d0))
56 | * **builders/flow:** issues of new version of babel/types ([9fbe7a1](https://github.com/sergeysova/telegram-typings/commit/9fbe7a1))
57 | * **builders/rust:** add stub for rust-keywords ([af986f7](https://github.com/sergeysova/telegram-typings/commit/af986f7))
58 | * **builders/rust:** Refactor to fix flow ([4395f5a](https://github.com/sergeysova/telegram-typings/commit/4395f5a))
59 | * **builders/rust:** Resolve rust keywords ([5e24d8c](https://github.com/sergeysova/telegram-typings/commit/5e24d8c))
60 |
61 |
62 | ### Features
63 |
64 | * **builder/rust:** Add simple Rust builder ([c53e283](https://github.com/sergeysova/telegram-typings/commit/c53e283))
65 | * **builders/rust:** Complete rust building ([004da7d](https://github.com/sergeysova/telegram-typings/commit/004da7d))
66 | * **flow-builder:** Build flow types as declare modules ([c443055](https://github.com/sergeysova/telegram-typings/commit/c443055))
67 | * **rust:** Bump version to 3.5.1 ([7d0182d](https://github.com/sergeysova/telegram-typings/commit/7d0182d))
68 |
69 |
70 |
71 |
72 | ## [0.3.5-1](https://github.com/sergeysova/telegram-typings/compare/c42d8d8...v0.3.5-1) (2017-12-27)
73 |
74 |
75 | ### Features
76 |
77 | * Add flow types ([be8293e](https://github.com/sergeysova/telegram-typings/commit/be8293e))
78 | * Build on travis. Ignore package-lock ([a941277](https://github.com/sergeysova/telegram-typings/commit/a941277))
79 | * Parse fields ([c42d8d8](https://github.com/sergeysova/telegram-typings/commit/c42d8d8))
80 |
81 |
82 |
83 |
--------------------------------------------------------------------------------
/flow-typed/npm/@babel/generator_vx.x.x.js:
--------------------------------------------------------------------------------
1 | // flow-typed signature: 24bd8756bfb5781af41decf57a1861bc
2 | // flow-typed version: <>/@babel/generator_v7.0.0-beta.35/flow_v0.61.0
3 |
4 | /**
5 | * This is an autogenerated libdef stub for:
6 | *
7 | * '@babel/generator'
8 | *
9 | * Fill this stub out by replacing all the `any` types.
10 | *
11 | * Once filled out, we encourage you to share your work with the
12 | * community by sending a pull request to:
13 | * https://github.com/flowtype/flow-typed
14 | */
15 |
16 | declare module '@babel/generator' {
17 | declare module.exports: any;
18 | }
19 |
20 | /**
21 | * We include stubs for each file inside this npm package in case you need to
22 | * require those files directly. Feel free to delete any files that aren't
23 | * needed.
24 | */
25 | declare module '@babel/generator/lib/buffer' {
26 | declare module.exports: any;
27 | }
28 |
29 | declare module '@babel/generator/lib/generators/base' {
30 | declare module.exports: any;
31 | }
32 |
33 | declare module '@babel/generator/lib/generators/classes' {
34 | declare module.exports: any;
35 | }
36 |
37 | declare module '@babel/generator/lib/generators/expressions' {
38 | declare module.exports: any;
39 | }
40 |
41 | declare module '@babel/generator/lib/generators/flow' {
42 | declare module.exports: any;
43 | }
44 |
45 | declare module '@babel/generator/lib/generators/index' {
46 | declare module.exports: any;
47 | }
48 |
49 | declare module '@babel/generator/lib/generators/jsx' {
50 | declare module.exports: any;
51 | }
52 |
53 | declare module '@babel/generator/lib/generators/methods' {
54 | declare module.exports: any;
55 | }
56 |
57 | declare module '@babel/generator/lib/generators/modules' {
58 | declare module.exports: any;
59 | }
60 |
61 | declare module '@babel/generator/lib/generators/statements' {
62 | declare module.exports: any;
63 | }
64 |
65 | declare module '@babel/generator/lib/generators/template-literals' {
66 | declare module.exports: any;
67 | }
68 |
69 | declare module '@babel/generator/lib/generators/types' {
70 | declare module.exports: any;
71 | }
72 |
73 | declare module '@babel/generator/lib/generators/typescript' {
74 | declare module.exports: any;
75 | }
76 |
77 | declare module '@babel/generator/lib/index' {
78 | declare module.exports: any;
79 | }
80 |
81 | declare module '@babel/generator/lib/node/index' {
82 | declare module.exports: any;
83 | }
84 |
85 | declare module '@babel/generator/lib/node/parentheses' {
86 | declare module.exports: any;
87 | }
88 |
89 | declare module '@babel/generator/lib/node/whitespace' {
90 | declare module.exports: any;
91 | }
92 |
93 | declare module '@babel/generator/lib/printer' {
94 | declare module.exports: any;
95 | }
96 |
97 | declare module '@babel/generator/lib/source-map' {
98 | declare module.exports: any;
99 | }
100 |
101 | // Filename aliases
102 | declare module '@babel/generator/lib/buffer.js' {
103 | declare module.exports: $Exports<'@babel/generator/lib/buffer'>;
104 | }
105 | declare module '@babel/generator/lib/generators/base.js' {
106 | declare module.exports: $Exports<'@babel/generator/lib/generators/base'>;
107 | }
108 | declare module '@babel/generator/lib/generators/classes.js' {
109 | declare module.exports: $Exports<'@babel/generator/lib/generators/classes'>;
110 | }
111 | declare module '@babel/generator/lib/generators/expressions.js' {
112 | declare module.exports: $Exports<'@babel/generator/lib/generators/expressions'>;
113 | }
114 | declare module '@babel/generator/lib/generators/flow.js' {
115 | declare module.exports: $Exports<'@babel/generator/lib/generators/flow'>;
116 | }
117 | declare module '@babel/generator/lib/generators/index.js' {
118 | declare module.exports: $Exports<'@babel/generator/lib/generators/index'>;
119 | }
120 | declare module '@babel/generator/lib/generators/jsx.js' {
121 | declare module.exports: $Exports<'@babel/generator/lib/generators/jsx'>;
122 | }
123 | declare module '@babel/generator/lib/generators/methods.js' {
124 | declare module.exports: $Exports<'@babel/generator/lib/generators/methods'>;
125 | }
126 | declare module '@babel/generator/lib/generators/modules.js' {
127 | declare module.exports: $Exports<'@babel/generator/lib/generators/modules'>;
128 | }
129 | declare module '@babel/generator/lib/generators/statements.js' {
130 | declare module.exports: $Exports<'@babel/generator/lib/generators/statements'>;
131 | }
132 | declare module '@babel/generator/lib/generators/template-literals.js' {
133 | declare module.exports: $Exports<'@babel/generator/lib/generators/template-literals'>;
134 | }
135 | declare module '@babel/generator/lib/generators/types.js' {
136 | declare module.exports: $Exports<'@babel/generator/lib/generators/types'>;
137 | }
138 | declare module '@babel/generator/lib/generators/typescript.js' {
139 | declare module.exports: $Exports<'@babel/generator/lib/generators/typescript'>;
140 | }
141 | declare module '@babel/generator/lib/index.js' {
142 | declare module.exports: $Exports<'@babel/generator/lib/index'>;
143 | }
144 | declare module '@babel/generator/lib/node/index.js' {
145 | declare module.exports: $Exports<'@babel/generator/lib/node/index'>;
146 | }
147 | declare module '@babel/generator/lib/node/parentheses.js' {
148 | declare module.exports: $Exports<'@babel/generator/lib/node/parentheses'>;
149 | }
150 | declare module '@babel/generator/lib/node/whitespace.js' {
151 | declare module.exports: $Exports<'@babel/generator/lib/node/whitespace'>;
152 | }
153 | declare module '@babel/generator/lib/printer.js' {
154 | declare module.exports: $Exports<'@babel/generator/lib/printer'>;
155 | }
156 | declare module '@babel/generator/lib/source-map.js' {
157 | declare module.exports: $Exports<'@babel/generator/lib/source-map'>;
158 | }
159 |
--------------------------------------------------------------------------------
/flow-typed/npm/@babel/types_v7.0.x.js:
--------------------------------------------------------------------------------
1 | // import { numberTypeAnnotation } from "@babel/types/lib/builders/generated";
2 |
3 | // flow-typed signature: 29daf43d438bce142dd0df073cf3d87d
4 | // flow-typed version: <>/@babel/types_v7.0.0-beta.35/flow_v0.61.0
5 |
6 | /**
7 | * This is an autogenerated libdef stub for:
8 | *
9 | * '@babel/types'
10 | *
11 | * Fill this stub out by replacing all the `any` types.
12 | *
13 | * Once filled out, we encourage you to share your work with the
14 | * community by sending a pull request to:
15 | * https://github.com/flowtype/flow-typed
16 | */
17 |
18 | declare module '@babel/types' {
19 | declare module.exports: any;
20 | }
21 |
--------------------------------------------------------------------------------
/flow-typed/npm/cheerio_v1.0.x.js:
--------------------------------------------------------------------------------
1 | // flow-typed signature: 5c7248937eba250b209acc675dabd4ac
2 | // flow-typed version: <>/cheerio_v1.0.0-rc.2/flow_v0.61.0
3 |
4 | /**
5 | * This is an autogenerated libdef stub for:
6 | *
7 | * 'cheerio'
8 | *
9 | * Fill this stub out by replacing all the `any` types.
10 | *
11 | * Once filled out, we encourage you to share your work with the
12 | * community by sending a pull request to:
13 | * https://github.com/flowtype/flow-typed
14 | */
15 |
16 | type $Spread = /* ::{
17 | ...$Exact,
18 | ...$Exact,
19 | }
20 | type noop1 = */ A & B
21 |
22 | declare module 'cheerio' {
23 | declare type Cheerio = {|
24 | [index: number]: CheerioElement,
25 | length: number,
26 |
27 | attr: (name: string) => string,
28 |
29 | data(name?: string, value?: any): any,
30 |
31 | val(value?: string): Cheerio,
32 | removeAttr(name: string): Cheerio,
33 | has(selector: string | CheerioElement): Cheerio,
34 |
35 | hasClass(className: string): boolean,
36 | addClass(classNames: string): Cheerio,
37 |
38 | removeClass(className?: string | (index: number, className: string) => string): Cheerio,
39 |
40 | toggleClass(className: string, toggleSwitch?: boolean): Cheerio,
41 | toggleClass(toggleSwitch?: boolean): Cheerio,
42 | toggleClass(func: (index: number, className: string, toggleSwitch: boolean) => string, toggleSwitch?: boolean): Cheerio,
43 |
44 | is(selector: string | CheerioElement | CheerioElement[] | Cheerio | (index: number, element: CheerioElement) => boolean): boolean,
45 |
46 | // Form
47 | serialize(): string,
48 | serializeArray(): { name: string, value: string }[],
49 |
50 | // Traversing
51 |
52 | find(selector: string | Cheerio): Cheerio,
53 |
54 | parent(selector?: string): Cheerio,
55 | parents(selector?: string): Cheerio,
56 | parentsUntil(selector?: string | CheerioElement | Cheerio, filter?: string): Cheerio,
57 |
58 | prop(name: string): any,
59 | prop(name: string, value: any): Cheerio,
60 |
61 | closest(): Cheerio,
62 | closest(selector: string): Cheerio,
63 |
64 | next(selector?: string): Cheerio,
65 | nextAll(selector?: string): Cheerio,
66 |
67 | nextUntil(selector?: string | CheerioElement | Cheerio, filter?: string): Cheerio,
68 |
69 | prev(selector?: string): Cheerio,
70 | prevAll(selector?: string): Cheerio,
71 | prevUntil(selector?: string | CheerioElement | Cheerio, filter?: string): Cheerio,
72 | slice(start: number, end?: number): Cheerio,
73 | siblings(selector?: string): Cheerio,
74 |
75 | children(selector?: string): Cheerio,
76 | contents(): Cheerio,
77 |
78 | each(func: (index: number, element: CheerioElement) => any): Cheerio,
79 | map(func: (index: number, element: CheerioElement) => any): Cheerio,
80 |
81 | filter(selector: string | Cheerio | CheerioElement | CheerioElement[]): Cheerio,
82 | filter(func: (index: number, element: CheerioElement) => boolean): Cheerio,
83 |
84 | not(selector: string | Cheerio | CheerioElement): Cheerio,
85 | not(func: (index: number, element: CheerioElement) => boolean): Cheerio,
86 |
87 | first(): Cheerio,
88 | last(): Cheerio,
89 |
90 | eq(index: number): Cheerio,
91 | get(index?: number): string[] | CheerioElement | CheerioElement[],
92 | index(selector?: string | Cheerio): number,
93 | end(): Cheerio,
94 | add(selectorOrHtml: string | CheerioElement | CheerioElement[] | Cheerio, context?: Document): Cheerio,
95 | addBack(filter?: string): Cheerio,
96 |
97 | // Manipulation
98 | appendTo(target: Cheerio): Cheerio,
99 | prependTo(target: Cheerio): Cheerio,
100 | append(content: string | Document | Document [] | Cheerio, ...contents: any[]): Cheerio,
101 | prepend(content: string | Document | Document[] | Cheerio, ...contents: any[]): Cheerio,
102 | after(content: string | Document | Document[] | Cheerio, ...contents: any[]): Cheerio,
103 |
104 | insertAfter(content: string | Document | Cheerio): Cheerio,
105 | before(content: string | Document | Document[] | Cheerio, ...contents: any[]): Cheerio,
106 | insertBefore(content: string | Document | Cheerio): Cheerio,
107 | remove(selector?: string): Cheerio,
108 | replaceWith(content: string | CheerioElement | CheerioElement[] | Cheerio | () => Cheerio): Cheerio,
109 |
110 | empty(): Cheerio,
111 |
112 |
113 | html: () => string | (html: string) => Cheerio,
114 | text: () => string | (text: string) => Cheerio,
115 |
116 | // See https://github.com/cheeriojs/cheerio/issues/731
117 | /*wrap(content: string): Cheerio,
118 | wrap(content: Document): Cheerio,
119 | wrap(content: Cheerio): Cheerio,*/
120 |
121 | css(propertyName: string): string,
122 | css(propertyNames: string[]): string[],
123 | css(propertyName: string, value: string): Cheerio,
124 | css(propertyName: string, value: number): Cheerio,
125 | css(propertyName: string, func: (index: number, value: string) => string): Cheerio,
126 | css(propertyName: string, func: (index: number, value: string) => number): Cheerio,
127 | css(properties: Object): Cheerio,
128 |
129 | // Rendering
130 |
131 | // Miscellaneous
132 |
133 | clone(): Cheerio,
134 |
135 | // Not Documented
136 |
137 | toArray(): CheerioElement[],
138 | |}
139 |
140 | declare type CheerioElement = {|
141 | // Document References
142 | // Node Console
143 | tagName: string,
144 | type: string,
145 | name: string,
146 | attribs: { [attr: string]: string },
147 | children: CheerioElement[],
148 | childNodes: CheerioElement[],
149 | lastChild: CheerioElement,
150 | firstChild: CheerioElement,
151 | next: CheerioElement,
152 | nextSibling: CheerioElement,
153 | prev: CheerioElement,
154 | previousSibling: CheerioElement,
155 | parent: CheerioElement,
156 | parentNode: CheerioElement,
157 | nodeValue: string,
158 | data?: string,
159 | |}
160 |
161 | declare type CheerioOptionsInterface = {|
162 | // Document References
163 | // Cheerio https://github.com/cheeriojs/cheerio
164 | // HTMLParser2 https://github.com/fb55/htmlparser2/wiki/Parser-options
165 | // DomHandler https://github.com/fb55/DomHandler
166 |
167 | xmlMode?: boolean,
168 | decodeEntities?: boolean,
169 | lowerCaseTags?: boolean,
170 | lowerCaseAttributeNames?: boolean,
171 | recognizeCDATA?: boolean,
172 | recognizeSelfClosing?: boolean,
173 | normalizeWhitespace?: boolean,
174 | |}
175 |
176 | declare type CheerioSelector =
177 | | (selector: string | Cheerio | CheerioElement) => Cheerio
178 | | (selector: string | Cheerio | CheerioElement, context: string | CheerioElement | CheerioElement[] | Cheerio, root: string) => Cheerio
179 |
180 |
181 | declare type CheerioStatic = {|
182 | (selector: string | Cheerio | CheerioElement): Cheerio,
183 | // Document References
184 | // Cheerio https://github.com/cheeriojs/cheerio
185 | // JQuery http://api.jquery.com
186 | xml(): string,
187 | root(): Cheerio,
188 | contains(container: CheerioElement, contained: CheerioElement): boolean,
189 | parseHTML(data: string, context?: Document, keepScripts?: boolean): Document[],
190 |
191 | html(options?: CheerioOptionsInterface): string,
192 | html(selector: string | Cheerio | CheerioElement, options?: CheerioOptionsInterface): string,
193 | |}
194 |
195 | declare type CheerioAPI = $Spread
199 |
200 | declare module.exports: CheerioAPI;
201 | }
202 |
--------------------------------------------------------------------------------
/flow-typed/npm/debug_v3.x.x.js:
--------------------------------------------------------------------------------
1 | // flow-typed signature: da5374f88debab76c20fc67be7295ba7
2 | // flow-typed version: da30fe6876/debug_v3.x.x/flow_>=v0.28.x
3 |
4 | declare module "debug" {
5 | declare type Debugger = {
6 | (...args: Array): void,
7 | (formatter: string, ...args: Array): void,
8 | (err: Error, ...args: Array): void,
9 | enabled: boolean,
10 | log: () => {},
11 | namespace: string
12 | };
13 |
14 | declare module.exports: (namespace: string) => Debugger;
15 |
16 | declare var names: Array;
17 | declare var skips: Array;
18 | declare var colors: Array;
19 |
20 | declare function disable(): void;
21 | declare function enable(namespaces: string): void;
22 | declare function enabled(name: string): boolean;
23 | declare function humanize(): void;
24 | declare function useColors(): boolean;
25 | declare function log(): void;
26 |
27 | declare var formatters: {
28 | [formatter: string]: () => {}
29 | };
30 | }
31 |
--------------------------------------------------------------------------------
/flow-typed/npm/node-fetch_v1.x.x.js:
--------------------------------------------------------------------------------
1 | // flow-typed signature: 284e255a331cbe00e3ddf88897c9452d
2 | // flow-typed version: 7e7beb7540/node-fetch_v1.x.x/flow_>=v0.44.x
3 |
4 | declare module 'node-fetch' {
5 | declare export class Request mixins Body {
6 | constructor(input: string | Request, init?: RequestInit): this;
7 | method: string;
8 | url: string;
9 | headers: Headers;
10 | context: RequestContext;
11 | referrer: string;
12 | redirect: RequestRedirect;
13 |
14 | // node-fetch extensions
15 | compress: boolean;
16 | agent: http$Agent;
17 | counter: number;
18 | follow: number;
19 | hostname: string;
20 | protocol: string;
21 | port: number;
22 | timeout: number;
23 | size: number
24 | }
25 |
26 | declare type HeaderObject = {
27 | [index: string]: string
28 | }
29 |
30 | declare interface RequestInit {
31 | method?: string,
32 | headers?: HeaderObject,
33 | body?: BodyInit,
34 | redirect?: RequestRedirect,
35 |
36 | // node-fetch extensions
37 | timeout?: number,
38 | compress?: boolean,
39 | size?: number,
40 | agent?: http$Agent,
41 | follow?: number
42 | }
43 |
44 | declare type RequestContext =
45 | 'audio' | 'beacon' | 'cspreport' | 'download' | 'embed' |
46 | 'eventsource' | 'favicon' | 'fetch' | 'font' | 'form' | 'frame' |
47 | 'hyperlink' | 'iframe' | 'image' | 'imageset' | 'import' |
48 | 'internal' | 'location' | 'manifest' | 'object' | 'ping' | 'plugin' |
49 | 'prefetch' | 'script' | 'serviceworker' | 'sharedworker' |
50 | 'subresource' | 'style' | 'track' | 'video' | 'worker' |
51 | 'xmlhttprequest' | 'xslt';
52 | declare type RequestRedirect = 'follow' | 'error' | 'manual';
53 |
54 | declare export class Headers {
55 | append(name: string, value: string): void;
56 | delete(name: string): void;
57 | get(name: string): string;
58 | getAll(name: string): Array;
59 | has(name: string): boolean;
60 | set(name: string, value: string): void;
61 | forEach(callback: (value: string, name: string) => void): void
62 | }
63 |
64 | declare export class Body {
65 | bodyUsed: boolean;
66 | body: stream$Readable;
67 | json(): Promise;
68 | json(): Promise;
69 | text(): Promise;
70 | buffer(): Promise
71 | }
72 |
73 | declare export class Response mixins Body {
74 | constructor(body?: BodyInit, init?: ResponseInit): this;
75 | error(): Response;
76 | redirect(url: string, status: number): Response;
77 | type: ResponseType;
78 | url: string;
79 | status: number;
80 | ok: boolean;
81 | size: number;
82 | statusText: string;
83 | timeout: number;
84 | headers: Headers;
85 | clone(): Response
86 | }
87 |
88 | declare type ResponseType =
89 | | 'basic'
90 | | 'cors'
91 | | 'default'
92 | | 'error'
93 | | 'opaque'
94 | | 'opaqueredirect';
95 |
96 | declare interface ResponseInit {
97 | status: number,
98 | statusText?: string,
99 | headers?: HeaderInit
100 | }
101 |
102 | declare type HeaderInit = Headers | Array;
103 | declare type BodyInit = string;
104 |
105 | declare export default function fetch(url: string | Request, init?: RequestInit): Promise
106 | }
107 |
--------------------------------------------------------------------------------
/flow-typed/npm/rust-keywords_v1.x.x.js:
--------------------------------------------------------------------------------
1 | // flow-typed signature: 1932a49479a06ed0af538391abd190bc
2 | // flow-typed version: <>/rust-keywords_v1.0.1/flow_v0.61.0
3 |
4 | /**
5 | * This is an autogenerated libdef stub for:
6 | *
7 | * 'rust-keywords'
8 | *
9 | * Fill this stub out by replacing all the `any` types.
10 | *
11 | * Once filled out, we encourage you to share your work with the
12 | * community by sending a pull request to:
13 | * https://github.com/flowtype/flow-typed
14 | */
15 |
16 | declare module 'rust-keywords' {
17 | declare module.exports: Array;
18 | }
19 |
--------------------------------------------------------------------------------
/javascript/index.js:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/sergeysova/telegram-typings/840f78b12c77e2c935ddf0bf90da173e51cdc5ff/javascript/index.js
--------------------------------------------------------------------------------
/javascript/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "telegram-typings",
3 | "version": "5.0.0",
4 | "description": "Telegram typings for TypeScript and Flowtype to create bots",
5 | "main": "index.js",
6 | "typings": "telegram-typings.d.ts",
7 | "repository": {
8 | "type": "git",
9 | "url": "git+https://github.com/sergeysova/telegram-typings.git"
10 | },
11 | "keywords": [
12 | "telegram",
13 | "bots",
14 | "typings",
15 | "types",
16 | "flow",
17 | "type",
18 | "typescript",
19 | "script",
20 | "build",
21 | "generate"
22 | ],
23 | "author": "Sergey Sova (https://sergeysova.com)",
24 | "license": "MIT",
25 | "bugs": {
26 | "url": "https://github.com/sergeysova/telegram-typings/issues"
27 | },
28 | "homepage": "https://github.com/sergeysova/telegram-typings#readme",
29 | "dependencies": {}
30 | }
31 |
--------------------------------------------------------------------------------
/javascript/readme.md:
--------------------------------------------------------------------------------
1 | # telegram-typings
2 |
3 | Full types parsed from core.telegram.org/bots/api for TypeScript and Flowtype
4 |
5 | ## Installation
6 |
7 | Just install it as your dependency and use
8 |
9 | ```bash
10 | npm install --save telegram-typings
11 | ```
12 |
13 | ```ts
14 | // typescript
15 | import { User, Chat, Voice } from 'telegram-typings'
16 | ```
17 |
18 | ### Flow
19 |
20 | ```bash
21 | # Search in flow-typed
22 | flow-typed search telegram-typings
23 |
24 | # if not found, copy content of ./javascript/index.js.flow to your flow-typed
25 | wget https://raw.githubusercontent.com/sergeysova/telegram-typings/master/javascript/index.js.flow -O ./flow-typed/npm/telegram-typings_vx.x.x.js
26 | # next use as normal module
27 | ```
28 |
29 | ```js
30 | // flow
31 | import type { User, Chat, Voice } from 'telegram-typings'
32 | ```
33 |
--------------------------------------------------------------------------------
/lib/builders/abstract-js.js:
--------------------------------------------------------------------------------
1 | const { BaseBuilder } = require('./base')
2 | /*:: const { Union, Field } = require('../store')*/
3 |
4 |
5 | class AbstractJsBuilder extends BaseBuilder {
6 | buildFloat() {
7 | return this.buildInteger()
8 | }
9 |
10 | buildCommentBlock(lines/*: string[]*/) {
11 | return [{
12 | type: 'CommentBlock',
13 | value: `*\n${lines.filter((e) => !!e).map((line) => ` * ${line}`).join('\n')}\n `,
14 | }]
15 | }
16 |
17 | buildCommentSeeLink(link/*: string*/) {
18 | return `@see ${link}`
19 | }
20 | }
21 |
22 | module.exports = {
23 | AbstractJsBuilder,
24 | }
25 |
26 |
--------------------------------------------------------------------------------
/lib/builders/base.js:
--------------------------------------------------------------------------------
1 | const { Interface, Method, Union /*::, Store, */ } = require('../store')
2 |
3 |
4 | const ARRAY_OF_LITERAL = 'Array of '
5 | const INTERSECTION_LITERAL = ' and'
6 | const UNION_LITERAL = ' or'
7 |
8 | /**
9 | * Class for creating base types.
10 | */
11 | class BaseBuilder {
12 | /* :: store: Store */
13 |
14 | /**
15 | * Creates a new BaseBuilder instance
16 | * @param {Store} store
17 | */
18 | constructor(store/*: Store */) {
19 | this.store = store
20 | }
21 |
22 | /**
23 | * Converts an instance of a Type to the babel AST
24 | */
25 | buildInterface(object/*: Interface*/) { // eslint-disable-line no-unused-vars
26 | throw new TypeError('The `buildInterface` method should be overriden')
27 | }
28 |
29 | /**
30 | * Converts an instance of a Type to the babel AST
31 | */
32 | buildMethod(object/*: Method*/) { // eslint-disable-line no-unused-vars
33 | throw new TypeError('The `buildMethod` method should be overriden')
34 | }
35 |
36 | /**
37 | * Converts an instance of a Union to the babel AST
38 | */
39 | buildUnion(object/*: Union*/) { // eslint-disable-line no-unused-vars
40 | throw new TypeError('The `buildUnion` method should be overriden')
41 | }
42 |
43 | /**
44 | * Wraps a type with the AST array node
45 | */
46 | buildArrayOfType(type/*: string */) { // eslint-disable-line no-unused-vars
47 | throw new TypeError('The `buildArrayOfType` method should be overriden')
48 | }
49 |
50 | /**
51 | * Wraps a type with the AST union node
52 | */
53 | buildUnionOfTypes(types/*: Array */) { // eslint-disable-line no-unused-vars
54 | throw new TypeError('The `buildUnionOfTypes` method should be overriden')
55 | }
56 |
57 | /**
58 | * Wraps a type with the AST union node
59 | */
60 | // eslint-disable-next-line no-unused-vars
61 | buildUnionOfTypesFromLiteral(types/*: string */, separator/*: string */) {
62 | throw new TypeError('The `buildUnionOfTypesFromLiteral` method should be overriden')
63 | }
64 |
65 | /**
66 | * Create root ast for file
67 | */
68 | buildProgram(body/*: mixed*/) { // eslint-disable-line no-unused-vars
69 | throw new TypeError('The `buildProgram` should be overriden')
70 | }
71 |
72 | /**
73 | * Wrap statements to a module
74 | */
75 | buildModule(interfaces/*: any[]*/) { // eslint-disable-line no-unused-vars
76 | throw new TypeError('The `buildModule` method should be overriden')
77 | }
78 |
79 | /**
80 | * Convert lines of comments to code
81 | */
82 | buildCommentBlock(lines/*: string[]*/) { // eslint-disable-line no-unused-vars
83 | throw new TypeError('The `buildCommentBlock` method should be overriden')
84 | }
85 |
86 | /**
87 | * Convert link to see comment
88 | */
89 | buildCommentSeeLink(link/*: string*/) { // eslint-disable-line no-unused-vars
90 | throw new TypeError('The `buildCommentSeeLink` method should be overriden')
91 | }
92 |
93 | /**
94 | * Convert description and links to comment code
95 | */
96 | buildComments(description/*: string*/ = '', links/*: string[]*/ = []) {
97 | const lines = description.replace(/(.{1,72}\s)\s*?/g, '\n$1').split('\n')
98 |
99 | return this.buildCommentBlock(lines.concat(links.map(this.buildCommentSeeLink)))
100 | }
101 |
102 | /**
103 | * Create source code from store of types
104 | */
105 | build()/*: { code: string }*/ {
106 | const types = this.iterateOverTypes()
107 |
108 | return this.buildProgram(this.buildModule(types))
109 | // return generate(bt.program(this.buildModule(types), [], 'module'))
110 | }
111 |
112 | /**
113 | * Convert list of types to list of AST nodes
114 | * Apply only non native types
115 | */
116 | iterateOverTypes() {
117 | return [...this.store.iterate()]
118 | .filter((object) => !object.native)
119 | .map((object) => {
120 | if (object instanceof Interface) {
121 | return this.buildInterface(object)
122 | }
123 | if (object instanceof Method) {
124 | return this.buildMethod(object)
125 | }
126 |
127 | if (object instanceof Union) {
128 | const type = this.store.get(object.name) || { variants: [] }
129 |
130 | // $FlowDisable
131 | const callbackfn = (name) => !type.variants.includes(name)
132 | const unknown = object.variants.filter(callbackfn)
133 |
134 | if (unknown.length > 0) {
135 | throw new TypeError(`${unknown.join(', ')} not found in the store`)
136 | }
137 |
138 | return this.buildUnion(object)
139 | }
140 |
141 | throw new TypeError('Builder supports only Union and Interface objects')
142 | })
143 | .filter((ast) => !!ast)
144 | }
145 |
146 | buildFloat() {
147 | return 'number'
148 | }
149 |
150 | buildInteger() {
151 | return 'integer'
152 | }
153 |
154 | buildString() {
155 | return 'string'
156 | }
157 |
158 | buildBoolean() {
159 | return 'boolean'
160 | }
161 |
162 | buildBooleanLiteral(value/*: boolean*/) {
163 | return value ? 'true' : 'false'
164 | }
165 |
166 | buildReference(type/*: any*/)/*: any*/ {
167 | return type
168 | }
169 |
170 | /**
171 | * Create AST node to set into property name
172 | * @param {string} name Name of type in Store. Can be recursive `Array of TYPE`
173 | */
174 | buildNativeType(name/*: string | Array*/) {
175 | if (Array.isArray(name)) {
176 | return this.buildUnionOfTypes(name)
177 | }
178 |
179 | if (name.indexOf(ARRAY_OF_LITERAL) === 0) {
180 | return this.buildArrayOfType(name)
181 | }
182 |
183 | if (name.includes(INTERSECTION_LITERAL)) {
184 | return this.buildUnionOfTypesFromLiteral(name, INTERSECTION_LITERAL)
185 | }
186 |
187 | if (name.includes(UNION_LITERAL)) {
188 | return this.buildUnionOfTypesFromLiteral(name, UNION_LITERAL)
189 | }
190 |
191 | if (name.includes(',')) {
192 | return this.buildUnionOfTypes(name.split(',').map((s) => s.trim()))
193 | }
194 |
195 | const type = this.store.get(name)
196 |
197 | if (!type) {
198 | throw new TypeError(`${name} not found in store`)
199 | }
200 |
201 | if (type.native) {
202 | switch (type.name.toLowerCase()) {
203 | case 'integer':
204 | return this.buildInteger()
205 |
206 | case 'float':
207 | case 'float number':
208 | return this.buildFloat()
209 |
210 | case 'string':
211 | return this.buildString()
212 |
213 | case 'boolean':
214 | return this.buildBoolean()
215 |
216 | case 'true':
217 | return this.buildBooleanLiteral(true)
218 |
219 | default:
220 | return this.buildReference(type.name)
221 | }
222 | }
223 |
224 | return this.buildReference(type.build())
225 | }
226 |
227 | static build(store/*: Store */) {
228 | return new this(store).build()
229 | }
230 | }
231 |
232 | /**
233 | * Create CommentBlock AST node
234 | */
235 | function commentBlock(value/*: string*/) {
236 | return {
237 | type: 'CommentBlock',
238 | value,
239 | }
240 | }
241 |
242 | /**
243 | * Split description to lines add return AST node
244 | */
245 | function smartComment(description/*:string*/ = '', links/*: string[]*/ = []) {
246 | const descriptionLines = description.replace(/(.{1,72}\s)\s*?/g, '\n * $1')
247 | const linksLines = links.reduce((acc, link) => (
248 | `${acc} * @see ${link}\n`
249 | ), '')
250 |
251 | return commentBlock(`*${descriptionLines}\n${linksLines} `)
252 | }
253 |
254 | module.exports = {
255 | BaseBuilder,
256 | commentBlock,
257 | smartComment,
258 | ARRAY_OF_LITERAL,
259 | }
260 |
--------------------------------------------------------------------------------
/lib/builders/flow.js:
--------------------------------------------------------------------------------
1 | const bt = require('@babel/types')
2 | const { default: generate } = require('@babel/generator')
3 | const { AbstractJsBuilder } = require('./abstract-js')
4 | const { ARRAY_OF_LITERAL } = require('./base')
5 | /*:: const { Union, Interface, Method, Field } = require('../store')*/
6 |
7 | function methodNameToPayloadName(methodName) {
8 | return `${methodName[0].toUpperCase()}${methodName.slice(1)}Payload`
9 | }
10 |
11 | class FlowBuilder extends AbstractJsBuilder {
12 | buildUnion(object/*: Union*/) {
13 | const variants = object.variants.map((name) => bt.genericTypeAnnotation(bt.identifier(name)))
14 | const ast = bt.declareTypeAlias(
15 | bt.identifier(object.name),
16 | undefined,
17 | bt.unionTypeAnnotation(variants)
18 | )
19 |
20 | ast.leadingComments = this.buildComments(object.description || '', object.links)
21 | return ast
22 | }
23 |
24 | buildUnionOfTypes(types/*: Array*/) {
25 | return bt.unionTypeAnnotation(types.map((name) => this.buildNativeType(name)))
26 | }
27 |
28 | buildUnionOfTypesFromLiteral(types/*: string*/, separator/*: string*/) {
29 | const reduced = types.split(separator).reduce((r, v) => [...r, v.trim()], [])
30 |
31 | return bt.arrayTypeAnnotation(this.buildNativeType(reduced))
32 | }
33 |
34 | buildInterface(object/*: Interface*/) {
35 | const fields = Object.keys(object.fields)
36 | .map((fieldName) => this.buildField(object.fields[fieldName]))
37 | const ast = bt.declareTypeAlias(
38 | bt.identifier(object.name),
39 | undefined,
40 | bt.objectTypeAnnotation(fields),
41 | )
42 |
43 | ast.leadingComments = this.buildComments(object.description || '', object.links)
44 |
45 | return ast
46 | }
47 |
48 | buildMethod(object/*: Method*/) {
49 | const args = Object.keys(object.fields)
50 | .map((fieldName) => this.buildField(object.fields[fieldName]))
51 |
52 | const ast = bt.declareTypeAlias(
53 | bt.identifier(methodNameToPayloadName(object.name)),
54 | undefined,
55 | bt.objectTypeAnnotation(args),
56 | )
57 |
58 | ast.leadingComments = this.buildComments(object.description || '', object.links)
59 |
60 | return ast
61 | }
62 |
63 | buildField(object/*: Field*/) {
64 | const ast = bt.objectTypeProperty(
65 | bt.identifier(object.name),
66 | this.buildNativeType(object.type)
67 | )
68 |
69 | ast.optional = object.optional
70 | ast.leadingComments = this.buildComments(object.description || '', object.links)
71 |
72 | return ast
73 | }
74 |
75 | buildArrayOfType(type/*: string*/) {
76 | return bt.arrayTypeAnnotation(this.buildNativeType(type.substr(ARRAY_OF_LITERAL.length)))
77 | }
78 |
79 | buildInteger() {
80 | return bt.numberTypeAnnotation()
81 | }
82 |
83 | buildString() {
84 | return bt.stringTypeAnnotation()
85 | }
86 |
87 | buildBoolean() {
88 | return bt.booleanTypeAnnotation()
89 | }
90 |
91 | buildBooleanLiteral(value/*: boolean*/) {
92 | const ast = bt.booleanLiteralTypeAnnotation(false)
93 |
94 | ast.value = value
95 |
96 | return ast
97 | }
98 |
99 | buildReference(type/*: any*/)/*: any*/ {
100 | return bt.genericTypeAnnotation(bt.identifier(type))
101 | }
102 |
103 | buildModule(types/*: mixed[]*/)/*: mixed[]*/ {
104 | return [bt.declareModule(bt.stringLiteral('telegram-typings'), bt.blockStatement(types))]
105 | }
106 |
107 | buildProgram(body/*: any*/) {
108 | return generate(bt.program(body, [], 'module'))
109 | }
110 | }
111 |
112 | module.exports = {
113 | FlowBuilder,
114 | }
115 |
--------------------------------------------------------------------------------
/lib/builders/rust.js:
--------------------------------------------------------------------------------
1 | const keywords = require('rust-keywords')
2 | const { BaseBuilder, ARRAY_OF_LITERAL } = require('./base')
3 | /*:: const { Union, Interface, Method, Field } = require('../store')*/
4 |
5 |
6 | // const hasLifetime = (typeName) => !(['i64', 'bool', 'f64'].includes(typeName))
7 |
8 | class RustBuilder extends BaseBuilder {
9 | buildFloat() {
10 | return 'f64'
11 | }
12 |
13 | buildInteger() {
14 | return 'i64'
15 | }
16 |
17 | buildString() {
18 | return 'String'
19 | }
20 |
21 | buildBoolean() {
22 | return 'bool'
23 | }
24 |
25 | buildBooleanLiteral(value/*: boolean*/) { // eslint-disable-line no-unused-vars
26 | // Rust don't have value types
27 | return 'bool'
28 | }
29 |
30 | buildReference(type/*: any*/)/*: any*/ {
31 | return `Box<${String(type)}>`
32 | }
33 |
34 | buildArrayOfType(type/*: string*/) {
35 | return `Vec<${this.buildNativeType(type.substr(ARRAY_OF_LITERAL.length))}>`
36 | }
37 |
38 | buildInterface(object/*: Interface*/) {
39 | const fields = Object.keys(object.fields)
40 | .map((fieldName) => this.buildField(object.fields[fieldName]))
41 | // Disabled because not used now, but can be used in future
42 | // const hasLifetimeIn = fields.some((def) => def.indexOf('\'a') !== -1)
43 | const lifetime = '' // !hasLifetimeIn ? '<\'a> ' : ''
44 |
45 | return `${this.buildComments(object.description || '', object.links).split('\n').map((e) => e.trim()).join('\n')}
46 | #[derive(Serialize, Deserialize, Debug, Clone)]
47 | pub struct ${object.name}${lifetime} {
48 | ${fields.join('\n\n ')}
49 | }`
50 | }
51 |
52 | // TODO: Implement method serialization for Rust
53 | buildMethod(object/*: Method*/) { // eslint-disable-line no-unused-vars
54 | return ''
55 | }
56 |
57 | buildUnion(object/*: Union*/) {
58 | return `${this.buildComments(object.description || '', object.links).split('\n').map((e) => e.trim()).join('\n')}
59 | #[derive(Serialize, Deserialize, Debug, Clone)]
60 | pub enum ${object.name} {
61 | ${object.variants.map((vari) => `${vari}(Box<${vari}>)`).join(',\n ')}
62 | }`
63 | }
64 |
65 | buildUnionOfTypes(types/*: Array*/) { // eslint-disable-line no-unused-vars
66 | throw new Error('Unions are not yet supported for Rust')
67 | }
68 |
69 | buildField(object/*: Field*/) {
70 | const type = object.optional
71 | ? `Option<${this.buildNativeType(object.type)}>`
72 | : this.buildNativeType(object.type)
73 | const name = keywords.indexOf(object.name) !== -1
74 | ? `${object.name}_tl`
75 | : object.name
76 | const rename = name !== object.name
77 | ? `#[serde(rename = "${object.name}")]`
78 | : ''
79 | const comments = this.buildComments(object.description || '', object.links)
80 | const lifetime = '' // hasLifetime(this.buildNativeType(object.type)) ? '&\'a ' : ''
81 |
82 | return rename
83 | ? `${comments}\n ${rename}\n pub ${name}: ${lifetime}${type},`
84 | : `${comments}\n pub ${name}: ${lifetime}${type},`
85 | }
86 |
87 | buildModule(types/*: string[]*/) {
88 | return types.join('\n\n')
89 | }
90 |
91 | buildProgram(body/*: any*/) {
92 | return {
93 | code: `#[macro_use]
94 | extern crate serde_derive;
95 | extern crate serde;
96 |
97 | ${body}
98 | `,
99 | }
100 | }
101 |
102 | buildCommentBlock(lines/*: string[]*/) {
103 | return lines.filter((e) => !!e)
104 | .map((line) => ` /// ${line}`).join('\n')
105 | }
106 |
107 | buildCommentSeeLink(link/*: string*/) {
108 | return `See ${link}`
109 | }
110 | }
111 |
112 | module.exports = {
113 | RustBuilder,
114 | }
115 |
--------------------------------------------------------------------------------
/lib/builders/typescript.js:
--------------------------------------------------------------------------------
1 | const bt = require('@babel/types')
2 | const { default: generate } = require('@babel/generator')
3 | const { AbstractJsBuilder } = require('./abstract-js')
4 | const { ARRAY_OF_LITERAL } = require('./base')
5 | /*:: const { Union, Field, Interface, Method } = require('../store')*/
6 |
7 |
8 | class TypeScriptBuilder extends AbstractJsBuilder {
9 | buildUnion(object/*: Union */) {
10 | const ast = bt.exportNamedDeclaration(
11 | bt.tSTypeAliasDeclaration(
12 | bt.identifier(object.name),
13 | undefined,
14 | bt.tSUnionType(object.variants.map((name) => (
15 | bt.tSTypeReference(bt.identifier(name))
16 | )))
17 | ),
18 | [],
19 | )
20 |
21 | ast.leadingComments = this.buildComments(object.description || '', object.links)
22 |
23 | return ast
24 | }
25 |
26 | buildUnionOfTypes(types/*: Array*/) {
27 | // TODO: Build unions with AST builders, not raw strings.
28 | // The architecture between Flow builder and TypeScript builder differs, and we need
29 | // to return a `string` type instead of an AST node from this method
30 | const map = types.map((type) => this.buildNativeType(type)).join(' | ')
31 |
32 | return types.length > 1 ? `(${map})` : map
33 | }
34 |
35 | buildUnionOfTypesFromLiteral(types/*: string*/, separator/*: string*/) {
36 | return this.buildNativeType(types.split(separator).reduce((r, v) => [...r, v.trim()], []))
37 | }
38 |
39 | buildInterface(object/*: Interface*/) {
40 | const fields = Object.keys(object.fields)
41 | .map((fieldName) => this.buildField(object.fields[fieldName]))
42 | const ast = bt.exportNamedDeclaration(
43 | bt.tsInterfaceDeclaration(
44 | bt.identifier(object.name),
45 | undefined,
46 | null,
47 | bt.tsInterfaceBody(fields),
48 | ),
49 | []
50 | )
51 |
52 | ast.leadingComments = this.buildComments(object.description || '', object.links)
53 |
54 | return ast
55 | }
56 |
57 | buildMethod(object /*: Method*/) {
58 | const fields = Object.keys(object.fields)
59 | .map((fieldName) => this.buildField(object.fields[fieldName]))
60 | const ast = bt.exportNamedDeclaration(
61 | bt.tsInterfaceDeclaration(
62 | bt.identifier(object.name),
63 | undefined,
64 | null,
65 | bt.tsInterfaceBody(fields),
66 | ),
67 | []
68 | )
69 |
70 | ast.leadingComments = this.buildComments(object.description || '', object.links)
71 |
72 | return ast
73 | }
74 |
75 | buildField(object/*: Field*/) {
76 | const ast = bt.tsPropertySignature(
77 | bt.identifier(object.name),
78 | bt.tsTypeAnnotation(bt.tsTypeReference(bt.identifier(this.buildNativeType(object.type))))
79 | )
80 |
81 | ast.optional = object.optional
82 | ast.leadingComments = this.buildComments(object.description || '', object.links)
83 |
84 | return ast
85 | }
86 |
87 | buildArrayOfType(type/*: string*/) {
88 | return `${this.buildNativeType(type.substr(ARRAY_OF_LITERAL.length))}[]`
89 | }
90 |
91 | buildInteger() {
92 | return 'number'
93 | }
94 |
95 | buildString() {
96 | return 'string'
97 | }
98 |
99 | buildModule(types/*: mixed[]*/)/*: mixed[]*/ {
100 | return types
101 | }
102 |
103 | buildProgram(body/*: any*/) {
104 | return generate(bt.program(body, [], 'module'))
105 | }
106 | }
107 |
108 | module.exports = {
109 | TypeScriptBuilder,
110 | }
111 |
--------------------------------------------------------------------------------
/lib/main.js:
--------------------------------------------------------------------------------
1 | const path = require('path')
2 | const { writeFileSync } = require('fs')
3 |
4 | const { Store, Interface, Union, Field } = require('./store')
5 | const { addNatives } = require('./native')
6 | const { requestAndParse } = require('./parser')
7 |
8 | const { TypeScriptBuilder } = require('./builders/typescript')
9 | const { FlowBuilder } = require('./builders/flow')
10 | const { RustBuilder } = require('./builders/rust')
11 |
12 |
13 | /* eslint-disable no-console */
14 | const libJavascript = path.resolve(__dirname, '..', 'javascript')
15 | const libRust = path.resolve(__dirname, '..', 'rust', 'src')
16 |
17 | function buildFlow(store/*: Store*/) {
18 | const { code } = FlowBuilder.build(store)
19 |
20 | writeFileSync(path.resolve(libJavascript, 'index.js.flow'), code, { encoding: 'utf8' })
21 | }
22 |
23 | function buildTypeScript(store/*: Store*/) {
24 | const { code } = TypeScriptBuilder.build(store)
25 |
26 | writeFileSync(path.resolve(libJavascript, 'index.d.ts'), code, { encoding: 'utf8' })
27 | }
28 |
29 | function buildRust(store/*: Store*/) {
30 | const { code } = RustBuilder.build(store)
31 |
32 | writeFileSync(path.resolve(libRust, 'lib.rs'), code, { encoding: 'utf8' })
33 | }
34 |
35 | function addBuiltins(store) {
36 | store.add(new Interface('CallbackGame', {
37 | description: 'A placeholder, currently holds no information. Use BotFather to set up your game.',
38 | }))
39 | store.add(new Interface('InputFile', {
40 | description: 'This object represents the contents of a file to be uploaded. '
41 | + 'Must be posted using multipart/form-data in the usual way that files are uploaded via the browser.',
42 | }))
43 | store.add(new Interface('PassportData', {
44 | description: 'Contains information about Telegram Passport data shared with the bot by the user.',
45 | }, {
46 | data: new Field('data', 'Array of EncryptedPassportElement'),
47 | credentials: new Field('credentials', 'EncryptedCredentials'),
48 | }))
49 | store.add(new Interface('EncryptedPassportElement', {
50 | desciption: 'Contains information about documents or other Telegram Passport elements shared with the bot by the user.',
51 | }))
52 | store.add(new Interface('EncryptedCredentials', {
53 | description: 'Contains data required for decrypting and authenticating EncryptedPassportElement.'
54 | + ' See the Telegram Passport Documentation for a complete description of the data decryption'
55 | + ' and authentication processes.',
56 | }))
57 | store.add(new Interface('VoiceChatStarted', {
58 | description: 'This object represents a service message about a voice chat started in the chat. Currently holds no information.',
59 | }))
60 | // TODO: remove after parse UNIONS
61 | store.add(new Union('InputMessageContent', {
62 | description: 'This object represents the content of a message to be sent as a result of an inline query.',
63 | }, [
64 | 'InputTextMessageContent',
65 | 'InputLocationMessageContent',
66 | 'InputVenueMessageContent',
67 | 'InputContactMessageContent',
68 | ]))
69 | store.add(new Union('InputMedia', {
70 | description: 'This object represents the content of a media message to be sent.',
71 | }, [
72 | 'InputMediaPhoto',
73 | 'InputMediaVideo',
74 | 'InputMediaAudio',
75 | 'InputMediaDocument',
76 | 'InputMediaAnimation',
77 | ]))
78 | store.add(new Union('InlineQueryResult', {
79 | description: 'This object represents one result of an inline query',
80 | }, [
81 | 'InlineQueryResultCachedAudio',
82 | 'InlineQueryResultCachedDocument',
83 | 'InlineQueryResultCachedGif',
84 | 'InlineQueryResultCachedMpeg4Gif',
85 | 'InlineQueryResultCachedPhoto',
86 | 'InlineQueryResultCachedSticker',
87 | 'InlineQueryResultCachedVideo',
88 | 'InlineQueryResultCachedVoice',
89 | 'InlineQueryResultArticle',
90 | 'InlineQueryResultAudio',
91 | 'InlineQueryResultContact',
92 | 'InlineQueryResultGame',
93 | 'InlineQueryResultDocument',
94 | 'InlineQueryResultGif',
95 | 'InlineQueryResultLocation',
96 | 'InlineQueryResultMpeg4Gif',
97 | 'InlineQueryResultPhoto',
98 | 'InlineQueryResultVenue',
99 | 'InlineQueryResultVideo',
100 | 'InlineQueryResultVoice',
101 | ]))
102 | store.add(new Union('PassportElementError', {
103 | description: 'This object represents an error in the Telegram Passport element which was submitted that should be resolved by the user',
104 | }, [
105 | 'PassportElementErrorDataField',
106 | 'PassportElementErrorFrontSide',
107 | 'PassportElementErrorReverseSide',
108 | 'PassportElementErrorSelfie',
109 | 'PassportElementErrorFile',
110 | 'PassportElementErrorFiles',
111 | 'PassportElementErrorTranslationFile',
112 | 'PassportElementErrorTranslationFiles',
113 | 'PassportElementErrorUnspecified',
114 | ]))
115 | store.add(new Union('ChatMember', {
116 | description: 'This object contains information about one member of a chat. Currently, the following 6 types of chat members are supported:',
117 | }, [
118 | 'ChatMemberOwner',
119 | 'ChatMemberAdministrator',
120 | 'ChatMemberMember',
121 | 'ChatMemberRestricted',
122 | 'ChatMemberLeft',
123 | 'ChatMemberBanned',
124 | ]))
125 | store.add(new Union('BotCommandScope', {
126 | description: 'This object represents the scope to which bot commands are applied. Currently, the following 7 scopes are supported:',
127 | }, [
128 | 'BotCommandScopeDefault',
129 | 'BotCommandScopeAllPrivateChats',
130 | 'BotCommandScopeAllGroupChats',
131 | 'BotCommandScopeAllChatAdministrators',
132 | 'BotCommandScopeChat',
133 | 'BotCommandScopeChatAdministrators',
134 | 'BotCommandScopeChatMember',
135 | ]))
136 | }
137 |
138 | async function main() {
139 | const store = new Store()
140 |
141 | addNatives(store)
142 | addBuiltins(store)
143 |
144 | await requestAndParse(store)
145 |
146 | buildFlow(store)
147 | buildTypeScript(store)
148 | // buildRust(store)
149 | }
150 |
151 | module.exports = main
152 |
--------------------------------------------------------------------------------
/lib/native.js:
--------------------------------------------------------------------------------
1 | const { Interface/*::, Store*/ } = require('./store')
2 |
3 |
4 | class NativeBoolean extends Interface {
5 | constructor() {
6 | super('Boolean', { native: true }, {})
7 | }
8 | }
9 |
10 | class NativeTrue extends Interface {
11 | constructor() {
12 | super('True', { native: true }, {})
13 | }
14 | }
15 |
16 | class NativeInteger extends Interface {
17 | constructor() {
18 | super('Integer', { native: true }, {})
19 | }
20 | }
21 |
22 | class NativeFloat extends Interface {
23 | constructor() {
24 | super('Float', { native: true }, {})
25 | }
26 | }
27 |
28 | /**
29 | * @see https://core.telegram.org/bots/api#inlinequeryresultlocation
30 | */
31 | class NativeFloatNumber extends Interface {
32 | constructor() {
33 | super('Float number', { native: true }, {})
34 | }
35 | }
36 |
37 | class NativeString extends Interface {
38 | constructor() {
39 | super('String', { native: true }, {})
40 | }
41 | }
42 |
43 | function addNatives(store/*: Store*/) {
44 | store.add(new NativeBoolean())
45 | store.add(new NativeTrue())
46 | store.add(new NativeInteger())
47 | store.add(new NativeFloat())
48 | store.add(new NativeFloatNumber())
49 | store.add(new NativeString())
50 | }
51 |
52 | module.exports = {
53 | NativeBoolean,
54 | NativeTrue,
55 | NativeInteger,
56 | NativeFloat,
57 | NativeFloatNumber,
58 | NativeString,
59 |
60 | addNatives,
61 | }
62 |
--------------------------------------------------------------------------------
/lib/parser.js:
--------------------------------------------------------------------------------
1 | const cheerio = require('cheerio')
2 | /*:: import type { Cheerio, CheerioStatic, CheerioElement } from 'cheerio'*/
3 | const { default: fetch } = require('node-fetch')
4 | const debug = require('debug')('tt:parser')
5 |
6 | // eslint-disable-next-line no-unused-vars
7 | const { Interface, Method, Field, Store } = require('./store')
8 |
9 |
10 | /* eslint-disable no-console, no-magic-numbers */
11 |
12 | const API_URL = 'https://core.telegram.org/bots/api'
13 |
14 | /**
15 | * Find previous special typed element in siblings
16 | */
17 | function findPrev(type/*: string*/, element/*: Cheerio*/) {
18 | let tries = 5
19 | let prev = element
20 |
21 | do {
22 | if (prev.is(type)) {
23 | return prev
24 | }
25 |
26 | prev = prev.prev()
27 | }
28 | while (--tries)
29 |
30 | return prev
31 | }
32 |
33 | /**
34 | * Find next special typed element in siblings
35 | * @param {string} type
36 | * @param {Cheerio} element
37 | */
38 | function findNext(type, element) {
39 | let tries = 5
40 | let next = element
41 |
42 | do {
43 | if (next.is(type)) {
44 | return next
45 | }
46 |
47 | next = next.next()
48 | }
49 | while (--tries)
50 |
51 | return next
52 | }
53 |
54 | /**
55 | * Convert list with `.each()` and `.length` to classic array
56 | */
57 | function toArray(target/*: Cheerio*/)/*: Promise*/ {
58 | return new Promise((resolve) => {
59 | const arr/*: Cheerio[]*/ = []
60 |
61 | target.each((index, element/*: CheerioElement*/) => {
62 | arr.push(cheerio(element))
63 |
64 | if (target.length - 1 === index) {
65 | resolve(arr)
66 | }
67 | })
68 | })
69 | }
70 |
71 | async function parseFields(table) { // eslint-disable-line no-unused-vars
72 | return undefined
73 | }
74 |
75 | /**
76 | * @param {Cheerio} description
77 | * @return {Promise>}
78 | */
79 | function parseLinks(description/*: Cheerio*/) {
80 | const links = description.find('a').toArray()
81 | .map((element) => cheerio(element).attr('href'))
82 | .map((linkStr) => (
83 | linkStr.startsWith('http')
84 | ? linkStr
85 | : `https://core.telegram.org/bots/api${linkStr}`
86 | ))
87 |
88 | return [...new Set(links)]
89 | }
90 |
91 | async function handleInterface({ name, description, rows }) {
92 | const fields = {}
93 |
94 | for (const row of rows) {
95 | const [flName, flType, flDescr] = await toArray(row.find('td'))
96 | let fieldDescription
97 | let optional = false
98 |
99 | fieldDescription = flDescr.text().trim()
100 | if (fieldDescription.includes('Optional.')) {
101 | optional = true
102 | fieldDescription = fieldDescription.replace('Optional.', '').trim()
103 | }
104 | const links = parseLinks(flDescr)
105 |
106 | const fieldName = flName.text().trim()
107 | let fieldType = flType.text().trim()
108 |
109 | if (['Field', 'Parameter'].includes(fieldName)) {
110 | continue // eslint-disable-line no-continue
111 | }
112 |
113 | if (fieldType.includes(' or ')) {
114 | fieldType = fieldType.split(' or ')
115 | }
116 |
117 | debug(`${name.text().trim()}.${fieldName}: ${Array.isArray(fieldType) ? fieldType.join(' | ') : fieldType} ::: ${fieldDescription}`)
118 |
119 | const field = new Field(
120 | fieldName,
121 | fieldType,
122 | {
123 | description: fieldDescription,
124 | links,
125 | optional,
126 | }
127 | )
128 |
129 | fields[field.name] = field
130 | }
131 |
132 | const typeClass = new Interface(
133 | name.text().trim(),
134 | { description: description.text().trim(), links: parseLinks(description) },
135 | fields
136 | )
137 |
138 | debug(name.text(), ':::', description.text())
139 |
140 | return typeClass
141 | }
142 |
143 |
144 | async function handleMethod({ name, description, rows }) {
145 | const fields = {}
146 |
147 | for (const row of rows) {
148 | const [flName, flType, flRequired, flDescr] = await toArray(row.find('td'))
149 | const fieldDescription = flDescr.text().trim()
150 | const optional = flRequired.text().trim() === 'Optional'
151 |
152 | const links = parseLinks(flDescr)
153 |
154 | const fieldName = flName.text().trim()
155 | let fieldType = flType.text().trim()
156 |
157 | // fieldName = fieldName.charAt(0).toUpperCase() + fieldName.slice(1)
158 |
159 | if (['Field', 'Parameter'].includes(fieldName)) {
160 | continue // eslint-disable-line no-continue
161 | }
162 |
163 | if (fieldType.includes(' or ')) {
164 | fieldType = fieldType.split(' or ')
165 | }
166 |
167 | debug(`${name.text().trim()}.${fieldName}: ${Array.isArray(fieldType) ? fieldType.join(' | ') : fieldType} ::: ${fieldDescription}`)
168 |
169 | const field = new Field(
170 | fieldName,
171 | fieldType,
172 | {
173 | description: fieldDescription,
174 | links,
175 | optional,
176 | }
177 | )
178 |
179 | fields[field.name] = field
180 | }
181 |
182 | const trimmedName = name.text().trim()
183 | const startCasedName = trimmedName.charAt(0).toUpperCase() + trimmedName.slice(1)
184 |
185 | const typeClass = new Method(
186 | startCasedName,
187 | { description: description.text().trim(), links: parseLinks(description) },
188 | fields
189 | )
190 |
191 | debug(name.text(), ':::', description.text())
192 |
193 | return typeClass
194 | }
195 |
196 | /**
197 | *
198 | * @param {Store} store
199 | */
200 | async function requestAndParse(store/*: Store*/) {
201 | const result = await (await fetch(API_URL)).text()
202 | const body = cheerio.load(result)
203 | const tables/*: Cheerio*/ = body('body').find('table')
204 |
205 | /** @type {Array} */
206 | const list = await toArray(tables)
207 |
208 | for (const table of list) {
209 | const type = table.find('thead tr:first-child th:first-child').text()
210 |
211 | let typeClass
212 |
213 | if (!['Field', 'Parameter'].includes(type)) {
214 | continue // eslint-disable-line no-continue
215 | }
216 |
217 | const name = findPrev('h4', table)
218 | const description = findNext('p', name)
219 |
220 | if (name.text().includes(' ')) {
221 | console.warn('WRONG NAME:', name.text())
222 | continue // eslint-disable-line no-continue
223 | }
224 |
225 | const rows = await toArray(table.find('tbody tr'))
226 |
227 | if (type === 'Field') {
228 | typeClass = await handleInterface({ name, description, rows })
229 | }
230 | else if (type === 'Parameter') {
231 | typeClass = await handleMethod({ name, description, rows })
232 | }
233 |
234 | if (!typeClass) {
235 | continue // eslint-disable-line no-continue
236 | }
237 |
238 | store.add(typeClass)
239 | }
240 |
241 | return store
242 | }
243 |
244 | module.exports = {
245 | requestAndParse,
246 | }
247 |
--------------------------------------------------------------------------------
/lib/store.js:
--------------------------------------------------------------------------------
1 | /* eslint-disable class-methods-use-this */
2 |
3 | /* :: type Attributes = {
4 | description?: string,
5 | links?: string[],
6 | native?: boolean,
7 | } */
8 |
9 | /**
10 | * Item save only name, description, links, native flag
11 | */
12 | class Item {
13 | /*:: name: string*/
14 | /*:: description: ?string*/
15 | /*:: links: string[]*/
16 | /*:: native: boolean*/
17 |
18 | constructor(
19 | name/*: string*/,
20 | { description, links = [], native = false }/*: Attributes*/
21 | ) {
22 | this.name = name
23 | this.description = description
24 | this.links = links
25 | this.native = native
26 | }
27 |
28 | build() {
29 | return this.name
30 | }
31 | }
32 |
33 | /*:: type FieldAttributes = { ...Attributes, optional: boolean }*/
34 | /**
35 | * Field represent field of object/interface
36 | */
37 | class Field extends Item {
38 | /*:: type: string | Array*/
39 | /*:: optional: boolean*/
40 |
41 | constructor(
42 | name/*: string*/,
43 | type/*: string | Array*/,
44 | attributes/*: FieldAttributes*/ = { optional: false }
45 | ) {
46 | super(name, attributes)
47 |
48 | this.type = type
49 | this.optional = attributes.optional
50 | }
51 | }
52 |
53 | /**
54 | * Type is a some type and can be saved in Store
55 | */
56 | class Type extends Item { }
57 |
58 | /*:: type FieldMap = { [name: string]: Field }*/
59 | /**
60 | * Type is a interface/type object definition
61 | */
62 | class Interface extends Type {
63 | /*:: fields: FieldMap*/
64 |
65 | constructor(name/*: string*/, attributes/*: Attributes*/, fields/*: FieldMap*/ = {}) {
66 | super(name, attributes)
67 |
68 | this.fields = fields
69 | }
70 | }
71 | /**
72 | * Type is a method definition
73 | */
74 | class Method extends Type {
75 | /*:: fields: FieldMap*/
76 |
77 | constructor(name/*: string*/, attributes/*: Attributes*/, fields/*: FieldMap*/ = {}) {
78 | super(name, attributes)
79 |
80 | this.fields = fields
81 | }
82 | }
83 |
84 | /**
85 | * Union is a one of types
86 | * @example
87 | * type Foo = A | B | C
88 | */
89 | class Union extends Type {
90 | /*:: variants: string[]*/
91 |
92 | constructor(name/*: string*/, attributes/*: Attributes*/, variants/*: string[]*/ = []) {
93 | super(name, attributes)
94 |
95 | this.variants = variants
96 | }
97 | }
98 |
99 | /**
100 | * Store saves Types
101 | */
102 | class Store {
103 | /*:: types: Map*/
104 |
105 | constructor() {
106 | this.types = new Map()
107 | }
108 |
109 | add(target/*: Type*/) {
110 | this.types.set(target.name, target)
111 | }
112 |
113 | get(targetName/*: string*/)/*: ?Type*/ {
114 | return this.types.get(targetName)
115 | }
116 |
117 | has(targetName/*: string*/)/*: boolean*/ {
118 | return this.types.has(targetName)
119 | }
120 |
121 | * iterate()/*: Iterable*/ {
122 | yield* this.types.values()
123 | }
124 |
125 | serialize() {
126 | return [...this.types.values()]
127 | .reduce((acc, type) => {
128 | if (type instanceof Interface || type instanceof Method) {
129 | acc.types[type.name] = type
130 | }
131 | else if (type instanceof Union) {
132 | acc.unions[type.name] = type
133 | }
134 |
135 | return acc
136 | }, { types: {}, unions: {} })
137 | }
138 | }
139 |
140 | module.exports = {
141 | Interface,
142 | Method,
143 | Union,
144 | Field,
145 | Store,
146 | }
147 |
--------------------------------------------------------------------------------
/license:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2017 Sergey Sova
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
23 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "telegram-typings-generator",
3 | "version": "5.0.0",
4 | "private": true,
5 | "description": "Telegram typings generator",
6 | "main": "index.js",
7 | "typings": "telegram-typings.d.ts",
8 | "scripts": {
9 | "test": "npm run test:lint && npm run test:flow",
10 | "test:flow": "flow status",
11 | "test:lint": "eslint .",
12 | "dev": "DEBUG=tt:* nodemon -w lib -w bin/telegram-typings ./bin/telegram-typings",
13 | "build": "node ./bin/telegram-typings && rustfmt rust/src/lib.rs || true",
14 | "make:changelog": "conventional-changelog -p angular -i changelog.md -r 0 -s && true",
15 | "changelog": "npm test && npm run make:changelog && git add changelog.md && git commit -m 'chore: changelog'",
16 | "publish": "pushd javascript && npm publish && popd",
17 | "postpublish": "pushd rust && cargo publish && popd",
18 | "precommit": "npm run test:lint",
19 | "prepush": "npm test",
20 | "commitmsg": "commitlint -e $GIT_PARAMS"
21 | },
22 | "repository": {
23 | "type": "git",
24 | "url": "git+https://github.com/sergeysova/telegram-typings.git"
25 | },
26 | "keywords": [
27 | "telegram",
28 | "bots",
29 | "typings",
30 | "types",
31 | "flow",
32 | "type",
33 | "typescript",
34 | "script",
35 | "build",
36 | "generate"
37 | ],
38 | "author": "Sergey Sova (https://lestad.top)",
39 | "license": "MIT",
40 | "bugs": {
41 | "url": "https://github.com/sergeysova/telegram-typings/issues"
42 | },
43 | "homepage": "https://github.com/sergeysova/telegram-typings#readme",
44 | "dependencies": {},
45 | "devDependencies": {
46 | "@atomix/eslint-config": "^6.4.0",
47 | "@babel/generator": "^7.0.0-beta.36",
48 | "@babel/types": "^7.0.0-beta.36",
49 | "@commitlint/cli": "^6.2.0",
50 | "cheerio": "^1.0.0-rc.2",
51 | "conventional-changelog-cli": "^1.3.22",
52 | "cz-customizable": "^5.2.0",
53 | "debug": "^3.1.0",
54 | "eslint": "^4.19.1",
55 | "flow-bin": "^0.71.0",
56 | "husky": "^0.14.3",
57 | "node-fetch": "^2.6.1",
58 | "nodemon": "^1.17.3",
59 | "rust-keywords": "^1.0.1"
60 | },
61 | "config": {
62 | "commitizen": {
63 | "path": "node_modules/cz-customizable"
64 | }
65 | }
66 | }
67 |
--------------------------------------------------------------------------------
/rust/.gitignore:
--------------------------------------------------------------------------------
1 |
2 | # Created by https://www.gitignore.io/api/rust
3 |
4 | ### Rust ###
5 | # Generated by Cargo
6 | # will have compiled files and executables
7 | /target/
8 |
9 | # Remove Cargo.lock from gitignore if creating an executable, leave it for libraries
10 | # More information here http://doc.crates.io/guide.html#cargotoml-vs-cargolock
11 | Cargo.lock
12 |
13 | # These are backup files generated by rustfmt
14 | **/*.rs.bk
15 |
16 | # End of https://www.gitignore.io/api/rust
17 |
--------------------------------------------------------------------------------
/rust/Cargo.toml:
--------------------------------------------------------------------------------
1 | [package]
2 | name = "telegram-typings"
3 | version = "3.6.1"
4 | authors = ["Sergey Sova "]
5 | license = "MIT"
6 | description = "Structs represents telegram bot typings"
7 | repository = "https://github.com/sergeysova/telegram-typings.git"
8 | documentation = "https://docs.rs/telegram-typings"
9 | categories = ["data-structures"]
10 |
11 | [dependencies]
12 | serde_derive = "1.0.26"
13 | serde = "1.0.26"
14 |
--------------------------------------------------------------------------------
/rust/README.md:
--------------------------------------------------------------------------------
1 | # Telegram Typings
2 | [](https://crates.io/crates/telegram-typings)
3 | [](https://docs.rs/telegram-typings)
4 |
5 |
6 |
7 | This library has structs to parse Telegram Bot Answer with serde.
8 |
9 | ## Usage
10 | Add this to your `Cargo.toml`
11 | ``` toml
12 | [dependencies]
13 | telegram-typings = "3.5.2"
14 | ```
15 |
16 |
--------------------------------------------------------------------------------
/rust/src/lib.rs:
--------------------------------------------------------------------------------
1 | #[macro_use]
2 | extern crate serde_derive;
3 | extern crate serde;
4 |
5 | /// A placeholder, currently holds no information. Use BotFather to set up
6 | /// your game.
7 | #[derive(Serialize, Deserialize, Debug, Clone)]
8 | pub struct CallbackGame {}
9 |
10 | /// This object represents the contents of a file to be uploaded. Must be
11 | /// posted using multipart/form-data in the usual way that files are
12 | /// uploaded via the browser.
13 | #[derive(Serialize, Deserialize, Debug, Clone)]
14 | pub struct InputFile {}
15 |
16 | /// This object represents the content of a message to be sent as a result
17 | /// of an inline query.
18 | #[derive(Serialize, Deserialize, Debug, Clone)]
19 | pub enum InputMessageContent {
20 | InputTextMessageContent(Box),
21 | InputLocationMessageContent(Box),
22 | InputVenueMessageContent(Box),
23 | InputContactMessageContent(Box),
24 | }
25 |
26 | /// This object represents the content of a media message to be sent.
27 | #[derive(Serialize, Deserialize, Debug, Clone)]
28 | pub enum InputMedia {
29 | InputMediaPhoto(Box),
30 | InputMediaVideo(Box),
31 | }
32 |
33 | /// This object represents one result of an inline query
34 | #[derive(Serialize, Deserialize, Debug, Clone)]
35 | pub enum InlineQueryResult {
36 | InlineQueryResultCachedAudio(Box),
37 | InlineQueryResultCachedDocument(Box),
38 | InlineQueryResultCachedGif(Box),
39 | InlineQueryResultCachedMpeg4Gif(Box),
40 | InlineQueryResultCachedPhoto(Box),
41 | InlineQueryResultCachedSticker(Box),
42 | InlineQueryResultCachedVideo(Box),
43 | InlineQueryResultCachedVoice(Box),
44 | InlineQueryResultArticle(Box),
45 | InlineQueryResultAudio(Box),
46 | InlineQueryResultContact(Box),
47 | InlineQueryResultGame(Box),
48 | InlineQueryResultDocument(Box),
49 | InlineQueryResultGif(Box),
50 | InlineQueryResultLocation(Box),
51 | InlineQueryResultMpeg4Gif(Box),
52 | InlineQueryResultPhoto(Box),
53 | InlineQueryResultVenue(Box),
54 | InlineQueryResultVideo(Box),
55 | InlineQueryResultVoice(Box),
56 | }
57 |
58 | /// This object represents an incoming update.At most one of the optional
59 | /// parameters can be present in any given update.
60 | /// See https://core.telegram.org/bots/api#available-types
61 | #[derive(Serialize, Deserialize, Debug, Clone)]
62 | pub struct Update {
63 | /// The update‘s unique identifier. Update identifiers start from a certain
64 | /// positive number and increase sequentially. This ID becomes especially
65 | /// handy if you’re using Webhooks, since it allows you to ignore repeated
66 | /// updates or to restore the correct update sequence, should they get out
67 | /// of order. If there are no new updates for at least a week, then
68 | /// identifier of the next update will be chosen randomly instead of sequentially.
69 | /// See https://core.telegram.org/bots/api#setwebhook
70 | pub update_id: i64,
71 |
72 | /// New incoming message of any kind — text, photo, sticker, etc.
73 | pub message: Option>,
74 |
75 | /// New version of a message that is known to the bot and was edited
76 | pub edited_message: Option>,
77 |
78 | /// New incoming channel post of any kind — text, photo, sticker, etc.
79 | pub channel_post: Option>,
80 |
81 | /// New version of a channel post that is known to the bot and was edited
82 | pub edited_channel_post: Option>,
83 |
84 | /// New incoming inline query
85 | /// See https://core.telegram.org/bots/api#inline-mode
86 | pub inline_query: Option>,
87 |
88 | /// The result of an inline query that was chosen by a user and sent to
89 | /// their chat partner. Please see our documentation on the feedback
90 | /// collecting for details on how to enable these updates for your bot.
91 | /// See https://core.telegram.org/bots/api#inline-mode
92 | /// See https://core.telegram.org/bots/api/bots/inline#collecting-feedback
93 | pub chosen_inline_result: Option>,
94 |
95 | /// New incoming callback query
96 | pub callback_query: Option>,
97 |
98 | /// New incoming shipping query. Only for invoices with flexible price
99 | pub shipping_query: Option>,
100 |
101 | /// New incoming pre-checkout query. Contains full information about checkout
102 | pub pre_checkout_query: Option>,
103 | }
104 |
105 | /// Contains information about the current status of a webhook.
106 | #[derive(Serialize, Deserialize, Debug, Clone)]
107 | pub struct WebhookInfo {
108 | /// Webhook URL, may be empty if webhook is not set up
109 | pub url: String,
110 |
111 | /// True, if a custom certificate was provided for webhook certificate checks
112 | pub has_custom_certificate: bool,
113 |
114 | /// Number of updates awaiting delivery
115 | pub pending_update_count: i64,
116 |
117 | /// Unix time for the most recent error that happened when trying to deliver
118 | /// an update via webhook
119 | pub last_error_date: Option,
120 |
121 | /// Error message in human-readable format for the most recent error that
122 | /// happened when trying to deliver an update via webhook
123 | pub last_error_message: Option,
124 |
125 | /// Maximum allowed number of simultaneous HTTPS connections to the webhook
126 | /// for update delivery
127 | pub max_connections: Option,
128 |
129 | /// A list of update types the bot is subscribed to. Defaults to all update types
130 | pub allowed_updates: Option>,
131 | }
132 |
133 | /// This object represents a Telegram user or bot.
134 | #[derive(Serialize, Deserialize, Debug, Clone)]
135 | pub struct User {
136 | /// Unique identifier for this user or bot
137 | pub id: i64,
138 |
139 | /// True, if this user is a bot
140 | pub is_bot: bool,
141 |
142 | /// User‘s or bot’s first name
143 | pub first_name: String,
144 |
145 | /// User‘s or bot’s last name
146 | pub last_name: Option,
147 |
148 | /// User‘s or bot’s username
149 | pub username: Option,
150 |
151 | /// IETF language tag of the user's language
152 | /// See https://en.wikipedia.org/wiki/IETF_language_tag
153 | pub language_code: Option,
154 | }
155 |
156 | /// This object represents a chat.
157 | #[derive(Serialize, Deserialize, Debug, Clone)]
158 | pub struct Chat {
159 | /// Unique identifier for this chat. This number may be greater than 32 bits
160 | /// and some programming languages may have difficulty/silent defects in
161 | /// interpreting it. But it is smaller than 52 bits, so a signed 64 bit
162 | /// integer or double-precision float type are safe for storing this identifier.
163 | pub id: i64,
164 |
165 | /// Type of chat, can be either “private”, “group”, “supergroup” or “channel”
166 | #[serde(rename = "type")]
167 | pub type_tl: String,
168 |
169 | /// Title, for supergroups, channels and group chats
170 | pub title: Option,
171 |
172 | /// Username, for private chats, supergroups and channels if available
173 | pub username: Option,
174 |
175 | /// First name of the other party in a private chat
176 | pub first_name: Option,
177 |
178 | /// Last name of the other party in a private chat
179 | pub last_name: Option,
180 |
181 | /// True if a group has ‘All Members Are Admins’ enabled.
182 | pub all_members_are_administrators: Option,
183 |
184 | /// Chat photo. Returned only in getChat.
185 | /// See https://core.telegram.org/bots/api#getchat
186 | pub photo: Option>,
187 |
188 | /// Description, for supergroups and channel chats. Returned only in getChat.
189 | /// See https://core.telegram.org/bots/api#getchat
190 | pub description: Option,
191 |
192 | /// Chat invite link, for supergroups and channel chats. Returned only in getChat.
193 | /// See https://core.telegram.org/bots/api#getchat
194 | pub invite_link: Option,
195 |
196 | /// Pinned message, for supergroups and channel chats. Returned only in getChat.
197 | /// See https://core.telegram.org/bots/api#getchat
198 | pub pinned_message: Option>,
199 |
200 | /// For supergroups, name of group sticker set. Returned only in getChat.
201 | /// See https://core.telegram.org/bots/api#getchat
202 | pub sticker_set_name: Option,
203 |
204 | /// True, if the bot can change the group sticker set. Returned only in getChat.
205 | /// See https://core.telegram.org/bots/api#getchat
206 | pub can_set_sticker_set: Option,
207 | }
208 |
209 | /// This object represents a message.
210 | #[derive(Serialize, Deserialize, Debug, Clone)]
211 | pub struct Message {
212 | /// Unique message identifier inside this chat
213 | pub message_id: i64,
214 |
215 | /// Sender, empty for messages sent to channels
216 | pub from: Option>,
217 |
218 | /// Date the message was sent in Unix time
219 | pub date: i64,
220 |
221 | /// Conversation the message belongs to
222 | pub chat: Box,
223 |
224 | /// For forwarded messages, sender of the original message
225 | pub forward_from: Option>,
226 |
227 | /// For messages forwarded from channels, information about the original channel
228 | pub forward_from_chat: Option>,
229 |
230 | /// For messages forwarded from channels, identifier of the original message
231 | /// in the channel
232 | pub forward_from_message_id: Option,
233 |
234 | /// For messages forwarded from channels, signature of the post author if present
235 | pub forward_signature: Option,
236 |
237 | /// For forwarded messages, date the original message was sent in Unix time
238 | pub forward_date: Option,
239 |
240 | /// For replies, the original message. Note that the Message object in this
241 | /// field will not contain further reply_to_message fields even if it itself
242 | /// is a reply.
243 | pub reply_to_message: Option>,
244 |
245 | /// Date the message was last edited in Unix time
246 | pub edit_date: Option,
247 |
248 | /// The unique identifier of a media message group this message belongs to
249 | pub media_group_id: Option,
250 |
251 | /// Signature of the post author for messages in channels
252 | pub author_signature: Option,
253 |
254 | /// For text messages, the actual UTF-8 text of the message, 0-4096 characters.
255 | pub text: Option,
256 |
257 | /// For text messages, special entities like usernames, URLs, bot commands,
258 | /// etc. that appear in the text
259 | pub entities: Option>>,
260 |
261 | /// For messages with a caption, special entities like usernames, URLs, bot
262 | /// commands, etc. that appear in the caption
263 | pub caption_entities: Option>>,
264 |
265 | /// Message is an audio file, information about the file
266 | pub audio: Option>,
267 |
268 | /// Message is a general file, information about the file
269 | pub document: Option>,
270 |
271 | /// Message is a game, information about the game. More about games »
272 | /// See https://core.telegram.org/bots/api#games
273 | pub game: Option>,
274 |
275 | /// Message is a photo, available sizes of the photo
276 | pub photo: Option>>,
277 |
278 | /// Message is a sticker, information about the sticker
279 | pub sticker: Option>,
280 |
281 | /// Message is a video, information about the video
282 | pub video: Option>,
283 |
284 | /// Message is a voice message, information about the file
285 | pub voice: Option>,
286 |
287 | /// Message is a video note, information about the video message
288 | /// See https://telegram.org/blog/video-messages-and-telescope
289 | pub video_note: Option>,
290 |
291 | /// Caption for the audio, document, photo, video or voice, 0-200 characters
292 | pub caption: Option,
293 |
294 | /// Message is a shared contact, information about the contact
295 | pub contact: Option>,
296 |
297 | /// Message is a shared location, information about the location
298 | pub location: Option>,
299 |
300 | /// Message is a venue, information about the venue
301 | pub venue: Option>,
302 |
303 | /// New members that were added to the group or supergroup and information
304 | /// about them (the bot itself may be one of these members)
305 | pub new_chat_members: Option>>,
306 |
307 | /// A member was removed from the group, information about them (this member
308 | /// may be the bot itself)
309 | pub left_chat_member: Option>,
310 |
311 | /// A chat title was changed to this value
312 | pub new_chat_title: Option,
313 |
314 | /// A chat photo was change to this value
315 | pub new_chat_photo: Option>>,
316 |
317 | /// Service message: the chat photo was deleted
318 | pub delete_chat_photo: Option,
319 |
320 | /// Service message: the group has been created
321 | pub group_chat_created: Option,
322 |
323 | /// Service message: the supergroup has been created. This field can‘t be
324 | /// received in a message coming through updates, because bot can’t be a
325 | /// member of a supergroup when it is created. It can only be found in
326 | /// reply_to_message if someone replies to a very first message in a
327 | /// directly created supergroup.
328 | pub supergroup_chat_created: Option,
329 |
330 | /// Service message: the channel has been created. This field can‘t be
331 | /// received in a message coming through updates, because bot can’t be a
332 | /// member of a channel when it is created. It can only be found in
333 | /// reply_to_message if someone replies to a very first message in a channel.
334 | pub channel_chat_created: Option,
335 |
336 | /// The group has been migrated to a supergroup with the specified
337 | /// identifier. This number may be greater than 32 bits and some programming
338 | /// languages may have difficulty/silent defects in interpreting it. But it
339 | /// is smaller than 52 bits, so a signed 64 bit integer or double-precision
340 | /// float type are safe for storing this identifier.
341 | pub migrate_to_chat_id: Option,
342 |
343 | /// The supergroup has been migrated from a group with the specified
344 | /// identifier. This number may be greater than 32 bits and some programming
345 | /// languages may have difficulty/silent defects in interpreting it. But it
346 | /// is smaller than 52 bits, so a signed 64 bit integer or double-precision
347 | /// float type are safe for storing this identifier.
348 | pub migrate_from_chat_id: Option,
349 |
350 | /// Specified message was pinned. Note that the Message object in this field
351 | /// will not contain further reply_to_message fields even if it is itself a reply.
352 | pub pinned_message: Option>,
353 |
354 | /// Message is an invoice for a payment, information about the invoice. More
355 | /// about payments »
356 | /// See https://core.telegram.org/bots/api#payments
357 | pub invoice: Option>,
358 |
359 | /// Message is a service message about a successful payment, information
360 | /// about the payment. More about payments »
361 | /// See https://core.telegram.org/bots/api#payments
362 | pub successful_payment: Option>,
363 |
364 | /// The domain name of the website on which the user has logged in. More
365 | /// about Telegram Login »
366 | /// See https://core.telegram.org/bots/api/widgets/login
367 | pub connected_website: Option,
368 | }
369 |
370 | /// This object represents one special entity in a text message. For
371 | /// example, hashtags, usernames, URLs, etc.
372 | #[derive(Serialize, Deserialize, Debug, Clone)]
373 | pub struct MessageEntity {
374 | /// Type of the entity. Can be mention (@username), hashtag, bot_command,
375 | /// url, email, bold (bold text), italic (italic text), code (monowidth
376 | /// string), pre (monowidth block), text_link (for clickable text URLs),
377 | /// text_mention (for users without usernames)
378 | /// See https://telegram.org/blog/edit#new-mentions
379 | #[serde(rename = "type")]
380 | pub type_tl: String,
381 |
382 | /// Offset in UTF-16 code units to the start of the entity
383 | pub offset: i64,
384 |
385 | /// Length of the entity in UTF-16 code units
386 | pub length: i64,
387 |
388 | /// For “text_link” only, url that will be opened after user taps on the text
389 | pub url: Option,
390 |
391 | /// For “text_mention” only, the mentioned user
392 | pub user: Option>,
393 | }
394 |
395 | /// This object represents one size of a photo or a file / sticker thumbnail.
396 | /// See https://core.telegram.org/bots/api#document
397 | /// See https://core.telegram.org/bots/api#sticker
398 | #[derive(Serialize, Deserialize, Debug, Clone)]
399 | pub struct PhotoSize {
400 | /// Unique identifier for this file
401 | pub file_id: String,
402 |
403 | /// Photo width
404 | pub width: i64,
405 |
406 | /// Photo height
407 | pub height: i64,
408 |
409 | /// File size
410 | pub file_size: Option,
411 | }
412 |
413 | /// This object represents an audio file to be treated as music by the
414 | /// Telegram clients.
415 | #[derive(Serialize, Deserialize, Debug, Clone)]
416 | pub struct Audio {
417 | /// Unique identifier for this file
418 | pub file_id: String,
419 |
420 | /// Duration of the audio in seconds as defined by sender
421 | pub duration: i64,
422 |
423 | /// Performer of the audio as defined by sender or by audio tags
424 | pub performer: Option,
425 |
426 | /// Title of the audio as defined by sender or by audio tags
427 | pub title: Option,
428 |
429 | /// MIME type of the file as defined by sender
430 | pub mime_type: Option,
431 |
432 | /// File size
433 | pub file_size: Option,
434 | }
435 |
436 | /// This object represents a general file (as opposed to photos, voice
437 | /// messages and audio files).
438 | /// See https://core.telegram.org/bots/api#photosize
439 | /// See https://core.telegram.org/bots/api#voice
440 | /// See https://core.telegram.org/bots/api#audio
441 | #[derive(Serialize, Deserialize, Debug, Clone)]
442 | pub struct Document {
443 | /// Unique file identifier
444 | pub file_id: String,
445 |
446 | /// Document thumbnail as defined by sender
447 | pub thumb: Option>,
448 |
449 | /// Original filename as defined by sender
450 | pub file_name: Option,
451 |
452 | /// MIME type of the file as defined by sender
453 | pub mime_type: Option,
454 |
455 | /// File size
456 | pub file_size: Option,
457 | }
458 |
459 | /// This object represents a video file.
460 | #[derive(Serialize, Deserialize, Debug, Clone)]
461 | pub struct Video {
462 | /// Unique identifier for this file
463 | pub file_id: String,
464 |
465 | /// Video width as defined by sender
466 | pub width: i64,
467 |
468 | /// Video height as defined by sender
469 | pub height: i64,
470 |
471 | /// Duration of the video in seconds as defined by sender
472 | pub duration: i64,
473 |
474 | /// Video thumbnail
475 | pub thumb: Option>,
476 |
477 | /// Mime type of a file as defined by sender
478 | pub mime_type: Option,
479 |
480 | /// File size
481 | pub file_size: Option,
482 | }
483 |
484 | /// This object represents a voice note.
485 | #[derive(Serialize, Deserialize, Debug, Clone)]
486 | pub struct Voice {
487 | /// Unique identifier for this file
488 | pub file_id: String,
489 |
490 | /// Duration of the audio in seconds as defined by sender
491 | pub duration: i64,
492 |
493 | /// MIME type of the file as defined by sender
494 | pub mime_type: Option,
495 |
496 | /// File size
497 | pub file_size: Option,
498 | }
499 |
500 | /// This object represents a video message (available in Telegram apps as of v.4.0).
501 | /// See https://telegram.org/blog/video-messages-and-telescope
502 | #[derive(Serialize, Deserialize, Debug, Clone)]
503 | pub struct VideoNote {
504 | /// Unique identifier for this file
505 | pub file_id: String,
506 |
507 | /// Video width and height as defined by sender
508 | pub length: i64,
509 |
510 | /// Duration of the video in seconds as defined by sender
511 | pub duration: i64,
512 |
513 | /// Video thumbnail
514 | pub thumb: Option>,
515 |
516 | /// File size
517 | pub file_size: Option,
518 | }
519 |
520 | /// This object represents a phone contact.
521 | #[derive(Serialize, Deserialize, Debug, Clone)]
522 | pub struct Contact {
523 | /// Contact's phone number
524 | pub phone_number: String,
525 |
526 | /// Contact's first name
527 | pub first_name: String,
528 |
529 | /// Contact's last name
530 | pub last_name: Option,
531 |
532 | /// Contact's user identifier in Telegram
533 | pub user_id: Option,
534 | }
535 |
536 | /// This object represents a point on the map.
537 | #[derive(Serialize, Deserialize, Debug, Clone)]
538 | pub struct Location {
539 | /// Longitude as defined by sender
540 | pub longitude: f64,
541 |
542 | /// Latitude as defined by sender
543 | pub latitude: f64,
544 | }
545 |
546 | /// This object represents a venue.
547 | #[derive(Serialize, Deserialize, Debug, Clone)]
548 | pub struct Venue {
549 | /// Venue location
550 | pub location: Box,
551 |
552 | /// Name of the venue
553 | pub title: String,
554 |
555 | /// Address of the venue
556 | pub address: String,
557 |
558 | /// Foursquare identifier of the venue
559 | pub foursquare_id: Option,
560 | }
561 |
562 | /// This object represent a user's profile pictures.
563 | #[derive(Serialize, Deserialize, Debug, Clone)]
564 | pub struct UserProfilePhotos {
565 | /// Total number of profile pictures the target user has
566 | pub total_count: i64,
567 |
568 | /// Requested profile pictures (in up to 4 sizes each)
569 | pub photos: Vec>>,
570 | }
571 |
572 | /// This object represents a file ready to be downloaded. The file can be
573 | /// downloaded via the link
574 | /// https://api.telegram.org/file/bot/. It is guaranteed
575 | /// that the link will be valid for at least 1 hour. When the link expires,
576 | /// a new one can be requested by calling getFile.
577 | /// See https://core.telegram.org/bots/api#getfile
578 | #[derive(Serialize, Deserialize, Debug, Clone)]
579 | pub struct File {
580 | /// Unique identifier for this file
581 | pub file_id: String,
582 |
583 | /// File size, if known
584 | pub file_size: Option,
585 |
586 | /// File path. Use https://api.telegram.org/file/bot/ to
587 | /// get the file.
588 | pub file_path: Option,
589 | }
590 |
591 | /// This object represents a custom keyboard with reply options (see
592 | /// Introduction to bots for details and examples).
593 | /// See https://core.telegram.org/bots#keyboards
594 | #[derive(Serialize, Deserialize, Debug, Clone)]
595 | pub struct ReplyKeyboardMarkup {
596 | /// Array of button rows, each represented by an Array of KeyboardButton objects
597 | /// See https://core.telegram.org/bots/api#keyboardbutton
598 | pub keyboard: Vec>>,
599 |
600 | /// Requests clients to resize the keyboard vertically for optimal fit
601 | /// (e.g., make the keyboard smaller if there are just two rows of buttons).
602 | /// Defaults to false, in which case the custom keyboard is always of the
603 | /// same height as the app's standard keyboard.
604 | pub resize_keyboard: Option,
605 |
606 | /// Requests clients to hide the keyboard as soon as it's been used. The
607 | /// keyboard will still be available, but clients will automatically display
608 | /// the usual letter-keyboard in the chat – the user can press a special
609 | /// button in the input field to see the custom keyboard again. Defaults to false.
610 | pub one_time_keyboard: Option,
611 |
612 | /// Use this parameter if you want to show the keyboard to specific users
613 | /// only. Targets: 1) users that are @mentioned in the text of the Message
614 | /// object; 2) if the bot's message is a reply (has reply_to_message_id),
615 | /// sender of the original message.Example: A user requests to change the
616 | /// bot‘s language, bot replies to the request with a keyboard to select the
617 | /// new language. Other users in the group don’t see the keyboard.
618 | /// See https://core.telegram.org/bots/api#message
619 | pub selective: Option,
620 | }
621 |
622 | /// This object represents one button of the reply keyboard. For simple text
623 | /// buttons String can be used instead of this object to specify text of the
624 | /// button. Optional fields are mutually exclusive.
625 | #[derive(Serialize, Deserialize, Debug, Clone)]
626 | pub struct KeyboardButton {
627 | /// Text of the button. If none of the optional fields are used, it will be
628 | /// sent as a message when the button is pressed
629 | pub text: String,
630 |
631 | /// If True, the user's phone number will be sent as a contact when the
632 | /// button is pressed. Available in private chats only
633 | pub request_contact: Option,
634 |
635 | /// If True, the user's current location will be sent when the button is
636 | /// pressed. Available in private chats only
637 | pub request_location: Option,
638 | }
639 |
640 | /// Upon receiving a message with this object, Telegram clients will remove
641 | /// the current custom keyboard and display the default letter-keyboard. By
642 | /// default, custom keyboards are displayed until a new keyboard is sent by
643 | /// a bot. An exception is made for one-time keyboards that are hidden
644 | /// immediately after the user presses a button (see ReplyKeyboardMarkup).
645 | /// See https://core.telegram.org/bots/api#replykeyboardmarkup
646 | #[derive(Serialize, Deserialize, Debug, Clone)]
647 | pub struct ReplyKeyboardRemove {
648 | /// Requests clients to remove the custom keyboard (user will not be able to
649 | /// summon this keyboard; if you want to hide the keyboard from sight but
650 | /// keep it accessible, use one_time_keyboard in ReplyKeyboardMarkup)
651 | /// See https://core.telegram.org/bots/api#replykeyboardmarkup
652 | pub remove_keyboard: bool,
653 |
654 | /// Use this parameter if you want to remove the keyboard for specific users
655 | /// only. Targets: 1) users that are @mentioned in the text of the Message
656 | /// object; 2) if the bot's message is a reply (has reply_to_message_id),
657 | /// sender of the original message.Example: A user votes in a poll, bot
658 | /// returns confirmation message in reply to the vote and removes the
659 | /// keyboard for that user, while still showing the keyboard with poll
660 | /// options to users who haven't voted yet.
661 | /// See https://core.telegram.org/bots/api#message
662 | pub selective: Option,
663 | }
664 |
665 | /// This object represents an inline keyboard that appears right next to the
666 | /// message it belongs to.
667 | /// See https://core.telegram.org/bots#inline-keyboards-and-on-the-fly-updating
668 | #[derive(Serialize, Deserialize, Debug, Clone)]
669 | pub struct InlineKeyboardMarkup {
670 | /// Array of button rows, each represented by an Array of
671 | /// InlineKeyboardButton objects
672 | /// See https://core.telegram.org/bots/api#inlinekeyboardbutton
673 | pub inline_keyboard: Vec>>,
674 | }
675 |
676 | /// This object represents one button of an inline keyboard. You must use
677 | /// exactly one of the optional fields.
678 | #[derive(Serialize, Deserialize, Debug, Clone)]
679 | pub struct InlineKeyboardButton {
680 | /// Label text on the button
681 | pub text: String,
682 |
683 | /// HTTP url to be opened when button is pressed
684 | pub url: Option,
685 |
686 | /// Data to be sent in a callback query to the bot when button is pressed,
687 | /// 1-64 bytes
688 | /// See https://core.telegram.org/bots/api#callbackquery
689 | pub callback_data: Option,
690 |
691 | /// If set, pressing the button will prompt the user to select one of their
692 | /// chats, open that chat and insert the bot‘s username and the specified
693 | /// inline query in the input field. Can be empty, in which case just the
694 | /// bot’s username will be inserted.Note: This offers an easy way for users
695 | /// to start using your bot in inline mode when they are currently in a
696 | /// private chat with it. Especially useful when combined with switch_pm…
697 | /// actions – in this case the user will be automatically returned to the
698 | /// chat they switched from, skipping the chat selection screen.
699 | /// See https://core.telegram.org/bots/api/bots/inline
700 | /// See https://core.telegram.org/bots/api#answerinlinequery
701 | pub switch_inline_query: Option,
702 |
703 | /// If set, pressing the button will insert the bot‘s username and the
704 | /// specified inline query in the current chat's input field. Can be empty,
705 | /// in which case only the bot’s username will be inserted.This offers a
706 | /// quick way for the user to open your bot in inline mode in the same chat
707 | /// – good for selecting something from multiple options.
708 | pub switch_inline_query_current_chat: Option,
709 |
710 | /// Description of the game that will be launched when the user presses the
711 | /// button.NOTE: This type of button must always be the first button in the
712 | /// first row.
713 | pub callback_game: Option>,
714 |
715 | /// Specify True, to send a Pay button.NOTE: This type of button must always
716 | /// be the first button in the first row.
717 | /// See https://core.telegram.org/bots/api#payments
718 | pub pay: Option,
719 | }
720 |
721 | /// This object represents an incoming callback query from a callback button
722 | /// in an inline keyboard. If the button that originated the query was
723 | /// attached to a message sent by the bot, the field message will be
724 | /// present. If the button was attached to a message sent via the bot (in
725 | /// inline mode), the field inline_message_id will be present. Exactly one
726 | /// of the fields data or game_short_name will be present.
727 | /// See https://core.telegram.org/bots/api/bots#inline-keyboards-and-on-the-fly-updating
728 | /// See https://core.telegram.org/bots/api#inline-mode
729 | #[derive(Serialize, Deserialize, Debug, Clone)]
730 | pub struct CallbackQuery {
731 | /// Unique identifier for this query
732 | pub id: String,
733 |
734 | /// Sender
735 | pub from: Box,
736 |
737 | /// Message with the callback button that originated the query. Note that
738 | /// message content and message date will not be available if the message is
739 | /// too old
740 | pub message: Option>,
741 |
742 | /// Identifier of the message sent via the bot in inline mode, that
743 | /// originated the query.
744 | pub inline_message_id: Option,
745 |
746 | /// Global identifier, uniquely corresponding to the chat to which the
747 | /// message with the callback button was sent. Useful for high scores in games.
748 | /// See https://core.telegram.org/bots/api#games
749 | pub chat_instance: String,
750 |
751 | /// Data associated with the callback button. Be aware that a bad client can
752 | /// send arbitrary data in this field.
753 | pub data: Option,
754 |
755 | /// Short name of a Game to be returned, serves as the unique identifier for
756 | /// the game
757 | /// See https://core.telegram.org/bots/api#games
758 | pub game_short_name: Option,
759 | }
760 |
761 | /// Upon receiving a message with this object, Telegram clients will display
762 | /// a reply interface to the user (act as if the user has selected the bot‘s
763 | /// message and tapped ’Reply'). This can be extremely useful if you want to
764 | /// create user-friendly step-by-step interfaces without having to sacrifice
765 | /// privacy mode.
766 | /// See https://core.telegram.org/bots/api/bots#privacy-mode
767 | #[derive(Serialize, Deserialize, Debug, Clone)]
768 | pub struct ForceReply {
769 | /// Shows reply interface to the user, as if they manually selected the
770 | /// bot‘s message and tapped ’Reply'
771 | pub force_reply: bool,
772 |
773 | /// Use this parameter if you want to force reply from specific users only.
774 | /// Targets: 1) users that are @mentioned in the text of the Message object;
775 | /// 2) if the bot's message is a reply (has reply_to_message_id), sender of
776 | /// the original message.
777 | /// See https://core.telegram.org/bots/api#message
778 | pub selective: Option,
779 | }
780 |
781 | /// This object represents a chat photo.
782 | #[derive(Serialize, Deserialize, Debug, Clone)]
783 | pub struct ChatPhoto {
784 | /// Unique file identifier of small (160x160) chat photo. This file_id can
785 | /// be used only for photo download.
786 | pub small_file_id: String,
787 |
788 | /// Unique file identifier of big (640x640) chat photo. This file_id can be
789 | /// used only for photo download.
790 | pub big_file_id: String,
791 | }
792 |
793 | /// This object contains information about one member of a chat.
794 | #[derive(Serialize, Deserialize, Debug, Clone)]
795 | pub struct ChatMember {
796 | /// Information about the user
797 | pub user: Box,
798 |
799 | /// The member's status in the chat. Can be “creator”, “administrator”,
800 | /// “member”, “restricted”, “left” or “kicked”
801 | pub status: String,
802 |
803 | /// Restricted and kicked only. Date when restrictions will be lifted for
804 | /// this user, unix time
805 | pub until_date: Option,
806 |
807 | /// Administrators only. True, if the bot is allowed to edit administrator
808 | /// privileges of that user
809 | pub can_be_edited: Option,
810 |
811 | /// Administrators only. True, if the administrator can change the chat
812 | /// title, photo and other settings
813 | pub can_change_info: Option,
814 |
815 | /// Administrators only. True, if the administrator can post in the channel,
816 | /// channels only
817 | pub can_post_messages: Option,
818 |
819 | /// Administrators only. True, if the administrator can edit messages of
820 | /// other users and can pin messages, channels only
821 | pub can_edit_messages: Option,
822 |
823 | /// Administrators only. True, if the administrator can delete messages of
824 | /// other users
825 | pub can_delete_messages: Option,
826 |
827 | /// Administrators only. True, if the administrator can invite new users to
828 | /// the chat
829 | pub can_invite_users: Option,
830 |
831 | /// Administrators only. True, if the administrator can restrict, ban or
832 | /// unban chat members
833 | pub can_restrict_members: Option,
834 |
835 | /// Administrators only. True, if the administrator can pin messages,
836 | /// supergroups only
837 | pub can_pin_messages: Option,
838 |
839 | /// Administrators only. True, if the administrator can add new
840 | /// administrators with a subset of his own privileges or demote
841 | /// administrators that he has promoted, directly or indirectly (promoted by
842 | /// administrators that were appointed by the user)
843 | pub can_promote_members: Option,
844 |
845 | /// Restricted only. True, if the user can send text messages, contacts,
846 | /// locations and venues
847 | pub can_send_messages: Option,
848 |
849 | /// Restricted only. True, if the user can send audios, documents, photos,
850 | /// videos, video notes and voice notes, implies can_send_messages
851 | pub can_send_media_messages: Option,
852 |
853 | /// Restricted only. True, if the user can send animations, games, stickers
854 | /// and use inline bots, implies can_send_media_messages
855 | pub can_send_other_messages: Option,
856 |
857 | /// Restricted only. True, if user may add web page previews to his
858 | /// messages, implies can_send_media_messages
859 | pub can_add_web_page_previews: Option,
860 | }
861 |
862 | /// Contains information about why a request was unsuccessful.
863 | #[derive(Serialize, Deserialize, Debug, Clone)]
864 | pub struct ResponseParameters {
865 | /// The group has been migrated to a supergroup with the specified
866 | /// identifier. This number may be greater than 32 bits and some programming
867 | /// languages may have difficulty/silent defects in interpreting it. But it
868 | /// is smaller than 52 bits, so a signed 64 bit integer or double-precision
869 | /// float type are safe for storing this identifier.
870 | pub migrate_to_chat_id: Option,
871 |
872 | /// In case of exceeding flood control, the number of seconds left to wait
873 | /// before the request can be repeated
874 | pub retry_after: Option,
875 | }
876 |
877 | /// Represents a photo to be sent.
878 | #[derive(Serialize, Deserialize, Debug, Clone)]
879 | pub struct InputMediaPhoto {
880 | /// Type of the result, must be photo
881 | #[serde(rename = "type")]
882 | pub type_tl: String,
883 |
884 | /// File to send. Pass a file_id to send a file that exists on the Telegram
885 | /// servers (recommended), pass an HTTP URL for Telegram to get a file from
886 | /// the Internet, or pass "attach://" to upload a new one
887 | /// using multipart/form-data under name. More info on
888 | /// Sending Files »
889 | /// See https://core.telegram.org/bots/api#sending-files
890 | pub media: String,
891 |
892 | /// Caption of the photo to be sent, 0-200 characters
893 | pub caption: Option,
894 |
895 | /// Send Markdown or HTML, if you want Telegram apps to show bold, italic,
896 | /// fixed-width text or inline URLs in the media caption.
897 | /// See https://core.telegram.org/bots/api#markdown-style
898 | /// See https://core.telegram.org/bots/api#html-style
899 | /// See https://core.telegram.org/bots/api#formatting-options
900 | pub parse_mode: Option,
901 | }
902 |
903 | /// Represents a video to be sent.
904 | #[derive(Serialize, Deserialize, Debug, Clone)]
905 | pub struct InputMediaVideo {
906 | /// Type of the result, must be video
907 | #[serde(rename = "type")]
908 | pub type_tl: String,
909 |
910 | /// File to send. Pass a file_id to send a file that exists on the Telegram
911 | /// servers (recommended), pass an HTTP URL for Telegram to get a file from
912 | /// the Internet, or pass "attach://" to upload a new one
913 | /// using multipart/form-data under name. More info on
914 | /// Sending Files »
915 | /// See https://core.telegram.org/bots/api#sending-files
916 | pub media: String,
917 |
918 | /// Caption of the video to be sent, 0-200 characters
919 | pub caption: Option,
920 |
921 | /// Send Markdown or HTML, if you want Telegram apps to show bold, italic,
922 | /// fixed-width text or inline URLs in the media caption.
923 | /// See https://core.telegram.org/bots/api#markdown-style
924 | /// See https://core.telegram.org/bots/api#html-style
925 | /// See https://core.telegram.org/bots/api#formatting-options
926 | pub parse_mode: Option,
927 |
928 | /// Video width
929 | pub width: Option,
930 |
931 | /// Video height
932 | pub height: Option,
933 |
934 | /// Video duration
935 | pub duration: Option,
936 |
937 | /// Pass True, if the uploaded video is suitable for streaming
938 | pub supports_streaming: Option,
939 | }
940 |
941 | /// This object represents a sticker.
942 | #[derive(Serialize, Deserialize, Debug, Clone)]
943 | pub struct Sticker {
944 | /// Unique identifier for this file
945 | pub file_id: String,
946 |
947 | /// Sticker width
948 | pub width: i64,
949 |
950 | /// Sticker height
951 | pub height: i64,
952 |
953 | /// Sticker thumbnail in the .webp or .jpg format
954 | pub thumb: Option>,
955 |
956 | /// Emoji associated with the sticker
957 | pub emoji: Option,
958 |
959 | /// Name of the sticker set to which the sticker belongs
960 | pub set_name: Option,
961 |
962 | /// For mask stickers, the position where the mask should be placed
963 | pub mask_position: Option>,
964 |
965 | /// File size
966 | pub file_size: Option,
967 | }
968 |
969 | /// This object represents a sticker set.
970 | #[derive(Serialize, Deserialize, Debug, Clone)]
971 | pub struct StickerSet {
972 | /// Sticker set name
973 | pub name: String,
974 |
975 | /// Sticker set title
976 | pub title: String,
977 |
978 | /// True, if the sticker set contains masks
979 | pub contains_masks: bool,
980 |
981 | /// List of all set stickers
982 | pub stickers: Vec>,
983 | }
984 |
985 | /// This object describes the position on faces where a mask should be
986 | /// placed by default.
987 | #[derive(Serialize, Deserialize, Debug, Clone)]
988 | pub struct MaskPosition {
989 | /// The part of the face relative to which the mask should be placed. One of
990 | /// “forehead”, “eyes”, “mouth”, or “chin”.
991 | pub point: String,
992 |
993 | /// Shift by X-axis measured in widths of the mask scaled to the face size,
994 | /// from left to right. For example, choosing -1.0 will place mask just to
995 | /// the left of the default mask position.
996 | pub x_shift: f64,
997 |
998 | /// Shift by Y-axis measured in heights of the mask scaled to the face size,
999 | /// from top to bottom. For example, 1.0 will place the mask just below the
1000 | /// default mask position.
1001 | pub y_shift: f64,
1002 |
1003 | /// Mask scaling coefficient. For example, 2.0 means double size.
1004 | pub scale: f64,
1005 | }
1006 |
1007 | /// This object represents an incoming inline query. When the user sends an
1008 | /// empty query, your bot could return some default or trending results.
1009 | #[derive(Serialize, Deserialize, Debug, Clone)]
1010 | pub struct InlineQuery {
1011 | /// Unique identifier for this query
1012 | pub id: String,
1013 |
1014 | /// Sender
1015 | pub from: Box,
1016 |
1017 | /// Sender location, only for bots that request user location
1018 | pub location: Option>,
1019 |
1020 | /// Text of the query (up to 512 characters)
1021 | pub query: String,
1022 |
1023 | /// Offset of the results to be returned, can be controlled by the bot
1024 | pub offset: String,
1025 | }
1026 |
1027 | /// Represents a link to an article or web page.
1028 | #[derive(Serialize, Deserialize, Debug, Clone)]
1029 | pub struct InlineQueryResultArticle {
1030 | /// Type of the result, must be article
1031 | #[serde(rename = "type")]
1032 | pub type_tl: String,
1033 |
1034 | /// Unique identifier for this result, 1-64 Bytes
1035 | pub id: String,
1036 |
1037 | /// Title of the result
1038 | pub title: String,
1039 |
1040 | /// Content of the message to be sent
1041 | pub input_message_content: Box,
1042 |
1043 | /// Inline keyboard attached to the message
1044 | /// See https://core.telegram.org/bots/api/bots#inline-keyboards-and-on-the-fly-updating
1045 | pub reply_markup: Option>,
1046 |
1047 | /// URL of the result
1048 | pub url: Option,
1049 |
1050 | /// Pass True, if you don't want the URL to be shown in the message
1051 | pub hide_url: Option,
1052 |
1053 | /// Short description of the result
1054 | pub description: Option,
1055 |
1056 | /// Url of the thumbnail for the result
1057 | pub thumb_url: Option,
1058 |
1059 | /// Thumbnail width
1060 | pub thumb_width: Option,
1061 |
1062 | /// Thumbnail height
1063 | pub thumb_height: Option,
1064 | }
1065 |
1066 | /// Represents a link to a photo. By default, this photo will be sent by the
1067 | /// user with optional caption. Alternatively, you can use
1068 | /// input_message_content to send a message with the specified content
1069 | /// instead of the photo.
1070 | #[derive(Serialize, Deserialize, Debug, Clone)]
1071 | pub struct InlineQueryResultPhoto {
1072 | /// Type of the result, must be photo
1073 | #[serde(rename = "type")]
1074 | pub type_tl: String,
1075 |
1076 | /// Unique identifier for this result, 1-64 bytes
1077 | pub id: String,
1078 |
1079 | /// A valid URL of the photo. Photo must be in jpeg format. Photo size must
1080 | /// not exceed 5MB
1081 | pub photo_url: String,
1082 |
1083 | /// URL of the thumbnail for the photo
1084 | pub thumb_url: String,
1085 |
1086 | /// Width of the photo
1087 | pub photo_width: Option,
1088 |
1089 | /// Height of the photo
1090 | pub photo_height: Option,
1091 |
1092 | /// Title for the result
1093 | pub title: Option,
1094 |
1095 | /// Short description of the result
1096 | pub description: Option,
1097 |
1098 | /// Caption of the photo to be sent, 0-200 characters
1099 | pub caption: Option,
1100 |
1101 | /// Send Markdown or HTML, if you want Telegram apps to show bold, italic,
1102 | /// fixed-width text or inline URLs in the media caption.
1103 | /// See https://core.telegram.org/bots/api#markdown-style
1104 | /// See https://core.telegram.org/bots/api#html-style
1105 | /// See https://core.telegram.org/bots/api#formatting-options
1106 | pub parse_mode: Option,
1107 |
1108 | /// Inline keyboard attached to the message
1109 | /// See https://core.telegram.org/bots/api/bots#inline-keyboards-and-on-the-fly-updating
1110 | pub reply_markup: Option>,
1111 |
1112 | /// Content of the message to be sent instead of the photo
1113 | pub input_message_content: Option>,
1114 | }
1115 |
1116 | /// Represents a link to an animated GIF file. By default, this animated GIF
1117 | /// file will be sent by the user with optional caption. Alternatively, you
1118 | /// can use input_message_content to send a message with the specified
1119 | /// content instead of the animation.
1120 | #[derive(Serialize, Deserialize, Debug, Clone)]
1121 | pub struct InlineQueryResultGif {
1122 | /// Type of the result, must be gif
1123 | #[serde(rename = "type")]
1124 | pub type_tl: String,
1125 |
1126 | /// Unique identifier for this result, 1-64 bytes
1127 | pub id: String,
1128 |
1129 | /// A valid URL for the GIF file. File size must not exceed 1MB
1130 | pub gif_url: String,
1131 |
1132 | /// Width of the GIF
1133 | pub gif_width: Option,
1134 |
1135 | /// Height of the GIF
1136 | pub gif_height: Option,
1137 |
1138 | /// Duration of the GIF
1139 | pub gif_duration: Option,
1140 |
1141 | /// URL of the static thumbnail for the result (jpeg or gif)
1142 | pub thumb_url: String,
1143 |
1144 | /// Title for the result
1145 | pub title: Option,
1146 |
1147 | /// Caption of the GIF file to be sent, 0-200 characters
1148 | pub caption: Option,
1149 |
1150 | /// Send Markdown or HTML, if you want Telegram apps to show bold, italic,
1151 | /// fixed-width text or inline URLs in the media caption.
1152 | /// See https://core.telegram.org/bots/api#markdown-style
1153 | /// See https://core.telegram.org/bots/api#html-style
1154 | /// See https://core.telegram.org/bots/api#formatting-options
1155 | pub parse_mode: Option,
1156 |
1157 | /// Inline keyboard attached to the message
1158 | /// See https://core.telegram.org/bots/api/bots#inline-keyboards-and-on-the-fly-updating
1159 | pub reply_markup: Option>,
1160 |
1161 | /// Content of the message to be sent instead of the GIF animation
1162 | pub input_message_content: Option>,
1163 | }
1164 |
1165 | /// Represents a link to a video animation (H.264/MPEG-4 AVC video without
1166 | /// sound). By default, this animated MPEG-4 file will be sent by the user
1167 | /// with optional caption. Alternatively, you can use input_message_content
1168 | /// to send a message with the specified content instead of the animation.
1169 | #[derive(Serialize, Deserialize, Debug, Clone)]
1170 | pub struct InlineQueryResultMpeg4Gif {
1171 | /// Type of the result, must be mpeg4_gif
1172 | #[serde(rename = "type")]
1173 | pub type_tl: String,
1174 |
1175 | /// Unique identifier for this result, 1-64 bytes
1176 | pub id: String,
1177 |
1178 | /// A valid URL for the MP4 file. File size must not exceed 1MB
1179 | pub mpeg4_url: String,
1180 |
1181 | /// Video width
1182 | pub mpeg4_width: Option,
1183 |
1184 | /// Video height
1185 | pub mpeg4_height: Option,
1186 |
1187 | /// Video duration
1188 | pub mpeg4_duration: Option,
1189 |
1190 | /// URL of the static thumbnail (jpeg or gif) for the result
1191 | pub thumb_url: String,
1192 |
1193 | /// Title for the result
1194 | pub title: Option,
1195 |
1196 | /// Caption of the MPEG-4 file to be sent, 0-200 characters
1197 | pub caption: Option,
1198 |
1199 | /// Send Markdown or HTML, if you want Telegram apps to show bold, italic,
1200 | /// fixed-width text or inline URLs in the media caption.
1201 | /// See https://core.telegram.org/bots/api#markdown-style
1202 | /// See https://core.telegram.org/bots/api#html-style
1203 | /// See https://core.telegram.org/bots/api#formatting-options
1204 | pub parse_mode: Option,
1205 |
1206 | /// Inline keyboard attached to the message
1207 | /// See https://core.telegram.org/bots/api/bots#inline-keyboards-and-on-the-fly-updating
1208 | pub reply_markup: Option>,
1209 |
1210 | /// Content of the message to be sent instead of the video animation
1211 | pub input_message_content: Option>,
1212 | }
1213 |
1214 | /// Represents a link to a page containing an embedded video player or a
1215 | /// video file. By default, this video file will be sent by the user with an
1216 | /// optional caption. Alternatively, you can use input_message_content to
1217 | /// send a message with the specified content instead of the video.
1218 | #[derive(Serialize, Deserialize, Debug, Clone)]
1219 | pub struct InlineQueryResultVideo {
1220 | /// Type of the result, must be video
1221 | #[serde(rename = "type")]
1222 | pub type_tl: String,
1223 |
1224 | /// Unique identifier for this result, 1-64 bytes
1225 | pub id: String,
1226 |
1227 | /// A valid URL for the embedded video player or video file
1228 | pub video_url: String,
1229 |
1230 | /// Mime type of the content of video url, “text/html” or “video/mp4”
1231 | pub mime_type: String,
1232 |
1233 | /// URL of the thumbnail (jpeg only) for the video
1234 | pub thumb_url: String,
1235 |
1236 | /// Title for the result
1237 | pub title: String,
1238 |
1239 | /// Caption of the video to be sent, 0-200 characters
1240 | pub caption: Option,
1241 |
1242 | /// Send Markdown or HTML, if you want Telegram apps to show bold, italic,
1243 | /// fixed-width text or inline URLs in the media caption.
1244 | /// See https://core.telegram.org/bots/api#markdown-style
1245 | /// See https://core.telegram.org/bots/api#html-style
1246 | /// See https://core.telegram.org/bots/api#formatting-options
1247 | pub parse_mode: Option,
1248 |
1249 | /// Video width
1250 | pub video_width: Option,
1251 |
1252 | /// Video height
1253 | pub video_height: Option,
1254 |
1255 | /// Video duration in seconds
1256 | pub video_duration: Option,
1257 |
1258 | /// Short description of the result
1259 | pub description: Option