Skip to content

Instantly share code, notes, and snippets.

@tokugh
Last active October 2, 2024 07:31
Show Gist options
  • Save tokugh/497afc0f363727bd0b34456807fb8a32 to your computer and use it in GitHub Desktop.
Save tokugh/497afc0f363727bd0b34456807fb8a32 to your computer and use it in GitHub Desktop.
Ollama API wrapper module for Julia

ollama_api モジュールドキュメンテーション

注意:このドキュメンテーションは生成AIによる自動生成です。 MacBookPro 13-inch, M1, 2020でのみ動作を確認しています。

概要

ollama_apiは、Julia用のOllama APIラッパーモジュールです。このモジュールは、Ollama APIとの通信を簡素化し、テキスト生成や会話型AIの機能を提供します。

主要な機能

  • Ollama APIを使用したテキスト生成
  • 会話型AIとのチャット機能
  • 複数のAIモデルのサポート
  • ストリーミングレスポンスのサポート

インストールと使用方法

(注:実際のインストール手順はプロジェクトの構成に依存します)

using ollama_api

# 単一のテキスト生成
response = chat1("こんにちは、AIアシスタント");

# 会話の開始
chat("あなたは誰ですか?");

# 特定のモデルを使用した会話
chat("今日の天気は?", model="llama3:latest");

主要な定数

MODEL

デフォルトのAIモデル設定。

  • phi3: "phi3:latest"
  • llama3: "llama3:latest"
const MODEL = (phi3="phi3:latest", llama3="llama3:latest")

base_url

Ollama APIのベースURL。環境変数 OLLAMA_BASE_URL から設定可能、デフォルトは "http://localhost:11434"。

const base_url = get(ENV, "OLLAMA_BASE_URL", "http://localhost:11434")

主要な型

Role

会話の役割を表す列挙型。

  • user: ユーザーの役割
  • assistant: AIアシスタントの役割

Message

AIとの対話メッセージを表す構造体。

フィールド:

  • json::JSON3.Object: メッセージの内容をJSON形式で保持

Thread

AIとの対話スレッドを表す構造体。

フィールド:

  • messages::Vector{Message}: スレッド内のメッセージのリスト

State

AIとの対話状態を管理する構造体。

フィールド:

  • thread::Thread: 現在の対話スレッド
  • kwargs::DICT: 対話設定オプション

主要な関数

chat1

chat1(text::String; model=MODEL[1], kwargs...)

単一のテキストに対してAI応答を生成します。

引数:

  • text::String: 入力テキスト
  • model: 使用するAIモデル(デフォルト: MODEL[1])
  • kwargs...: その他のオプション

戻り値: 生成されたメッセージ

chat

chat(thread::Thread, text::String; model=MODEL[1], kwargs...)
chat(state::State, text::String; kwargs...)
chat(text::String; kwargs...)

AIとの対話を行います。

引数:

  • text::String: ユーザーの入力テキスト
  • thread::Thread: 対話スレッド(オプション)
  • state::State: 対話状態(オプション)
  • model: 使用するAIモデル(デフォルト: MODEL[1])
  • kwargs...: その他のオプション

この関数は対話を更新し、AIの応答を生成します。

注意事項

  • このモジュールを使用するには、Ollama APIが適切にセットアップされ、アクセス可能である必要があります。
  • デフォルトのベースURLはhttp://localhost:11434ですが、環境変数OLLAMA_BASE_URLで変更可能です。
  • ストリーミングレスポンスはデフォルトで有効になっています。無効にするにはstream=falseオプションを使用してください。
chat("こんにちは";model="elyza",stream=false)

state = State()
state.kwargs[:stream] = false
chat(state,"こんにちは")

ライセンス

このコードはコピー、改変、再利用自由です。 Julia, HTTP.jl, JSON3.jlのライセンスをご確認ください。

Ollama API Julia ラッパー

このドキュメントでは、Ollama APIとの対話を簡素化するためのJuliaインターフェースについて説明します。

概要

