# First steps on Hystore Hystore is the platform to build the store of your game server (Minecraft or Hytale) or your digital product store. You take care of the products and the server; Hystore takes care of the storefront, the payment, the automatic delivery and the dashboard where everything comes together. This guide shows the shortest path from sign-up to the first sale. Each step points to the page that explains the screen in detail. ![The Hystore dashboard with the month's sales, the plan usage and the menu on the left](shots/store-home.webp) ## The path to the first sale 1. **Create the account and the store.** Hyler, the Hystore robot, signs you up in a chat: account, email code, store and plan. See [Create the account and the store](/en/store/create/). 2. **Create the categories.** In **Store > Categories** you group the products, for example VIPs, Kits and Cash. See [Categories](/en/products/categories/). 3. **Connect the game server.** In **Store > Servers** you add the server and install the Hystore plugin with its token. The plugin is what delivers the purchases in the game. See [Install the plugin](/en/plugins/). 4. **Add the products.** Each product has a price, a picture and the commands the plugin runs when the purchase is approved. See [Products](/en/products/). 5. **Turn on a payment method.** In **Settings > Payments** you connect Mercado Pago, Stripe, PayPal or PicPay. The money from sales goes straight to your account. See [Payment methods](/en/payments/). 6. **Make the store yours.** In **Customization > Store Appearance** you pick the layout, the colors, the logo and the home page. See [Layout and colors](/en/appearance/). > [!TIP] > Your store address shows at the top of every dashboard screen, in **Store > Address**. Click it to open the storefront in a new tab and see each change > the way players see it. ## Game store or digital product store The store type comes from the plan chosen when the store is created, and it does not change later: | Type | For whom | What changes in the dashboard | | --- | --- | --- | | Minecraft | Minecraft servers | Servers, plugin, in-game delivery, VIP and launcher | | Hytale | Hytale servers | Servers, plugin and in-game delivery | | Digital products | Whoever sells files, keys or access | File, key or content delivery, no server | In a digital product store, the **Players** menu becomes **Customers**, and the server and plugin groups go away. See [Digital products](/en/products/digital/). ## Where to go next - [Get to know the dashboard](/en/store/dashboard/): the menu, the store bar, the language and Hyler. - [Store settings](/en/store/settings/): name, contact, time zone, terms and modules. - [Address and custom domain](/en/store/domain/): change the subdomain and connect your own domain. - [Team and access roles](/en/store/team/): bring your team in with the right permissions. # Create the account and the store Signing up on Hystore is a chat with Hyler. He asks one thing at a time and, while you answer, builds a preview of the store on the side with the name, the address and the layout you chose. At the end, the store is already live. ![The sign-up screen: the store preview on the left and the chat with Hyler on the right](shots/store-register.webp) ## Before you start Have at hand: - an email you can open now (a 6-digit code arrives); - the name of the server or the store; - the server IP, if you already have one (you can skip it and add it later); - your own domain, if you want to use one (you can skip it too). ## Step by step 1. Open [app.hystore.com.br/register](https://app.hystore.com.br/register). At the top you pick the language of the chat (**PT**, **EN** or **ES**). 2. **Your account.** Tell Hyler what to call you, then your email and a password. The password needs 8 to 128 characters, with an uppercase letter, a lowercase letter, a number and a symbol; Hyler checks each rule as you type, and the eye next to the field shows what you typed. Then pass the anti-bot check. 3. **Email confirmed.** Type the 6-digit code that arrived by email. If it did not arrive, check the spam folder. The resend button has a wait time that grows with each request. 4. **The store.** Pick the game (Minecraft, Hytale or digital products), the server name and the store address. Hyler checks right away whether `yourserver.hystore.com.br` is free. 5. Two optional steps: your **own domain** (Hyler shows the DNS records to set up) and the **server IP**. Tap **Not now** or **I don't have it yet** to skip. 6. Pick the **currency** and the storefront **layout**. The layout can change later, in **Customization > Store Appearance**. 7. **The plan.** Only the plans of the chosen store type show up. Hyler shows the price and whether the plan has a free trial. 8. Check the **summary**. If you have a Hystore coupon, type it in **Got a coupon? Type it here** and tap **Apply** to see the discounted price. 9. **Payment.** With a free trial, the store is created without any charge. Without one, the payment happens right there, in the chat, and the store is released once it is approved. > [!NOTE] > The free trial is once per account. With a trial, the store goes live without > asking for payment. If you already used the trial on another store, the new > one starts pending and is released as soon as the payment is approved. ## Create another store on the same account One account can have many stores, each with its own plan. 1. In the dashboard, click the **+** on the store bar, the thin column on the left. 2. The same chat opens, already knowing who you are: Hyler skips the account part and goes straight to the game, the name and the address. 3. Pick the plan and create. The new store shows up on the store bar, with the initials of its name. ![Creating another store with the + on the store bar: the chat starts at the store](shots/store-new.webp) > [!WARNING] > The store type (Minecraft, Hytale or digital products) comes from the plan > and does not change later. To sell another type, create another store. ## Addresses that cannot be used Some subdomains belong to the platform and are refused, like `api`, `painel`, `app`, `webhooks`, `cdn`, `checkout`, `suporte` and `hyler`, plus any address with `hystore` or `hyler` in it. Pick your server's name, like `redepixel` or `skyblock-world`. ## After creating - Open the [dashboard](/en/store/dashboard/) and follow the order in [First steps](/en/store/). - The plan and the charges are in [Plan and subscription](/en/store/plan/). # Get to know the dashboard The dashboard lives at [app.hystore.com.br](https://app.hystore.com.br). It is where you run the whole store: products, orders, players, look, plugin, Discord and the rest. This page shows where everything is. ![The dashboard open on Dashboard: store bar, menu, top bar and the month's numbers](shots/store-home.webp) ## The three columns **Store bar** (the thin column on the left): - each store of the account shows as a square with the initials of its name; click to switch stores; - the **+** creates another store (see [Create the account and the store](/en/store/create/)); - at the bottom are **My Profile** (the person icon) and **Logout**; - Hystore partners also see the handshake icon, which opens the [partner area](/en/store/partner-program/). **Store menu** (the middle column), in groups that open and close: | Group | What it has | | --- | --- | | Dashboard | The month's numbers | | Team | Sub-users, access roles and audit logs | | Players | The store's players and their roles (Customers, in a digital store) | | Store | Products, categories, coupons, partners, gifts, month goal, servers and orders | | Plugin | How it works, permissions and commands, what's new, in-game store, announcements and texts | | Finance | Entries, bills, budgets, reports and Hyler review | | Forum | Forum categories, boards and badges | | Support | Tickets, news, wiki and forms | | Customization | Store appearance, widgets, code theme, theme access and emails | | Launcher | The store launcher for Windows and Android | | Discord | The store bot in your Discord server | Below the groups come **Plans** and, at the end of the menu, **Settings**. **Content** (the big area on the right). At the top of every screen are the **Store Address**, which opens the storefront in a new tab, and how many days are left until the plan renews or expires. > [!NOTE] > A group only shows up when its module is on and the plan includes it. If one > is missing, check **Settings > Modules**. See > [Store settings](/en/store/settings/#modules). ## Theme, language and Hyler - In the top right corner, the **sun** or the **moon** switches between the light and the dark theme, and the **globe** switches the dashboard language between Portuguese, English and Spanish. The choice is kept in the browser. - Each screen with content shows the **Tip for this screen**, with three tips from Hyler. If you close it, click Hyler on the **Need Help?** card to bring it back. - On the same card, **Chat with Hyler** opens the help chat: ask in English, Portuguese or Spanish, like "where do I create a coupon?", and he answers with the path and the link to the screen. - **Replay the tour** shows again, screen by screen, where everything is. ## The Dashboard The first screen of the menu shows how the store is doing in the month: - **Total revenue**, **Orders** and **Average order value** (revenue divided by orders), compared with the previous month; - **Resource Usage**: how much of the plan is already used in products, categories, posts, coupons, team users, storage, servers and forms; - the charts of revenue over the month, orders by status and sales by category; - the summary of partners and tickets, and the latest orders. The month picker, at the top right, changes every number at once. > [!TIP] > When a **Resource Usage** bar gets close to the end, it is time to look at the > plans in **Plans**. See [Plan and subscription](/en/store/plan/). ## Useful to know - Switching stores loses nothing: each store keeps its own products, orders, settings and plan. - The **Store Address** link uses the primary address. If you connected your own domain, it shows there. See [Address and custom domain](/en/store/domain/). # Store settings **Settings**, at the end of the menu, holds the store details, the time zone, the social networks, the terms shown in the storefront and the modules that are on. The screen has five tabs: **General**, **Domains**, **Payments**, **Modules** and **Terms**. Domains and Payments have pages of their own: [Address and custom domain](/en/store/domain/) and [Payment methods](/en/payments/). ![The General tab of the settings: store details, time zone and social networks](shots/store-settings.webp) ## General The **General information** card holds the main details: | Field | What it is for | | --- | --- | | Store name | The store's name, as players and the dashboard see it | | Description | A short summary of what the store sells | | Company tax ID (CNPJ, optional) | Your Brazilian company number, if you have one | | Contact email | The store's contact email | After changing anything, click **Save changes**, at the end of the tab. ### Time zone The time zone decides at what time the store's day and month close. It applies to [Finance](/en/finance/) and to the ticket metrics on the Dashboard. 1. On the **Time zone** card, turn on **Close the day in the store time zone**. 2. Pick the time zone in the list. You can search, for example `Sao_Paulo` or `New_York`. 3. Click **Save changes**. > [!NOTE] > When it is off, the day closes in UTC. A sale at 11 pm on the 31st in New York > time only lands in the right month of Finance with `America/New_York` chosen. > Changing the time zone redoes the turn of every month right away, past months > included; nothing needs to be entered again. The sales numbers on the Dashboard still close the month in UTC, so near the turn of the month they can be a little different from Finance. ### Social networks On the **Social networks** card, paste the link of each profile: Instagram, Discord, Twitter / X, TikTok, Telegram and WhatsApp. Links must start with `https://`, for example `https://discord.gg/yourinvite` or `https://wa.me/15551234567`. An empty field does not show in the store. ## Terms The **Terms** tab holds the legal texts shown in the storefront: - **Terms of Service**: the purchase rules of your store; - **Privacy Policy**: how the store handles player data; - **Server rules**: the rules of conduct in the game; - **Data collection**: the text that explains which data the store collects. Write each text and click **Save terms**. ![The Terms tab with the store's legal texts](shots/store-terms.webp) > [!WARNING] > Your store's terms are yours: Hystore does not write or review this text. Be > clear about delivery time, refunds and what the player gets. That avoids > disputes with the payment provider. ## Modules The **Modules** tab turns parts of the store on and off: Forum, Wiki, Support (tickets), Forms, Launcher, Widgets, Emails, Discord, Finance, VIP and Code theme. 1. Find the module in the list. 2. Use the switch on the right to turn it on or off. The change applies right away and the menu group shows up or goes away. ![The Modules tab with the switch of each module](shots/store-modules.webp) Turning a module off deletes nothing: the content stays saved and comes back exactly as it was when you turn it on again. A module the plan does not include shows as locked, with the **See plans** button. > [!TIP] > Need to take the forum or the wiki down for a while to reorganize? Turn the > module off: players stop seeing it, nothing is lost, and everything comes back > the same when you turn it on again. # Address and custom domain Every store starts with a free Hystore address, like `redepixel.hystore.com.br`. On plans that include it, you can also connect a domain of your own, like `shop.yourserver.com`. Both addresses keep working at the same time. All of this is in **Settings > Domains**. ![The Domains tab: the Hystore subdomain on top and the custom domain below](shots/store-domain.webp) ## Change the Hystore subdomain 1. On the **Hystore subdomain** card, type the new name in **Subdomain**. Use only lowercase letters, numbers and hyphens. 2. Click **Check availability**. The screen says **Subdomain available** or **Subdomain already in use**. 3. Click **Save subdomain**. **Current domains** lists every address of the store; the one marked **(Primary)** is the one the dashboard uses in links. > [!WARNING] > Platform addresses are reserved and refused, like `api`, `painel`, `app`, > `webhooks`, `cdn`, `checkout`, `suporte` and `hyler`, plus any name with > `hystore` or `hyler` in it. The subdomain the store already has keeps working > until you save another one. ## Connect your own domain You need a registered domain (at GoDaddy, Namecheap, Cloudflare or wherever you like) and access to its DNS panel. 1. On the **Custom domain** card, type the domain in **Your domain**, for example `shop.yourserver.com` or `yourserver.com`. 2. Open your provider's DNS panel and create the records the screen shows in **How to set up the DNS**: | Type | Name | Value | Proxy (Cloudflare) | | --- | --- | --- | --- | | CNAME | `@` | `store.hystore.com.br` | Off (DNS only) | | CNAME | `www` | `store.hystore.com.br` | Off (DNS only) | 3. Back in the dashboard, click **Save custom domain**. 4. The security certificate (the HTTPS padlock) is issued on its own in a few seconds. You do not need to buy or install anything. > [!TIP] > On Cloudflare, leave the cloud **grey** (DNS only) on both records. With the > orange cloud, the store's certificate cannot be issued. Some providers do not accept a CNAME on the root record (`@`). In that case, create only the `www` record: the store opens at `www.yourdomain.com`. If your plan has no custom domain, the card shows **Premium feature**. See the plans that include it in [Plan and subscription](/en/store/plan/). ## The domain is already on another store If the domain is connected to another Hystore store (an old store of yours, for example), the screen shows **Prove the domain is yours**, with a TXT record that belongs to your store: | Type | Name | Value | | --- | --- | --- | | TXT | `_hystore.yourdomain.com` | the value the screen shows, with the **Copy** button | 1. Create this TXT record in the domain's DNS. 2. Click **Verify and bring the domain**. 3. Once the record is found, the domain leaves the other store and moves to yours. DNS propagation can take a few minutes. After the check, the TXT record can be deleted. ## Common problems | What happens | What to do | | --- | --- | | The store does not open on the new domain | Check that the CNAMEs point to `store.hystore.com.br` and wait for DNS propagation (minutes, sometimes a few hours) | | The browser says the connection is not secure | On Cloudflare, leave the cloud grey; the certificate is issued on its own once the DNS points straight | | The domain is "already in use" | It is on another store: use the TXT record above to bring it over | | The domain field does not show | The current plan does not include a custom domain | # Plan and subscription **Plans**, in the menu, holds the store's plan, the features it includes, the charges and everything that happened to the subscription. Only the store owner sees this screen. ![The Plans screen: the current plan, the domains and the available plans](shots/store-plan.webp) ## The three tabs | Tab | What it shows | | --- | --- | | Overview | The current plan, how many days are left, the renewal date, the included features, the domains and the available plans | | Invoices | Every charge, by card and by Pix, with the summary (total paid, last payment, next charge and open issues) and filters | | Timeline | Everything that happened, newest first: payments, attempts, plan changes and store changes | Plans are separate per store type (Minecraft, Hytale and digital products). A store can only switch to a plan of its own type. ## Change the plan 1. In **Available Plans**, pick the new plan. 2. Check the amount and the payment method. 3. Confirm. The new plan applies as soon as the payment is approved. To change or cancel a subscription that already exists, use **Manage Subscription**, on the current plan card. > [!NOTE] > Whoever pays with Pix and changes plan loses no days: what is left of the paid > period turns into extra days on the new plan. ## Payment methods In a store priced in Brazilian reais, the payment method is chosen at checkout: - **Credit card**: a recurring charge. The first charge happens right away and the next ones happen on their own, on the same card, every plan period, until you cancel in Plans. The payment screen shows the amount and how often before you confirm. - **Pix** and **Automatic Pix**, when Hystore turns Pix on: with Pix, each payment is worth one period, and the renewal arrives by email and shows in Plans with the QR code; with Automatic Pix, you authorize once in your bank app and each monthly payment is debited on its own. Stores priced in US dollars pay by card, through Stripe. > [!TIP] > With Automatic Pix on, one-off Pix and the card are unavailable, so you are > never charged twice. To change plan, turn on the Automatic Pix of the new plan; > the old one is canceled once the new one is authorized. ## Invoices and invoice PDF On the **Invoices** tab: 1. Use the filters by payment method and by status (paid, open, with a problem or refunded). 2. Click **Details** to see the summary of a charge. 3. Click **Invoice PDF** to download the Hystore invoice in the dashboard language. The receipts that exist, from the card or from Pix, are attached at the end of the same PDF. A failed card charge shows why it was declined, the attempts and when the next one happens, with the button to pay now. > [!WARNING] > The invoice PDF is not a Brazilian tax invoice (nota fiscal). ## Cancel and ask for a refund - **Up to 7 days** after subscribing, canceling refunds the last charge and ends the plan right away. This works once per store. On a card, the money comes back within 10 business days; with Pix, it goes back to the account that paid. - **After 7 days**, canceling takes effect at the end of the period already paid, without refunding part of it. When the plan ends by refund, the store moves right away to the free plan of the same type, if there is one and the store fits all its limits (products, categories, posts, coupons, forms, servers, team and storage). If it does not fit, the store is suspended and deleted 10 days later. The owner gets an email in both cases. The full rules are in the [Refund Policy](https://hystore.com.br/en/refunds). ## When a payment fails or the plan expires 1. Hystore warns you by email, with the deadline: 3 days from the warning (or until the end of the paid period, if that is later) to sort it out. 2. After the deadline, the store moves to the free plan of the same type, if it fits all its limits. If the free plan has no custom domain, the domain is turned off and the store stays on the Hystore address. 3. If it does not fit, the store is suspended (it goes offline for players) and is deleted 20 days later, with email warnings 15, 10, 5 and 1 day before. On a card, a reminder email also arrives 3 days before each charge, with the amount, the date and the card. ## Free plan and ads On a plan with ads, like the free one, the storefront may show Hystore ads, always with the **Ad** label and at most two per page. Cart, payment, profile, support, forms and legal pages never have ads. For a store without ads, subscribe to a paid plan (the free trial of a paid plan has no ads either). ## Hystore coupon The Hystore coupon gives a discount on the store's plan. It can come from a Hystore partner or from a promotion, and it goes in the summary when the store is created, in **Got a coupon? Type it here**. While the coupon is active, the Plans screen shows a strip with the code and how many payments still get the discount. That coupon is for the Hystore plan. The coupons your store gives players are in **Store > Coupons**; see [Coupons](/en/products/coupons/). # Team and access roles You do not need to run the store alone. In **Team**, in the menu, you bring people into the dashboard and choose what each one can see and do. The group has three screens: **Sub-users**, **Access Roles** and **Audit Logs**. The order that works: create the roles first, then invite the people. ## Create an access role A role is a set of permissions, like "Support" or "Administrator". Changing a role applies right away to every member who has it. 1. Open **Team > Access Roles** and click **New role**. 2. Give it a **Name** (for example, `Support`) and, if you like, a **Description** of what the person does. 3. In **Permissions**, check what the role can do. Permissions come in groups by area, like Products, Orders, Players, Coupons, Support Tickets, Posts, Wiki, Forms, Finance, VIPs and Discord. Each group has the view, create, edit or manage of that area. 4. Click **Create role**. ![Access Roles: each role shows the permissions it has](shots/store-roles.webp) > [!TIP] > Start small. A support role, for example, only needs to view and manage > tickets, view players and view orders. **Select all** is for a role you fully > trust, and **Clear all** empties the list. Every role needs at least one permission. To delete a role, use the trash icon; first make sure nobody is using that role. ### Permissions worth a closer look - **Finance** has three levels: **View Finance**, **Manage Finance** and **Receive budget alerts** (the person only gets the alert by email and on Discord, without opening Finance). - **Code theme** separates who views, who edits, who publishes and who creates access keys for tools and AI. - In a digital product store the **Digital products** group shows up, with managing files and keys, and the **Servers** group goes away. ## Invite someone to the team 1. Open **Team > Sub-users** and click **Invite**. 2. Fill in the person's **Email** and **Name**. 3. Pick the **Role**. It is required; if there is none yet, the **Create role** link takes you to the roles screen. 4. Click **Invite**. Whoever has no Hystore account yet gets one with the invite and receives the email to log in. Whoever already has an account starts seeing your store on the store bar. ![Sub-users: the store team with each person's role](shots/store-team.webp) In the list, the **Actions** column has: - **Role**: opens **Change role** to switch the person's role; - **Remove**: takes the person out of the store. Dashboard access ends right away. > [!NOTE] > Some screens belong to the owner only, like **Plans**, **Servers** and the > forum settings. They do not show for the team, whatever the role. ## Audit Logs **Team > Audit Logs** shows what was done in the store: who did it, when and on which resource. It helps explain a change ("who changed the VIP price?") and follow the team's work. 1. Filter by **action** or by **resource type** (like Ticket or Product). 2. Click **Search**. 3. Open a record to see the details. **See the original record** shows the action code and who acted. ![Audit Logs: each line says who did what and when](shots/store-audit.webp) What the platform itself did, like approving a payment, shows as **System**. Alert actions, like a webhook signature that does not match, are highlighted. # Profile and security **My Profile**, the person icon on the store bar (the thin column on the left), holds your details, your password, two-factor authentication and the link to the Hystore community Discord. These options belong to your account and apply to all your stores. ![My Profile: account details, password, two-factor authentication and the community Discord](shots/store-profile.webp) ## Name and email The display name can be changed; it is how the dashboard and the team see you. The account email does not change from the profile. The screen shows whether it is verified and since when you are a member. ## Change the password 1. On the **Change password** card, type the **Current password**. 2. Type the **New password** (at least 8 characters) and repeat it in **Confirm new password**. 3. Click **Change password**. Forgot your password? On the login screen, click **Forgot password?**: a reset link arrives by email, valid once and for a short time. ## Turn on two-factor authentication (2FA) With 2FA, logging in asks for the password and a code from your phone. Even if someone finds out the password, they cannot get in without the phone. 1. Install an authenticator app, like Google Authenticator or Authy. 2. On the **Two-factor authentication (2FA)** card, click **Turn on 2FA**. 3. Scan the QR code with the app. 4. Type the 6-digit code the app shows in **Verification code** and click **Confirm and turn on**. 5. The screen shows the **Recovery codes**. They only show now: click **Download codes**, keep the file somewhere safe and click **Saved them, close**. > [!WARNING] > Each recovery code works once, for when you do not have the authenticator app. > Without the app and without the codes, there is no way in. Keep the codes off > your phone. To create new codes, use **Regenerate codes** and confirm with the app's current code; the old codes stop working. To turn 2FA off, type the app's code in **Current code to turn it off** and click **Turn off 2FA**. > [!TIP] > Turn on 2FA for the store owner and ask the team to do the same. The dashboard > handles money, orders and player data: it is the simplest way to keep someone > with a leaked password out. ## Hystore Community on Discord The official Hystore Discord server gives roles to customers. You link your account here: 1. In the **Hystore Community on Discord** section, click **Connect Discord**. 2. Discord opens and asks for your authorization; it only shares your username. 3. Back in the dashboard, the section shows **Connected as** and your role in the server. The roles are **Cliente Hystore** for whoever has at least one active store, plus **Cliente PRO** on the Profissional plan and **Cliente Enterprise** on Network. The role follows the plan on its own and goes away when the account has no active store. **Disconnect** removes the roles. > [!NOTE] > That is the Hystore server. The Discord bot of your store, in your players' > server, is in the **Discord** group of the menu. See > [Connect the bot](/en/discord/). # Hystore partners The Hystore partner program is for people who recommend the platform, like content creators and owners of server networks. The partner gets a link and a coupon; whoever creates a store with them gets a discount on the plan, and the partner earns a commission on each payment. > [!NOTE] > Hystore decides who becomes a partner, by invitation. Without an invitation, > the partner area does not show up. This program is different from > [Store partners](/en/products/partners/), the partners your store has with > players. ## How to get in 1. The invitation arrives by email. If you do not have a Hystore account yet, it brings the link to create your password. 2. Log in to the dashboard. On the store bar, right above **My Profile**, the handshake icon shows up: that is the **Partner area**. It opens even without a store. ## What the partner area has | Part | What it shows | | --- | --- | | Your link | The address `hystore.com.br/p/yourname`, to copy. Whoever comes in through it is marked as your referral for 30 days, and the sign-up already has your coupon applied | | Your coupon | The code, the discount it gives, on how many payments, and how much you earn from each payment | | Visits | Visits through the link in the last 30 days, how many different people, and the chart of the last 90 days | | Stores that used your coupon | The store name, the plan, since when and whether it is paying | | Commissions | Each payment from a store with your coupon, with the amount paid, your commission, the status and when it is released | | Payouts | What Hystore has already paid you | | Payout details | Your Pix key and your Brazilian tax ID (CPF or CNPJ), stored encrypted (the screen only shows the end) | ## How the commission works 1. A store subscribes to a plan with your coupon. 2. Each payment from that store becomes a commission **on hold**. 3. After the hold period agreed with Hystore, the commission becomes **available**. 4. Hystore pays it out by Pix, to the details you registered. A refunded payment generates no commission. A commission can also show as paid out, reversed, under review or voided. > [!TIP] > Fill in the **Payout details** as soon as you get in. Without the Pix key, the > available commission waits until you complete them. If the partnership is paused, the screen says so: the coupon and the link stop giving a discount until Hystore turns them back on. # Products A product is what a player buys in your store: a VIP, a kit, cash, an unban. Each product has a name, a picture, a price, a category and, in a game store, the commands the plugin runs on the server when the payment is approved. Everything is in **Store > Products**. ![The product list, grouped by category, in the order they show in the store](shots/products-list.webp) > [!NOTE] > Before the first product, create at least one category. Without one, the > screen asks you to add a category first. See [Categories](/en/products/categories/). ## Create a product 1. In **Store > Products**, click **Create Product**. 2. In **Basic Information**, fill in the **Product Name**, the **Short Description** (it shows on the product card, up to 255 characters), the full **Description** and the **Category** (and the **Subcategory**, if there is one). 3. In **Product Image**, upload the picture. 800x800 px is recommended, PNG or JPG up to 5 MB. 4. In **Pricing**, enter the **Regular Price**. For a sale, turn on **Add Promotional Price?** and enter the **Promotional Price** and, if you like, the **Promotion Quantity Limit**. 5. Set up the delivery (see below) and click **Create Product**. ![The create product form: picture, purchase, duration, details and price](shots/products-create.webp) ### Purchase settings - **Set Purchase Limits?**: turn it on to require a **Minimum Quantity** per order and a limit per player. - **Manage Stock?**: off, the stock is endless. On, enter the **Stock Quantity**. Each order takes its units right when it is placed, an order that expires unpaid gives them back, and with stock at zero the store shows **Sold out** and does not let anyone buy more than there is. ### Product duration With **Permanent Product?** on, the purchase lasts forever. Turn it off to sell something that expires and enter the **Duration (in days)**, for example a 30-day VIP. ## Server delivery In **Server Delivery**, pick the **Delivery Server** and say what the plugin should do when the payment is approved. **How this product is delivered** has two options: - **Delivery commands**: the commands run on the server after the payment, one per line, in order. Use `{player}` where the buyer's nick goes. - **VIP system**: the plugin handles the whole VIP (it starts, counts the time and ends on its own). See [VIP on the product](/en/products/vip/). Examples of delivery commands: ```text Delivery Commands give {player} diamond_sword 1 eco give {player} 1000 broadcast &a{player} bought the Legendary sword kit! ``` > [!TIP] > Whoever buys more than one unit gets the commands once per unit: 3 units, 3 > times. For cash, create one product per pack (1,000, 5,000) instead of selling > cash unit by unit. With no server added, the list shows the shortcut to **Store → Servers**. See [Install the plugin](/en/plugins/). ### Site role In **Site role**, the product can give a player role to the buyer, like "Gold" or "Diamond". With a duration, the role lasts the same days and then the previous one comes back; buying again extends it. A staff role is never replaced, and whoever already has a higher-priority role keeps it. See [Players and roles](/en/products/players/). ## Product order In the list, each category is a card with its subcategories inside, and the products show in store order (the number next to them is the position). 1. Drag the product by the handle on the left. 2. Drop it in the new spot. The order is saved when you drop it and applies to the store and to `/loja` inside the game. With the keyboard: **Tab** to the handle, **space** to pick it up, the **arrow keys** up and down, **space** to drop it, **Esc** cancels. The order is within the category: to move a product to another one, change the category in the form, and it goes to the start of the new one. A new product also goes to the start. With a search or a status filter on, the handle goes away, because the list is not complete. ## Edit, deactivate and delete - **Edit** opens the same form, all filled in. - In the three-dot menu, **Deactivate** takes the product out of the storefront without deleting anything; **Activate** brings it back. - **Delete** is final: the product leaves the store and does not come back. > [!WARNING] > Prefer deactivating over deleting a product that has already sold: deactivated, > it leaves the storefront and can come back whenever you want. Deleted, it does > not come back. ## Going further - [VIP on the product](/en/products/vip/): the VIP that starts and ends on its own. - [Digital products](/en/products/digital/): file, key or content. - [Coupons](/en/products/coupons/) and [Gifts](/en/products/gifts/): discounts and redeem codes. # Categories Categories group the products in the store, like VIPs, Kits and Cash. Each one has its own page in the storefront, with a picture and a banner, and it can have subcategories. Everything is in **Store > Categories**. ![The category list with the number of products and the subcategories](shots/products-categories.webp) ## Create a category 1. In **Store > Categories**, click **Create Category**. 2. In **Category Name**, type the name, for example `VIPs`. 3. The **Slug (URL friendly)** is the piece of the address of the category page in the store, like `vips`. If you leave it blank, it comes from the name. Use only lowercase letters, numbers and hyphens. 4. In **Category Image**, upload a square picture (300x300 px recommended): it shows in the list. 5. In **Category Banner**, upload the wide banner (1200x400 px recommended): it shows at the top of the category page. 6. Click **Create Category**. ![The create category form](shots/products-category-create.webp) ## Subcategories To organize further, create categories inside categories, up to 3 levels: **Root → Level 1 → Level 2**. Example: ```text Example layout Kits ├── PvP kits │ ├── Swords │ └── Bows └── Building kits ``` 1. When creating, turn on **Is this a subcategory?**. 2. In **Parent Category**, pick the category above it. > [!TIP] > A few well-chosen categories sell more than many. Players find what they want > faster. Use a subcategory when a category grows past about 8 products. ## Edit, deactivate and delete - **Edit** changes the name, the slug, the picture and the banner. - **Deactivate** hides the category from the store without deleting anything; **Activate** brings it back. - **Delete** is final. To change the order of the products inside a category, use the product list. See [Products](/en/products/#product-order). # Digital products A digital product store sells what is delivered over the internet: files (textures, maps, plugins, e-books), license keys and access. It has no game server, plugin, commands or nick: the buyer logs in with their email and gets everything in **My purchases**, on their profile in the store. > [!NOTE] > The store type comes from the plan chosen when the store is created. To sell > digital products, create a store of the **Digital products** type. There, the > **Players** menu becomes **Customers** and **Servers** leaves the menu. ## The two delivery types When you create the product, the **Digital delivery** card asks for the type: | Type | What the buyer gets | Stock | | --- | --- | --- | | File to download | The newest file you uploaded, to download | Endless | | License key | A key from your stock, only theirs | The number of active keys | The type does not change after the product is created. To sell another way, create another product. After creating, the dashboard opens the **Product delivery** screen. Later, on the edit product screen, the **Manage delivery** button takes you there. ![The Product delivery screen of a file: upload a new version and the uploaded versions](shots/products-digital.webp) ## File to download 1. In **Upload a new version**, drag the file to the dashed area or click it to choose. It accepts up to 500 MB: zip, rar, 7z, jar, pdf, images and other common formats. Executable programs are not accepted. 2. Enter the **Version** (for example `2.1`) and, if you like, what changed. 3. Click **Upload version**. Each upload becomes a version, listed in **Uploaded versions**. Buyers always download the newest one, including those who bought before it. The download limit per purchase goes from 1 to 1000, or stays empty for no limit. > [!WARNING] > A file product with no uploaded version cannot be bought. Upload the first > version before you announce it. ## License key 1. Paste the keys, one per line, up to 2000 per upload. Repeated keys are left out. 2. Each purchase gets one active key. Each key shows on a card with its status: - **Active**: goes to the next purchase; - **Sold out**: already delivered to a buyer and stays with them; - **Inactive**: turned off by the store; no purchase gets it. An active key can be turned off, and an inactive one turned back on. The list shows 9 keys per page, with a status filter and a search: up to 4 characters searches the end of the key; pasting the whole key finds exactly that one. > [!NOTE] > The dashboard stores the key encrypted and only shows its end. That is why you > cannot search for a piece in the middle. With no active key, the store shows > **Sold out**; if a purchase runs out of keys, the delivery finishes on its own > once you paste more. ## Message to buyers On the same screen, the **Message to buyers** is an optional text of up to 10,000 characters: install steps, a link, an access. It shows in **My purchases** next to the file or the key, only for buyers, with clickable links. ```text Example message Thanks for buying! 1. Download the file below. 2. Put the folder in .minecraft/resourcepacks. 3. Turn it on in Options > Resource Packs. Questions? https://discord.gg/yourserver ``` ## On the order In **Store > Orders**, the order of a digital product has the **Digital delivery** card, with each unit, the downloads used and the end of the key that was delivered. **Revoke access** takes that unit away from the buyer. A refund through the payment provider revokes the access on its own. See [Orders](/en/products/orders/). Uploading and deleting versions, pasting and removing keys and revoking access need the **Manage files and keys** permission. See [Team and access roles](/en/store/team/). # VIP on the product On Hystore, the VIP is written on the product itself. With the **VIP system**, the plugin takes care of everything on the server: it puts the player in the group, counts the time, shows `/vip` with a menu, warns before it ends and removes the VIP on its own at the end. There is no separate VIP screen. ![The server delivery of a VIP: VIP system with LuckPerms](shots/products-vip.webp) ## Turn on the VIP system 1. In **Store > Products**, create or open the VIP product. 2. In **Product Duration**, turn off **Permanent Product?** and enter the days (for example, 30). For a VIP that lasts forever, leave **Permanent Product?** on. 3. In **Server Delivery**, pick the **Delivery Server**. 4. In **How this product is delivered**, pick **VIP system**. Delivery commands that were already written move to the commands on activation. 5. Set up the options below and save the product. ## How the VIP is given on the server | Option | When to use | What happens | | --- | --- | --- | | LuckPerms (recommended) | The server uses LuckPerms | The plugin puts the player in the group you enter. With a time limit, LuckPerms itself removes it when it ends, even with the store offline | | Custom commands | Another permission plugin | You write the commands to add and to remove, which run when the VIP starts and when it stops | With LuckPerms, the group is the VIP: two products with the same group (for example 30 and 90 days, or 30 days and permanent) are the same VIP, and the time adds up. The dashboard shows which other product shares the VIP, and the rules apply to all of them. > [!WARNING] > If LuckPerms is chosen and the delivery server does not have LuckPerms > installed, the product warns that the VIP will not be given. Install LuckPerms > or use **Custom commands**. ## The other options - **VIP name in game**: the name shown in `/vip`. - **When it starts**: **At purchase**, or when the player activates it in `/vip` (the VIP is stored until then). - **How the time runs**: real time (the default: it runs even with the player offline) or only while the player is online (it counts play time only). - **Accepts upgrade**: whoever has a lower-priority VIP sees this VIP in **My VIPs** and in `/vip upgrade`, and pays only the difference. - **Commands on activation**: run once, the first time the VIP applies (kit, tag, announcement). - **Commands when it ends**: run once, when the VIP ends for good. - In the advanced options: how many days ahead to warn about the end, the priority (with more than one VIP, the highest priority applies and the others wait paused, losing no time), the color and the menu item in the game. Commands accept `{player}`, `{vip}`, `{dias}` (days) and `{segundos}` (seconds). On a permanent VIP, `{dias}` is 36500. ```text Commands on activation give {player} diamond 16 broadcast &6{player} is now {vip}! ``` > [!TIP] > Do not put a command that adds the group forever (like `lp user {player} parent > add vipgold`) in the commands on activation: with it, the VIP never ends. The > VIP system itself adds and removes the group. ## VIP upgrade With **Accepts upgrade** on, a player with a smaller VIP buys the bigger one by paying the difference, through the store cart. The price comes from the products on sale for each VIP: the player pays the difference in price per day times the time left, never less than R$ 1.00. Once paid, the time that was left moves to the new VIP. Coupons do not discount an upgrade. ## Buying again, refunds and the game - Buying again adds time (the days times the quantity). - A refund or cancellation removes the days of that purchase. When the VIP ends, the commands when it ends run and the next paused VIP applies again. - In the game, the player uses `/vip` (profile, my VIPs, activate, switch and history) and `/tempovip`. They also see their VIPs on their store profile, in **My VIPs**. - With PlaceholderAPI on the server, there are `%hystore_vip%`, `%hystore_vip_dias%` and `%hystore_vip_tempo%`. Whoever has a VIP shows in **Players**, on the **With VIP** tab, where you give, remove time, freeze and remove VIPs by hand. See [Players and roles](/en/products/players/#player-vips). # Coupons A coupon gives the player a discount at checkout. It works for welcome offers, date promotions (Black Friday, the server's anniversary), partnerships with content creators and Discord campaigns. Everything is in **Store > Coupons**. ![The coupon list with the discount, the uses and the validity of each one](shots/products-coupons.webp) ## Create a coupon 1. In **Store > Coupons**, click **Create Coupon**. 2. In **Basic Information**, enter the **Coupon Code** (for example `WELCOME10`) and the **Coupon Name**, which only you see. The code is saved in uppercase and does not change later. 3. In **Discount**, pick the **Discount Type**: **Percentage (%)** or **Fixed Amount ($)**, and the value. 4. If you like, limit the coupon: - minimum purchase amount; - total use limit (for example, the first 300); - limit per player (for example, 1 use per player); - expiration date; - the products it applies to. 5. Save. ![The create coupon form](shots/products-coupon-create.webp) An expired coupon stops working on its own. In the list, each coupon shows its status (**Active**, **Inactive** or **Expired**), the discount, the uses, the validity and the minimum purchase. > [!TIP] > Combine limits for a safe promotion. A Black Friday example: `BLACK20`, 20% > off, 300 uses in total, 1 per player, expiring on Sunday night. For a welcome > coupon, 1 use per player is enough. ## Announce on the server In Minecraft and Hytale stores, check **Announce on the server** when saving: whoever is playing sees the code, the discount and the validity in the chat. With **Also as a title on screen**, the announcement shows big in the middle of the screen. Only an active, valid coupon is announced, and whoever announces needs the permission to send notices to the server. ## Partner coupon In **Partner coupon**, the coupon can be linked to a player, like a content creator. Each sale paid with the coupon becomes a commission for them. The coupon then shows the partner badge and the nick. See [Store partners](/en/products/partners/). ## Edit and delete **Edit** changes everything but the code. On the edit screen, the **Coupon Status** switch turns the coupon on and off: off, it stops working and can be turned on again later. **Delete** is final. > [!NOTE] > These are the coupons your store gives players. The coupon that discounts the > Hystore plan is a different one, used when the store is created. See > [Plan and subscription](/en/store/plan/#hystore-coupon). # Gifts A gift is a redeem code that gives the player store credit or a product, without paying. It works for giveaways, event rewards, streams, partnerships and to make up for a problem on the server. Everything is in **Store > Gifts**. ![The gift list with the type, the uses and the validity](shots/products-gifts.webp) ## Create a gift 1. In **Store > Gifts**, click **Create Gift**. 2. Enter the **Gift Code** (the wand next to it generates a code) and the **Gift Name**. 3. In **Reward Type**, pick the **Gift Type**: - **Credit ($)**: the amount goes to the player's balance in the store; - **Product**: the product is delivered on redeem, like a purchase. 4. Set, if you like, the total redeem limit and the validity. 5. Save. ![The create gift form](shots/products-gift-create.webp) Each player redeems each gift only once. A product gift delivers what the product delivers: if the product uses the VIP system, the gift gives the VIP (the product's days, or forever on a permanent product). > [!NOTE] > Gifts cannot be edited. To change one, delete it and create another with the > same code. ## Redeem on the site and in the game - **On the site**: the player opens the store's **Gifts** page (the address ends in `/presentes`) and types the code. - **In the game** (Minecraft and Hytale, plugin 2.8.0 or newer): with the account linked through `/vincular`, the player uses `/resgatar ` (or `/usarkey`). The same rules as the site apply: active, within the date, within the use limit and once per player. ```text In the game chat /resgatar LIVE500 ``` Typing a wrong code many times blocks new tries for a few minutes. See [Linking and commands](/en/plugins/linking/). > [!TIP] > For a stream, create a credit gift with a use limit and a short validity, like > `LIVE500`, 100 redeems, valid until the end of the week. Whoever was watching > gets it, and the code does not float around for months. # Month goal The month goal shows on the store home page how much the community has bought and how much is left to reach an amount, with rewards at each milestone. It is a way to turn sales into an event: "at R$ 5,000, there is a new BedWars map". Everything is in **Store > Month Goal**. ![The Month Goal screen: amount, dates and rewards with the in-game reward](shots/products-goal.webp) ## Create the goal 1. In **Store > Month Goal**, turn on **Enable Monthly Goal**. 2. Enter the **Goal Target Amount**, the **Start Date** and the **End Date**. 3. In **Rewards**, click **Add Reward** for each milestone. Each one has the **Reward Description** and the **Required Amount**. 4. Save. The preview, on the same screen, shows how the goal looks in the store. The collected amount adds up on its own from confirmed orders (paid, processing, shipped or delivered) from the start date on. ## In-game reward In Minecraft and Hytale stores (plugin 2.7.0 or newer), each milestone can have an in-game reward for when the store passes it: - **Who receives it**: **Who is online on the server** (whoever is playing at that moment) or **Everyone on the server, even offline** (whoever is offline gets it when they join, up to 30 days later; only those who had played before the milestone; on Hytale, only those online). - **For each player who receives it**: one command per line, without the slash, with `{player}` where the nick goes. - **Once on the console**: commands without a player, which run once on each server. ```text For each player who receives it give {player} diamond 5 eco give {player} 500 ``` ```text Once on the console say The goal was reached! Thank you, community! ``` When the store passes the milestone, the chat tells everyone and the commands run only once per goal; refunds and editing the goal do not repeat them. Up to 20 commands in each box, up to 500 characters each. > [!NOTE] > A milestone the store had already passed when the commands were saved is marked > as reached, and its commands do not run. Editing the commands needs the plugin > settings permission. ## The goal on the game screen On the in-game goal card (plugin 2.5.0 or newer), with each purchase that moves the goal, the top bar and the bottom bar of the screen show how much is left: only when someone buys (for the time you pick, from 3 to 300 seconds) or fixed on screen all the time. Pick both, just one or none, the color and the bar design. The same design applies to the PlaceholderAPI placeholders: `%hystore_meta_barra%`, `%hystore_meta%`, `%hystore_meta_atual%`, `%hystore_meta_alvo%` and `%hystore_meta_falta%`. > [!TIP] > Goals that work have rewards for everyone, not only buyers: a double XP event, > a kit for the whole server, a new map. That way those who do not buy also cheer, > and spread the word. # Store partners Store partners are players with their own coupon, like content creators who promote the server. Each sale paid with their coupon becomes a commission, and you follow everything in **Store > Partners**: sales generated, commission owed and payouts made. ![The partner list with sales, commission on hold, available and paid](shots/products-partners.webp) > [!NOTE] > The money from sales goes to your payment provider account, as always. You pay > the commission to the partner, by Pix or in store credits. Hystore calculates, > you pay and record it. ## Create a partner A partner is born from a coupon: 1. In **Store > Coupons**, create or open the partner's coupon, for example `TIOCRAFT`. 2. In **Partner coupon**, link the coupon to the player and set the commission (as a percentage or a fixed amount). 3. Save. The player shows up in **Store > Partners**. ## How the commission moves 1. A player buys with the partner's coupon. 2. The commission stays **On hold** for the days you set. The hold covers the payment provider's refund window. 3. After the hold, it becomes **Available to pay**. 4. You pay the partner (Pix or store credits) and click **Record payout** on the partner. The partner's screen has the sales and the commission per day, their coupons and the payout history. Use **Reverse** on a sale that should not earn a commission; a refund through the payment provider also removes the commission. If the commission goes negative, the reversal is taken from the next payout. ## Suspend and delete - **Suspend** makes the partner's coupons stop working. - **Delete** removes the partner from the list and from the partner area in the store. Before that, pay or reverse what is on hold or available. ## What the partner sees The partner follows sales and commission in an area of their own, on their account in your store. > [!TIP] > A 30-day hold covers most card and Pix refunds. Paying before that risks paying > commission on a sale that will be returned. This is your store's program with players. Hystore's own partner program is a different one; see [Hystore partners](/en/store/partner-program/). # Orders Every purchase in the store becomes an order. In **Store > Orders** you see all of them, with the player, the total, the payment method, the date and the status, and open each one for the details and the delivery. ![The order list with the player, the total, the payment and the status](shots/products-orders.webp) ## Find an order The search at the top accepts the order number, the player's nick or the status. **Clear** goes back to the full list. ## Order statuses | Status | What it means | | --- | --- | | Pending | The order was placed and is waiting for the payment | | Paid | The payment was approved and the delivery was created for the server | | Delivered | The delivery finished in the game | | Expired | 45 minutes passed without payment: the order stops counting and returns the stock | | Cancelled | The order was cancelled | | Refunded | The payment was refunded or disputed at the payment provider | ## Order details Open an order to see: - the **Order items**, with the quantity and the price of each one; - the **Summary**: subtotal, discount (and the coupon used), credits used and total; - the **Nickname** that receives the delivery; - the **Payment**: the method and the **Payment ID**, the transaction number at the payment provider, handy to find the sale there; - the server delivery, with each command and whether it was delivered. ![The details of an order: items, summary, player, payment and delivery](shots/products-order.webp) > [!TIP] > A player says they paid and did not get it? Open the order. If it is > **Pending**, the payment provider has not approved the payment yet. If it is > **Paid** and the delivery did not go out, check that the server is on and the > plugin connected in **Store > Servers**: the delivery waits for the server and > goes out on its own. ## Refund and dispute An order refunded or disputed at the payment provider becomes **Refunded**: - deliveries that had not gone out to the server are cancelled; - credits bought in that order leave the player's balance (what they already spent does not come back); - the order stops counting in the dashboard sales. A VIP given by the VIP system also loses the days of that purchase. See [VIP on the product](/en/products/vip/). ## Digital products In a digital product store, the order shows the **Digital delivery** card, with what the order released in **My purchases**: each unit, the downloads used and the end of the key delivered. **Revoke access** takes that unit away from the buyer. See [Digital products](/en/products/digital/). # Players and roles A player is whoever creates an account in your store to buy, open a ticket or join the forum. The **Players** group in the menu has two screens: **Players**, with every account, and **Roles**, with the players' roles (VIP, staff and others). In a digital product store, the group is called **Customers**, and customers log in with their email, without a nick. ![The player list with the role, the status and the sign-up date](shots/products-players.webp) ## Find and create players - The search accepts name, email or nickname. - **New Player** creates an account by hand, with name, email, password and nickname. Without picking a role, the default role applies. In a digital store, the new customer form does not ask for a nick: it comes from the email. ## The player's profile Open a player to see the total spent, the credits, the last login, the sign-up date, the orders, the tickets, the cart, the redeemed gifts and the Discord link. On the profile: - **Send Credits** adds balance to their account; the history is in **Credits History**; - **Edit User** changes name, email, nickname and role; - **Ban User** and **Unban User**; - **Deactivate account** blocks logging in and buying, but keeps the orders and the credits; - **Export Data (GDPR)** downloads everything the store keeps about that player, to answer a data request. ![The player's profile with balance, sign-up and their VIPs](shots/products-player.webp) ## Player VIPs On the **With VIP** tab, in **Players**, are all the store's VIPs. Search by nick or email and filter by status (active, stored, paused, frozen, ended, removed) and by VIP. ![The With VIP tab: each VIP with its status and time left](shots/products-player-vips.webp) - **Give VIP** asks for the nick, the VIP and the days, or forever. It adds to the VIP the player already has, or creates it. - In each row's menu: **Add 7 days**, **Change time** (a negative number removes time; removing everything ends the VIP), activate (for stored or paused), **Freeze** (stops the clock and removes the VIP on the server; **Unfreeze** brings it back), **Remove** and **History**. Every action goes to the VIP history, with the email of whoever did it, and to the store audit. In the game, staff with the `hystore.admin.vip` permission use: ```text Staff commands in the game /vip admin /darvip /removervip /congelarvip ``` ## Player roles **Players > Roles** holds the roles players have in the store and the forum, like Member, Gold VIP, Moderator and Administrator. 1. Click **Create role**. 2. Enter the **Role name** and the **Priority**: a higher number sits higher in the hierarchy. The arrows in the list change the order. 3. Check **This is a staff role** only for the server team. A staff role cannot be sold. 4. In **Visual customisation**, the **User CSS** and the **Badge CSS** change the player's name and badge in the forum. 5. Save. ![Player roles, from highest to lowest](shots/products-roles.webp) ```css Badge CSS background: #d97706; color: #ffffff; font-weight: 700; ``` The **Default** role is the one every new player gets. A product can give a role to the buyer (see [Products](/en/products/#site-role)), and, with the Discord bot, the role can be linked to a role in the Discord server (see [Linking and roles](/en/discord/linking/)). > [!NOTE] > On a staff role you can check server team permissions, like publishing news, > receiving budget alerts and the new ticket alert in the game. These are game and > site permissions, different from the [dashboard access roles](/en/store/team/). # Payment methods On Hystore, each store gets paid through its own account at the payment provider (the gateway). The money from sales goes straight to your Mercado Pago, Stripe, PayPal or PicPay account: Hystore does not receive, hold or pass on the money from sales. Everything is in **Settings > Payments**. ![The Payments tab: each gateway with its on switch and the credential fields](shots/payments-tab.webp) ## Which gateway to pick | Gateway | Payment methods | Good for | | --- | --- | --- | | [Mercado Pago](/en/payments/mercado-pago/) | Pix, card and boleto | Stores in Brazil: Pix is the method that sells the most | | [Stripe](/en/payments/stripe/) | Cards from all over the world | Players outside Brazil, international cards | | [PayPal](/en/payments/paypal/) | PayPal account and card | Players from other countries who prefer PayPal | | [PicPay](/en/payments/picpay/) | Pix, card and PicPay balance | Whoever already uses PicPay to get paid | You can turn on more than one at the same time: the player picks at checkout. ## How to connect a gateway Each card on the tab has a step by step inside the screen itself. The path is always the same: 1. Create the application (or app) on the gateway's site, with your account. 2. Copy the credentials (keys and tokens) and paste them into the card's fields. 3. Register on the gateway's site the **webhook address** the screen shows, with the **Copy URL** button. 4. Turn on the gateway's switch and save. > [!WARNING] > The webhook is what approves orders on its own: it is how the gateway tells the > store the payment went through. Without the webhook registered, the player pays > and the order stays stuck in **Pending**. Once saved, the secrets you paste (Access Token, secret key, Client Secret) do not come back to the screen: it shows **(configured)** instead of the value. > [!TIP] > Use production credentials to get paid for real. Test (sandbox) credentials only > simulate the payment: they are for checking that everything works before opening > the store. ## Payment guide in the store wiki On the Mercado Pago and PayPal cards, the **Add payment guide to store Wiki** button creates an article in your store's wiki explaining to players how to pay (Pix, card or PayPal). See [Store wiki](/en/community/wiki/). ## Store balance (credits) Besides the gateways, a player can have balance in the store: credits they buy, get as a gift or receive from the team, and use to pay for orders. The balance is a record of your store, not money held by Hystore. ## Fees and Finance With the Finance module on, each active gateway has the **Fees for Finance** block, where you confirm the fees Finance takes off each sale. See [Gateway fees](/en/payments/fees/). # Gateway fees Every gateway charges a fee per sale. For [Finance](/en/finance/) to show the real profit, it takes that fee off each sale. Fees are in **Settings > Payments**, on the card of each active gateway, in the **Fees for Finance** block (click to open it). ![The Mercado Pago Fees for Finance block, with the fee of each payment method](shots/payments-fees.webp) > [!NOTE] > The block only shows with the Finance module on. Fees do not change what the > player pays or what the gateway charges: they are only for Finance's numbers. ## Confirm the fees 1. Open **Fees for Finance** on the gateway's card. 2. Each gateway comes filled with its public table, in the store currency. For each payment method there is the percentage on the order amount and the fixed amount per order. 3. Check it against your contract. A negotiated contract changes the numbers. 4. In **Applies to**, pick: - **All sales, including past ones**: fixes the history too; - **Sales from**: keeps the old fee on sales before the date. 5. Click **Confirm fees**. Until you confirm, the block shows **Not confirmed**, that gateway's sales show in Finance with no fee taken off, and the Finance overview warns you, with a link that opens the right gateway. ## Example A R$ 50.00 credit card sale, with a fee of 4.98% + R$ 0.00: ```text Calculation fee = 50.00 × 4.98% + 0.00 = 2.49 Finance counts: revenue 50.00, gateway fee 2.49 ``` The discount shows as **Gateway fees** on the overview and in Entries, and goes into the profit, the margin per product, the budgets and the forecast. ## What changes per gateway | Gateway | What to know | | --- | --- | | Mercado Pago | Pick the same payout term as your account (**Receive right away**, **in 14 days** or **in 30 days**), found under fees and installments on the Mercado Pago site | | Stripe | The checkout does not say whether the sale was by card, Pix or boleto: all use the card fee | | PayPal | The real fee of each sale comes from reconciliation, when available | | PicPay | Does not report the fee of each sale: always uses the table. The Pix fee comes blank for you to fill in | > [!TIP] > On Mercado Pago, Stripe and PayPal, when [Reconciliation](/en/finance/reconciliation/) > reads the real fee of a sale, it replaces the table. The table still applies to > sales not yet reconciled. ## A gateway that is off A gateway that is off and never sold does not show the block and appears only as Inactive in **Finance > Settings**. If it already sold, the block stays on the card, because the old sales still use the table, and it says how many sales have no fee. # Mercado Pago Mercado Pago takes Pix, card and boleto, with the money going to your Mercado Pago account. It is the gateway most used by stores in Brazil. You need a Mercado Pago account (personal or business). The step by step is also on the Mercado Pago card, in **Settings > Payments**, under **How to set up Mercado Pago, step by step**. ![The Mercado Pago step by step open in the dashboard, with the webhook URL to copy](shots/payments-mp.webp) ## 1. Create the application 1. Open the [Mercado Pago Developer Panel](https://www.mercadopago.com.br/developers/panel/app) and log in with your account. 2. Click **Create application** (Criar aplicação). 3. Give it a name (for example, `Rede Pixel`), check **Online payments** (Pagamentos online) and save. ## 2. Copy the Public Key and the Access Token 1. Inside the application, open **Production credentials** in the side menu. 2. Copy the **Public key** and paste it into the **Public Key** field of the dashboard. 3. Copy the **Access token** and paste it into the **Access Token** field. > [!WARNING] > Use the production credentials. Test ones only simulate: the player "pays" and > nothing reaches your account. ## 3. Set up the webhook 1. In the application's side menu, open **Webhooks > Configure notifications**. 2. In **Production URL**, paste the URL the dashboard shows (**Copy URL** button). It looks like this: ```text Webhook URL https://webhooks.hystore.com.br/api/v1/webhooks/mercadopago/ ``` 3. In **Events**, check only **Payments**. 4. Click **Save**. 5. Mercado Pago shows the **Secret key** (Signing Secret). Copy it and paste it into the **Webhook Secret** field of the dashboard. ## 4. Turn it on and save Turn on the Mercado Pago card's switch and save. Done: Pix, card and boleto show up for the player at checkout. > [!TIP] > Make a cheap test purchase (a R$ 1.00 product, for example) with Pix. If the > order moves to **Paid** on its own within seconds, the webhook is right. ## Common problems | What happens | What to do | | --- | --- | | The order stays Pending after the Pix is paid | Check the webhook production URL and that the **Payments** event is checked | | Error on save: Public Key or Access Token | Both fields are required and must be production ones, from the same application | | Test payments do not show in the account | Test credentials only simulate; switch to production ones | Mercado Pago fees in Finance: see [Gateway fees](/en/payments/fees/). # Stripe Stripe takes cards from all over the world, with the money going to your Stripe account. It is the choice for selling to players outside Brazil. You need a Stripe account activated for payments (with the company details and the bank account filled in on the Stripe Dashboard). ![The Stripe card in the dashboard with the webhook step by step](shots/payments-stripe.webp) ## 1. Copy the API keys 1. On the [Stripe Dashboard](https://dashboard.stripe.com/apikeys), open **Developers > API keys**. 2. Switch to live mode (test mode off). 3. Copy the **publishable key**, which starts with `pk_live_`, and paste it into the **Public Key** field of the dashboard. 4. Reveal and copy the **secret key**, which starts with `sk_live_`, and paste it into **Secret Key**. Stripe shows the secret key only once: keep it somewhere safe. ## 2. Create the webhook 1. On the Stripe Dashboard, open **Developers > Webhooks** and click add endpoint. 2. Paste as the destination the URL the dashboard shows. It looks like this: ```text Webhook URL https://webhooks.hystore.com.br/api/v1/webhooks/stripe/ ``` 3. Select these events: ```text Webhook events checkout.session.completed checkout.session.async_payment_succeeded checkout.session.async_payment_failed checkout.session.expired charge.refunded charge.dispute.closed ``` 4. Save the endpoint and copy the **signing secret**, which starts with `whsec_`. 5. Paste it into **Webhook secret**, in the dashboard. > [!WARNING] > The webhook secret is required. Without it, the store cannot check that the > notice really came from Stripe, and a paid order is never confirmed. ## 3. Turn it on and save Turn on the Stripe card's switch and save. The player pays on a secure Stripe page and comes back to the store with the order approved. > [!NOTE] > Stripe's checkout does not say whether the sale was by card or another method, so > Finance uses the card fee for every Stripe sale. See > [Gateway fees](/en/payments/fees/). ## Refunds and disputes With the `charge.refunded` and `charge.dispute.closed` events, a refund and a lost dispute on Stripe mark the order as **Refunded** on their own: deliveries that had not gone out are cancelled. See [Orders](/en/products/orders/). # PayPal PayPal takes payments from players all over the world, with a PayPal account or a card, and the money goes to your PayPal account. You need a **PayPal Business account**: it is free and different from a personal account. If you do not have one, create it at [paypal.com](https://www.paypal.com/br/business) and confirm the email before going on. ![The PayPal step by step open in the dashboard](shots/payments-paypal.webp) ## 1. Log in to the developer portal 1. Go to [developer.paypal.com](https://developer.paypal.com/). 2. Click **Log in to Dashboard** and log in with the Business account email and password. ## 2. Create the app and copy the credentials 1. In the left menu, click **Apps & Credentials**. 2. Click **Create App**, give it a name (for example, `Rede Pixel`) and click **Create App**. 3. Copy the **Client ID** and paste it into the dashboard field. 4. Click **Show**, below the Client ID, to reveal the **Client Secret**. Copy it and paste it into the dashboard field. > [!WARNING] > Keep the Client Secret somewhere safe. If you close the page without copying it, > you will need to generate another one. ## 3. Register the webhook 1. On the same app page, scroll to **Webhooks** and click **Add Webhook**. 2. In **Webhook URL**, paste the URL the dashboard shows. It looks like this: ```text Webhook URL https://webhooks.hystore.com.br/api/v1/webhooks/paypal/ ``` 3. In **Event types**, check only these events: ```text Webhook events Checkout order approved Payment capture completed Payment capture denied Payment capture refunded Payment capture reversed ``` 4. Click **Save Webhook**. 5. PayPal shows the new webhook with a code, like `5XA12345ABCDE`. Copy it and paste it into the **Webhook ID** field of the dashboard. ## 4. Sandbox or production The PayPal portal starts in **Sandbox** mode (testing with fake money). Make a test purchase. When everything works, go back to the portal, switch to **Live** at the top, and repeat steps 2 and 3 to get the production credentials and Webhook ID. In the dashboard, the PayPal card shows **PRODUCTION** or **SANDBOX**. > [!TIP] > Sandbox and Live credentials are different, and so is the webhook. If the store > is in production and orders do not get approved, check that the Webhook ID you > pasted is the Live one. ## Guide for players The **Add payment guide to store Wiki** button creates in your store's wiki an article explaining to players how to pay with PayPal, step by step. # PicPay PicPay takes Pix, card and PicPay wallet balance, with the money going to your PicPay business account. You need an account on the **PicPay Business Panel** (Painel de Negócios). ![The PicPay card in the dashboard, with where to get each credential](shots/payments-picpay.webp) ## Where to get each credential | Dashboard field | Where it is on PicPay | | --- | --- | | Client ID and Client Secret | Business Panel > **Integrations** > **Checkout API test** card > **Generate**. The Secret shows only once: keep it | | Webhook token | Business Panel > **Settings** > **My Checkout**, when you register the notification URL the dashboard shows. It also shows only once | | Merchant CNPJ and Transparent Token | Requested from PicPay support. Only needed for cards in Transparent mode | > [!WARNING] > Without the webhook token, the payment is never confirmed. Test and production > credentials are different: pick the right **Environment** (**Testing (sandbox)** > or **Production**) and use the credentials of that environment. ## How the player pays In **How the player pays**, pick the mode: - **Transparent: on your store**: the player pays without leaving the store. For the card to show in this mode, the CNPJ and the Transparent Token are required; without them, Pix and the wallet keep working. - **Standard: on the PicPay page**: the player goes to the PicPay page and comes back. - **Lightbox: window over your store**: the payment opens in a window on top of the store. In **Methods offered**, pick at least one among card, PicPay wallet and Pix. > [!NOTE] > In Standard and Lightbox modes, PicPay builds the payment screen, and it may > offer other methods besides the ones picked here. Your choice sets what your > store shows before sending the player there. ## Fees PicPay does not report the fee of each sale, so Finance always uses the table you confirm. PicPay does not publish the Pix fee for Checkout: the field comes blank for you to fill in. See [Gateway fees](/en/payments/fees/). # Finance Finance is the store's cash book: what came in, what went out and the month's result. Sales, gateway fees, refunds, the Hystore subscription and partner commissions come in on their own; the other expenses (hosting, plugins, team, marketing) you enter yourself. With everything together, the store knows whether it is making a profit. The module is in the **Finance** group of the menu and must be on in **Settings > Modules**, on a plan that includes Finance. ![The Finance overview: income, expenses, profit, margin, goals and budgets](shots/finance-overview.webp) ## The overview In **Finance > Overview**, for the chosen period: - **Income**, **Expenses**, **Profit** (or **Loss**) and **Margin**, each compared with the previous period of the same length; - the **Store sales** panel: what was sold, the gateway fee, the refunds and the net sales; - the month's **Goals** and the **Budgets** card, with how much of each limit is used; - the income and expenses chart (day by day in one month, month by month across several), expenses by category and the summary of bills to pay. Commission paid in store credits shows on its own card, outside expenses, because it does not leave the cash. > [!WARNING] > The yellow warning at the top, like "sales paid by Stripe show without the > gateway fee", means the fees are not confirmed yet. Click **Confirm fees** and > check the table. See [Gateway fees](/en/payments/fees/). ## Pick the period At the top, pick **From** and **To**: any month from the store's creation to the current month. With a single month, the arrows move month by month. **All time** takes everything from the store's creation until today. The same filter shows in Entries, Reports and Reconciliation. The day closes in the store time zone (the change link takes you to [Store settings](/en/store/settings/#time-zone)). ## Monthly report and email summary The **Monthly report** (or **Period report**) link opens the report ready to print: income, expenses, result and margin with the comparison, the sales, the categories, the period's entries and the open bills. **Print or save as PDF** opens the print window; to keep the file, choose **Save as PDF**. In the first days of each month, the store owner gets the summary of the month that closed by email: result, income, expenses, the three heaviest categories and the overdue bills. A month with no activity sends no email. To stop it, turn off **Monthly summary by email** in **Finance > Settings**. ## The Finance screens | Screen | What it is for | Guide | | --- | --- | --- | | Entries, Bills to pay, Recurring expenses, Categories | Day to day: entering expenses and income | [Entries and bills](/en/finance/entries/) | | Budgets, Projection, Settings (goals) | Planning the month and the next ones | [Budgets, goals and forecast](/en/finance/planning/) | | Reports, Marketing | Margin per product and server, campaign return | [Reports](/en/finance/reports/) | | Reconciliation | The real fee the gateway charged and what is left to release | [Reconciliation](/en/finance/reconciliation/) | | Hyler review | A reading of your finances made by AI | [Hyler review](/en/finance/analysis/) | > [!TIP] > Start by confirming the gateway fees and entering the recurring expenses > (hosting, plugins, domain). With just that, the overview profit is already close > to the real one. Who can see and change Finance depends on the role: **View Finance**, **Manage Finance** and **Receive budget alerts**. See [Team and access roles](/en/store/team/). # Entries and bills Day-to-day Finance lives in four screens: **Entries**, **Bills to pay**, **Recurring expenses** and **Categories**. ## Entries **Finance > Entries** has everything that came in and went out, with the automatic lines (each day's sales and fees, refunds, subscription and commissions, with the **Automatic** badge) and your own entries. ![The entry list with the automatic and the manual ones](shots/finance-entries.webp) ### Enter an expense or an income 1. Click **New entry**. 2. Pick expense or income, the category, the description, the amount and the due date. These are required (they have an asterisk). 3. If you like, fill in the payee, the payment method, the server, the campaign, the note and the receipt. 4. With **Already paid** on, enter the payment day (it cannot be after today). Off, the entry goes to **Bills to pay**. 5. Save. The amount field only takes numbers: the thousands separator and the cents go in on their own. Type `1234,5` and it becomes `1.234,50` (in the store's number format). > [!NOTE] > An entry counts in the month of the day it was paid, not of its due date. An > October bill paid on November 2 goes into November's result. The **Receipt** accepts PDF, PNG, JPG or WebP up to 2 MB. It stays with the entry, and only people with access to the store's Finance can download it. Only manual entries have **Edit** and **Delete**. Commission paid in credits shows with the **Off cash** badge and is not added to the totals. ### Export for the accountant **Export CSV** downloads the period with the screen's filters, to open in Excel or send to the accountant. Filter by type, source and category before exporting. ## Bills to pay and to receive **Finance > Bills to pay** has the open bills, split into **Overdue**, **Next 7 days** and **After**: - entries with no payment date yet; - partner commission already past its hold (**Record payout** opens the same record as the Partners screen); - the next Hystore subscription charge (**See plan** goes to Plans). **Mark as paid** records the payment with today's date, in the store time zone. Pending income is under **To receive**, with **Mark as received**. The **New bill to pay** and **New amount to receive** buttons create the entry already pending. ![Bills to pay split by due date](shots/finance-payables.webp) ## Recurring and installment expenses **Finance > Recurring expenses** holds what repeats (host, domain, team) or was split into installments. 1. Click **New recurring expense**. 2. Pick the category, the description, the amount of each charge, the frequency (weekly, monthly or yearly) and the first due date. 3. In **Until when**, pick **No end**, **Installments** (2 to 120) or **Until a date**. 4. Turn on **Automatic debit** if the bill is charged on its own: the entry comes in already paid on the due date. 5. Save. The entry for each due date is created on its own and shows in Bills to pay up to 35 days before. In installments, the description carries the installment number, like `(3/6)`. ![Recurring expenses with how much each one weighs per month](shots/finance-recurring.webp) > [!TIP] > Add the server hosting as a monthly recurring expense with automatic debit. It > comes in on its own every month, and the [projection](/en/finance/planning/#projection) > starts counting it. **Edit** changes the amount, category and texts of pending entries from today on; what is already paid stays as it is. To change the frequency or the dates, end it and add another one. **End** stops generating and removes from bills to pay the pending entries that would fall after today. ## Categories **Finance > Categories** holds the income and expense categories. The store starts with the default ones: | Category | Examples | | --- | --- | | Infrastructure | Server hosting, protection and network, domain and DNS, backup | | Software | Plugins and mods, licenses, the Hystore platform, game accounts | | Development | Custom work, builds and maps, design, video, translation | | Team | Staff, developers, bonuses | | Marketing | Ads, content creators, partner commission, giveaways | | Fees and taxes, Other | The rest of the expenses | Income ones include sales, sponsorship, donations, content monetization, sales outside the site and owners' contributions. **New category** creates one with a name and a color; the pencil renames it or changes the color. **Archive** removes the category from the choices without touching old entries, and **Show archived** lets you bring it back. ![The Finance categories with the color of each one](shots/finance-categories.webp) # Budgets, goals and forecast Three tools for planning: **Budgets** (a spending limit per category), **Goals** (how much to bring in and how much to keep in the month) and **Projection** (what should come in and go out in the next months). ## Budgets In **Finance > Budgets**: 1. Click **New budget**. 2. Pick an expense category, the monthly limit and at what percentage you want to be warned (80 by default). 3. Save. The limit applies to every month, until you change or remove it. The screen shows, for the current month, how much of each budget is already spent, with the **Close to the limit** and **Over budget** badges; the mark on the bar shows where the warning fires. It counts what is already paid in the month, including automatic expenses (fees, subscription, commissions) in their category. ![Budgets with how much is spent and the Close to the limit and Over budget badges](shots/finance-budgets.webp) ### Budget alerts Each alert goes out once per category and per month: when it reaches the warning percentage and when it passes the limit. It shows in **Recent alerts** and, with the **Budget alerts by email and Discord** switch on in **Finance > Settings**, it goes: - by email to the store owner and to whoever has the **Receive budget alerts** permission in their role (dashboard team or server staff); - as a Discord direct message to whoever has their account linked, with the Discord bot connected. > [!TIP] > A Marketing budget with an 80% warning avoids the surprise of overspending on ads > in a weak sales month. ## Monthly goals In **Finance > Settings**, on the **Goals and alerts** card, enter the **Monthly income goal** and the **Monthly result goal** and click **Save**. Leave them blank for no goal. Goals show on the overview with how much was already done. The mark on the bar is what is expected by today, in proportion to the days of the month: below it, the screen warns that the store is behind pace. ![The Finance settings: goals, alerts and the automatic review](shots/finance-settings.webp) > [!NOTE] > These goals are internal, for you only. The storefront's > [Month goal](/en/products/goal/), which players see, is a different one; it shows > next to them on the overview only in the month it was active. ## Projection **Finance > Projection** shows what should come in and go out in the next 3, 6 or 12 months: - what is already known comes separately: recurring expenses, pending bills, the Hystore subscription and partner commissions; - sales are an estimate: they repeat the average of the last closed months with activity, and the cost of selling (fees, refunds and commissions) follows the same proportion; - the current month shows what already came in and went out, plus the estimate for the days left. ![The projection of the next months with the break-even point](shots/finance-projection.webp) ### Break-even point The **Break-even point** card shows the fixed costs per month (recurring expenses and the Hystore subscription), the cost of selling and how much the store needs to sell per month not to close in the red, compared with average sales. ```text Example fixed costs: R$ 900.00 per month cost of selling: 8% of sales needs to sell: 900.00 ÷ (1 − 0.08) = R$ 978.26 per month ``` With no recurring expenses added, fixed costs use the average of the entered expenses. A projection is not a guarantee: sales can vary. # Reports The reports answer two questions: which product and which server bring the most result, and how much came back from each campaign. They are in **Finance > Reports** and **Finance > Marketing**. ## Margin by product In **Finance > Reports**, **Products** tab, each product sold in the period shows with **Sold**, **Received**, **Fee**, **Cost per unit**, **Cost** and **Margin**. ![Reports: the margin of each product in the period](shots/finance-reports.webp) - **Received** is the part of the order that belonged to the product, with coupon and credits already taken off. - The gateway **Fee** is split by the period's average fee, because it is charged per order. - **Cost** is what you enter with the pencil, per unit: license, key, payout to the creator. If delivering costs nothing, enter zero. - **Margin** is received minus fee and cost, as an amount and a percentage. A product with no cost entered shows as **Not set**, and its margin only takes off the fee. ```text Margin example Gold VIP: 10 sold, received R$ 499.00 fee: R$ 24.85 cost: R$ 0.00 per unit margin: 499.00 − 24.85 − 0.00 = R$ 474.15 (95%) ``` ## Result by server On the **Servers** tab, each store server shows with the **Received** from sales of its products, the fee and the cost of those products, **Other income** and the expenses linked to it, and the **Result**. For an expense to count on a server, pick the server in the **Server** field when entering it or when adding a recurring expense. A product counts on the server chosen in its own form. Whatever belongs to no server goes on the **No server** line. The Hystore subscription, partner commissions and refunds belong to the whole store and do not enter this report. > [!TIP] > Enter the hosting of each server with the server chosen. Then you can see whether > BedWars pays for itself or whether Survival holds up the network. ## Marketing In **Finance > Marketing** you measure the return of each campaign. 1. Click **New campaign**. 2. Give it a name, pick the channel (ads, content creator, server list, giveaway, community or other), the start, the end (optional) and the coupons that measure its sales. 3. Save. ![Marketing: the return of each campaign](shots/finance-campaigns.webp) - **Sold** counts the orders paid with those coupons, within the period. - **Invested** adds the paid entries linked to the campaign (pick the campaign in the **Campaign** field when entering) and the partner commission of those orders. - **Return** shows how much came back for each unit of money invested, with orders, new buyers and cost per order. Each coupon belongs to one campaign only: use a coupon of its own for each campaign. Next to each coupon is the store link with `?cupom=` and the copy button; whoever opens that link gets the code taken to the cart. ```text Campaign link https://redepixel.hystore.com.br/?cupom=TIOCRAFT ``` **Archive** removes the campaign from the choices without deleting the numbers. # Reconciliation The fee table is an estimate. **Finance > Reconciliation** shows the fee the gateway really charged on each sale and the money it will still release to your account. ![Reconciliation: real fee against the table and what is left to receive from the gateway](shots/finance-reconciliation.webp) ## How it works Every 30 minutes, Finance checks the store's Mercado Pago, Stripe and PayPal, with the credential already in **Settings > Payments**, read only. For each approved sale, it stores the fee, the net amount and the release date. - Where the real fee is known, it replaces the table's in the numbers. - The rest is still estimated by the table confirmed on the gateway's card. See [Gateway fees](/en/payments/fees/). - **Reconcile now** runs the check right away, without waiting the 30 minutes. > [!NOTE] > The real fee is what the gateway took from the sale. On a card paid in > installments with interest paid by the buyer, the interest does not count as the > store's fee, because the buyer pays it. ## The cards on the screen - **Real against the table** shows whether the gateway charged more or less than the table would for the same sales. If the gap is big, adjust the table on the gateway's card. - **Receivable from the gateway** adds the paid sales whose money has not been released yet, with the expected dates. The same number shows on the overview. The period of the numbers is chosen in **From** and **To** or with **All time**; what is left to release does not depend on the period. > [!TIP] > On Mercado Pago, the release term depends on your account option (right away, 14 > or 30 days). If **Receivable from the gateway** looks high, check that term on > the Mercado Pago site. PicPay does not report fees or payouts: its sales follow the table. # Hyler review In the **Hyler review**, Hyler reads your Finance numbers and points out patterns, risks and where you can organize and save. The numbers (income, expenses, profit, margin) are calculated by the system; Hyler writes the reading of them. ![The Hyler review: new review, previous reviews and the result](shots/finance-analysis.webp) ## Run a review 1. Open **Finance > Hyler review**. 2. On the **New review** card, pick the type: - **Period**: the months you choose (the last 12 by default); - **Comparison**: a base period against another, which must start after the base ends (the store needs at least two months); - **All time**: since the store was created. 3. In **Use as the base**, pick the earlier review Hyler uses to say what got better and worse since then: the latest (the default), another from the list, or none. 4. Click **Run review**. A review takes a few seconds to a few minutes and keeps going even if you leave the screen. ## What the review has - At the top: income, expenses, profit (or loss) and margin of the period, with the monthly average, and a summary with the store's health. - In a comparison, the table of both periods with the change of each number. - With a review as the base, what changed since that review: before and now, and the points that got better, worse or stayed. - **Points of attention**, **Next steps**, opportunities with the estimated gain per month, **What is going well**, **Patterns** (strongest months and weekdays, best-selling products, fastest-growing expenses) and tips to organize your finances. Earlier reviews are in **Previous reviews**, with the period and the health of each one. ## Limit and automatic review Each review counts toward the plan's monthly limit, whatever the type; one that does not finish does not count. The screen shows how many were used this month. In **Finance > Settings**, the **Automatic Hyler review** switch runs a review on its own in the first days of each month (it also counts toward the limit). > [!TIP] > The more expenses entered and fees confirmed, the sharper the reading. A review > with half the expenses missing will think the store makes more profit than it > does. > [!WARNING] > It is a reading made by AI from your numbers. Check before deciding and, for > taxes, talk to an accountant. # Layout and colors In **Customization > Store Appearance** you decide how the store looks to players: the layout, the logo, the home page, the widgets and the colors. Changing the layout does not touch products, orders or texts, so you can try things freely. ![The Layout tab: the builder, the code theme and the ready layouts](shots/appearance-layout.webp) ## The four ready layouts All of them are live on example stores. Open them and browse to see how they look. ### Classic Dark, with the background image filling the opening screen and the widgets next to the news. See it at [reinopixel.hystore.com.br](https://reinopixel.hystore.com.br). ![The Classic layout on the Reino Pixel example store](shots/appearance-classic.webp) ### Aurora Light or dark, with a gradient band in your color, servers in a carousel, a ranking with player skins and a Discord card in the footer. See it at [vilabloco.hystore.com.br](https://vilabloco.hystore.com.br). ![The Aurora layout on the Vila Bloco example store](shots/appearance-aurora.webp) ### Celeste Light or dark, with a side menu over a sky of pixel clouds, a rotating offers banner, server and category tabs, product search and raised buttons. See it at [ilhasdoceu.hystore.com.br](https://ilhasdoceu.hystore.com.br). ![The Celeste layout on the Ilhas do Céu example store](shots/appearance-celeste.webp) On Celeste you can change the background around the store, on the **Layout background** card: **Brand color** (the sky follows the primary color), **Custom color** or **Image** (JPG, PNG or WebP up to 5 MB, 1920x1080 recommended). The **Pixel clouds** switch turns the clouds on or off. On a phone, the store fills the screen and the background does not show. ### Prisma Light or dark, with the look of a digital product store: a prominent search, a featured product on the side, a guarantees strip, big covers, a catalog with side filters and a fixed purchase card on the product page. It also works for game stores. See it at [estudiovoxel.hystore.com.br](https://estudiovoxel.hystore.com.br). ![The Prisma layout on the Estúdio Voxel example store](shots/appearance-prisma.webp) ## Change the layout 1. In **Customization > Store Appearance**, open the **Layout** tab. 2. Click the layout you want. Check **Use the colors suggested by this layout** so the primary, accent and icon colors become its own. 3. On Aurora, Celeste and Prisma, pick whether the store opens in light or dark mode. The player can switch with the sun and moon button, and their choice is kept in the browser. 4. Click **Save layout**. > [!TIP] > Want to change more than the ready layouts allow? The **Custom** layout is built in > the [Builder](/en/appearance/builder/), with no code. For full control, with your > code or your AI, use the [Code theme](/en/code-theme/). Aurora, Celeste and Prisma > also exist as code themes. ## Logo and favicon On the **Logo & Favicon** tab, upload: - the **logo**: PNG with a transparent background, around 200x60 px, up to 2 MB; - the **favicon**, the browser tab icon: 32x32 or 64x64 px, up to 512 KB. ![The Logo and Favicon tab](shots/appearance-branding.webp) ## Home page The **HomePage** tab holds the title, the subtitle, the background image (1920x1080, up to 5 MB), the server IP and what to show: status, IP, players online and top buyer. ![The HomePage tab: texts, background image and what to show](shots/appearance-hero.webp) ## Page widgets The **Widgets** tab holds the Discord widget (with the server ID) and the buyer rankings. Analytics, advertising and support tools are on another screen; see [Widgets](/en/appearance/widgets/). ## Colors On the **Colors** tab, click the square of each item to pick its color; blank uses the default color. On Aurora, Celeste and Prisma, the tab shows only the brand colors, because background, cards and text follow light or dark mode. ![The Colors tab of the appearance screen](shots/appearance-colors.webp) # Builder The builder is the store's drag and drop editor. With it you build the whole store your way (header, footer, every page), change colors, fonts and texts, without writing code. The result is the **Custom** layout. To open it: **Customization > Store Appearance**, **Layout** tab, **Open the builder** button. ![The builder: blocks on the left, the store in the middle and the block options on the right](shots/appearance-builder.webp) ## The parts of the screen - **On the left**, the tools: **Blocks** (what you can put on the page), **Layers** (the page structure), **Pages** and **Store theme**. - **In the middle**, your real store, in edit mode, with your products. - **On the right**, the options of whatever is selected, in two tabs: **Content** and **Style**. - **At the top**, the page being edited, the text language, the screen size (**Desktop**, **Tablet** or **Phone**), light or dark mode, undo and redo, the **Preview link** and **Publish**. ## Start the site When you open the builder for the first time, pick a template: | Template | What it brings | | --- | --- | | Blank | Just the header and the footer. The rest is up to you | | Showcase | Server cover, products, goal, ranking and news, already in place | | From Classic, Aurora, Celeste or Prisma | Starts just like the ready layout, to change what you want | ## Build the page 1. In **Blocks**, drag a block to the store, or click to add it near what is selected. There are structure blocks (**Section**, **Columns**, **Space**, **Divider**) and content blocks (**Title**, **Text**, **Image**, **Button**, **Icon**, **Video**, **List**, **Card**, **Gallery**, **Testimonial**, **Countdown**, **Questions and answers** and the store ones). 2. In **Ready-made sections**, drag a section already built and styled, like **Cover with background image**, **Featured products**, **Three highlights** or **Discord call**, and change the texts. 3. Click a block to see its options on the right. Double-clicking a text takes you straight to it. 4. On the **Style** tab, change that block's color, spacing and alignment. > [!TIP] > The builder saves on its own at every pause: **Draft saved** shows at the top. > Nothing reaches players until you click **Publish**. ## Pages **Pages** has the store pages (Home, Shop, Forum, Support and the others) and **Your pages**, which you create with **New page**. The address comes from the name, and **Show in the menu** adds the page to the menus. The header and the footer apply to every page. Clicking the header shows where it goes: on top, on the left or on the right. ## Store theme **Store theme** holds the choices that apply to the whole store: - **Ready-made palettes** and **Brand colors**; - **Light and dark**: the store modes and which one it opens in; - **Fonts**: for headings and text; - **Buttons, cards and fields**: corners and style; - **Store background** and **Width and animations**; - **Header and menu**: where it goes, its style and whether it follows the scroll. ## Texts in other languages The **PT**, **EN**, **ES** picker changes the language of the texts you are editing. When texts are missing in a language, the warning says how many. **Translate what is missing** uses AI to translate from one language to another; review before publishing. ## Publish and use it on the store 1. Use the **Preview link** to see the draft at the store address and send it to someone. The live store stays the same. 2. Click **Publish**. If there is a problem in the draft, the screen shows the warnings at the top. 3. The first time, answer **Use on the store now** so the store starts opening with the site you built. Each publication becomes a version in **Published versions**; **Restore** brings an older version back to the draft. > [!NOTE] > Going back to a ready layout in **Store Appearance > Layout** keeps the site saved: > you can come back to it later. While the store uses the code theme, the builder is > off. > [!WARNING] > If the same site is saved in another tab or by another person, the **The draft changed > somewhere else** warning shows, and nothing is saved until you choose: **Use the saved > version** loads the stored one, and **Keep mine** writes this tab's over it. # Widgets In **Customization > Widgets** you turn on analytics, advertising and support tools in the store, with no code. Each widget says where to find the ID in the service: paste it and turn it on. ![The Widgets screen with the consent notice and each tool](shots/appearance-widgets.webp) ## The tools | Type | Tool | What it is for | | --- | --- | --- | | Analytics | Google Analytics 4 | How many people visit the store and where they come from | | Analytics | Microsoft Clarity | Heatmaps and session recordings | | Advertising | Google Ads | Measure the sales from Google ads | | Advertising | Meta Pixel | Measure Facebook and Instagram ads | | Advertising | TikTok Pixel | Measure TikTok ads | | Advertising | OpenAI Ads | Measure OpenAI ads | | Advertising | Utmify | Track the sales of each campaign | | Support | Crisp | Support chat in the store | | Support | Tawk.to | Support chat in the store | ## Turn on a widget 1. Find the tool on the screen. 2. Get the ID on the service's site (the screen explains where). On Google Analytics 4, for example, it is the measurement ID: ```text Measurement ID G-PX12AB34CD ``` 3. Paste it in the field, turn on the switch and click **Save**. ## Player consent With an analytics or advertising tool on, the store shows a consent banner, and nothing loads before the player accepts. Brazil's data protection law (LGPD) requires it, and it cannot be turned off separately. Support tools do not need the banner. > [!NOTE] > Without consent, the tool does not load for that player. That is why Analytics numbers > stay below the real total of visits. > [!TIP] > To measure a campaign from start to finish, also use a coupon of its own in > [Marketing](/en/finance/reports/#marketing): the dashboard shows how much came back for > each unit of money invested. # Emails In **Customization > Emails** you customize the emails players receive: drag blocks, write in the languages you want and publish when it is ready. ![The store's email list, with the status of each one](shots/appearance-emails.webp) ## The store's emails | Email | When it goes out | Can it be turned off? | | --- | --- | --- | | Welcome | When the player creates an account in the store | Yes | | Password recovery | When the player asks to reset the password (it must include the reset link) | No | | Payment approved | When the order payment is confirmed | No | | Order delivered | When the order items are delivered on the server | Yes | | Order expired | When an order stays unpaid until the deadline | Yes | | Cart discount | When you offer a discount for an abandoned cart | Yes | Every email starts on. Until you publish your own, it goes out with the predefined template. Turned off with the switch in the list, it is not sent. Password recovery and payment approved are required: the switch is locked and they always go out. In a digital product store, the templates talk about **My purchases** instead of the server, and Order delivered becomes **Order released**. ## Edit an email ![The email editor: blocks on the left, the email in the middle and the options on the right](shots/appearance-email-editor.webp) 1. In the list, click the email. 2. Fill in the **Subject** and the **Preview text**, which shows next to the subject in the inbox. The **Variable** button inserts data like the player's nick. 3. Drag blocks to the email, or click to add: **Heading**, **Text**, **Button**, **Image**, **Divider**, **Spacer**, **Social links**, **Footer** and **Columns**. 4. Click a block to edit it. The **Style** tab changes the colors and the look. 5. Use **Preview** to see how it looks, and **Send me a test** to get a real one. 6. Click **Publish**. The published version becomes the one that is sent. ```text Subject with a variable Welcome, {{player.nick}}! ``` > [!WARNING] > A block with a red outline has something to fix. Fix it before publishing. > [!TIP] > **Save draft** keeps your work without changing what players receive. In **Published > versions**, **Restore** brings an older version to the draft; it only applies after > you publish again. ## Languages At the top of the editor, the tabs show the email's languages. Each player gets the email in their language when it exists; otherwise, in the default language. Every email needs the default language to be published. ## Sending settings In **Sending settings**, which apply to every custom email in the store: - **Languages** and **Default language**; - **Sender name**, shown in the inbox (empty uses the store name); - **Reply to**: the address that gets players' replies (optional). # News In **Support > News** you post updates for players: a server update, maintenance, the start of a season. The same post can show on the store, on the launcher and in the server chat. ![The news list, with the author, the title and the status of each post](shots/community-news.webp) ## Publish a post 1. In **Support > News**, click **New Post**. 2. Fill in **Title**, **Author Nick** and **Content**. The nick shows the player's head next to the post. 3. Upload the **Post Banner**: 1200x600 px, up to 5 MB. It is optional. 4. Pick where it shows under **Post Settings** (see below). 5. Click **Save Post**. ![The news form: banner and options on the left, text on the right](shots/community-news-form.webp) ```text Example post Title: The Winter Season has started Author Nick: Lucas Content: The new season is live. New map, ranking reset and a welcome kit for anyone who joins by Sunday. ``` ## The post options | Option | What it does | | --- | --- | | **Publish Immediately?** | On, players see it. Off, it stays as a draft | | **Show as Modal?** | Opens the post in a popup when the player enters the store | | **Show on the store** | Appears on the storefront and the store site | | **Show on the launcher** | Appears on the launcher home screen. The text shows without formatting and the full article opens in the browser. Only available if your plan includes the launcher | | **Announce on the server** | When saving, players online see the post title in the chat with the link to read it | | **Also as a title on screen** | Besides the chat, shows the big title on the screen of players online | > [!TIP] > Save the modal for what everyone needs to see, like maintenance or a new season. A > popup on every post wears players out. > [!NOTE] > **Announce on the server** only exists in Minecraft and Hytale stores, and needs the > plugin installed and the post published. Anyone without the **Send notice to the server** > permission does not see this option. See [In-game announcements](/en/plugins/announcements/). ## Publish from Discord or the store Players with a team role that has the **Publish News** permission can also publish from the store itself and with the bot's `/news` command. See [Player roles](/en/products/players/) and [Bot messages](/en/discord/messages/). ## Edit or delete In the list, the buttons to the right of each post edit or delete it. Deleting cannot be undone. To take a post down and keep the text, edit it and turn off **Publish Immediately?**. # Wiki The wiki is your store's help center: how to join the server, the commands, the rules. Readers find the answer without opening a ticket. It lives in **Support > Wiki**, and players read it at `/wiki`. ![The wiki on the store, as players see it](shots/community-wiki-store.webp) ## How it is organized Pages live inside categories, so start with those. An example: ```text Example structure Getting started How to join the server (featured) Basic commands How to protect your land Rules Server rules (featured) ``` ## Create a category 1. In **Support > Wiki**, click **New Category**. 2. Fill in the **Name**. The **Slug** is the part of the address; blank, it comes from the name. 3. If it sits inside another one, pick the **Parent Category**. Without it, this is a main category. 4. In **Order**, 0 is the first in the list. 5. Click **Create Category**. ![The new wiki category form](shots/community-wiki-category.webp) ## Create a page 1. Click **New Page**. 2. Fill in **Title**, **Category** and **Content**. The editor takes headings, lists, links and images. 3. Under **Tags**, mark the ones that fit the subject. 4. If you want, add **Attachments**: up to 5 files of up to 10 MB each. They upload after the page is created. 5. Turn on **Mark as featured** so the page comes first in its category. 6. With **Publish immediately** off, it stays as a draft, invisible to players. 7. Click **Create Page**. ![The new page form: title, category, content, tags and attachments](shots/community-wiki-page.webp) ## Look after the pages On the wiki screen, each page shows its **Views**, how many times it was edited and the readers' rating: they mark whether it was helpful. ![The wiki on the dashboard: open categories with their pages and each page's rating](shots/community-wiki.webp) - The **Move up** and **Move down** arrows change the order. A featured page does not move: it always stays on top. - In the three dots menu of each page: **Edit**, **Publish** or **Unpublish** and **Delete**. - In the menu of each category: **Edit**, **Activate** or **Deactivate** and **Delete**. > [!TIP] > A page with many views and a low rating is the first one to rewrite: many people look > for it and are not finding the answer. ## Tags In **Manage Tags**, **New Tag** creates a tag with a name and a color. The slug comes from the name if left blank. ![The wiki tags, each with its color](shots/community-wiki-tags.webp) # Forum The forum is where players talk to each other: they open topics, reply and react. It is at `/forum` on the store, and you set up its structure in the **Forum** group of the menu. ![The forum on the store, as players see it](shots/community-forum-store.webp) The forum has three parts. Set them up in this order, because every board needs a category: | Part | What it is | Example | | --- | --- | --- | | **Categories** | The groups on the forum page | General, Support, Events | | **Boards** | Where players open topics | Announcements, General chat | | **Badges** | Medals that members earn | Veteran: 100 posts | ## Create a category 1. In **Forum > Categories**, click **New Category**. 2. Fill in **Name** and **Slug**, the part of the address. Blank, the slug comes from the name. 3. Write the **Description** and pick the **Icon**: an emoji or the address of an image. 4. In **Order**, the lower number comes first. 5. Click **Save Category**. ![The new forum category form](shots/community-forum-category.webp) To change the order later, edit the category and change the number in **Order**. ![The list of forum categories](shots/community-forum-categories.webp) ## Create a board 1. In **Forum > Boards**, click **New Board**. 2. Pick the **Forum Category** it belongs to. 3. Fill in **Name**, **Slug** and **Description**. 4. Pick **Icon**, **Accent Color** and **Order**. 5. Click **Save Board**. ![The new board form](shots/community-forum-board.webp) The list shows how many topics and posts each one has. ![The list of boards with the topics and posts of each one](shots/community-forum-boards.webp) ## Create a badge 1. In **Forum > Badges**, click **New Badge**. 2. Fill in **Name** and **Description**. 3. Under **Type**, choose **System**. 4. Pick the **Icon** (an emoji), the **Background Color**, the **Visual Style** and the **Animation**. The **Preview** shows how it looks. 5. Under **Requirements for Automatic Award**, fill in how many **Posts**, **Topics** or **Reactions** the member needs. 6. Click **Create Badge**. ![The new badge form with the requirements filled in](shots/community-forum-badge.webp) ```text Example badge Name: Veteran Description: Wrote 100 forum posts Type: System Posts required: 100 ``` > [!WARNING] > Only **System** badges are earned on their own. A **Custom** badge is not given to > anyone, and for now there is no button to give a badge by hand. To reward members, use > **System**. If you fill in more than one requirement, the member must meet all of them. A field with 0 does not count. The check runs when the member creates a topic, replies or reacts. > [!NOTE] > A **System** badge with no requirements is given at each member's first participation. > It works, for example, as a welcome badge. ![The list of badges, with the type and requirements of each one](shots/community-forum-badges.webp) ## Moderate Moderation happens on the store itself, by players with a team role that has the forum permissions. They can pin, lock, move and delete topics, and edit or delete posts. See [Player roles](/en/products/players/). # Tickets Tickets are the store's support. The player opens one at `/suporte`, on the store, and the team replies in **Support > Tickets**, on the dashboard. ![The ticket list with status, priority and category](shots/community-tickets.webp) ## First of all: the categories The category is the ticket's subject, and the player must pick one when opening it. So create yours first. 1. In **Support > Tickets**, click **Manage Categories**. 2. Click **New Category**. 3. Fill in **Name** and **Description**. The **Slug** comes from the name if left blank. 4. Click **Create**. ![The ticket categories, in order](shots/community-ticket-categories.webp) ```text Example categories Payments: purchases that did not arrive and charges Bugs: something does not work on the server Reports: players breaking the rules ``` > [!NOTE] > A category is not deleted: it is deactivated, so old tickets keep the right subject. > Once deactivated, it leaves the list players see. ## How the player opens one At `/suporte`, after signing in, the player gives the title, the category, the priority and the message. The priority is the one they choose, and you see it in the list. ## Reply to a ticket 1. In the list, click the ticket. Use the search and the **Status**, **Priority** and **Category** filters to find what matters. 2. The details are on the left. Click **Assign to me** so the team knows who is on it. 3. Write in **Your reply** and click **Send Reply**. 4. Change the **Status** as the support moves on. ![An open ticket: details on the left and the conversation on the right](shots/community-ticket.webp) | Status | When to use it | | --- | --- | | **Open** | It arrived and nobody replied | | **In Progress** | The team is on it | | **Awaiting Customer** | You asked something and are waiting for the player | | **Resolved** | The problem is over | | **Closed** | Finished. It takes no more replies | > [!WARNING] > A **Closed** ticket takes no more replies from anyone. If the subject may come back, > leave it as **Resolved**. ## In-game notices In Minecraft and Hytale stores, with plugin 2.5.0 or newer, the server also tells people: - the player learns when the team replies to their ticket, right away or when they join up to 30 minutes later; - the online team gets a notice of new tickets: anyone with the `hystore.notify.tickets` permission on the server or a team role with **New ticket notice in game**. Turn it on and off in **Plugin > Announcements**, on the **Tickets** card. See [In-game announcements](/en/plugins/announcements/). ## Support from the store or Discord Players with a team role and the support permissions work from the store itself, at `/suporte/staff`, with no access to the dashboard. See [Player roles](/en/products/players/). With the bot, tickets can also go to a channel on your Discord server. See [Tickets on Discord](/en/discord/tickets/). Support numbers, like first response time and tickets per day, show on the [dashboard home](/en/store/dashboard/). # Forms Forms take applications and sign-ups: joining the team, suggestions, a tournament entry. You build the questions in **Support > Forms**, the player answers on the store, at `/formularios`, and you approve or reject each response. ![The list of forms, with the status and the number of questions of each one](shots/community-forms.webp) ## Create a form 1. In **Support > Forms**, click **New Form**. 2. Under **Basic Information**, fill in **Title** and **Slug**, the part of the form's address, and the **Description** if you want. 3. Click **Add Question** for each question and fill it in as in the box below. 4. Click **Create Form**. ![Editing a form: basic information, period and questions](shots/community-form-edit.webp) ```text Example: team application Title: Team application Slug: team (it lives at /formularios/team) 1. How old are you? Short text, numbers only, maximum 3 2. Why do you want to join the team? Long text 3. What time do you play? Single choice: Morning, Afternoon, Night ``` ## Question types | Type | The player answers with | | --- | --- | | **Short text** | One line. Good for age, nick or Discord | | **Long text** | A paragraph | | **Single choice** | One option from the list. Needs at least 2 options | | **Multiple choice** | One or more options from the list. Needs at least 2 options | On each question, **Required** blocks sending without an answer. On text questions, **Accept numbers only** takes digits only, and **Minimum characters** and **Maximum characters** limit the size, from 1 to 2000. Blank means no limit. ## When and who answers | Option | What it does | | --- | --- | | **Does the form start on another date?** | Off, it does not wait for a date to open | | **Does the form have an end date?** | Off, it stays open with no time limit | | **Form Active** | Off, players do not see it | | **Reapplyable** | Lets the same player answer again after sending | > [!NOTE] > The player must sign in to the store account to answer. After sending, they follow the > status at `/minhas-respostas`. ## Review the responses 1. In the list, click the three dots next to the form and **View Responses**. 2. Click **View Details** on the response you want to read. 3. If you want, write an **Observation**, which the player reads. 4. Click **Approve** or **Reject** and confirm. ![The responses a form received](shots/community-form-submissions.webp) ![An open response, with the questions and the review box](shots/community-form-submission.webp) > [!WARNING] > The review cannot change after you confirm it. Check before approving or rejecting. ```text Example observation Application approved! Get in touch on our Discord. ``` ## Forms on Discord With the bot, players can also answer on Discord, and the rules of each question apply there too. See [Forms on Discord](/en/discord/tickets/#forms). # Install the plugin The plugin connects your server to the store. It delivers purchases, handles VIP in game and brings announcements and `/loja` into the server. This section only shows in Minecraft and Hytale stores. The same Minecraft plugin runs from version 1.8.8 to the newest one, on Spigot, Paper and Folia. ![Plugin > How it works: the download, what the plugin does and how to install it](shots/plugins-overview.webp) ## Step by step You will need access to the server files, usually through your host's panel. ### 1. Create the server on the store 1. In **Store > Servers**, click **New Server**. 2. Give it a name, like `Survival`. The photo is optional. 3. Click **Create Server**. ![The new server window](shots/plugins-server-new.webp) ### 2. Copy the token After creating it, the screen shows the **token**, the password that links the plugin to this server. Copy it now: it shows only once, in this window. Lost it? Open the server and use **Regenerate Token** to get another one. ![The server token right after creating it](shots/plugins-server-token.webp) > [!WARNING] > The token is a password. Do not send it in a ticket, a screenshot or a group. If it > leaks, use **Regenerate Token** on the server screen: the old one stops at once and the > plugin only comes back with the new one. ### 3. Download and install the plugin 1. In **Plugin > How it works**, click **Download the plugin**. 2. Put the file in the server's `plugins` folder. 3. Start the server once. The plugin creates the file `plugins/Hystore/config.yml`. ### 4. Paste the token Open `plugins/Hystore/config.yml` and paste the token in the `token` field: ```yaml plugins/Hystore/config.yml token: "PASTE_YOUR_TOKEN_HERE" ``` On Hytale, the file is `config.json`, in the plugin's folder, with the same fields. ### 5. Reload and check 1. In the server console, type `/hystorereload`, or restart the server. 2. In **Store > Servers**, check the **Last plugin connection**. If it shows just now, it worked. ![The server list with each one's last connection](shots/plugins-servers.webp) > [!TIP] > **Never connected** means the plugin has not talked to the store yet. With no token, or > a wrong one, the plugin stays on and its commands say what is missing. Check that the > token was pasted in full and in quotes. ## Configuration file options After changing the file, use `/hystorereload` or restart the server. | Option | Default | What it does | | --- | --- | --- | | `token` | | The server password | | `poll-interval-seconds` | `30` | How many seconds between each search for deliveries | | `require-online` | `true` | `true`: the delivery waits for the player to be online. `false`: it runs right away, even offline | | `notify-player` | `true` | Tells the player when they get a delivery | | `auto-update` | `true` | Downloads new versions on its own | | `vip.language` | `auto` | VIP language: `auto` uses each player's game language. Or set `pt`, `en` or `es` | | `vip.announce-activation` | `true` | Announces in the chat when someone activates a VIP | | `vip.warn-every-hours` | `6` | With the VIP close to ending, warns every so many hours | | `debug` | `false` | Writes more details to the console | ## Updates Install it once. When a new version comes out, the plugin downloads it on its own, checks the Hystore signature and the new version applies on the next server restart. In **Plugin > What's new** you see what changed in each version. ![What's new in the plugin, version by version](shots/plugins-changelog.webp) ## Check the server In **Store > Servers > View Details**, the **On the server** card shows what the plugin reported: its version, whether it is outdated, the server software and the enabled plugins. There is a warning when LuckPerms is missing, which the product VIP may use. Continue in [Linking and commands](/en/plugins/linking/). # Linking and commands This page shows how the player links their store account to their server character, which commands the plugin has and who can use each one. ## Link the account to the game Linking proves the store account and the server player are the same person. That is what lets a player redeem gifts in game and buy with balance through `/loja`. It needs plugin 2.8.0 or newer. 1. On the store, the player opens **Profile > Game** and clicks **Generate code**. 2. On the server, they join with the same nick as the account and type the command with the code: ```text In the game chat /vincular K7QM2P ``` 3. Done. In **Profile > Game**, they see since when they are linked and can **Unlink**. > [!NOTE] > The code lasts 10 minutes and works once, and the nick in game must match the account. > Too many wrong codes block new attempts for a few minutes. Once linked, the player redeems gifts with `/resgatar `. See [Gifts](/en/products/gifts/). ## The commands | Command | What it does | Permission | | --- | --- | --- | | `/vip` | The player's VIP menu | `hystore.vip` | | `/vip upgrade` | Shows which VIP they can move up to and how much it costs | `hystore.vip.upgrade` | | `/tempovip [player]` | VIP time left. Seeing someone else's needs `hystore.vip.tempo.outros` | `hystore.vip` | | `/loja` | The [in-game store](/en/plugins/shop/) | `hystore.loja` | | `/vincular ` | Links the store account to the player | `hystore.vincular` | | `/resgatar ` or `/usarkey` | Redeems a gift | `hystore.resgatar` | | `/vip admin ` | A player's VIP panel (Minecraft) | `hystore.admin.vip` | | `/darvip ` | Gives a VIP | `hystore.admin.vip` | | `/removervip ` | Removes a VIP | `hystore.admin.vip` | | `/congelarvip ` | Freezes a VIP | `hystore.admin.vip` | | `/hystorereload` | Reloads the plugin | `hystore.reload` | | `/hystore aviso` | Used by the store, console only | | ## Who can use them: permissions Commands are used inside the game, so your server's permissions plugin decides, like LuckPerms, and not the dashboard roles. | Permission | Who has it by default | | --- | --- | | `hystore.vip`, `hystore.vip.upgrade`, `hystore.loja`, `hystore.vincular`, `hystore.resgatar` | Everyone | | `hystore.vip.tempo.outros`, `hystore.admin.vip`, `hystore.notify`, `hystore.notify.tickets`, `hystore.reload` | OP only | ![Plugin > Permissions and commands: the permission and command tables](shots/plugins-permissions.webp) To give your team the VIP commands with LuckPerms: ```text Server console lp group moderator permission set hystore.admin.vip true ``` Change `moderator` to the name of your team's group. > [!NOTE] > What the team does in game also goes through the store: the API checks the request and > each action stays in the VIP history, with the nick of who did it. ## Rename a command This is for when another plugin on the server already uses the same command, like `/loja`. 1. In **Plugin > Permissions and commands**, go to **Command names**. 2. Change the name and, if you want, add up to 3 aliases, separated by commas. 3. Click **Save names**. ![The Command names card](shots/plugins-command-names.webp) The plugin starts using the new name right away, with no restart, and frees the old name for the other plugin. The original name keeps working with the prefix, like `/hystore:loja`. The plugin and store texts that mention the command show the new name. - Names take 2 to 20 lowercase letters, numbers, `_` and `-`. - You cannot use server commands, like `/help` and `/tp`, or the same name on two commands. - If the new name already belongs to another plugin, the console warns and the command becomes `/hystore:`. - The arrow next to each row goes back to the default name. Changing it needs the **Configure the plugin** permission, in [Access roles](/en/store/team/). # In-game delivery When the payment is approved, the store sends the product's commands to the plugin, and it runs them in the server console, once for each unit bought. ```text Example: a product's commands give {player} diamond_sword 1 eco give {player} 1000 ``` `{player}` becomes the buyer's nick. You define the commands in the product's delivery tab. See [Products](/en/products/). ## How to follow it In **Store > Servers > View Details**: - **Pending Deliveries**: what is in this server's queue; - **Completed Deliveries**: what already went out, with the command and the time; - **Playing now**: who is online and the server's slots, with plugin 2.9.0 or newer; - **On the server**: the plugin version, the software and the enabled plugins. ![The server detail: connection, plugins, players online and deliveries](shots/plugins-server-detail.webp) | Status | What it means | | --- | --- | | **Pending** | In the queue, waiting for the plugin or the player | | **Sent** | The plugin received it | | **Delivered** | The command ran | | **Failed** | The server did not recognize the command | ## Offline player By default, the delivery waits: the plugin holds it and runs the commands when the player joins the server. To run right away even offline, like a role command, use `require-online: false` in `config.yml`. See [the options](/en/plugins/#configuration-file-options). ## The purchase was paid and did not arrive Follow this order: 1. **Did the player join the server?** With `require-online: true`, the delivery only goes out with them online. 2. **Is the nick right?** The delivery goes to the nick given at purchase. Check it in the [order](/en/products/orders/). 3. **Is the plugin connected?** In **Store > Servers**, check the **Last plugin connection** and that it uses the current token. 4. **Did the delivery fail?** In **View Details**, look for the delivery. **Failed** means a command the server did not recognize: check the product's commands and that they use `{player}`. 5. **Is the queue stuck?** If the queue does not move with the plugin connected, use `/hystorereload` in the console. > [!TIP] > Before selling, test the command in the server console with your nick. A command that > works in the console works in the delivery. ## How long each player played The plugin (2.9.0 or newer) counts every minute who is on each server: - on the dashboard, each player's detail shows the **Play time**: the total, the month's, whether they are online now or when they were last seen. See [Players](/en/products/players/); - on the store, the `/jogadores` page shows who is playing and the ranking of who played most. To hide this page, turn off **Players page** in [Store Appearance](/en/appearance/), next to the widgets. > [!NOTE] > If the server goes down without turning off the plugin, players on it stop counting as > online within 3 minutes, and the stopped time does not count as play time. # In-game store `/loja` brings your store into the server. The player types the command and sees the categories and products for sale, at the current price, without leaving the game. After picking a product, they have two ways out: - **Buy with balance**: pays the whole purchase with the store balance and receives it right away, with the same rules as the website (limit per player, stock, promotion, VIP and announcements); - **Pay on the website**: gets the product link in the chat. The link already puts the product in the cart. > [!NOTE] > Buying with balance needs the account [linked](/en/plugins/linking/) to this player, so > nobody spends someone else's balance with the same nick. Many purchases in a row by the > same nick block for a few minutes. ## Set it up In **Plugin > In-game store**: ![The In-game store screen with the options and the categories](shots/plugins-shop.webp) | Option | What it does | | --- | --- | | **Turn on /loja** | Off, `/loja` only says the in-game store is off | | **Buy with balance in game** | Off, `/loja` only sends the link | | **Products each server shows** | **Only the ones delivered on this server**, or **All store products**, each delivered on its own server | | **Categories in game** | Uncheck the categories that should not show | Click **Save the in-game store**. Digital, inactive and link-only products never show on `/loja`. ## Texts and command - The menu and chat texts are in **Plugin > Texts**, in the **In-game store** group. See [Announcements and texts](/en/plugins/announcements/#plugin-texts). - The permission is `hystore.loja`, open to everyone. - If another plugin on the server already uses `/loja`, use `/hystore:loja` or [rename the command](/en/plugins/linking/#rename-a-command). > [!TIP] > Keep buying with balance on and promote the store balance: the player buys in the middle > of a match, without opening the browser. # Announcements and texts In **Plugin > Announcements** you send notices to players online and pick what the store announces on its own. In **Plugin > Texts**, you change everything the plugin writes in game. ![The In-game announcements screen: notice, approved purchase and tickets](shots/plugins-announcements.webp) ## Send a notice now 1. In **Send a notice now**, write the text in **Notice**, up to 256 characters. 2. In **Where it shows**, pick **Chat** (up to 3 lines) or **Title on screen** (the first line is the title and the second, the subtitle). 3. With more than one server, mark where it shows. 4. Check it in the preview and click **Send notice**. ```text Example notice with colors &aEvent starting at spawn! &7Hurry up. ``` Use `&` for colors, like `&a` green and `&l` bold, or `&#RRGGBB` for any color. > [!NOTE] > The notice shows right away for players online and lasts 5 minutes: a server that was off > and comes back after that does not get it. Each notice sent stays in the store's audit log. > Sending needs the **Send notice to the server** permission. ## Announce purchases In **Approved purchase**, turn on **Announce purchases in game**. Each approved purchase, including those paid with balance or coupon, shows in the chat of all the store's servers, with the buyer's nick and the products. It comes off. | Option | What it does | | --- | --- | | **Hide the buyer's nick** | Changes the nick to "Someone" | | **Title on screen** | Shows the big title to all players online | | **Sound** | Plays a sound for all players online | | **Fireworks above the buyer** | Minecraft only, no damage, with the player online | ## Tickets - **Tell the player when the team replies to their ticket**: right away, or when they join, up to 30 minutes later. - **Tell the online team when a ticket is opened**: goes to anyone with `hystore.notify.tickets` on the server or a team role with **New ticket notice in game**. Both come on. See [Tickets](/en/community/tickets/). ## News and coupons When saving a news post or a coupon, the **Announce on the server** option shows the notice in the chat. See [News](/en/community/) and [Coupons](/en/products/coupons/). ## Store goal in game The bars, the placeholders and the collective reward are next to the goal, in **Store > Month Goal**. See [Monthly goal](/en/products/goal/). ## Which plugin version do I need? | Feature | Plugin | | --- | --- | | Notice and announced purchase | 2.4.0 or newer | | Tickets, news, coupons and goal | 2.5.0 or newer | The update arrives on its own. See your version in **Store > Servers > View Details**. ## Plugin texts In **Plugin > Texts** are all the texts the plugin writes in game, in the three languages. Each player sees them in their own game language. ![Plugin > Texts: each text, the markers it takes and the preview](shots/plugins-texts.webp) 1. Pick the language and use **Search text** to find what you want. 2. Edit the text. Next to it are the markers it takes, like `{player}` and `{vip}`, and the preview with the chat colors. 3. Click **Save texts**. It applies on the server within a minute, with no restart. ```text Example: VIP activated notice &a{player} activated &f{vip}&a for {tempo}! ``` **Back to default** undoes a text. Editing needs the **Configure the plugin** permission. > [!NOTE] > From Minecraft 1.8 to 1.15, the `&#RRGGBB` color becomes the closest classic color. # Turn on and identity The launcher is the app your players install to join the server, with your store's name and brand. It downloads the mods, sets up Java and opens the game on the right server. The store's plan defines whether it is included, how many builds per month, how many modpacks and how much space for mods. ![Launcher: the published version, the limits and the settings screens](shots/launcher-overview.webp) ## The path | Step | Screen | Needs a new installer? | | --- | --- | --- | | 1 | **Identity**: name, icon and executable | Yes | | 2 | **Appearance**: colors, logo, background and music | No | | 3 | **Modpacks**: server, version and files. See [Accounts and modpacks](/en/launcher/accounts/) | No | | 4 | **Accounts & login**: if the server uses its own login | No | | 5 | **Builds**: build the installer. See [Build the installer](/en/launcher/builds/) | | > [!TIP] > Only Identity asks for a new installer. The rest reaches players on the next launcher start, with no > reinstall and no build spent. ## App identity In **Launcher > Identity**: ![The App identity screen](shots/launcher-identity.webp) | Field | What it is | Example | | --- | --- | --- | | **App name** | What shows on the window and the Start menu. 3 to 40 characters | `Rede Pixel Launcher` | | **Bundle identifier** | How the system tells your launcher from others | `com.redepixel.launcher` | | **Executable name** | Lowercase, numbers and hyphens. It becomes the file name | `redepixel-launcher` | | **Channel** | **Stable** or **Beta**. Whoever installed from one does not get updates from the other | `Stable` | | **Installer icon** | Square PNG, at least 256x256 | | The icon can only be uploaded after saving the identity for the first time. Players who already have the launcher get the change through auto-update, after you build a new installer. > [!NOTE] > With **Launcher active** off, players see the unavailable screen. It is useful for maintenance, and you > do not need to build to turn it on or off. ## Appearance In **Launcher > Appearance**, the preview on the side shows how it looks. Nothing on this screen needs a build. ![The Appearance screen, with the launcher preview](shots/launcher-branding.webp) - **Texts**: **Display name** and **Tagline**. An empty tagline hides the line. - **Colors**: **Primary**, **Accent**, **Background** and **Text**, in the `#RRGGBB` format. - **Images**: **Logo** (PNG with a transparent background, up to 1024x512) and **Background** (JPG or PNG, up to 2560x1440). Up to 8 MB each. - **Background music**: MP3 or OGG, up to 8 MB. The **Initial volume** is just the start: the player adjusts or turns it off in their settings. | Extra | What it does | | --- | --- | | **Show news** | Shows the [news posts](/en/community/) marked for the launcher | | **Show server status** | Players online and availability | | **Show server address** | The IP shows on the home screen and the player copies it with one click | | **Show Minecraft version** | The version shows in the accent color | Click **Save appearance**. It applies on the next launcher start. # Accounts and modpacks The modpack tells the launcher what to install and which server to join. Accounts link the launcher login to the login your server already uses. ## Modpacks A modpack brings together the server address, the Minecraft version and the files the player needs to join. You create as many as your plan allows. ![The modpacks screen with the files of each one](shots/launcher-modpacks.webp) ### Create a modpack 1. In **Launcher > Servers**, click **New modpack**. 2. Fill it in as in the example below. 3. Click **Create modpack**. ![The new modpack window](shots/launcher-modpack-new.webp) ```text Example modpack Name: Survival Server address: jogar.redepixel.com.br Minecraft version: 1.20.1 Loader: Fabric Loader version: 0.15.11 Java: 17 Min RAM: 2048 MB Recommended RAM: 4096 MB ``` | Field | What it does | | --- | --- | | **Loader** | **Vanilla** to play without mods, or your server's mod loader | | **Java** | The screen shows the minimum for the chosen version | | **Min RAM** and **Recommended RAM** | The minimum cannot be higher than the recommended | | **Main modpack** | It opens by default. Only one can be the main | | **Auto-connect** | Joins the server directly when the game opens | ### Upload the files On the modpack card: - **Upload files**: up to 5 at a time. `.jar` is a mod, `.zip` is a resource, and configuration files work too; - **Import mods .zip**: for many mods at once, put them all in a `.zip`. The dashboard opens it, uploads one by one and shows a report of what was left out. In the file list, **Optional** lets the player choose whether they want that file, and **Android** says whether it also goes to the phone. > [!NOTE] > A resource pack is also a `.zip`, and it goes up whole through **Upload files**. Use **Import mods .zip** > only for the mods package. Players get it on the next start. What you change joins the changelog on its own. ## Changelog In **Launcher > Changelog**, the list builds itself as you change the modpacks. ![The changelog: what goes out in the next update and the published versions](shots/launcher-changelog.webp) **In the next update** shows what has not reached players yet: it joins the changelog in the next published build. On each change, write what it does if you want, because players understand a sentence better than a file name: ```text Example description sodium-1.20.1.jar: makes the game lighter ``` ## Accounts and login If your server uses nLogin, AuthMe or its own database, point Hystore to its accounts table. This way the player signs in to the launcher with the same nick and password as the server. Without it, the launcher refuses to create accounts: player accounts are born on the server. ![The Accounts and login screen: plugin, database and columns](shots/launcher-auth.webp) 1. In **Launcher > Accounts & login**, pick the **Plugin**. The table and column mapping is filled in with its default. Adjust it if you changed something on your server. 2. Under **Server database**, fill in **Host**, **Port**, **Database**, **User** and **Password**. 3. Under **Hash format**, leave **AUTO**, which detects each account's format. 4. Click **Save** and then **Test connection**. > [!WARNING] > A wrong mapping makes every player get "wrong password". Always test after saving: the test uses the stored > configuration and shows how many accounts it found and which formats cannot sign in. > [!TIP] > Create a database user just for this, with minimal permissions. The password never comes back from the API: > leave the field empty to keep the stored one. | Option | What it does | | --- | --- | | **Login on the launcher** | Turns on login with this configuration | | **Allow creating accounts from the launcher** | The player creates the account without joining the server first | | **Create the player in the store on first login** | Creates the player in the store the first time they sign in | | **Allow Hystore to write to the server database** | Password changes and weak hash migration write to your table. Leave it off if you do not need it | # Controls and Discord This page covers the buttons for those who play on the phone and what shows on the Discord profile of those who play. ## Phone controls In **Launcher > Phone controls** you set up the Android app buttons. It reaches players the next time they open the game, without building a new app. ![The controls editor with the phone preview](shots/launcher-controls.webp) > [!WARNING] > Until you save the controls, the Android app cannot be built: the default layout does not know the keys of > the mods or your server's commands. 1. Drag the buttons on the preview wherever you want. They snap to the edges and the center, with a line showing the alignment. Hold **Alt** to drop freely. 2. Click a button to pick the icon, the text and what it does. 3. Use **Button** and **Submenu** to add, and **In game** and **Screen open** to edit each moment. 4. Click **Save controls**. Each button can: - press a key; - send a command, like `/rtp`; - open a submenu; - work as an on and off switch, good for crouching and running. The text follows the phone's language. Blank, Portuguese applies. **Restore default** puts everything back in the factory place, and nothing changes for players until you save. ## Discord Rich Presence Shows on the Discord profile of those who play what the person is doing, with your store's name and image. No build needed: players get it on the next start. ![The Rich Presence screen, with the guide and the preview](shots/launcher-rich-presence.webp) ### On the Discord portal 1. On the [developer portal](https://discord.com/developers/applications), click **New Application** and give it your store's name. That name shows in bold on the player's profile. 2. In **General Information**, copy the **Application ID**. Numbers only, and it is not the bot token. 3. In **Rich Presence > Art Assets**, upload the images and name each one. The recommended size is 1024x1024. ### On the dashboard In **Launcher > Rich Presence**: 1. Paste the **Application ID** and turn on **Enable Rich Presence**. 2. Write the two lines of each moment, up to 128 characters per line. 3. Under **Images**, use the name you gave on the portal, in lowercase, or an `https` link. 4. If you want, add up to two **Buttons**, with a label and a link. 5. Click **Save**. ```text Example texts While in the launcher Line 1: In the launcher Line 2: Choosing a server While playing Line 1: Playing {modpack} Line 2: As {jogador} ``` The available markers show on the screen, above the fields. > [!NOTE] > The buttons show to those who see the profile, not to the player themselves. With Discord closed, nothing > shows. # Build the installer Building turns your configuration into the files the player downloads. Each build counts toward your plan's monthly limit. ![The builds screen, with Google Play and the generated files](shots/launcher-builds.webp) ## Build 1. Check the [Identity](/en/launcher/) and the [Modpacks](/en/launcher/accounts/). 2. In **Launcher > Builds**, click **Build installer**. 3. Follow the progress on the same screen. It takes a few minutes. 4. When it finishes, the files show with the **Download** button. If nothing changed since the last installer, the screen says so and does not spend a build. > [!WARNING] > Each new build replaces the previous one: when it is published, the old version's files go offline. Players > who already have the launcher get the new version through auto-update. ## How the player downloads it Your store's `/download` page offers the installer for each system and highlights the right one for whoever is opening it. > [!NOTE] > Installers are not digitally signed yet. On Windows, SmartScreen shows "unrecognized app": the player clicks > **More info > Run anyway**. The download page already explains this. On macOS, they must open it with the right > button and **Open**. ## Android app With Android available on your store, the buttons change to **Build installer and app** and **Build Android app**. First, save the [phone controls](/en/launcher/extras/#phone-controls): without them, the app does not build. The result brings the APK, with **Show QR code** to open directly on the phone, and the **Certificate fingerprint**, which is for checking that the file is the one Hystore generated. ## Publish on Google Play The **Publish on Google Play** card shows whether everything is ready, and **How to publish** opens the step by step. 1. Create your developer account at Google. It costs US$ 25, once, and verification takes a few days. A personal account requires a closed test before production; a company account does not. 2. Publish the **Privacy Policy** and the **Data Collection** summary. Play refuses the app without these two pages. The card shows when they are published. See [Settings](/en/store/settings/). 3. Build the Android app. With the pages ready, the **Play bundle (.aab)** also comes out. 4. Download the `.aab` and upload it through the Play Console. > [!TIP] > Play only takes a bundle with a version number higher than the last one. **New version for Play** builds only the > `.aab` with the next number, without changing the APK or the players' auto-update. It counts as a build. ## Got an error? | Message | What to do | | --- | --- | | Nothing changed since the last installer | There is nothing to build. Change something or use the current installer | | A build is already running | Wait for it to finish | | Waiting for a macOS machine | The macOS version needs a Mac. It joins the queue as soon as one is free, and it is not an error | | The build stopped here | The screen shows the step where it stopped. Check that step's data and build again | # Connect the bot The bot is your own Discord application, with your store's name and logo. With it on the server, you unlock account linking, tickets, forms, welcome messages, news with `/news` and purchase announcements. ![Discord: the bot status, the server and the parts it handles](shots/discord-overview.webp) ## Step by step The **Discord > Connection** screen guides each step. You will use the [Discord developer portal](https://discord.com/developers/applications). ![The five steps to set up the bot](shots/discord-setup.webp) ### 1. Create the application 1. On the portal, click **New Application**. You can use the store's name. 2. Under **Bot**, turn off **Public Bot**, so only you can add the bot. 3. Still under **Bot**, turn on **Message Content Intent**. Also turn on **Server Members Intent**, for welcome and leave messages. ### 2. Copy the return addresses 1. On the portal, open **OAuth2**, in the **Redirects** part. 2. Click **Add Redirect**, paste the first address shown on the screen and save. Players come back to the store through it after linking. 3. Also add the second address, through which you connect [your account](#your-discord-account). ### 3. Paste the token and the Client Secret 1. Under **Bot**, use **Reset Token** and copy the token. 2. Under **OAuth2**, use **Reset Secret** and copy the **Client Secret**. 3. Paste them in **Bot token** and **Client Secret**, and click **Connect bot**. > [!WARNING] > The token is the bot's password. Whoever has it controls the bot. Both are stored encrypted and do not show on the screen > again. If it leaks, generate another one on the portal and paste it in **Replace token**. ### 4. Invite the bot Click **Invite the bot** and pick your server. The invite already asks only for the permissions the bot needs. Never give it **Administrator**. The screen updates on its own when the bot shows up. ### 5. Confirm the server Click **Confirm server**. The bot stays only on this server: if someone adds it to another, it leaves on its own. Done. **Last signal** shows when the bot talked to the store. ![The Connection screen with the bot on](shots/discord-connection.webp) ## Your Discord account On the **Your Discord account (store owner)** card, click **Connect my Discord account** and authorize. With the account connected, the bot: - takes what you write in a ticket thread as a team reply on the website, in your name, and lets you close the ticket there; - sends to your direct messages the budget alerts from [Finance](/en/finance/planning/), the same as the email. > [!NOTE] > This link gives no role or permission on the server: it only tells the bot who the owner is. The server team does not use > this card, but the [player link](/en/discord/linking/). ## Appearance In **Discord > Appearance**: ![The Appearance screen: name, bot status and message colors](shots/discord-appearance.webp) - **Name and logo**: they are the store's. To change them, use **Change store identity**, and the bot follows in a few minutes. - **Bot status**: what shows under its name. Pick the **Dot**, the **Type** and the **Text**. The text takes variables with the state of the game server, which the bot checks every minute. **Text with the server offline** left blank uses the regular text. - **Message colors**: every bot message goes out in a box with the color of the message type and the store's name in the footer. Continue in [Linking and roles](/en/discord/linking/). # Linking and roles Linking connects the player's Discord to their store account, so the bot knows who is who. It allows giving roles and rewards and answering tickets. ![The Account linking screen](shots/discord-linking.webp) ## How the player links In **Discord > Account linking**, under **Where the player starts**, pick one: | Mode | How it works | | --- | --- | | **/link command** | The player types `/link` in any channel and gets the link, only for them | | **Fixed message in a channel** | The bot leaves a message with the **Link account** button in the chosen channel. `/link` leaves the server and `/unlink` stays | The player can also link on the store, in their profile, on the Discord tab. > [!NOTE] > Linking always ends on the store, with the player signed in. That stops anyone from using someone else's account. In the fixed message, pick the **Message channel** and write **Title**, **Text** and **Button text**. Blank, the bot uses the default text in the server's language. Click **Save and publish**. ```text Example message Title: Link your account Text: Get 100 store credits when you link. Button text: Link ``` ## Linked role Whoever links gets this role on the server, and loses it when unlinking. > [!WARNING] > On Discord, the bot's role must be above it in the server's role list. Otherwise, Discord will not let the bot give the role. ## Linking reward Give a gift to whoever links. Each player gets it only once, and so does each Discord account. | Reward | What the player gets | | --- | --- | | **Store credits** | Up to 1000, straight to the balance | | **Gift** | A product, which can be off the storefront. The bot sends a single-use code by direct message, and the delivery is the same as a purchase | In **Minimum Discord account age (days)**, slow down accounts created just to get the gift: an account newer than that links normally, but without the reward. Click **Save reward**. ## Link store roles to Discord roles Store team roles and Discord roles can walk together. That is what lets the team answer tickets and publish news on Discord. 1. In **Players > Roles**, edit a role. 2. On the **Discord** card, pick the **Discord role**. 3. Save. Whoever has this role in the store and linked Discord gets the role on the server, and loses it when leaving the role. Every website role change, on the dashboard, by purchase, expiration or refund, changes the Discord role right away and tells the person by direct message. **Sync Discord roles**, in the role list, does the opposite once: whoever already has the linked role on Discord gets the matching store role, with its permissions. See [Players](/en/products/players/). > [!TIP] > Using the bot on a server that already has roles? Link the roles first and run the sync, so you do not have to do the team one > by one. # Tickets and forms The bot brings the store's [tickets](/en/community/tickets/) and [forms](/en/community/forms/) into your Discord server. ## Tickets Each ticket becomes a private thread in the chosen channel, with the player and the team. What is written in the thread goes into the website ticket, and what is answered on the website shows in the thread. Attachments and stickers are not copied. ![The Tickets on Discord screen](shots/discord-tickets.webp) ### Turn it on 1. In **Discord > Tickets**, turn on **Tickets on Discord**. Support must be on in the store. 2. Pick the **Tickets channel**, a text channel. 3. Write the **Open ticket message**: **Title**, **Text** and **Button text**. Blank, it uses the default text. 4. Click **Save tickets** and **Publish message**. ```text Example message Title: Need help? Text: Click the button to talk to the team. Button text: Open ticket ``` **Mirror every ticket**, on, creates a thread even for those who did not link Discord, only with the team. Off, only tickets from linked players. ### Who answers Whoever has a store role [linked to a Discord role](/en/discord/linking/#link-store-roles-to-discord-roles) answers on Discord, with that role's Support permissions. The store owner answers by [connecting their own account](/en/discord/#your-discord-account). When the ticket closes, the thread is deleted, the conversation stays on the website and the player gets the link by direct message. > [!WARNING] > Check three things if the team does not see the threads or the bot does not reply: > > - the Discord roles have the **Manage Threads** permission on the tickets channel; > - on the Discord portal, under **Bot**, **Message Content Intent** is on; > - if the bot joined before tickets existed, use **Invite the bot again**, so it gets the thread permissions. ## Forms The player starts on the server and answers in the bot's direct messages, one question at a time. The answer goes into [Forms](/en/community/forms/), next to those from the website, and the result arrives by direct message. ![The Forms on Discord screen](shots/discord-forms.webp) ### Turn it on 1. Create at least one form in **Support > Forms**. 2. In **Discord > Forms**, turn on **Forms on Discord**. 3. In **Time to answer each question**, pick from 1 to 60 minutes. It applies to each question and to the review at the end. 4. In **Where the player starts**, pick a path. Only the chosen one is available on the server. | Path | How it works | | --- | --- | | **Message with all forms** | A message in a channel, with a button that opens the list of live forms | | **/form command** | The player types `/form` and picks by name | | **Message per form** | Each form has its own message, in its own channel, with a button that starts only that one | > [!NOTE] > The player must accept direct messages from the server, because the questions arrive there. The rules of each question, like > numbers only and character limit, apply on Discord too. # Welcome and announcements The bot tells the server when someone joins or leaves, when a news post goes out and when someone buys. All these messages use the same visual editor. ## Build the message On the welcome, news and purchases screens, the editor shows the message as it looks on Discord. ![The welcome message editor, with the parts and the preview](shots/discord-welcome.webp) 1. In **Parts**, drag a part to the preview, or click to add: **Author**, **Title**, **Text**, **Field**, **Thumbnail**, **Image**, **Footer**, **Date and time**. 2. Click a part of the preview to edit it on the right. 3. Use **Variables** to insert data that changes, like the name of who joined or the product bought. 4. Save. **Back to default** undoes everything. The preview uses sample data. The box color is the store's primary color, set in [Appearance](/en/discord/#appearance). ## Welcome and leave In **Discord > Welcome and leave**, joining and leaving have separate messages. 1. Turn on **Send welcome**, or **Send leave message**. 2. Pick the **Message channel**. 3. Build the message and save. **Mention who joined** puts the mention outside the box. That is what notifies the person: inside the box, the mention notifies nobody. > [!WARNING] > If the bot does not notice who joins, turn on **Server Members Intent** on the Discord portal, on the **Bot** tab. Without it, Discord > does not tell it. ## News with /news Whoever has permission publishes from Discord itself: the bot posts in the channel and the post goes on the website at the same time. ![The News on Discord screen](shots/discord-news.webp) 1. In **Discord > News**, turn on **News on Discord**. 2. Pick the **News channel**, text or announcement. The bot must be able to send messages in it. 3. Click **Save news**. On the server, whoever has permission types `/news`, writes the title and text in a Discord form and can attach an image. It becomes the post's banner on the website, with the writer's nick as the author. Whoever has a store role with **Publish News**, [linked to a Discord role](/en/discord/linking/#link-store-roles-to-discord-roles), publishes. The **Who publishes on Discord** card shows who can. > [!NOTE] > To edit or delete the post later, use [News](/en/community/) on the dashboard. What changes there does not change the message already on > Discord. Mentions in the text, like `@everyone`, notify nobody. ## Purchase announcement Each paid order can become an announcement in the channel. ![The Purchases on Discord screen](shots/discord-purchases.webp) 1. In **Discord > Purchases**, turn on **Announce purchases**. 2. Pick the **Announcement channel**. 3. Click **Save announcement**. **Hide the buyer nick** makes the announcement say "Someone" and not show the player's head. With many purchases at once, the bot announces at most ten every thirty seconds. ### Role per purchase The role per purchase is a website role, chosen when registering the product, under **Delivery**. If it is [linked to a Discord role](/en/discord/linking/#link-store-roles-to-discord-roles), the buyer gets both. A product with a duration gives back the previous role when it ends, and buying again extends it. A refund or order cancellation gives back the role within a minute. # Code theme A code theme draws your store's storefront from files you write: Liquid for the pages, CSS for the look and JSON for settings and texts. It goes beyond the drag-and-drop builder: any layout, your own sections and components, on every page of the store, and even small JavaScript apps in an isolated space. ## Where to start | You want to | Start with | |---|---| | Understand the whole path, from zero to the live store | [First steps](/en/code-theme/start/) | | Ask Claude, Cursor or another AI to change the store | [Connect your AI (MCP)](/en/code-theme/mcp/) | | Edit on your computer, with git and your AI | [hystore tool](/en/code-theme/cli/) | | Edit without installing anything | [Dashboard editor](/en/code-theme/editor/) | | Copy a banner, a product showcase, a countdown | [Ready examples](/en/code-theme/examples/) | | Add a wheel, a calculator or a mini game | [Isolated apps](/en/code-theme/apps/) | | Integrate with your system or CI | [Theme API](/en/code-theme/api/) | ## Four ways to edit - **In the dashboard**: Customization > Code theme > *Open the editor*. Code with autocomplete and checks, preview on the side. [Dashboard editor](/en/code-theme/editor/) - **On your computer, with your AI**: `npx @hystudios/hystore theme pull` downloads the theme and an `AGENTS.md` that teaches the format to Claude Code, Cursor, Codex and others. [hystore tool](/en/code-theme/cli/) - **With the AI connected to the store**: Claude, Cursor and other MCP apps sign in through the dashboard and edit the draft without installing anything. [Connect your AI](/en/code-theme/mcp/) - **Through the API**: theme keys for integrations and CI. [Theme API](/en/code-theme/api/) People who do not write code can still change texts, colours and the order of sections in **Customize theme**, with the fields the theme declares. ## From draft to live 1. **Draft**: every edit goes to the draft. The live store does not change. 2. **Check**: each file is checked when saved (forbidden HTML, Liquid syntax, CSS rules, JSON format). A file with an error is refused with the line and the reason. 3. **Preview**: a 24-hour link opens the draft on the store's real address. 4. **Publish**: in the dashboard, whoever has the *Publish the theme* permission publishes. From the tool, the AI or the API it is a **publish request** that this person approves, seeing what changed. 5. **Use in the store**: Code theme > In the store > *Use the theme in the store*. While the code theme is live, the builder is turned off. Picking a ready layout again takes the theme off the store without deleting it. The last 30 published versions are kept; any of them can come back to the draft. > [!TIP] > A store without a theme can start from a ready theme, with every page, light > and dark, in the store's colours: **Base** (simple and complete), **Aurora** > (gradient band, servers in a carousel), **Celeste** (a window over a sky > with pixel clouds, side menu) or **Prisma** (digital store look, catalog > with filters). ## What a theme cannot do - Run JavaScript on the page. Interaction comes from `data-hystore-*` attributes and `` elements the store handles. Real JavaScript only inside an [isolated app](/en/code-theme/apps/). - Touch money or accounts. Cart, payment, profile, purchases, password and sign-in are the store's own pages and open without the theme. - Read private data. The theme sees the store's public data and only the nick and skin of the visitor: never e-mail, balance or orders. - Hide the required area of the free plans (ads, legal links). The store checks the theme when it is saved, cleans the page again when it is drawn, and the content security policy blocks scripts. If the theme fails to draw, the page falls back to the store's default layout instead of going blank. ## Plans The code theme is a plan module: it shows in stores whose plan includes **Code theme**, and the owner can turn it off in Settings > Modules. Connecting an AI straight to the store is an option inside that module. Without the module, the theme screens show the way to the plans, keys and tool sessions stop working (disconnecting is still available) and a store that used the theme goes back to the ready layout, without deleting anything. ## Permissions Team > Access Roles, *Code theme* group: | Permission | Allows | |---|---| | View the theme | see files, versions and requests; open the editor read-only | | Edit the theme | change the draft, images and fonts; restore versions | | Publish the theme | publish, approve or refuse requests | | Theme credentials | create and revoke keys, see and disconnect tool sessions | A key or tool session never does more than the role of the person who created it allows, and it stops working if that person leaves the store or loses the permission. For every new key, tool login or AI app connected, the store owner (and the person who did it, if someone else) gets an e-mail with the link to disconnect. # First steps From zero to the new storefront live, in ten minutes. This guide follows the shortest path (all in the dashboard) and shows where the tool and the AI come in, so you can pick later. ## What you need - A store on Hystore whose plan includes the **Code theme** module. Check it in Settings > Modules: it must be on. - A role with the permissions of the *Code theme* group (the store owner has all of them). See [Permissions](/en/code-theme/#permissions). - To connect an AI straight to the store: the **Connect your AI** option inside the module, in the plan. ## 1. Pick a theme to start 1. Open the dashboard at [app.hystore.com.br](https://app.hystore.com.br). 2. Go to **Customization > Code theme**. 3. Pick one of the four ready themes: **Base**, **Aurora**, **Celeste** or **Prisma**. It becomes your draft, with every page, light and dark, and your store's colours. > [!NOTE] > Starting from a ready theme changes nothing on the store. The store only > changes its look when you publish and choose *Use the theme in the store*. ## 2. Make your first change 1. Click **Open the editor**. Files are on the left and the preview on the right. 2. Open `locales/en.json`. It keeps the theme's texts in English. 3. Change a text, for example the title at the top of the home page, and press **Ctrl+S**. The preview reloads with the new text. A text in the theme looks like this: ```liquid sections/hero.liquid

