<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: MyStars.tg</title>
    <description>The latest articles on DEV Community by MyStars.tg (mystarstg).</description>
    <link>https://dev.to/mystarstg</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Forganization%2Fprofile_image%2F13949%2Ff644f9af-2417-4f90-b481-14a701aa7b51.png</url>
      <title>DEV Community: MyStars.tg</title>
      <link>https://dev.to/mystarstg</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/mystarstg"/>
    <language>en</language>
    <item>
      <title>Fragment API SDK for Telegram Apps and Bots: A Practical Guide (Node.js &amp; Python)</title>
      <dc:creator>MyStars.tg</dc:creator>
      <pubDate>Wed, 08 Jul 2026 19:23:02 +0000</pubDate>
      <link>https://dev.to/mystarstg/fragment-api-sdk-for-telegram-apps-and-bots-a-practical-guide-nodejs-python-3bk2</link>
      <guid>https://dev.to/mystarstg/fragment-api-sdk-for-telegram-apps-and-bots-a-practical-guide-nodejs-python-3bk2</guid>
      <description>&lt;p&gt;Most Telegram commerce ideas hit the same wall right after the prototype stage: the bot or Mini App itself is easy to build, but Stars and Premium fulfilment still need a dependable backend flow. That's usually when people start searching for a &lt;strong&gt;Fragment API&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;MyStars FaaS&lt;/strong&gt; gives you that missing layer. FaaS here means &lt;strong&gt;Fragment as a Service&lt;/strong&gt;: your Telegram product keeps the user experience and order database, while MyStars exposes the fulfilment workflow through an API, official SDKs, and signed status updates.&lt;/p&gt;

&lt;p&gt;This guide is for wiring up a real Telegram app, bot, marketplace, creator tool, or reseller flow — not just another API overview.&lt;/p&gt;

&lt;h2&gt;
  
  
  The clean architecture: Telegram API in front, Fragment API behind it
&lt;/h2&gt;

&lt;p&gt;Keep the boundary simple:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Telegram API layer&lt;/strong&gt; — the parts users can see: bot commands, inline keyboards, Mini App screens, order cards, messages, support replies.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Your server layer&lt;/strong&gt; — your business logic: local orders, margin, fraud rules, admin controls, database writes, support evidence.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;MyStars FaaS layer&lt;/strong&gt; — the Fragment-as-a-Service workflow: pricing, recipient checks, order creation, payment instructions, fulfilment status.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That separation matters for security. Don't put the MyStars API key in a Telegram Mini App frontend. The client talks to your backend; your backend talks to MyStars.&lt;/p&gt;

&lt;h2&gt;
  
  
  Install the SDK for your stack
&lt;/h2&gt;

&lt;p&gt;Node.js / TypeScript — &lt;a href="https://www.npmjs.com/package/@mystars-tg/faas-sdk" rel="noopener noreferrer"&gt;@mystars-tg/faas-sdk&lt;/a&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; @mystars-tg/faas-sdk
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Python — &lt;a href="https://pypi.org/project/mystars-faas/" rel="noopener noreferrer"&gt;mystars-faas&lt;/a&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pip &lt;span class="nb"&gt;install &lt;/span&gt;mystars-faas
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Both are the official MyStars FaaS SDKs and link back to the &lt;a href="https://mystars.tg/docs" rel="noopener noreferrer"&gt;interactive API docs&lt;/a&gt;. The current package docs describe compatibility with FaaS API v1.9.0, worth checking against when comparing examples to the API reference.&lt;/p&gt;

&lt;h2&gt;
  
  
  Build the first backend route in TypeScript
&lt;/h2&gt;

&lt;p&gt;Don't try to do everything in the first route. Start with a server-only action that quotes, checks the recipient, and creates one fulfilment order from your own local order ID.&lt;/p&gt;

&lt;p&gt;Plain-English version of what it does:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;creates a MyStars client on the backend using &lt;code&gt;MYSTARS_API_KEY&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;asks MyStars for the current price of the selected Stars quantity&lt;/li&gt;
&lt;li&gt;checks whether the Telegram username can receive the product&lt;/li&gt;
&lt;li&gt;stops early if the recipient isn't eligible, instead of creating a bad order&lt;/li&gt;
&lt;li&gt;creates the fulfilment order with your own stable &lt;code&gt;localOrderId&lt;/code&gt; as the idempotency basis&lt;/li&gt;
&lt;li&gt;returns the quote and the MyStars order object so your app can store and show the payment instruction
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;MyStarsClient&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@mystars-tg/faas-sdk&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;MyStarsClient&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;production&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;process&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;env&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;MYSTARS_API_KEY&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;createStarsOrder&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;input&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;username&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;number&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;localOrderId&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;quote&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getPricing&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;stars&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;input&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;payment_currency&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;ton&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;});&lt;/span&gt;

  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;recipient&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;checkRecipient&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;stars&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;recipient&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;username&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;input&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;username&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;});&lt;/span&gt;

  &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;recipient&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;eligible&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;ok&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;message&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;recipient&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;telegram_message&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;order&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createOrder&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;stars&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;recipient&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;username&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;input&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;username&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="na"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;input&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;payment_currency&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;ton&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;callback_url&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;https://your-app.example.com/webhooks/mystars&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;idempotencyKey&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;`local-&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;input&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;localOrderId&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;

  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;ok&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;quote&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;order&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The important part is the idempotency key. Use something stable from your own system. If the HTTP request times out after the order was already created server-side, retry with the same key instead of creating a duplicate.&lt;/p&gt;