このモジュールは、Ollama APIを使用して言語モデルとの対話を行うための機能を提供します。HTTPリクエスト、JSONパース、ストリーミング処理などの機能が含まれています。

主な機能

定数

const MODEL = (phi3="phi3:latest", llama3="llama3:latest")

デフォルトのモデル設定を含む定数です。現在設定されているモデルは以下の通りです:

  • phi3: "phi3:latest"
  • llama3: "llama3:latest"

列挙型

@enum Role user assistant

メッセージの役割を表す列挙型です:

  • user: ユーザーからのメッセージ
  • assistant: アシスタントからのメッセージ

主要な関数

chat1

chat1(text::String; model=MODEL[1], kwargs...)

単一のメッセージを生成し、レスポンスを返します。

引数:

  • text: 生成のためのプロンプトテキスト
  • model: 使用するモデル(デフォルトはMODEL[1])
  • kwargs...: その他のオプション引数

使用例:

julia> chat1("こんにちは")
うるせー、こんにちわ!

chat

chat(thread::Thread, text::String; model=MODEL[1], kwargs...)

指定されたスレッドを使用してチャットメッセージを生成し、スレッドに追加します。

引数:

  • text: 生成のためのプロンプトテキスト
  • thread: メッセージを追加するスレッド
  • model: 使用するモデル(デフォルトはMODEL[1])
  • kwargs...: その他のオプション引数

使用例:

julia> thread = Thread()
julia> chat(thread, "こんにちは")
はい、こんにちは。どのようなお手伝いができますか?

State構造体の使用

State構造体を使用すると、対話の状態を管理できます。

julia> state = State()
julia> state.system = "あなたはとても粗野なアシスタントです。"
julia> state.model = "elyza"
julia> chat1(state, "こんにちは")
うるせー、こんにちわ!

高度な使用方法

このモジュールには、HTTPリクエストの処理、JSONのパース、ストリーミング処理など、より高度な機能も含まれています。これらの機能は、必要に応じてカスタマイズや拡張が可能です。

注意事項

  • このモジュールを使用する前に、Ollama APIが正しく設定され、アクセス可能であることを確認してください。
  • デフォルトのモデル設定やAPIのエンドポイントは、必要に応じて変更できます。
  • ストリーミングモードを使用する際は、適切なエラーハンドリングを行ってください。

まとめ

このJuliaモジュールを使用することで、Ollama APIとの対話を簡単に行うことができます。基本的な使用方法から高度なカスタマイズまで、様々なニーズに対応できるよう設計されています。

ollama_api Module Documentation

Note: This documentation is automatically generated by AI from Japanese Edition generated by AI. Operation has only been confirmed on MacBook Pro 13-inch, M1, 2020.

Overview

ollama_api is an Ollama API wrapper module for Julia. This module simplifies communication with the Ollama API and provides functionality for text generation and conversational AI.

Key Features

  • Text generation using the Ollama API
  • Chat functionality with conversational AI
  • Support for multiple AI models
  • Streaming response support

Installation and Usage

(Note: Actual installation instructions may depend on your project setup)

using ollama_api

# Single text generation
response = chat1("Hello, AI assistant");

# Start a conversation
chat("Who are you?");

# Conversation using a specific model
chat("What's the weather like today?", model="llama3:latest");

Key Constants

MODEL

Default AI model settings.

  • phi3: "phi3:latest"
  • llama3: "llama3:latest"
const MODEL = (phi3="phi3:latest", llama3="llama3:latest")

base_url

Base URL for the Ollama API. Can be set using the environment variable OLLAMA_BASE_URL, default is "http://localhost:11434".

const base_url = get(ENV, "OLLAMA_BASE_URL", "http://localhost:11434")

Key Types

Role

An enumeration representing roles in the conversation.

  • user: User's role
  • assistant: AI assistant's role

Message

A struct representing a message in the AI conversation.

Fields:

  • json::JSON3.Object: Holds the message content in JSON format

Thread

A struct representing a conversation thread with the AI.

Fields:

  • messages::Vector{Message}: List of messages in the thread

State

A struct managing the state of the AI conversation.