{{ 'home.hero_title' | t }}

``` And the value lives in the language file: ```json locales/en.json { "home": { "hero_title": "The best survival server in the world" } } ``` > [!TIP] > Change `locales/pt.json` and `locales/es.json` too: visitors in Portuguese or > Spanish see the text of their language. When one is missing, Portuguese > shows. ## 3. Change colours and sections without code 1. Go back to Code theme and open **Customize theme**. 2. In **Theme settings**, change the colours, texts and images the theme offers. 3. In **Sections of the page**, pick a page and move sections up and down, hide them or add new ones. 4. Click **Save**. Everything goes to the draft. ## 4. See the preview on the store's address The editor's preview is the store itself, with the draft. To send it to someone, use the preview link: it opens the draft on the store's real address for 24 hours, with a band saying it is a preview. The live store stays the same. ## 5. Publish 1. In Code theme, look at the list of changes and the errors (a theme with an error does not publish). 2. Click **Publish now**. This creates version 1 of your theme. ## 6. Turn the theme on in the store 1. In Code theme > **In the store**, click **Use the theme in the store**. 2. Open your store: the storefront is now your theme. While the code theme is live, the drag-and-drop builder is turned off. To go back, pick a ready layout again: the theme leaves the store without being deleted. ## Next steps - **Ask an AI to make the changes**: connect Claude, Cursor or another app in [Connect your AI](/en/code-theme/mcp/). You describe what you want and approve the publish. - **Edit on your computer**: the [hystore tool](/en/code-theme/cli/) downloads the theme, follows every save in the preview and works with git. - **Learn the format**: the [theme guide](/en/code-theme/guide/) explains files, sections, data and filters, and the [ready examples](/en/code-theme/examples/) give you code to copy. # Connect your AI (MCP) Connect Claude, Cursor or another AI straight to your store, with nothing to install and no key to copy. You just talk ("make a Black Friday banner at the top"), the AI reads the theme guide, edits the draft, sends you the preview link and asks to publish. A person always publishes, in the dashboard. There is one address, for any app that supports MCP: ```text https://mcp.hystore.com.br/mcp ``` > [!NOTE] > MCP (Model Context Protocol) is the open standard AI apps use to talk to > other services. The app keeps the address, signs you in through the Hystore > dashboard and gets the theme tools. ## Before you start - The store's plan must include **Code theme** with the **Connect your AI** option. Without it, the dashboard refuses the authorization and an existing connection stops answering. - The person who authorizes is someone in the store with theme permissions (see [Permissions](/en/code-theme/#permissions)). The AI never does more than that person can. - Each connection is for **one store**. To edit another store, connect again and pick the other store on the authorization screen. ## The path, in any app 1. Add the address `https://mcp.hystore.com.br/mcp` to the app as a remote MCP server (HTTP). Each app's steps are right below. 2. The app opens the browser on the **Connect an AI to your store** screen, in the Hystore dashboard. If you are not signed in, sign in first. 3. Check the app's name, pick the store and what the AI may do, and click **Authorize**. 4. Go back to the app. The connection shows as active, with the Hystore tools. 5. Ask something, for example: *"Use Hystore and tell me which store you are editing."* ## Claude (web and app) This works for [claude.ai](https://claude.ai) and for the Claude app on the computer and the phone: connectors belong to your account. 1. Open **Settings > Connectors**. 2. Click **Add custom connector**. 3. Fill in the name `Hystore` and the URL `https://mcp.hystore.com.br/mcp`. 4. Click **Add** and then **Connect**. The browser opens the Hystore dashboard: authorize (see [the authorization screen](#the-authorization-screen)). 5. In a new chat, open the chat's tools menu and check that **Hystore** is on. > [!TIP] > In the first message, ask: *"Read the Hystore theme guide and show me the > files of my theme."* That way the AI learns the format before editing. Custom connectors depend on your Claude plan. In company accounts (Team, Enterprise), whoever manages the organization adds the connector in the organization settings, and each person connects their own account afterwards. ## Claude Code In the terminal, once: ```bash claude mcp add --transport http hystore https://mcp.hystore.com.br/mcp ``` To have Hystore in every project, not only the current folder, add `--scope user`: ```bash claude mcp add --transport http --scope user hystore https://mcp.hystore.com.br/mcp ``` Then: 1. Run `claude` in the folder you work in. 2. Type `/mcp`, pick **hystore** and then **Authenticate**. 3. The browser opens the dashboard: authorize and go back to the terminal. 4. Ask: *"Use hystore to list the files of my theme."* > [!TIP] > Prefer the theme as files on your computer, with git? Use the > [hystore tool](/en/code-theme/cli/): Claude Code reads the `CLAUDE.md` it > writes and edits the files right in the folder. ## Cursor 1. Open **Cursor Settings > MCP** (in newer versions, *Tools & Integrations*) and click **New MCP Server**. Cursor opens the `mcp.json` file. 2. Paste: ```json ~/.cursor/mcp.json { "mcpServers": { "hystore": { "url": "https://mcp.hystore.com.br/mcp" } } } ``` 3. Save. Hystore shows in the list asking to sign in: click **Connect** (or *Login*) and authorize in the browser. 4. In Cursor's chat (Agent mode), ask: *"Use hystore to read the file layout/theme.liquid."* For a single project, use `.cursor/mcp.json` inside the project folder, with the same content. ## VS Code (GitHub Copilot) 1. Create the file `.vscode/mcp.json` in the project (or run the **MCP: Add Server...** command and pick HTTP): ```json .vscode/mcp.json { "servers": { "hystore": { "type": "http", "url": "https://mcp.hystore.com.br/mcp" } } } ``` 2. Click **Start**, shown above `"hystore"` in the file. VS Code asks to sign in: accept and authorize in the browser. 3. Open Copilot Chat in **Agent** mode, click the tools icon and check that the hystore tools are selected. ## Windsurf In **Windsurf Settings > Cascade > MCP Servers**, open the configuration file and paste: ```json ~/.codeium/windsurf/mcp_config.json { "mcpServers": { "hystore": { "serverUrl": "https://mcp.hystore.com.br/mcp" } } } ``` Refresh the server list and connect; the sign-in opens in the browser. ## Other apps Look in the app for *custom connector*, *remote MCP server* or *MCP over HTTP* and use the same address. No key or header is needed: the app finds where to sign in by itself (from the documents at `https://mcp.hystore.com.br/.well-known/`) and opens the dashboard. If the app only accepts local servers (command line), use the [hystore tool](/en/code-theme/cli/) instead of MCP. ## The authorization screen When the app asks for access, the dashboard shows **Connect an AI to your store**: - **The app's name**, as the app itself says it. Check it is the app you are connecting. - **Where the access goes.** When it is a program on your computer (Claude Code, Cursor, VS Code), the screen warns you: only authorize if you just asked for it. - **The store** the AI will edit. - **What the AI may do**, with boxes to untick: | On the screen | The AI may | |---|---| | Read the theme files | read files, versions, images and the public catalog | | Change the draft files | create, change and delete files and images of the draft | | Request a publish | send the draft for someone to approve in the dashboard | Click **Authorize** and go back to the app. **Refuse** gives no access at all. > [!WARNING] > If the screen opens without you asking for anything, click **Refuse**. > Nobody from Hystore asks you to authorize apps. ## Example requests Write as you would to a person. Some that work well: - *"Read the theme guide and explain how my theme is organized."* - *"On the home page, change the top title to 'Season 5 is here' in Portuguese, English and Spanish."* - *"Create a Black Friday section with a countdown to 11/28 at 23:59 and a button to the vips category. Put it at the top of the home."* - *"Show the 8 newest products of the kits category in cards with a buy button."* - *"Change the accent colour to gold and make the buttons rounder."* - *"Send me the preview link."* - *"Check the whole theme and fix the errors."* - *"Ask to publish with the note 'Black Friday banner'."* After the publish request, open **Customization > Code theme > Publish requests**, see what changed and click **Approve and publish** (or **Refuse**). ## What the AI can do | Tool | Does | |---|---| | `read_theme_guide` | reads the [theme guide](/en/code-theme/guide/), whole or one part | | `get_store` | the store's name and address, the connection's permissions | | `list_theme_files`, `read_theme_file` | reads the draft | | `write_theme_files` | creates, changes or deletes draft files, up to 100 at once | | `check_theme` | checks the whole draft | | `get_preview_link` | a 24-hour link to the draft on the store's address | | `request_publish` | asks to publish; someone approves in the dashboard | | `list_versions`, `read_version_file`, `restore_version` | published versions and bringing one back to the draft | | `list_assets`, `upload_asset`, `delete_asset` | the theme's images and fonts | | `read_catalog` | active categories and products, only what a visitor sees | Each tool's arguments and examples are in the [MCP reference](/en/code-theme/mcp-reference/#tools). Each file goes through the same check as in the dashboard: a file with an error goes back to the AI with the line and the reason, and nothing is saved. If someone changed the file in the dashboard meanwhile, the write is refused instead of erasing that change. The AI does **not** reach orders, payments, balance, players, coupons or settings, and it never publishes by itself. ## Disconnect The connection lasts 30 days and renews itself while the app is used. It shows in **Customization > Theme access > Connected sessions**, marked as *AI app*, with the app's name. **Disconnect** cuts the access at once. For every connected app, the store owner gets an e-mail with the link to disconnect. Every change made by the AI goes into the theme history with the MCP origin. ## Common problems | What happens | What to do | |---|---| | The dashboard says the store does not have the option | The plan needs **Code theme** with **Connect your AI**; also check Settings > Modules | | The **Authorize** button does not show | Your role needs theme permissions; ask the store owner | | The app says the connection expired | Disconnect and connect again; a connection unused for 30 days stops working | | The AI edited, but the store did not change | It edits the **draft**. Look at the preview and approve the publish request | | The AI says a file was refused | The message has the line and the reason; ask it to fix it. See [Common problems](/en/code-theme/faq/) | | The AI is editing the wrong store | Disconnect in Connected sessions and connect again picking the right store | For people who build apps and integrations, the sign-in, the routes and the messages are in the [MCP reference](/en/code-theme/mcp-reference/). # hystore tool `@hystudios/hystore` edits your store's code theme on your computer, with the AI you already use (Claude Code, Cursor, Codex, Copilot) and with git. It only needs [Node.js](https://nodejs.org) 18.17 or newer. ```bash npx @hystudios/hystore login npx @hystudios/hystore theme pull npx @hystudios/hystore theme dev ``` > [!TIP] > Using it every day? Install it once with `npm install -g @hystudios/hystore` > and replace `npx @hystudios/hystore` with `hystore` in the commands. ## Step by step ### 1. Sign in to your store ```bash npx @hystudios/hystore login ``` 1. The tool shows an 8-letter code and opens the dashboard in the browser. 2. Check that the code in the dashboard is the same as in the terminal. 3. Pick the store and what the tool may do (read, edit the draft, ask to publish). 4. Click **Authorize**. The terminal shows the connected store. There is no token to copy or paste. The code lasts 10 minutes and works once. ### 2. Download the theme ```bash mkdir my-store && cd my-store npx @hystudios/hystore theme pull ``` The folder looks like this: ```text my-store/ theme.json layout/theme.liquid pages/home.liquid sections/hero.liquid styles/theme.css locales/pt.json en.json es.json assets/logo.webp apps/roleta/index.html AGENTS.md rules and guide for the AI CLAUDE.md the same, for Claude Code .cursor/rules/hystore-theme.mdc for Cursor .claude/skills/hystore-theme/SKILL.md ``` A store without a theme? Use `theme new` to start from the Base theme: ```bash npx @hystudios/hystore theme new my-store ``` ### 3. Keep the preview running ```bash npx @hystudios/hystore theme dev ``` It checks and uploads every file you save and opens the preview on the store's address, which reloads by itself. Keep this terminal open while you work. ### 4. Edit, you or your AI Open the folder in your editor and ask the AI, for example: *"Make a Black Friday banner at the top of the home, in the store's colours, with texts in pt, en and es."* It reads `AGENTS.md` (or `CLAUDE.md`) and follows the theme rules. ### 5. Check ```bash npx @hystudios/hystore theme check ``` The same rules as the server, on your machine. An error shows the file, the line and the reason: ```text x sections/banner.liquid:3 Event attributes (onclick, onload...) are not allowed. Use data-hystore-* components. (html_event_handler) ``` ### 6. Ask to publish ```bash npx @hystudios/hystore theme publish --note "Black Friday banner" ``` This creates a **publish request**. Whoever has the *Publish the theme* permission opens **Customization > Code theme > Publish requests**, sees what changed and approves. ### 7. Keep it in git ```bash git init && git add . && git commit -m "Store theme" ``` No file in the folder has a token or a key: it can go to a repository. The tool already puts in `.gitignore` what should not go (`.hystore/`, with the sync state, and the `*.remote` copies). ## Commands | Command | What it does | |---|---| | `login` | signs in with the code approved in the dashboard | | `logout` | ends the session on the server too | | `whoami` | shows the store and the permissions | | `theme pull` | downloads the draft to the folder, with images, fonts and the AI files | | `theme push` | checks the folder and uploads what changed since the last sync | | `theme dev` | uploads on every save and opens the preview, which reloads by itself | | `theme check` | checks on your machine, with the same rules as the server | | `theme open` | opens a preview link of the draft (24 hours) | | `theme publish` | asks to publish (`--note "..."`); approved in the dashboard | | `theme versions` | lists the last 30 published versions | | `theme rollback ` | brings version n back to the draft (`--yes` skips the question) | | `theme new [folder]` | creates a folder from the Base theme | Options: `--dir `, `--force`, `--no-open`, `--lang pt|en|es`. `hystore pull` works like `hystore theme pull`. ## The session - It lasts 30 days and renews itself. It shows in **Customization > Theme access > Connected sessions**, where it can be disconnected. - It lives in your user folder (`~/.config/hystore`, or `%APPDATA%\hystore` on Windows), which only you can read. Never in the theme folder. - For every new login, the store owner gets an e-mail with the link to disconnect. ## Conflicts Each upload carries the version of each file you last downloaded. If someone changed that file in the dashboard meanwhile, the upload is refused instead of overwriting it. Run `theme pull`: - what changed only in the store comes in; - what changed only here stays; - a file changed in both places keeps yours, with the store's copy next to it as `.remote`. Merge, delete the `.remote` and upload again. `theme push --force` overwrites the store's version; `theme pull --force` makes the folder equal to the store. ## In CI (GitHub Actions) For CI, create a key in **Customization > Theme access > Create key** (scopes *read* and *edit*, and *request a publish* if CI will ask) and keep it in the repository secrets as `HYSTORE_THEME_TOKEN`. The tool uses that variable instead of the login. ```yaml .github/workflows/theme.yml name: theme on: push: branches: [main] jobs: upload: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - uses: actions/setup-node@v4 with: node-version: 20 - run: npx @hystudios/hystore theme check - run: npx @hystudios/hystore theme push --force env: HYSTORE_THEME_TOKEN: ${{ secrets.HYSTORE_THEME_TOKEN }} - run: npx @hystudios/hystore theme publish --note "Commit ${{ github.sha }}" env: HYSTORE_THEME_TOKEN: ${{ secrets.HYSTORE_THEME_TOKEN }} ``` - `--force`: in CI git is the source of truth, and the cloned folder has no sync state (`.hystore/`, which stays out of git). The upload writes the folder over the draft. - The last step only creates the request: the store changes when someone approves it in the dashboard. ## Security - Publishing is always a request approved in the dashboard. - The tool only reads and writes theme files in the folder; other files are left alone. - Images and fonts are only downloaded from Hystore's address and checked by their hash. # Dashboard editor Everything about the code theme is in **Customization > Code theme** in the dashboard at [app.hystore.com.br](https://app.hystore.com.br). ## The Code theme screen - What is live (version and date), the draft revision, which files are new, changed or removed, and the errors and warnings of the theme. - *Publish now*, *Publish requests* (approve or refuse what the tool and the API asked) and *Published versions* (restore one into the draft). - Start from a ready-made theme (Base, Aurora, Celeste or Prisma) in a store with no theme, and *Replace the draft with a ready-made theme* later. - *Theme images and fonts*: upload PNG, JPEG, WebP, GIF, AVIF up to 3 MB and WOFF, WOFF2 up to 1 MB (checked by their content; no SVG), up to 100 files and 40 MB. - *In the store*: *Use the theme in the store* once a version is published. ## Editor *Open the editor* opens a full-screen editor: - the theme's files on the left: create a file in a folder (blank or the same file from the Base theme), rename, delete; - tabs, code colors, completion of tags, filters, variables and blocks, and what each one does when you hover over it; - *Save* or Ctrl+S writes to the draft and reloads the preview; a file with an error is not saved and the error shows on its line; - if the file changed somewhere else, you choose between the saved version and yours; - *Difference* compares the file with what is live, and *History* with any published version, which can be brought back to the tab; - images and fonts dragged onto the code are uploaded and the code to use them is written where they fell; - the preview, on the side in computer, tablet or phone size, is the store itself on a 24-hour link; - in the `apps` folder, the **+** creates an [isolated app](/en/code-theme/apps/) with `index.html`, `app.js` and `app.json` at once. People with only *View the theme* open it read-only. ## Customize theme *Customize theme* changes the theme without code, with the preview on the side: - **Theme settings**: the fields of `theme.json` (colors, texts, images, switches); - **Sections of the page**: for each page, move sections up and down, hide, remove, add a section the theme has, and edit its fields. *Save* writes `config/values.json` and `templates/.json` to the draft; the store changes when it is published. If the theme changed somewhere else while the screen was open, nothing is written and the screen loads the saved version. # Hystore code theme guide A Hystore code theme is a folder of Liquid, CSS and JSON files that draws a store's storefront: header, footer, home, shop, product pages, news, players. The store's own code keeps the cart, payment, account and sign-in pages, which never load the theme. This guide is the reference for people and for AI assistants editing a theme. Everything here is checked by the Hystore servers: a file that breaks a rule is refused when it is saved, with the file, the line and the reason. ## Workflow ``` npx @hystudios/hystore login # approve in the dashboard (no token to paste) npx @hystudios/hystore theme pull # download the draft into this folder npx @hystudios/hystore theme dev # watch the folder, upload every save, live preview npx @hystudios/hystore theme check # check locally, without uploading npx @hystudios/hystore theme push # upload the changes to the draft npx @hystudios/hystore theme publish # ask to publish; someone with permission approves in the dashboard npx @hystudios/hystore theme versions # the last 30 published versions npx @hystudios/hystore theme rollback 3 # bring version 3 back to the draft npx @hystudios/hystore theme new # start a folder from the Hystore Base theme ``` - Edits always go to the **draft**. The live store only changes when a publish request is approved in the dashboard (Customization > Code theme). - The preview link (from `theme dev`) shows the draft on the store's real address for 24 hours and reloads by itself after each upload. - If someone changed a file in the dashboard after your last pull, the upload of that file is refused as a conflict: pull, merge, push again. ## Hard rules These are refused (the save fails): - ` ``` ```js hystore.products({ category: 'vips', limit: 6 }).then(function (products) { // [{ id, name, url, price, priceText, originalPrice, onSale, image, shortDescription, ... }] }); hystore.categories(); // active categories hystore.addToCart(productId, 1); // 'added', or 'login' (the store asks to sign in) hystore.navigate('/loja'); // a page of the store hystore.open('cart'); // 'cart' | 'login' | 'account' | 'search' hystore.context(); // { locale, colorMode, store: { name, currency } } hystore.customer(); // { loggedIn, nick, skinUrl }, only with "customer" in app.json hystore.resize(600); // or hystore.autosize() to follow the page ``` - Everything is public data: prices come from the store, and the cart only takes a product id. Money and account pages never show apps. - Load only the app's own files and `/sdk/v1.js`; scripts and styles from other sites, frames and forms are refused when saving. Images can be `data:` images or the theme's own images and fonts by their full address (`https://theme-assets.hystore.com.br/...`, as `GET /v1/theme/assets` and the MCP tool `list_assets` give it). - `app.json` is optional: `height` from 40 to 2000 pixels (320 by default), `name` for screen readers, `permissions` only `customer`. - Limits: 10 apps per theme, 20 files and 512 KB per app. - Too many messages are ignored; adding to the cart and changing page have their own small limits. ## Checklist before publishing - `npx @hystudios/hystore theme check` has no errors. - Every text a visitor reads goes through `| t`, in pt, en and es. - The theme works in the color modes it declares and on a phone. - Links to cart, account and sign in point to `/carrinho`, `/perfil` and `/entrar` (or use `data-hystore-open`). # Ready examples Recipes to copy. Each block shows the file it goes in and passes the store's check. After creating a section, add it in **Customize theme > Sections of the page** or in `templates/.json`. > [!TIP] > With the AI connected, you can ask for exactly this: *"Use the category > showcase example from the Hystore wiki for the kits, with 6 products."* ## Promotion banner A banner with a title, text and a button, all editable in Customize theme. ```liquid sections/promo-banner.liquid