&lt;p&gt;A few lines worth a second look:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;MyStarsClient.production(...)&lt;/code&gt; hits the live API — use a test/local order in your own system until you're ready for real traffic.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;getPricing(...)&lt;/code&gt; gives your backend a current quote. Don't hardcode prices in the bot UI.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;payment_currency: "ton"&lt;/code&gt; is the API enum for the native payment route in this SDK example. In your product UI, label that route as &lt;strong&gt;Gram&lt;/strong&gt; or &lt;strong&gt;Gram (ex. TON)&lt;/strong&gt; — keep &lt;strong&gt;TON&lt;/strong&gt; for the blockchain/network name.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;checkRecipient(...)&lt;/code&gt; protects the buyer from paying for a username or product that can't be fulfilled.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;callback_url&lt;/code&gt; is where MyStars sends order status updates after creation.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;idempotencyKey&lt;/code&gt; is the duplicate-order guard — it should come from your database order, not a random value generated in the browser.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The same flow in async Python
&lt;/h2&gt;

&lt;p&gt;Python teams usually want async code because their Telegram bot framework already is. The Python SDK supports that directly.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;mystars_faas&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;AsyncMyStarsClient&lt;/span&gt;

&lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;create_premium_order&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;username&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;str&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;months&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;int&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;local_order_id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;str&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="k"&gt;with&lt;/span&gt; &lt;span class="n"&gt;AsyncMyStarsClient&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;production&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;MYSTARS_API_KEY&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;quote&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get_pricing&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
            &lt;span class="nb"&gt;type&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;premium&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;months&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;months&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;payment_currency&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;usdt_ton&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="n"&gt;recipient&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;check_recipient&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;username&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nb"&gt;type&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;premium&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;recipient&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;eligible&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;ok&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="bp"&gt;False&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;message&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;recipient&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;telegram_message&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;

        &lt;span class="n"&gt;order&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;create_order&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
            &lt;span class="nb"&gt;type&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;premium&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;recipient&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;username&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;months&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;months&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;payment_currency&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;usdt_ton&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;callback_url&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;https://your-app.example.com/webhooks/mystars&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;idempotency_key&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;local-&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;local_order_id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;ok&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="bp"&gt;True&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;quote&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;quote&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;order&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;order&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In production: use exact money handling, keep the API key in an environment variable, and store the payment instruction exactly as returned. If the instruction includes a memo/comment, treat it as data — not copy you can rewrite.&lt;/p&gt;

&lt;p&gt;One clarification for anyone newer to this: the snippet above isn't a full bot. It's the backend piece your bot calls once the user has already picked a product — your bot still needs its own handlers, buttons, database writes, and user-facing messages around this function.&lt;/p&gt;

&lt;h2&gt;
  
  
  Add webhook verification before launch
&lt;/h2&gt;

&lt;p&gt;Order creation working isn't the finish line — you also need a trustworthy status path.&lt;/p&gt;

&lt;p&gt;Minimum webhook handler:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Receive the raw request body.&lt;/li&gt;
&lt;li&gt;Read the &lt;code&gt;X-Faas-Signature&lt;/code&gt; header.&lt;/li&gt;
&lt;li&gt;Verify the signature with your webhook secret.&lt;/li&gt;
&lt;li&gt;Dedupe by MyStars order ID and status.&lt;/li&gt;
&lt;li&gt;Update your local order only if the transition is valid.&lt;/li&gt;
&lt;li&gt;Notify the user through your bot or Mini App.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The TypeScript SDK ships webhook helpers (&lt;code&gt;constructEvent&lt;/code&gt;, Express middleware, Fastify support). The Python SDK includes &lt;code&gt;WebhookVerifier&lt;/code&gt; plus integrations for common Python web frameworks.&lt;/p&gt;

&lt;p&gt;Keep a polling/reconcile job as a backup. Webhooks are the fast path — reconciliation is what saves you when a network edge case shows up at 3 a.m.&lt;/p&gt;

&lt;h2&gt;
  
  
  A working reference: the blueprint bot
&lt;/h2&gt;

&lt;p&gt;The &lt;a href="https://github.com/MyStars-tg/blueprint_python_bot" rel="noopener noreferrer"&gt;MyStars Python blueprint bot&lt;/a&gt; is the best place to see all the moving parts together. It uses &lt;code&gt;mystars-faas==0.1.3&lt;/code&gt; for fulfilment, an aiohttp server for health checks and MyStars webhooks, Postgres + Redis for state, TON Center monitoring for on-chain payments, and admin commands for margin/reconciliation.&lt;/p&gt;

