An optional component handler for hikari, inspired by discord.py's views.

Overview

hikari-miru

An optional component handler for hikari, inspired by discord.py's views.

Installation

pip install git+https://github.com/HyperGH/hikari-miru.git

Usage

None: if event.is_bot or not event.content: return if event.content.startswith("hm.buttons"): view = MyView(bot, timeout=60) # Create a new view message = await event.message.respond("Rock Paper Scissors!", components=view.build()) view.start(message) # Start listening for interactions await view.wait() # Wait until the view times out or gets stopped await event.message.respond("Thank you for playing!") bot.run()">
import hikari
import hikari_miru as miru


class MyView(miru.View):

    @miru.button(label="Rock", emoji="🪨", style=hikari.ButtonStyle.PRIMARY)
    async def rock_button(self, button: miru.Button, interaction: hikari.ComponentInteraction):
        await interaction.create_initial_response(hikari.ResponseType.MESSAGE_CREATE, content=f"Paper!")

    @miru.button(label="Paper", emoji="📜", style=hikari.ButtonStyle.PRIMARY)
    async def paper_button(self, button: miru.Button, interaction: hikari.ComponentInteraction):
        await interaction.create_initial_response(hikari.ResponseType.MESSAGE_CREATE, content=f"Scissors!")

    @miru.button(label="Scissors", emoji="✂️", style=hikari.ButtonStyle.PRIMARY)
    async def scissors_button(self, button: miru.Button, interaction: hikari.ComponentInteraction):
        await interaction.create_initial_response(hikari.ResponseType.MESSAGE_CREATE, content=f"Rock!")

    @miru.button(emoji="⏹️", style=hikari.ButtonStyle.DANGER, row=2)
    async def stop_button(self, button: miru.Button, interaction: hikari.ComponentInteraction):
        await interaction.create_initial_response(hikari.ResponseType.DEFERRED_MESSAGE_UPDATE)
        self.stop() # Stop listening for interactions


bot = hikari.GatewayBot(token="...")


@bot.listen()
async def buttons(event: hikari.GuildMessageCreateEvent) -> None:

    if event.is_bot or not event.content:
        return

    if event.content.startswith("hm.buttons"):
        view = MyView(bot, timeout=60)  # Create a new view
        message = await event.message.respond("Rock Paper Scissors!", components=view.build())
        view.start(message)  # Start listening for interactions
        await view.wait() # Wait until the view times out or gets stopped
        await event.message.respond("Thank you for playing!")

bot.run()

Issues and support

For general usage help or questions, ping Hyper#0001 in the hikari discord, if you have found a bug or have a feature request, feel free to open an issue!

Contributing

If you wish to contribute, be sure to first enable the formatting pre-commit hook via git config core.hooksPath .githooks, then make your changes.

