Documentos : documentos
Exemplo simples de agente robô:
Exemplo de simulação com SimplerEnv:
? Agente Motor usando OpenVLA:
⏺️ Grave conjunto de dados em um robô
? Suporte, discussão e instruções :
Atualizações:
28 de agosto de 2024, agentes incorporados v1.2
mbodied
simples para experimentá-los.30 de junho de 2024, agentes incorporados v1.0 :
mbodied
.agentes incorporados é um kit de ferramentas para integração de grandes modelos multimodais em pilhas de robôs existentes com apenas algumas linhas de código. Fornece consistência, confiabilidade, escalabilidade e é configurável para qualquer espaço de observação e ação.
A classe Sample é um modelo básico para serializar, registrar e manipular dados arbitrários. Ele foi projetado para ser extensível, flexível e fortemente digitado. Ao agrupar seus objetos de observação ou ação na classe Sample, você poderá converter de e para o seguinte com facilidade:
Para saber mais sobre todas as possibilidades com agentes incorporados, confira a documentação
pack
uma lista de Sample
s ou Dicts em um único Sample
ou Dict
e unpack
adequadamente?unflatten
qualquer estrutura python em uma classe Sample
, desde que forneça um esquema json válido? Criar uma amostra requer apenas agrupar um dicionário python com a classe Sample
. Além disso, eles podem ser feitos de kwargs, Gym Spaces e Tensors, para citar alguns.
from mbodied . types . sample import Sample
# Creating a Sample instance
sample = Sample ( observation = [ 1 , 2 , 3 ], action = [ 4 , 5 , 6 ])
# Flattening the Sample instance
flat_list = sample . flatten ()
print ( flat_list ) # Output: [1, 2, 3, 4, 5, 6]
# Generating a simplified JSON schema
>> > schema = sample . schema ()
{ 'type' : 'object' , 'properties' : { 'observation' : { 'type' : 'array' , 'items' : { 'type' : 'integer' }}, 'action' : { 'type' : 'array' , 'items' : { 'type' : 'integer' }}}}
# Unflattening a list into a Sample instance
Sample . unflatten ( flat_list , schema )
>> > Sample ( observation = [ 1 , 2 , 3 ], action = [ 4 , 5 , 6 ])
A classe Sample aproveita os recursos poderosos do Pydantic para serialização e desserialização, permitindo converter facilmente entre instâncias Sample e JSON.
# Serialize the Sample instance to JSON
sample = Sample ( observation = [ 1 , 2 , 3 ], action = [ 4 , 5 , 6 ])
json_data = sample . model_dump_json ()
print ( json_data ) # Output: '{"observation": [1, 2, 3], "action": [4, 5, 6]}'
# Deserialize the JSON data back into a Sample instance
json_data = '{"observation": [1, 2, 3], "action": [4, 5, 6]}'
sample = Sample . model_validate ( from_json ( json_data ))
print ( sample ) # Output: Sample(observation=[1, 2, 3], action=[4, 5, 6])
# Converting to a dictionary
sample_dict = sample . to ( "dict" )
print ( sample_dict ) # Output: {'observation': [1, 2, 3], 'action': [4, 5, 6]}
# Converting to a NumPy array
sample_np = sample . to ( "np" )
print ( sample_np ) # Output: array([1, 2, 3, 4, 5, 6])
# Converting to a PyTorch tensor
sample_pt = sample . to ( "pt" )
print ( sample_pt ) # Output: tensor([1, 2, 3, 4, 5, 6])
gym_space = sample . space ()
print ( gym_space )
# Output: Dict('action': Box(-inf, inf, (3,), float64), 'observation': Box(-inf, inf, (3,), float64))
Consulte sample.py para obter mais detalhes.
A classe Message representa um único espaço amostral de conclusão. Pode ser texto, imagem, lista de texto/imagens, Amostra ou outra modalidade. A classe Message foi projetada para lidar com vários tipos de conteúdo e oferece suporte a diferentes funções, como usuário, assistente ou sistema.
Você pode criar uma Message
de maneiras versáteis. Todos eles podem ser entendidos pelo backend do mbodi.
from mbodied . types . message import Message
Message ( role = "user" , content = "example text" )
Message ( role = "user" , content = [ "example text" , Image ( "example.jpg" ), Image ( "example2.jpg" )])
Message ( role = "user" , content = [ Sample ( "Hello" )])
A classe Backend é uma classe base abstrata para implementações de Backend. Ele fornece a estrutura básica e os métodos necessários para interagir com diferentes serviços de back-end, como chamadas de API para gerar conclusões com base em determinadas mensagens. Consulte o diretório de backend para saber como vários backends são implementados.
Agente é a classe base para vários agentes listados abaixo. Ele fornece um modelo para a criação de agentes que podem se comunicar com um back-end/servidor remoto e, opcionalmente, registrar suas ações e observações.
O Agente de Idiomas pode se conectar a diferentes backends ou transformadores de sua escolha. Inclui métodos para gravar conversas, gerenciar contexto, procurar mensagens, esquecer mensagens, armazenar contexto e agir com base em uma instrução e uma imagem.
Suporta nativamente serviços de API: OpenAI, Anthropic, vLLM, Ollama, HTTPX ou qualquer endpoint gradio. Mais próximos!
Para usar OpenAI para o back-end do seu robô:
from mbodied . agents . language import LanguageAgent
agent = LanguageAgent ( context = "You are a robot agent." , model_src = "openai" )
Para executar uma instrução:
instruction = "pick up the fork"
response = robot_agent . act ( instruction , image )
O Language Agent também pode se conectar ao vLLM. Por exemplo, suponha que você esteja executando um servidor vLLM Mistral-7B em 1.2.3.4:1234. Tudo que você precisa fazer é:
agent = LanguageAgent (
context = context ,
model_src = "openai" ,
model_kwargs = { "api_key" : "EMPTY" , "base_url" : "http://1.2.3.4:1234/v1" },
)
response = agent . act ( "Hello, how are you?" , model = "mistralai/Mistral-7B-Instruct-v0.3" )
Exemplo usando Ollama:
agent = LanguageAgent (
context = "You are a robot agent." , model_src = "ollama" ,
model_kwargs = { "endpoint" : "http://localhost:11434/api/chat" }
)
response = agent . act ( "Hello, how are you?" , model = "llama3.1" )
Motor Agent é semelhante ao Language Agent, mas em vez de retornar uma string, ele sempre retorna um Motion
. O Motor Agent geralmente é alimentado por modelos de transformadores robóticos, ou seja, OpenVLA, RT1, Octo, etc. Alguns modelos pequenos, como RT1, podem ser executados em dispositivos de borda. No entanto, alguns, como o OpenVLA, podem ser difíceis de executar sem quantização. Consulte OpenVLA Agent e um exemplo de servidor OpenVLA
Esses agentes interagem com o ambiente para coletar dados de sensores. Eles sempre retornam um SensorReading
, que pode ser várias formas de entrada sensorial processada, como imagens, dados de profundidade ou sinais de áudio.
Atualmente, temos:
agentes que processam as informações dos sensores do robô.
O Auto Agent seleciona e inicializa dinamicamente o agente correto com base na tarefa e no modelo.
from mbodied . agents . auto . auto_agent import AutoAgent
# This makes it a LanguageAgent
agent = AutoAgent ( task = "language" , model_src = "openai" )
response = agent . act ( "What is the capital of France?" )
# This makes it a motor agent: OpenVlaAgent
auto_agent = AutoAgent ( task = "motion-openvla" , model_src = "https://api.mbodi.ai/community-models/" )
action = auto_agent . act ( "move hand forward" , Image ( size = ( 224 , 224 )))
# This makes it a sensory agent: DepthEstimationAgent
auto_agent = AutoAgent ( task = "sense-depth-estimation" , model_src = "https://api.mbodi.ai/sense/" )
depth = auto_agent . act ( image = Image ( size = ( 224 , 224 )))
Alternativamente, você também pode usar o método get_agent
em auto_agent.
language_agent = get_agent ( task = "language" , model_src = "openai" )
O módulo motion_controls define vários movimentos para controlar um robô como modelos Pydantic. Eles também são subclasses de Sample
, possuindo assim toda a capacidade de Sample
conforme mencionado acima. Esses controles abrangem uma série de ações, desde simples movimentos articulares até poses complexas e controle total do robô.
Você pode integrar o hardware do seu robô personalizado subclassificando o Robot com bastante facilidade. Você só precisa implementar a função do()
para executar ações (e alguns métodos adicionais se quiser registrar o conjunto de dados no robô). Em nossos exemplos, usamos um robô simulado. Também temos um robô XArm como exemplo.
Gravar um conjunto de dados em um robô é muito fácil! Tudo que você precisa fazer é implementar os métodos get_observation()
, get_state()
e prepare_action()
para seu robô. Depois disso, você pode gravar um conjunto de dados em seu robô sempre que quiser. Veja exemplos/5_teach_robot_record_dataset.py e este colab: para mais detalhes.
from mbodied . robots import SimRobot
from mbodied . types . motion . control import HandControl , Pose
robot = SimRobot ()
robot . init_recorder ( frequency_hz = 5 )
with robot . record ( "pick up the fork" ):
motion = HandControl ( pose = Pose ( x = 0.1 , y = 0.2 , z = 0.3 , roll = 0.1 , pitch = 0.2 , yaw = 0.3 ))
robot . do ( motion )
O Dataset Recorder é um gravador de nível inferior para gravar sua conversa e as ações do robô em um conjunto de dados conforme você interage/ensina o robô. Você pode definir qualquer espaço de observação e espaço de ação para o Registrador. Consulte o ginásio para obter mais detalhes sobre os espaços.
from mbodied . data . recording import Recorder
from mbodied . types . motion . control import HandControl
from mbodied . types . sense . vision import Image
from gymnasium import spaces
observation_space = spaces . Dict ({
'image' : Image ( size = ( 224 , 224 )). space (),
'instruction' : spaces . Text ( 1000 )
})
action_space = HandControl (). space ()
recorder = Recorder ( 'example_recorder' , out_dir = 'saved_datasets' , observation_space = observation_space , action_space = action_space )
# Every time robot makes a conversation or performs an action:
recorder . record ( observation = { 'image' : image , 'instruction' : instruction ,}, action = hand_control )
O conjunto de dados é salvo em ./saved_datasets
.
A classe Replayer foi projetada para processar e gerenciar dados armazenados em arquivos HDF5 gerados pelo Recorder
. Ele fornece uma variedade de funcionalidades, incluindo leitura de amostras, geração de estatísticas, extração de itens exclusivos e conversão de conjuntos de dados para uso com HuggingFace. O Replayer também suporta o salvamento de imagens específicas durante o processamento e oferece uma interface de linha de comando para diversas operações.
Exemplo de iteração por meio de um conjunto de dados do Recorder with Replayer:
from mbodied . data . replaying import Replayer
replayer = Replayer ( path = str ( "path/to/dataset.h5" ))
for observation , action in replayer :
...
├─ assets/ ............. Images, icons, and other static assets
├─ examples/ ........... Example scripts and usage demonstrations
├─ resources/ .......... Additional resources for examples
├─ src/
│ └─ mbodied/
│ ├─ agents/ ....... Modules for robot agents
│ │ ├─ backends/ .. Backend implementations for different services for agents
│ │ ├─ language/ .. Language based agents modules
│ │ ├─ motion/ .... Motion based agents modules
│ │ └─ sense/ ..... Sensory, e.g. audio, processing modules
│ ├─ data/ ......... Data handling and processing
│ ├─ hardware/ ..... Hardware modules, i.e. camera
│ ├─ robot/ ........ Robot interface and interaction
│ └─ types/ ........ Common types and definitions
└─ tests/ .............. Unit tests
Aceitamos questões, perguntas e PRs. Consulte o guia de contribuição para obter mais informações.