&lt;p&gt;Treat it as an engineering map, not a brand template — where to create the local order, where to call recipient checks, where to apply margin, where to monitor payment, where to call fulfilment, where to edit the Telegram order card after a terminal status.&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://github.com/MyStars-tg" rel="noopener noreferrer"&gt;MyStars GitHub org&lt;/a&gt; also hosts the SDK repos if you need to debug past what the README covers.&lt;/p&gt;

&lt;h2&gt;
  
  
  Backend endpoints to create in your own app
&lt;/h2&gt;

&lt;p&gt;A small production-grade integration usually starts with:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;POST /api/faas/quote
POST /api/faas/recipient-check
POST /api/orders
POST /webhooks/mystars
GET  /api/orders/:id
POST /api/admin/reconcile
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Your Telegram bot or Mini App should call your own &lt;code&gt;/api/orders&lt;/code&gt; route, not MyStars directly. That route validates the user, creates a local order, calls the SDK, stores the returned fulfilment order, and sends back only the safe fields your client needs.&lt;/p&gt;

&lt;h2&gt;
  
  
  Payment details users must not have to guess
&lt;/h2&gt;

&lt;p&gt;If your product shows a payment screen, be precise. For MyStars flows, &lt;strong&gt;USDT means USDT on TON&lt;/strong&gt; — other USDT networks aren't interchangeable. For the native route, current API examples still use &lt;code&gt;payment_currency: "ton"&lt;/code&gt;; buyer-facing copy should say &lt;strong&gt;Gram / GRAM (ex. TON)&lt;/strong&gt; for the token and &lt;strong&gt;TON&lt;/strong&gt; for the network.&lt;/p&gt;

&lt;p&gt;Read the order's &lt;code&gt;expires_at&lt;/code&gt; field instead of hardcoding a payment timeout — the docs note the payment window was extended to 1 hour, and &lt;code&gt;expires_at&lt;/code&gt; is the source of truth.&lt;/p&gt;

&lt;h2&gt;
  
  
  What to test before real traffic
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;one Stars order and one Premium order&lt;/li&gt;
&lt;li&gt;one ineligible-recipient path&lt;/li&gt;
&lt;li&gt;retrying order creation with the same idempotency key&lt;/li&gt;
&lt;li&gt;valid and invalid webhook signatures&lt;/li&gt;
&lt;li&gt;duplicated webhook event delivery&lt;/li&gt;
&lt;li&gt;expired order handling&lt;/li&gt;
&lt;li&gt;support evidence: username, local order ID, MyStars order ID, payment hash, memo/comment, status&lt;/li&gt;
&lt;li&gt;admin-only access for margin, reconcile, refund, broadcast, and manual fulfilment commands&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Unglamorous, but it's what makes a Telegram Stars bot feel reliable instead of experimental.&lt;/p&gt;

&lt;h2&gt;
  
  
  FAQ
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Is this a direct public Fragment API?&lt;/strong&gt;&lt;br&gt;
MyStars FaaS is a Fragment-as-a-Service layer. Your app integrates with MyStars APIs and SDKs, while MyStars handles the fulfilment workflow behind that interface.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Can I use it from a Telegram Mini App?&lt;/strong&gt;&lt;br&gt;
Yes — keep the API key on your backend. The Mini App calls your server, your server calls MyStars FaaS.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Which package should I start with?&lt;/strong&gt;&lt;br&gt;
&lt;code&gt;@mystars-tg/faas-sdk&lt;/code&gt; for Node.js/TypeScript, &lt;code&gt;mystars-faas&lt;/code&gt; for Python and async Telegram bots.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Do I need the blueprint bot?&lt;/strong&gt;&lt;br&gt;
No, but it helps if you're building a reseller-style bot with payments, admin commands, reconciliation, and status updates.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What's the safest first milestone?&lt;/strong&gt;&lt;br&gt;
One end-to-end test: quote → recipient check → local order → MyStars order → verified webhook or polling update. After that works, add margin, refund policy, admin tools, and support workflows.&lt;/p&gt;




&lt;p&gt;Full API reference, SDK links, and current contract notes: &lt;a href="https://mystars.tg/docs" rel="noopener noreferrer"&gt;mystars.tg/docs&lt;/a&gt;. Source for the SDKs and the blueprint bot: &lt;a href="https://github.com/MyStars-tg" rel="noopener noreferrer"&gt;github.com/MyStars-tg&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Originally published on the &lt;a href="https://mystars.tg/blog/fragment-api-sdk-telegram-apps-bots-mystars-faas" rel="noopener noreferrer"&gt;MyStars.tg blog&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>telegram</category>
      <category>api</category>
      <category>webdev</category>
      <category>python</category>
    </item>
  </channel>
</rss>