Comments
  • Components break in hikari 2.0.0.dev110

    Components break in hikari 2.0.0.dev110

    Steps to reproduce

    1. Upgrade to hikari 2.0.0.dev110
    2. Send a message with any components
    3. Try to use said components
    4. Observe the components failing

    Expected result

    The bot should've responded to the component interaction.

    Actual result

    The bot didn't respond to any component interactions.

    System information

    hikari-miru - package information
    ----------------------------------
    Miru version: 1.1.1
    Install path: /root/venv/lib/python3.10/site-packages/miru
    Hikari version: 2.0.0.dev110
    Install path: /root/venv/lib/python3.10/site-packages/hikari
    Python: CPython 3.10.5 (GCC 12.1.0)
    System: Linux x86_64 (solar) - 5.18.16-arch1-1
    

    Further information

    No response

    Checklist

    • [X] I have made sure to remove ANY sensitive information (bot token, passwords, credentials, personal details, etc.).
    • [X] I have searched the issue tracker and have made sure it's not a duplicate. If it is a follow up of another issue, I have specified it.
    bug 
    opened by piotr25691 6
  • Allow customization of item and context classes

    Allow customization of item and context classes

    Wake up babe new pr just dropped

    import miru
    
    
    
    class MyButton(miru.Button):
        ...
    
    class MyContext(miru.Context):
        ...
    
    class MyView(miru.View):
        @miru.button(cls=MyButton, context_cls=MyContext, label="label")
        async def foo(self, button: MyButton, context: MyContext):
            ...
        
        @miru.button(label="label")
        async def bar(self, button: MyButton, context: MyContext):
            ...
    
    view = MyView()
    
    enhancement 
    opened by thesadru 4
  • Persistant components between bot restarts

    Persistant components between bot restarts

    Summary

    Miru should replace the current component persistence system to one thats easier to work with/possibly more efficient. I believe a side effect of my implementation will also allow custom timeout responses for buttons.

    Why is this needed?

    I think it is good if bots can still respond to a button after a restart.

    Ideal implementation

    # Internal
    class ComponentInfo:
        """Info used to distinguish miru components from each other."""
        ....
    
    # External
    # The user is expected to implement these functions if they want to use persistence between restarts.
    
    # Called when a component is created
    @miru.persistence.save_component
    async def save(nonce: str, component: miru.ComponentInfo) -> None:
        """Save a ComponentInfo object"""
        ...
    
    # Called when a component nonce is received that isn't in the cachce
    @miru.persistence.load_component
    async def load(nonce: str) -> miru.ComponentInfo | None:
        """Load a ComponentInfo object. Return `None` if the object doesn't exist."""
        ...
    
    # Called when 
    @miru.persistence.delete_component
    async def load(nonce: str) -> None:
        """Delete a component with a specific nonce."""
        ...
    

    The internals will need to be reworked is have "registry/cache" with all the components. The nonce will be used to run the correct callback. This is similar to how crescent works so I can vouch for the system.

    Checklist

    • [X] I have searched the issue tracker and have made sure it's not a duplicate. If it is a follow up of another issue, I have specified it.
    enhancement 
    opened by Lunarmagpie 3
  • Change autodefer to auto_defer

    Change autodefer to auto_defer

    This is more of a suggestion, but it might make consistency between different handlers and libs for Hikari more consistent if these references were changed.

    opened by GoogleGenius 1
  • link buttons cannot be added

    link buttons cannot be added

    When I try to add link buttons with the following code, an error is raised and it doesn't work.

    view = miru.View()
    view.add_item(miru.Button(label="View Online", url=str(ctx.options.user.display_avatar_url)))
    return await ctx.respond(e, components=view.build())
    

    The issue lies in https://github.com/HyperGH/hikari-miru/blob/main/miru/button.py#L127 and causes a following error:

    Traceback (most recent call last):
      File "C:\Users\User\PycharmProjects\h\iodine\lib\site-packages\lightbulb\app.py", line 994, in handle_message_create_for_prefix_commands
        await self.process_prefix_commands(context)
      File "C:\Users\User\PycharmProjects\h\iodine\lib\site-packages\lightbulb\app.py", line 966, in process_prefix_commands
        await context.invoke()
      File "C:\Users\User\PycharmProjects\h\iodine\lib\site-packages\lightbulb\context\base.py", line 292, in invoke
        await self.command.invoke(self)
      File "C:\Users\User\PycharmProjects\h\iodine\lib\site-packages\lightbulb\commands\prefix.py", line 112, in invoke
        await self(context)
      File "C:\Users\User\PycharmProjects\h\iodine\lib\site-packages\lightbulb\commands\base.py", line 435, in __call__
        return await self.callback(context)
      File "D:\Coding\Iodine\cogs\tools.py", line 41, in avatar
        view.add_item(miru.Button(label="View Online", url=str(ctx.options.user.display_avatar_url)))
      File "C:\Users\User\PycharmProjects\h\iodine\lib\site-packages\miru\button.py", line 109, in __init__
        self.style = hikari.ButtonStyle.LINK
      File "C:\Users\User\PycharmProjects\h\iodine\lib\site-packages\miru\button.py", line 128, in style
        raise ValueError("A link button cannot have it's style changed. Remove the url first.")
    ValueError: A link button cannot have it's style changed. Remove the url first.
    
    bug 
    opened by piotr25691 1
  • Fix typing issues in miru

    Fix typing issues in miru

    Some internal changes had to be made to make miru type-safe

    Changes

    • make items generic (item.view can now be given attributes)
    • make @button and @select be typed to return the same function that was given
      • A possible alternative is returning the actual type, happy to hear your opinions on this one!
    • added all missing typing.Any and None annotations where they were forgotten
    opened by thesadru 1
  • Add readme files to subdirectories

    Add readme files to subdirectories

    Summary

    Add readme files to most important subdirectories with short explainers detailing what can be found in the directory & directing users to helpful resources.

    Why is this needed?

    Because it is fancy.

    Ideal implementation

    Sit down and write them.

    Checklist

    • [X] I have searched the issue tracker and have made sure it's not a duplicate. If it is a follow up of another issue, I have specified it.
    enhancement 
    opened by HyperGH 0
  • Fix a few bugs and inconsistencies

    Fix a few bugs and inconsistencies

    See changelog.

    • no longer use explicit submodules unless they're exported
    • no longer use pass where it's not needed
    • ignore when 3rd party libraries are missing stubs
    • for the sake of user experience assume the class is initialized when annotating
    • make the colorama dependency optional (gawd the dependency management is funky)
    • allow for unloading miru and stopping all views
    enhancement 
    opened by thesadru 0
  • Add colorama to requirements

    Add colorama to requirements

    I install hikari-miru and did python3 -m miru and it said no package named colorama, after installing, it worked fine but it didn't install with hikari-miru, so I suggest adding it as a requirement

    bug 
    opened by VG08 0
  • Add exercises to documentation

    Add exercises to documentation

    Summary

    Add short exercises to documentation to facilitate learning the different features of the library.

    Why is this needed?

    It helps people learn the library a lot quicker if there are potentially quick example problems to solve.

    Ideal implementation

    To be decided.

    Checklist

    • [X] I have searched the issue tracker and have made sure it's not a duplicate. If it is a follow up of another issue, I have specified it.
    enhancement 
    opened by HyperGH 0