{{ section.settings.tag }}

{{ section.settings.title }}

{{ section.settings.text }}

{%- if section.settings.button_url != blank -%} {{ section.settings.button_label }} {%- endif -%}
{% schema %} { "name": "Promotion banner", "settings": [ { "id": "tag", "type": "text", "label": "Tag", "default": "This week only" }, { "id": "title", "type": "text", "label": "Title", "default": "Black Friday: up to 50% off" }, { "id": "text", "type": "textarea", "label": "Text", "default": "Kits, VIPs and cosmetics on sale." }, { "id": "button_label", "type": "text", "label": "Button text", "default": "See the deals" }, { "id": "button_url", "type": "url", "label": "Button link", "default": "/loja" } ] } {% endschema %} ``` ```css styles/promo-banner.css .promo { padding: 48px 20px; background: linear-gradient(120deg, hsl(var(--primary)), #1d4ed8); color: #fff; } .promo-in { max-width: 960px; margin: 0 auto; } .promo-tag { display: inline-block; padding: 4px 10px; border-radius: 999px; background: rgba(255, 255, 255, .18); font-weight: 700; font-size: 13px; } .promo h2 { margin: 12px 0 8px; font-size: clamp(28px, 4vw, 44px); } .promo-btn { display: inline-block; margin-top: 12px; padding: 12px 22px; border-radius: 12px; background: #f5b544; color: #1c1305; font-weight: 700; text-decoration: none; } ``` ## Category showcase The products of a category, with price, sale and a buy button. ```liquid sections/category-showcase.liquid {% load products, category: section.settings.category, limit: section.settings.count as items %}

{{ section.settings.title }}

{%- for p in items -%}
{%- if p.image -%}{{ p.name }}{%- endif -%}

{{ p.name }}

{%- if p.on_sale -%}{{ p.original_price | money }} {% endif -%} {{ p.price | money }}

{%- if p.sold_out -%} {{ 'product.sold_out' | t }} {%- else -%} {%- endif -%}
{%- else -%}

{{ 'showcase.empty' | t }}

{%- endfor -%}
{% schema %} { "name": "Category showcase", "settings": [ { "id": "title", "type": "text", "label": "Title", "default": "Kits" }, { "id": "category", "type": "text", "label": "Category slug", "default": "kits" }, { "id": "count", "type": "range", "label": "How many", "min": 2, "max": 24, "default": 8 } ] } {% endschema %} ``` The slug is the end of the category's address in the store (`/loja/survival/kits` has the slug `kits`). The texts `product.add`, `product.sold_out` and `showcase.empty` live in the language files: ```json locales/en.json { "product": { "add": "Buy", "sold_out": "Sold out" }, "showcase": { "empty": "No products here yet." } } ``` ## Countdown The store fills in the numbers by itself, with no JavaScript in the theme. ```liquid sections/countdown.liquid

{{ section.settings.title }}

0 {{ 'time.days' | t }} 0 {{ 'time.hours' | t }} 0 {{ 'time.minutes' | t }} 0 {{ 'time.seconds' | t }}
{% schema %} { "name": "Countdown", "settings": [ { "id": "title", "type": "text", "label": "Title", "default": "The new season starts in" }, { "id": "ends_at", "type": "text", "label": "Date and time (UTC)", "default": "2026-12-24T23:59:00Z" } ] } {% endschema %} ``` ## Server IP and players online ```liquid sections/server-bar.liquid {% load server_status as status %}
{%- if status and status.online -%} {{ status.players_online }}/{{ status.players_max }} {{ 'server.online' | t }} {%- else -%} {{ 'server.offline' | t }} {%- endif -%}
{% schema %} { "name": "Server bar", "settings": [] } {% endschema %} ``` Clicking the IP copies the address. The store fills `` with the players online. ## Top buyers of the month ```liquid sections/top-buyers.liquid {% load ranking, period: 'month', limit: 5 as top %}

{{ section.settings.title }}

    {%- for row in top -%}
  1. {{ row.position }}. {{ row.nick }} {{ row.total_spent | money }}
  2. {%- endfor -%}
{% schema %} { "name": "Top buyers", "settings": [{ "id": "title", "type": "text", "label": "Title", "default": "Top of the month" }] } {% endschema %} ``` ## Frequently asked questions An accordion with questions the store owner adds as blocks. ```liquid sections/faq.liquid

{{ section.settings.title }}

{%- for block in section.blocks -%}
{{ block.settings.answer }}
{%- endfor -%}
{% schema %} { "name": "FAQ", "settings": [{ "id": "title", "type": "text", "label": "Title", "default": "Questions" }], "blocks": [ { "type": "question", "name": "Question", "settings": [ { "id": "question", "type": "text", "label": "Question" }, { "id": "answer", "type": "textarea", "label": "Answer" } ] } ] } {% endschema %} ``` ## Theme colours and options General settings live in `theme.json` and become fields in Customize theme: ```json theme.json { "name": "My theme", "version": "1.0.0", "color_modes": ["dark", "light"], "settings": [ { "id": "accent", "type": "color", "label": "Accent colour", "default": "#f5b544" }, { "id": "radius", "type": "range", "label": "Roundness", "min": 0, "max": 28, "default": 14 } ] } ``` Colours and numbers become CSS variables at the theme's root: ```css styles/theme.css .button { background: var(--theme-accent); border-radius: calc(var(--theme-radius) * 1px); } html:not(.dark) .card { background: #fff; color: #0b1526; } html.dark .card { background: #0d1524; color: #e8eef8; } ``` And any general setting shows in Liquid as `{{ settings.accent }}`. ## Switch colour mode and language ```liquid components/header-tools.liquid
``` Use it in the layout with `{% render 'header-tools' %}`. ## More - The [theme guide](/en/code-theme/guide/) lists every data source, filter, ready-made block and interactive piece. - For JavaScript (wheel, quiz, calculator), see [Isolated apps](/en/code-theme/apps/). - The Base, Aurora, Celeste and Prisma themes are great to learn from: start one in the dashboard and open its files in the editor. # Isolated apps An app is a small page with real JavaScript (a prize wheel, a price calculator, a quiz, a mini game, an animation) that the theme places anywhere in the store. It runs isolated, in a frame on another domain, and talks to the store only through a bridge with rules: it reads the public catalog, adds products to the cart and changes pages. It never reaches prices, payment, accounts or other visitors' data. ## How it works - The app lives in `apps//` in the theme, with `index.html` (required), scripts, styles and an optional `app.json`. - The theme places it on a page with ``. - The store opens the app in a frame on `hystoreapps.cloud`, with a policy that blocks the network (`fetch`, XHR, WebSocket), cookies, storage, forms, new windows and navigating the store page. - The app calls `window.hystore`, the bridge, loaded by ` ``` `/sdk/v1.js` is the bridge. The other files belong to the app, with relative addresses (`app.css`, `app.js`). ### 4. Style it ```css apps/roleta/app.css * { box-sizing: border-box; } body { margin: 0; padding: 16px; font: 15px/1.5 system-ui, sans-serif; color: #e8eef8; background: transparent; text-align: center; } html.light body { color: #0b1526; } .hello { margin: 0 0 12px; font-weight: 700; } .stage { position: relative; width: 260px; height: 260px; margin: 0 auto 16px; } .wheel { width: 100%; height: 100%; border-radius: 50%; border: 6px solid #f5b544; transition: transform 4s cubic-bezier(.17, .67, .12, .99); } .pointer { position: absolute; top: -6px; left: 50%; z-index: 1; transform: translateX(-50%); border: 12px solid transparent; border-top: 22px solid #f5b544; } .spin { padding: 10px 28px; border: 0; border-radius: 12px; background: #0ea5e9; color: #fff; font-weight: 700; cursor: pointer; } .spin:disabled { opacity: .5; cursor: default; } .result { min-height: 64px; margin-top: 14px; } .result button { margin-left: 8px; padding: 6px 14px; border: 0; border-radius: 10px; background: #f5b544; color: #1c1305; font-weight: 700; cursor: pointer; } ``` ### 5. Write the script ```js apps/roleta/app.js (function () { var wheel = document.getElementById('wheel'); var spin = document.getElementById('spin'); var result = document.getElementById('result'); var products = []; var turns = 0; // The store's colour mode and language. hystore.context().then(function (ctx) { document.documentElement.classList.toggle('light', ctx.colorMode === 'light'); }); // The nick of whoever is signed in (needs "customer" in app.json). hystore.customer().then(function (me) { if (me.loggedIn) document.getElementById('hello').textContent = 'Good luck, ' + me.nick + '!'; }).catch(function () { /* without the permission: the default text stays */ }); // The public products of the "kits" category. hystore.products({ category: 'kits', limit: 8 }).then(function (list) { products = list.filter(function (p) { return !p.soldOut; }); if (!products.length) { result.textContent = 'No kit available right now.'; return; } paint(); spin.disabled = false; }); function paint() { var slice = 360 / products.length; var colors = ['#0ea5e9', '#1d4ed8']; var stops = products.map(function (p, i) { return colors[i % 2] + ' ' + i * slice + 'deg ' + (i + 1) * slice + 'deg'; }); wheel.style.background = 'conic-gradient(' + stops.join(', ') + ')'; } spin.addEventListener('click', function () { var i = Math.floor(Math.random() * products.length); var slice = 360 / products.length; turns += 5; wheel.style.transform = 'rotate(' + (turns * 360 - (i * slice + slice / 2)) + 'deg)'; spin.disabled = true; setTimeout(function () { show(products[i]); spin.disabled = false; }, 4200); }); function show(product) { result.textContent = ''; var text = document.createElement('p'); text.textContent = 'You got: ' + product.name + ' for ' + product.priceText; var buy = document.createElement('button'); buy.type = 'button'; buy.textContent = 'Add to cart'; buy.addEventListener('click', function () { hystore.addToCart(product.id, 1).then(function (answer) { if (answer === 'added') hystore.open('cart'); else if (answer === 'sold_out') buy.textContent = 'Sold out'; // 'login': the store already asked the person to sign in. }); }); text.appendChild(buy); result.appendChild(text); } })(); ``` > [!TIP] > Build texts with `textContent` and `createElement`, as above. It is the right > habit for any data that comes from outside, even inside the isolated frame. ### 6. Place the app on a page In a section or page of the theme, where the app should show: ```liquid sections/roleta.liquid

{{ section.settings.title }}

{% schema %} { "name": "Kit wheel", "settings": [ { "id": "title", "type": "text", "label": "Title", "default": "Try your luck" } ] } {% endschema %} ``` Then add the section in **Customize theme > Sections of the page**, or in `templates/home.json`. ### 7. Look at the preview and publish 1. Save. The editor's preview (and the preview link) show the app with the **draft** files. 2. Try spinning and adding to the cart. 3. Publish the theme. The store then uses the files of the published version. ## The bridge: window.hystore Every function returns a *Promise*. When refused, it rejects with an error whose message is the reason (see [Errors](#errors)). | Function | What it does | Returns | |---|---|---| | `hystore.context()` | language, colour mode and store | `{ locale, colorMode, store: { name, currency } }` | | `hystore.products(options)` | active products, only what a visitor sees | list of products | | `hystore.categories(options)` | active categories | list of categories | | `hystore.addToCart(id, quantity)` | adds the product to the cart (quantity 1 to 99) | `'added'`, `'login'` or `'sold_out'` | | `hystore.navigate(path)` | opens a store page, such as `/loja` or `/noticias` | `true` | | `hystore.open(place)` | opens `'cart'`, `'login'`, `'account'` or `'search'` | `true` | | `hystore.customer()` | who is looking (with `customer` in `app.json`) | `{ loggedIn, nick, skinUrl }` | | `hystore.resize(height)` | changes the frame's height (40 to 4000) | the height applied | | `hystore.autosize()` | follows the height of the app's page by itself | nothing | ### Options of products and categories | Option | Type | Example | |---|---|---| | `category` | category slug | `'kits'` | | `server` | server id | `'survival'` | | `query` | search text (up to 80 characters) | `'sword'` | | `limit` | 1 to 48 (12 when missing) | `6` | `categories` only takes `server`. ### A product ```json { "id": "0f558e5e-636a-4e5a-9739-24c711463ebf", "name": "Warrior kit", "slug": "warrior-kit", "url": "/loja/survival/kits/produto/warrior-kit", "price": 19.9, "priceText": "$19.90", "originalPrice": 29.9, "originalPriceText": "$29.90", "onSale": true, "image": "https://...", "shortDescription": "Sword, armour and 64 apples", "durationDays": null, "minQuantity": 1, "soldOut": false, "digital": false, "categorySlug": "kits", "serverId": "survival" } ``` The price is only for showing: the cart uses the store's price, and the app only sends the product `id`. A category has `id`, `name`, `slug`, `url`, `description`, `image` and `productCount`. ### Errors | Message | When | |---|---| | `bad_payload` | wrong argument (an id that is not a product, a quantity outside 1 to 99, a path outside the store) | | `permission` | `customer()` without `"customer"` in `app.json` | | `rate_limited` | too many calls in a row; wait a little | | `failed` | the store could not answer right now | | `hystore: open this app inside the store` | the app was opened outside the store (straight at its address) | | `hystore: no answer` | the store did not answer in 10 seconds | ## Rules and limits - Load only the app's own files and `/sdk/v1.js`. Scripts and styles from other sites, `