mirror of
https://github.com/LonamiWebs/Telethon.git
synced 2024-11-10 19:46:36 +03:00
Generate simple examples for the docs
This commit is contained in:
parent
8f04ec820f
commit
477fbd8dc7
|
@ -59,8 +59,8 @@ users.getUsers#0d91a548 id:Vector<InputUser> = Vector<User></pre>
|
|||
<p>This is <b>not</b> Python code. It's the "TL definition". It's
|
||||
an easy-to-read line that gives a quick overview on the parameters
|
||||
and its result. You don't need to worry about this. See
|
||||
<a href="http://telethon.readthedocs.io/en/latest/extra/developing/understanding-the-type-language.html">here</a>
|
||||
for more details on it.</p>
|
||||
<a href="https://telethon.readthedocs.io/en/latest/extra/developing/understanding-the-type-language.html">Understanding
|
||||
the Type Language</a> for more details on it.</p>
|
||||
|
||||
<h3>Index</h3>
|
||||
<ul>
|
||||
|
@ -82,7 +82,7 @@ users.getUsers#0d91a548 id:Vector<InputUser> = Vector<User></pre>
|
|||
|
||||
<h3 id="methods">Methods</h3>
|
||||
<p>Currently there are <b>{method_count} methods</b> available for the layer
|
||||
{layer}. The complete list can be seen <a href="methods/index.html">here</a>.
|
||||
{layer}. <a href="methods/index.html">See the complete method list</a>.
|
||||
<br /><br />
|
||||
Methods, also known as <i>requests</i>, are used to interact with the
|
||||
Telegram API itself and are invoked through <code>client(Request(...))</code>.
|
||||
|
@ -92,8 +92,8 @@ users.getUsers#0d91a548 id:Vector<InputUser> = Vector<User></pre>
|
|||
some dialogs, users, etc.</p>
|
||||
|
||||
<h3 id="types">Types</h3>
|
||||
<p>Currently there are <b>{type_count} types</b>. You can see the full
|
||||
list <a href="types/index.html">here</a>.</p>
|
||||
<p>Currently there are <b>{type_count} types</b>.
|
||||
<a href="types/index.html">See the complete list of types</a>.</p>
|
||||
|
||||
<p>The Telegram types are the <i>abstract</i> results that you receive
|
||||
after invoking a request. They are "abstract" because they can have
|
||||
|
@ -106,8 +106,8 @@ users.getUsers#0d91a548 id:Vector<InputUser> = Vector<User></pre>
|
|||
an instance of it by using one of its, possibly multiple, constructors.</p>
|
||||
|
||||
<h3 id="constructors">Constructors</h3>
|
||||
<p>Currently there are <b>{constructor_count} constructors</b>. You can see
|
||||
the full list <a href="constructors/index.html">here</a>.</p>
|
||||
<p>Currently there are <b>{constructor_count} constructors</b>.
|
||||
<a href="constructors/index.html">See the list of all constructors</a>.</p>
|
||||
|
||||
<p>Constructors are the way you can create instances of the abstract types
|
||||
described above, and also the instances which are actually returned from
|
||||
|
@ -170,8 +170,13 @@ users.getUsers#0d91a548 id:Vector<InputUser> = Vector<User></pre>
|
|||
</ul>
|
||||
|
||||
<h3 id="example">Full example</h3>
|
||||
<p>Documentation for this is now
|
||||
<a href="http://telethon.readthedocs.io/en/latest/extra/advanced-usage/accessing-the-full-api.html">here</a>.
|
||||
<p>All methods shown here have dummy examples on how to write them,
|
||||
so you don't get confused with their TL definition. However, this may
|
||||
not always run. They are just there to show the right syntax.</p>
|
||||
|
||||
<p>You should check out
|
||||
<a href="http://telethon.readthedocs.io/en/latest/extra/advanced-usage/accessing-the-full-api.html">how
|
||||
to access the full API</a> in ReadTheDocs.
|
||||
</p>
|
||||
</div>
|
||||
<script src="js/search.js"></script>
|
||||
|
|
|
@ -95,11 +95,16 @@ class DocsWriter:
|
|||
raise RuntimeError('No menu had been started in the first place.')
|
||||
self.write('</ul>')
|
||||
|
||||
def write_title(self, title, level=1):
|
||||
def write_title(self, title, level=1, id=None):
|
||||
"""Writes a title header in the document body,
|
||||
with an optional depth level
|
||||
"""
|
||||
self.write('<h{level}>{title}</h{level}>', title=title, level=level)
|
||||
if id:
|
||||
self.write('<h{lv} id="{id}">{title}</h{lv}>',
|
||||
title=title, lv=level, id=id)
|
||||
else:
|
||||
self.write('<h{lv}>{title}</h{lv}>',
|
||||
title=title, lv=level)
|
||||
|
||||
def write_code(self, tlobject):
|
||||
"""Writes the code for the given 'tlobject' properly
|
||||
|
|
|
@ -297,7 +297,8 @@ def _write_html_pages(tlobjects, errors, layer, input_res, output_dir):
|
|||
docs.write_title(tlobject.class_name)
|
||||
|
||||
if tlobject.is_function:
|
||||
docs.write_text('Bots <strong>can{}</strong> use this method.'
|
||||
docs.write_text('Bots <strong>can{}</strong> use this method. '
|
||||
'<a href="#examples">See code examples.</a>'
|
||||
.format("" if tlobject.bot_usable else "'t"))
|
||||
if tlobject.is_function and tlobject.bot_usable:
|
||||
bot_docs_paths.append(filename)
|
||||
|
@ -410,6 +411,28 @@ def _write_html_pages(tlobjects, errors, layer, input_res, output_dir):
|
|||
docs.write_text('You can import these from '
|
||||
'<code>telethon.errors</code>.')
|
||||
|
||||
docs.write_title('Example', id='examples')
|
||||
docs.write(
|
||||
'<pre>from telethon.sync import TelegramClient\n'
|
||||
'from telethon import functions, types\n'
|
||||
'\n'
|
||||
'with TelegramClient(name, api_id, api_hash) as client:\n'
|
||||
' result = client(')
|
||||
tlobject.as_example(docs, indent=1)
|
||||
docs.write(')\n')
|
||||
if tlobject.result.startswith('Vector'):
|
||||
docs.write(
|
||||
' for x in result:\n'
|
||||
' print(x'
|
||||
)
|
||||
else:
|
||||
docs.write(' print(result')
|
||||
if tlobject.result != 'Bool' \
|
||||
and not tlobject.result.startswith('Vector'):
|
||||
docs.write('.stringify()')
|
||||
|
||||
docs.write(')</pre>')
|
||||
|
||||
depth = '../' * (2 if tlobject.namespace else 1)
|
||||
docs.add_script(src='prependPath = "{}";'.format(depth))
|
||||
docs.add_script(relative_src=paths['search.js'])
|
||||
|
|
|
@ -1,6 +1,64 @@
|
|||
import re
|
||||
|
||||
|
||||
KNOWN_NAMED_EXAMPLES = {
|
||||
('peer', 'InputPeer'): "'TelethonOffTopic'",
|
||||
('channel', 'InputChannel'): "'TelethonOffTopic'",
|
||||
('user_id', 'InputUser'): "'Lonami'",
|
||||
('users', 'InputUser'): "'Lonami'",
|
||||
('message', 'string'): "'Hello there!'",
|
||||
('expires_at', 'date'): 'datetime.timedelta(minutes=5)',
|
||||
('until_date', 'date'): 'datetime.timedelta(days=14)',
|
||||
('view_messages', 'true'): 'None',
|
||||
('send_messages', 'true'): 'None',
|
||||
('limit', 'int'): '100',
|
||||
('hash', 'int'): '0',
|
||||
('hash', 'string'): "'A4LmkR23G0IGxBE71zZfo1'",
|
||||
('min_id', 'int'): '0',
|
||||
('max_id', 'int'): '0',
|
||||
('add_offset', 'int'): '0',
|
||||
('title', 'string'): "'My awesome title'",
|
||||
('device_model', 'string'): "'ASUS Laptop'",
|
||||
('system_version', 'string'): "'Arch Linux'",
|
||||
('app_version', 'string'): "'1.0'",
|
||||
('system_lang_code', 'string'): "'en'",
|
||||
('lang_pack', 'string'): "''",
|
||||
('lang_code', 'string'): "'en'",
|
||||
('chat_id', 'int'): '478614198'
|
||||
}
|
||||
|
||||
KNOWN_TYPED_EXAMPLES = {
|
||||
'int128': "int.from_bytes(os.urandom(16), 'big')",
|
||||
'bytes': "b'arbitrary\\x7f data \\xfa here'",
|
||||
'long': "-12398745604826",
|
||||
'string': "'some string here'",
|
||||
'int': '42',
|
||||
'date': 'datetime.datetime(2018, 6, 25)',
|
||||
'double': '7.13',
|
||||
'Bool': 'False',
|
||||
'true': 'True',
|
||||
'InputChatPhoto': "client.upload_file('/path/to/photo.jpg')"
|
||||
}
|
||||
|
||||
# These are flags that are cleaner to leave off
|
||||
OMITTED_EXAMPLES = {
|
||||
'silent',
|
||||
'background',
|
||||
'clear_draft',
|
||||
'reply_to_msg_id',
|
||||
'random_id',
|
||||
'reply_markup',
|
||||
'entities',
|
||||
'embed_links',
|
||||
'hash',
|
||||
'min_id',
|
||||
'max_id',
|
||||
'add_offset',
|
||||
'grouped',
|
||||
'broadcast'
|
||||
}
|
||||
|
||||
|
||||
class TLArg:
|
||||
def __init__(self, name, arg_type, generic_definition):
|
||||
"""
|
||||
|
@ -131,3 +189,29 @@ class TLArg:
|
|||
'name': self.name.replace('is_self', 'self'),
|
||||
'type': re.sub(r'\bdate$', 'int', self.real_type())
|
||||
}
|
||||
|
||||
def as_example(self, f, indent=0):
|
||||
if self.is_generic:
|
||||
f.write('other_request')
|
||||
return
|
||||
|
||||
known = (KNOWN_NAMED_EXAMPLES.get((self.name, self.type))
|
||||
or KNOWN_TYPED_EXAMPLES.get(self.type))
|
||||
if known:
|
||||
f.write(known)
|
||||
return
|
||||
|
||||
assert self.omit_example() or self.cls, 'TODO handle ' + str(self)
|
||||
|
||||
# Pick an interesting example if any
|
||||
for cls in self.cls:
|
||||
if cls.is_good_example():
|
||||
cls.as_example(f, indent)
|
||||
break
|
||||
else:
|
||||
# If no example is good, just pick the first
|
||||
self.cls[0].as_example(f, indent)
|
||||
|
||||
def omit_example(self):
|
||||
return (self.is_flag or self.can_be_inferred) \
|
||||
and self.name in OMITTED_EXAMPLES
|
||||
|
|
|
@ -102,3 +102,42 @@ class TLObject:
|
|||
'type':
|
||||
self.result
|
||||
}
|
||||
|
||||
def is_good_example(self):
|
||||
return not self.class_name.endswith('Empty')
|
||||
|
||||
def as_example(self, f, indent=0):
|
||||
f.write('functions' if self.is_function else 'types')
|
||||
if self.namespace:
|
||||
f.write('.')
|
||||
f.write(self.namespace)
|
||||
|
||||
f.write('.')
|
||||
f.write(self.class_name)
|
||||
f.write('(')
|
||||
|
||||
args = [arg for arg in self.real_args if not arg.omit_example()]
|
||||
if not args:
|
||||
f.write(')')
|
||||
return
|
||||
|
||||
f.write('\n')
|
||||
indent += 1
|
||||
remaining = len(args)
|
||||
for arg in args:
|
||||
remaining -= 1
|
||||
f.write(' ' * indent)
|
||||
f.write(arg.name)
|
||||
f.write('=')
|
||||
if arg.is_vector:
|
||||
f.write('[')
|
||||
arg.as_example(f, indent)
|
||||
if arg.is_vector:
|
||||
f.write(']')
|
||||
if remaining:
|
||||
f.write(',')
|
||||
f.write('\n')
|
||||
|
||||
indent -= 1
|
||||
f.write(' ' * indent)
|
||||
f.write(')')
|
||||
|
|
Loading…
Reference in New Issue
Block a user