Releases(v2.0.1)
  • v2.0.1(Dec 6, 2022)

  • v2.0.0(Dec 5, 2022)

    • BREAKING: View.start() is now asynchronous and needs to be awaited.

    • BREAKING: View.start_listener() has been removed. Use View.start() instead.

    • Added support for modals via miru.Modal.

    • Added support for text input fields via miru.TextInput.

    • Added RawComponentContext, RawModalContext, ViewContext, and ModalContext that inherit from Context.

    • Added miru.InteractionResponse, an object representing responses sent out by the application to interactions.

    • Context.respond() and Context.edit_response() now return an InteractionResponse object.

    • Added Context.bot and Context.author as aliases for Context.app and Context.user respectively.

    • Added overloads to Context.defer() to allow use of different deffered response-types.

    • Added miru.abc.ViewItem and miru.abc.ModalItem that inherit from miru.abc.Item.

    • Views now expect items of type ViewItem and provide ViewContext.

    • Button and Select are now subclasses of ViewItem.

    • Added miru.abc.ItemHandler. View and Modal are subclasses of this object.

    • Added miru.abc.ItemHandler.last_context to access the last received context & interaction by the item handler.

    • miru.abc.ItemHandler now implements Sequence[hikari.api.MessageActionRowBuilder], and thus can be treated as a sequence of action rows. This means that calling .build() on item handlers is no longer required.

    • Removed miru.Interaction.

    • Added View.from_message() classmethod to allow creation of views from message components.

    • Added View.wait_for_input() to wait for any component interaction relating to the view.

    • Added timeout parameter to ItemHandler.wait().

    • Added View.get_context() and Modal.get_context() for custom context support.

    • Added two new event types ModalInteractionCreateEvent and ComponentInteractionCreateEvent.

    • These listeners include the corresponding raw context with the event object, along with every field from hikari.InteractionCreateEvent.

    • ItemHandler.add_item(), ItemHandler.remove_item(), and ItemHandler.clear_items() now return the ItemHandler object to allow for method chaining.

    • Added responded kwarg to NavigatorView to have the ability to send navigators on acknowledged interactions.

    • Added start_at kwarg to NavigatorView to define what the first page should be.

    • Added a “Jump to page” modal to built-in ext.nav.IndicatorButton when pressed.

    • Allow passing datetime.timedelta to ItemHandler.timeout upon instantiation.

    • Add delete_after to Context.respond() as a kwarg, and as a method to InteractionResponse.

    • Added miru.ext.nav.utils.Paginator to help pagination of long strings.

    • View.start() now accepts awaitables that return hikari.Message, thus allowing it to function with custom objects that support this behaviour.

    • Fixed selectoption is_default fields being ignored.

    • Deprecate miru.load and miru.unload in favor of miru.install and miru.uninstall.

    Source code(tar.gz)
    Source code(zip)
Ice Skating Simulator for Winter and Christmas [yay]

Ice Skating Simulator for Winter and Christmas [yay]

1 Aug 21, 2022
The little-endian version of MessagePack

MessagePackEL This is the little-endian version of MessagePack, except the endianness is different, the rest is exactly the same as MessagePack. C lib

dukelec 9 May 13, 2022
A series of basic programs written in Python