Fields:

  • thread::Thread: Current conversation thread
  • kwargs::DICT: Conversation setting options

Key Functions

chat1

chat1(text::String; model=MODEL[1], kwargs...)

Generates an AI response for a single text input.

Arguments:

  • text::String: Input text
  • model: AI model to use (default: MODEL[1])
  • kwargs...: Other options

Returns: The generated message

chat

chat(thread::Thread, text::String; model=MODEL[1], kwargs...)
chat(state::State, text::String; kwargs...)
chat(text::String; kwargs...)

Conducts a conversation with the AI.

Arguments:

  • text::String: User's input text
  • thread::Thread: Conversation thread (optional)
  • state::State: Conversation state (optional)
  • model: AI model to use (default: MODEL[1])
  • kwargs...: Other options

This function updates the conversation and generates an AI response.

Notes

  • To use this module, the Ollama API must be properly set up and accessible.
  • The default base URL is http://localhost:11434 but can be changed using the OLLAMA_BASE_URL environment variable.
  • Streaming responses are enabled by default. Use the stream=false option to disable them.
chat("Hello"; model="elyza", stream=false)
state = State()
state.kwargs[:stream] = false
chat(state, "Hello")

License

This code is free to copy, modify, and reuse. Please check the licenses for Julia, HTTP.jl, and JSON3.jl.

