summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md47
-rw-r--r--components/storage.rb2
-rw-r--r--controllers/instance.rb49
-rw-r--r--controllers/interfaces/cli.rb34
-rw-r--r--controllers/session.rb17
-rw-r--r--docker-compose.example.yml1
-rw-r--r--ports/dsl/nano-bots.rb8
-rw-r--r--static/cartridges/default.yml14
8 files changed, 139 insertions, 33 deletions
diff --git a/README.md b/README.md
index 5d0bb3b..c129f81 100644
--- a/README.md
+++ b/README.md
@@ -13,6 +13,8 @@ https://user-images.githubusercontent.com/113217272/237840989-1e29a5cc-6644-48d0
- [Command Line](#command-line)
- [Library](#library)
- [Cartridges](#cartridges)
+- [Providers](#providers)
+- [Debugging](#debugging)
- [Development](#development)
- [Publish to RubyGems](#publish-to-rubygems)
@@ -41,11 +43,20 @@ export OPENAI_API_ADDRESS=https://api.openai.com
export OPENAI_API_ACCESS_TOKEN=your-token
export OPENAI_API_USER_IDENTIFIER=your-user
-export NANO_BOTS_STATE_DIRECTORY=/home/user/.local/state/nano-bots
-export NANO_BOTS_CARTRIDGES_DIRECTORY=/home/user/.local/share/nano-bots/cartridges
+# export NANO_BOTS_STATE_DIRECTORY=/home/user/.local/state/nano-bots
+# export NANO_BOTS_CARTRIDGES_DIRECTORY=/home/user/.local/share/nano-bots/cartridges
```
-Alternatively, if your current directory has a `.env` file with the environment variables, they will be automatically loaded.
+Alternatively, if your current directory has a `.env` file with the environment variables, they will be automatically loaded:
+
+```sh
+OPENAI_API_ADDRESS=https://api.openai.com
+OPENAI_API_ACCESS_TOKEN=your-token
+OPENAI_API_USER_IDENTIFIER=your-user
+
+# NANO_BOTS_STATE_DIRECTORY=/home/user/.local/state/nano-bots
+# NANO_BOTS_CARTRIDGES_DIRECTORY=/home/user/.local/share/nano-bots/cartridges
+```
## Docker
@@ -72,6 +83,7 @@ services:
OPENAI_API_USER_IDENTIFIER: your-user
volumes:
- ./your-cartridges:/cartridges
+ # - ./your-data:/data
```
Enter the container:
@@ -81,6 +93,10 @@ docker compose run nano-bots
Start playing:
```sh
+nb - - eval "hello"
+nb - - repl
+
+nb cartridges/assistant.yml - eval "hello"
nb cartridges/assistant.yml - repl
```
@@ -93,6 +109,9 @@ After installing the gem, the `nb` binary command will be available for your pro
Examples of usage:
```bash
+nb - - eval "hello"
+# => Hello! How may I assist you today?
+
nb to-en-us-translator.yml - eval "Salut, comment ça va?"
# => Hello, how are you doing?
@@ -115,6 +134,8 @@ cat article.txt |
```
```bash
+nb - - repl
+
nb assistant.yml - repl
```
@@ -145,6 +166,16 @@ require 'securerandom'
SecureRandom.hex # => 6ea6c43c42a1c076b1e3c36fa349ac2c
```
+### Debugging
+
+```sh
+nb - - cartridge
+nb cartridge.yml - cartridge
+
+nb - STATE-KEY state
+nb cartridge.yml STATE-KEY state
+```
+
### Library
To use it as a library:
@@ -198,6 +229,16 @@ provider:
Check the Nano Bots specification to learn more about [how to build cartridges](https://icebaker.github.io/nano-bots/#/README?id=cartridges).
+## Providers
+
+Currently supported providers:
+
+- [ ] [Vicuna](https://github.com/lm-sys/FastChat)
+- [x] [Open AI](https://platform.openai.com/docs/api-reference)
+- [ ] [Google PaLM](https://developers.generativeai.google/)
+- [ ] [Alpaca](https://github.com/tatsu-lab/stanford_alpaca)
+- [ ] [LLaMA](https://github.com/facebookresearch/llama)
+
## Development
```bash
diff --git a/components/storage.rb b/components/storage.rb
index 3d3f58d..d46455f 100644
--- a/components/storage.rb
+++ b/components/storage.rb
@@ -19,7 +19,7 @@ module NanoBot
path = "#{path.sub(%r{/$}, '')}/ruby-nano-bots/#{cartridge[:meta][:author].to_slug.normalize}"
path = "#{path}/#{cartridge[:meta][:name].to_slug.normalize}"
- path = "#{path}/#{cartridge[:meta][:version].to_s.gsub('.', '-').to_slug.normalize}/#{key.to_slug.normalize}"
+ path = "#{path}/#{cartridge[:meta][:version].to_s.gsub('.', '-').to_slug.normalize}/#{key}"
path = "#{path}/state.json"
FileUtils.mkdir_p(File.dirname(path))
diff --git a/controllers/instance.rb b/controllers/instance.rb
index f3cbd74..b22a785 100644
--- a/controllers/instance.rb
+++ b/controllers/instance.rb
@@ -12,35 +12,64 @@ require_relative './session'
module NanoBot
module Controllers
class Instance
- def initialize(cartridge_path:, state: nil)
+ def initialize(cartridge_path:, stream:, state: nil)
+ @stream = stream
+
load_cartridge!(cartridge_path)
provider = Components::Provider.new(@cartridge[:provider])
- @session = Session.new(provider:, cartridge: @cartridge, state:)
+ @session = Session.new(provider:, cartridge: @cartridge, state:, stream: @stream)
+ end
+
+ def cartridge
+ puts YAML.dump(@safe_cartridge)
end
- def debug
- @session.debug
+ def state
+ @session.state
end
def eval(input)
Interfaces::Eval.evaluate(input, @cartridge, @session)
+
+ return unless @stream.is_a?(StringIO)
+
+ @stream.flush
+ result = @stream.string.clone
+ @stream.truncate(0)
+ @stream.rewind
+ result
end
def repl
+ if @stream.is_a?(StringIO)
+ @stream.flush
+ @stream = $stdout
+ @session.stream = @stream
+ end
Interfaces::REPL.start(@cartridge, @session)
end
private
def load_cartridge!(path)
- @cartridge = Logic::Helpers::Hash.symbolize_keys(
- YAML.safe_load(
- File.read(Components::Storage.cartridge_path(path)),
- permitted_classes: [Symbol]
- )
- )
+ elected_path = if path.strip == '-'
+ File.expand_path('../static/cartridges/default.yml', __dir__)
+ else
+ Components::Storage.cartridge_path(path)
+ end
+
+ if elected_path.nil?
+ @stream.write("Cartridge file not found: \"#{path}\"\n")
+ raise StandardError, "Cartridge file not found: \"#{path}\""
+ end
+
+ @cartridge = YAML.safe_load(File.read(elected_path), permitted_classes: [Symbol])
+
+ @safe_cartridge = Marshal.load(Marshal.dump(@cartridge))
+
+ @cartridge = Logic::Helpers::Hash.symbolize_keys(@cartridge)
inject_environment_variables!(@cartridge)
end
diff --git a/controllers/interfaces/cli.rb b/controllers/interfaces/cli.rb
index 3574a80..2a93044 100644
--- a/controllers/interfaces/cli.rb
+++ b/controllers/interfaces/cli.rb
@@ -13,20 +13,38 @@ module NanoBot
puts NanoBot::GEM[:version]
exit
when 'help', '', nil
+ puts ''
puts "Nano Bots #{NanoBot::GEM[:version]}"
- puts ' nb cartridge.yml - eval "Hello"'
+ puts ''
+ puts ' nb - - eval "hello"'
+ puts ' nb - - repl'
+ puts ''
+ puts ' nb cartridge.yml - eval "hello"'
puts ' nb cartridge.yml - repl'
- puts ' nb cartridge.yml - debug'
- puts ' nb cartridge.yml STATE-KEY eval "Hello"'
+ puts ''
+ puts ' nb - STATE-KEY eval "hello"'
+ puts ' nb - STATE-KEY repl'
+ puts ''
+ puts ' nb cartridge.yml STATE-KEY eval "hello"'
puts ' nb cartridge.yml STATE-KEY repl'
- puts ' nb cartridge.yml STATE-KEY debug'
+ puts ''
+ puts ' nb - - cartridge'
+ puts ' nb cartridge.yml - cartridge'
+ puts ''
+ puts ' nb - STATE-KEY state'
+ puts ' nb cartridge.yml STATE-KEY state'
+ puts ''
puts ' nb version'
+ puts ' nb help'
+ puts ''
exit
end
params = { cartridge_path: ARGV[0], state: ARGV[1], command: ARGV[2] }
- bot = Instance.new(cartridge_path: params[:cartridge_path], state: params[:state])
+ bot = Instance.new(
+ cartridge_path: params[:cartridge_path], state: params[:state], stream: $stdout
+ )
case params[:command]
when 'eval'
@@ -35,8 +53,10 @@ module NanoBot
bot.eval(params[:input])
when 'repl'
bot.repl
- when 'debug'
- bot.debug
+ when 'state'
+ bot.state
+ when 'cartridge'
+ bot.cartridge
else
raise "TODO: [#{params[:command]}]"
end
diff --git a/controllers/session.rb b/controllers/session.rb
index ff3b8ad..afaca18 100644
--- a/controllers/session.rb
+++ b/controllers/session.rb
@@ -12,12 +12,13 @@ module NanoBot
STREAM_TIMEOUT_IN_SECONDS = 5
class Session
- def initialize(provider:, cartridge:, state: nil)
+ attr_accessor :stream
+
+ def initialize(provider:, cartridge:, state: nil, stream: $stdout)
+ @stream = stream
@provider = provider
@cartridge = cartridge
- @output = $stdout
-
@stateless = state.nil? || state.strip == '-' || state.strip.empty?
if @stateless
@@ -30,7 +31,7 @@ module NanoBot
end
end
- def debug
+ def state
pp({
state: {
path: @state_path,
@@ -67,7 +68,7 @@ module NanoBot
process(input, mode:)
end
- def stream(interface)
+ def streaming(interface)
provider = @provider.settings.key?(:stream) ? @provider.settings[:stream] : true
interface = interface.key?(:stream) ? interface[:stream] : true
@@ -77,7 +78,7 @@ module NanoBot
def process(input, mode:)
interface = Logic::Helpers::Hash.fetch(@cartridge, [:interfaces, mode.to_sym]) || {}
- streaming = stream(interface)
+ streaming = streaming(interface)
input[:interface] = interface
@@ -105,11 +106,11 @@ module NanoBot
end
def flush
- @output.flush
+ @stream.flush
end
def print(content)
- @output.write(content)
+ @stream.write(content)
end
end
end
diff --git a/docker-compose.example.yml b/docker-compose.example.yml
index 1ec49c1..f3af38f 100644
--- a/docker-compose.example.yml
+++ b/docker-compose.example.yml
@@ -10,3 +10,4 @@ services:
OPENAI_API_USER_IDENTIFIER: your-user
volumes:
- ./your-cartridges:/cartridges
+ # - ./your-data:/data
diff --git a/ports/dsl/nano-bots.rb b/ports/dsl/nano-bots.rb
index bce169c..40bed1d 100644
--- a/ports/dsl/nano-bots.rb
+++ b/ports/dsl/nano-bots.rb
@@ -7,16 +7,16 @@ require_relative '../../controllers/instance'
require_relative '../../controllers/interfaces/cli'
module NanoBot
- def self.new(cartridge:, state: '-')
- Controllers::Instance.new(cartridge_path: cartridge, state:)
+ def self.new(cartridge: '-', state: '-')
+ Controllers::Instance.new(cartridge_path: cartridge, state:, stream: StringIO.new)
end
def self.cli
Controllers::Interfaces::CLI.handle!
end
- def self.repl(cartridge:, state: '-')
- Controllers::Instance.new(cartridge_path: cartridge, state:).repl
+ def self.repl(cartridge: '-', state: '-')
+ Controllers::Instance.new(cartridge_path: cartridge, state:, stream: $stdout).repl
end
def self.version
diff --git a/static/cartridges/default.yml b/static/cartridges/default.yml
new file mode 100644
index 0000000..b5eed62
--- /dev/null
+++ b/static/cartridges/default.yml
@@ -0,0 +1,14 @@
+---
+meta:
+ name: Unknown
+ author: Nobody
+ version: 0.0.0
+
+provider:
+ name: openai
+ settings:
+ model: gpt-3.5-turbo
+ credentials:
+ address: ENV/OPENAI_API_ADDRESS
+ access-token: ENV/OPENAI_API_ACCESS_TOKEN
+ user-identifier: ENV/OPENAI_API_USER_IDENTIFIER