Primeros programas en Python Una serie de programas básicos escritos en Python

Madirex 1 Feb 15, 2022
a really simple bot that send you memes from reddit to whatsapp

a really simple bot that send you memes from reddit to whatsapp want to use use it? install the dependencies with pip3 install -r requirements.txt the

pai 10 Nov 28, 2021
the classic version Of torrentleechx #Unmaintained #Archived

TorrentleechX-Classic Old Modified Version Repo #Unmaintained #Archived for support join here working example group Leech Here For Any Issues/Imroveme

XcodersHub 18 Jan 30, 2022
Proyecto desarrollado para el programa #FutureDevelopers, tabla periódica interactiva.

Tabla_Periodica Proyecto desarrollado para el programa #FutureDevelopers, tabla periódica interactiva. Descripcion primer entregable: Tabla periodica

1 Dec 04, 2021
Cvdl-hw2 - Find Contour, Camera Calibration, Augmented Reality and Stereo Disparity Map

opevcvdl-hw2 This project uses openCV and Qt to achieve the requirements. Version Python 3.7 opencv-contrib-python 3.4.2.17 Matplotlib 3.1.1 pyqt5 5.1

Kenny Cheng 3 Aug 17, 2022
⏰ Shutdown Timer is an application that you can shutdown, restart, logoff, and hibernate your computer with a timer.

Shutdown Timer is a an application that you can shutdown, restart, logoff, and hibernate your computer with a timer. After choosing an action from the

Mehmet Güdük 5 Jun 27, 2022
Data derived from the OpenType specification

This package currently provides the opentypespec.tags module, which exports FEATURE_TAGS, SCRIPT_TAGS, LANGUAGE_TAGS and BASELINE_TAGS dictionaries, representing data from the Layout Tag Registry

Simon Cozens 4 Dec 01, 2022
Auto-ropper is a tool that aims to automate the exploitation of ROP.

Auto-ropper is a tool that aims to automate the exploitation of ROP. Its goal is to become a tool that no longer requires user interaction.

Zerotistic 16 Nov 13, 2022
Object-oriented programming (OOP) is a method of structuring a program by bundling related properties and behaviors into individual objects. In this tutorial, you’ll learn the basics of object-oriented programming in Python.

06_Python_Object_Class Introduction 👋 Objected oriented programming as a discipline has gained a universal following among developers. Python, an in-

Milaan Parmar / Милан пармар / _米兰 帕尔马 239 Dec 20, 2022
A carrot-based color palette you didn't know you needed.

A package to produce a carrot-inspired color palette for python/matplotlib. Install: pip install carrotColors Update: pip install --upgrade carrotColo

10 Sep 28, 2021
Odoo. Open Source Apps To Grow Your Business.

Odoo Odoo is a suite of web based open source business apps. The main Odoo Apps include an Open Source CRM, Website Builder, eCommerce, Warehouse Mana

Odoo 27.6k Jan 09, 2023
Data wrangling & common calculations for results from qMem measurement software

qMem Datawrangler This script processes output of qMem measurement software into an Origin ® compatible *.csv files and matplotlib graphs to quickly v

Julian 1 Nov 30, 2021
SpaCy3Urdu: run command to setup assets(dataset from UD)

Project setup run command to setup assets(dataset from UD) spacy project assets It uses project.yml file and download the data from UD GitHub reposito

Muhammad Irfan 1 Dec 14, 2021
calculadora financiera hecha en python

Calculadora financiera Calculadora de factores financieros basicos, puede calcular tanto factores como expresiones algebraicas en funcion de dichos fa

crudo 5 Nov 10, 2021
a wordle-solver written in python

Wordle Solver Overview This is yet another wordle solver. It is built with the word list of the official wordle website, but it should also work with

Shoubhit Dash 10 Sep 24, 2022
Tc-python - A Python script to receive message from a twitch chat

Twitch-Chat 📜 I did a script in Python to receive messages from a twitch chat.

miyucode 2 May 31, 2022
Gaia: a chrome extension that curates environmental news of a company

Gaia - Gaia: Your Environment News Curator Call for Code 2021 Gaia: a chrome extension that curates environmental news of a company Explore the docs »

4 Mar 19, 2022
Hoopoe - Get notified of important stuff, right away.

Hoopoe - Get notified of important stuff, right away. Report a Bug · Request a Feature . Ask a Question Table of Contents About Getting Started Prereq

Vahid Al 8 Nov 12, 2022