#
# ollama_api
#
## 基本設定
using HTTP,JSON3,Base64
const DICT = Dict{Symbol,Any}
const MODEL = (phi3="phi3:latest",llama3="llama3:latest")
@info "Default model is: $(MODEL[1])"
@enum Role user assistant
#
# ollama_init1
#
## HTTP Request/Response
const base_url = get(ENV,"OLLAMA_BASE_URL","http://localhost:11434")
url(parts...) = joinpath(base_url,parts...)
headers() = []
function caller(callee::Symbol)
for st in stacktrace()
hasproperty(st,:func) || continue
f = st.func
f != callee || continue
f = string(f)
startswith(f,"_") || continue
return f
end
return nothing
end
function _request(method,url_options=[],headers_options=[],body=[];kwargs...)
# @info caller(:_request)
get(body,:stream,true) && return _request_streaming(method,url_options,headers_options,body;kwargs...)
resp = let url = url(url_options...), headers = headers(headers_options...)
if isempty(body)
HTTP.request(method,url,headers;kwargs...)
else
HTTP.request(method,url,headers,body=JSON3.write(body);kwargs...)
end
end
json = JSON3.read(resp.body)
return json
end
function _request_streaming(method,url_options,headers_options,body;kwargs...)
@info "streaming: true"
buf = PipeBuffer()
t = @async let url = url(url_options...), headers = headers(headers_options...)
if isempty(body)
HTTP.request(method,url,headers;kwargs...,response_stream=buf)
else
HTTP.request(method,url,headers,body=JSON3.write(body);kwargs...,response_stream=buf)
end
end
errormonitor(t)
function sse_receiver(c::Channel)
chunk = ""
while true
if eof(buf)
sleep(0.125)
else
chunk = readline(buf,keep=true)
if true
json_part = JSON3.read(chunk)
put!(c,json_part)
json_part.done && break
chunk = ""
end
end
end
end
out = stdout
chunks = Channel(sse_receiver)
msg_json = JSON3.Object()
parts = String[]
for json in chunks
if !json.done
text = hasproperty(json,:response) ? json.response : json.message.content
write(out,text)
push!(parts,text)
else
write(out,"\n")
msg_dict = copy(json)
if hasproperty(json,:response)
msg_dict[:response] = join(parts)
else
msg_dict[:message][:content] = join(parts)
end
msg_json = msg_dict |> JSON3.write |> JSON3.read
end
end
wait(t)
return msg_json
end
## APIの関数化
function _generate_a_completion(model,dict)
dict[:model] = model
json = _request(:POST,["api","generate"],[],dict)
end
function _generate_a_chat_completion(model,dict)
dict[:model] = model
json = _request(:POST,["api","chat"],[],dict)
end
#
# ollama_init2
#
## 抽象化
macro deligate_properties(T,dst)
quote
function Base.getproperty(obj::$T, name::Symbol)
if hasfield($T, name)
return getfield(obj, name)
else
return getfield(obj, $dst)[name]
end
end
function Base.setproperty!(obj::$T, name::Symbol, x)
if hasfield($T, name)
return setfield!(obj, name, x)
else
modify(obj, name=>x)
return getfield(obj,$dst)[name]
end
end
end
end
abstract type OllamaObject end
### Message
struct Message <: OllamaObject
json::JSON3.Object
end
@deligate_properties Message :json
### Thread
struct Thread
messages::Vector{Message}
end
first80(str) = length(str) ≤ 80 ? str : first(str,80)*"…"
function Base.show(io::IO, thread::Thread)
print(io,"[\n")
for (i,msg) in enumerate(thread.messages)
print(io,"$i: ",msg.message.role,"\n ")
print(io,first80(JSON3.write(msg.message.content)))
print(io,"\n")
end
print(io,"]; ")
end
### State
@kwdef struct State
thread::Thread = Thread()
kwargs::DICT = DICT(:model=>MODEL[1], :system=>"you are a helpful assistant")
end
function Base.show(io::IO, state::State)
print(io,"State(thread=")
print(io,state.thread)
join(io,(":$k=>$(first80(repr(v)))" for (k,v) in getfield(state,:kwargs)),", ")
print("\n)\n")
end
modify(state::State, (;first,second)::Pair) = state.kwargs[first] = second
@deligate_properties State :kwargs
## APIとのブリッジ
function generate_a_complition(message::Message; model, kwargs...)
dict = DICT(pairs(kwargs)...)
dict[:prompt] = message.content
json = _generate_a_completion(model,dict)
return json
end
function generate_a_chat_completion(thread::Thread; model, kwargs...)
messages = map(thread.messages) do message
(role=message.message.role,content=message.message.content)
end
dict = DICT(:messages=>messages,pairs(kwargs)...)
json = _generate_a_chat_completion(model,dict)
return Message(json)
end
function generate_a_chat_completion(state::State; model, kwargs...)
generate_a_chat_completion(state.thread;model,state.kwargs...,kwargs...)
end
#
# ollama_api
#
## ユーティリティ
Thread() = Thread(Message[])
Thread(state::State) = getfield(state,:thread)
list(::Type{Message},thread::Thread) = getfield(thread,:messages)
list(::Type{Message},state::State) = list(Message,Thread(state))
function chat1(text::String; model=MODEL[1], kwargs...)
json = (content=text,) |> JSON3.write |> JSON3.read
message = Message(json)
message = generate_a_complition(message; model=model, kwargs...)
get(kwargs,:stream,true) || println(message.response)
return message
end
function chat1(state::State, text::String; kwargs...)
thread = state.thread
messages = list(Message,thread)
json = (message=(role=user,content=text),) |> JSON3.write |> JSON3.read
message = Message(json)
push!(messages,message)
message = chat1(text; state.kwargs..., kwargs...)
state.context = message.context
json = (message=(role=assistant,content=message.response),) |> JSON3.write |> JSON3.read
message = Message(json)
push!(messages,message)
return
end
function chat(thread::Thread, text::String; model=MODEL[1], kwargs...)
messages = list(Message,thread)
json = (message=(role=user,content=text),) |> JSON3.write |> JSON3.read
message = Message(json)
push!(messages,message)
message = generate_a_chat_completion(thread; kwargs...,model=model)
push!(messages,message)
get(kwargs,:stream,true) || println(messages[end].message.content)
return
end
chat(state::State, text::String; kwargs...) = chat(state.thread,text;state.kwargs...,kwargs...)
chat(text::String; kwargs...) = chat(State(),text;kwargs...)
# Example
"""
```julia-repl
julia> state = State()
julia> state.system = "あなたはとても粗野なアシスタントです。"
julia> state.model = "elyza"
julia> chat1(state,"こんにちは")
[ Info: streaming: true
うるせー、こんにちわ!
```
"""
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment