-
Notifications
You must be signed in to change notification settings - Fork 22
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: adds reactive implementation for all APIs (#5)
- Loading branch information
1 parent
080f0f4
commit b4d1fc5
Showing
11 changed files
with
413 additions
and
217 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
# ``OllamaKit`` | ||
|
||
A Swift library for interacting with the Ollama API. | ||
|
||
## Overview | ||
|
||
``OllamaKit`` is a Swift-based library crafted to streamline interactions with the Ollama API. It encapsulates the complexities of network communication and data processing, providing a simplified and efficient interface for Swift applications to communicate with the Ollama API. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
// | ||
// OllamaKit+Chat.swift | ||
// | ||
// | ||
// Created by Kevin Hermawan on 02/01/24. | ||
// | ||
|
||
import Alamofire | ||
import Combine | ||
import Foundation | ||
|
||
extension OllamaKit { | ||
/// Establishes a Combine publisher for streaming chat responses from the Ollama API, based on the provided data. | ||
/// | ||
/// This method sets up a streaming connection using the Combine framework, facilitating real-time data handling as chat responses are generated by the Ollama API. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let chatData = OKChatRequestData(/* parameters */) | ||
/// | ||
/// ollamaKit.chat(data: chatData) | ||
/// .sink(receiveCompletion: { completion in | ||
/// // Handle completion or error | ||
/// }, receiveValue: { chatResponse in | ||
/// // Handle each chat response | ||
/// }) | ||
/// .store(in: &cancellables) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKChatRequestData`` used to initiate the chat streaming from the Ollama API. | ||
/// - Returns: An `AnyPublisher<OKChatResponse, AFError>` emitting the live stream of chat responses from the Ollama API. | ||
public func chat(data: OKChatRequestData) -> AnyPublisher<OKChatResponse, AFError> { | ||
return Future<OKChatResponse, AFError> { promise in | ||
let request = AF.streamRequest(router.chat(data: data)).validate() | ||
|
||
request.responseStreamDecodable(of: OKChatResponse.self, using: decoder) { stream in | ||
switch stream.event { | ||
case .stream(let result): | ||
switch result { | ||
case .success(let response): | ||
promise(.success(response)) | ||
case .failure(let error): | ||
promise(.failure(error)) | ||
} | ||
case .complete(_): | ||
break | ||
} | ||
} | ||
}.eraseToAnyPublisher() | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
// | ||
// OllamaKit+CopyModel.swift | ||
// | ||
// | ||
// Created by Kevin Hermawan on 01/01/24. | ||
// | ||
|
||
import Alamofire | ||
import Combine | ||
import Foundation | ||
|
||
extension OllamaKit { | ||
/// Asynchronously requests the Ollama API to copy a model. | ||
/// | ||
/// This method sends a request to the Ollama API to copy a model based on the provided ``OKCopyModelRequestData``. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let requestData = OKCopyModelRequestData(/* parameters */) | ||
/// try await ollamaKit.copyModel(data: requestData) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKCopyModelRequestData`` containing the details needed to copy the model. | ||
/// - Throws: An error if the request to copy the model fails. | ||
public func copyModel(data: OKCopyModelRequestData) async throws -> Void { | ||
let request = AF.request(router.copyModel(data: data)).validate() | ||
_ = try await request.serializingData().response.result.get() | ||
} | ||
|
||
/// Requests the Ollama API to copy a model, returning the result as a Combine publisher. | ||
/// | ||
/// This method provides a reactive approach to request a model copy operation. It accepts ``OKCopyModelRequestData`` and returns a Combine publisher that completes when the copy operation is finished. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let requestData = OKCopyModelRequestData(/* parameters */) | ||
/// | ||
/// ollamaKit.copyModel(data: requestData) | ||
/// .sink(receiveCompletion: { completion in | ||
/// // Handle completion | ||
/// }, receiveValue: { | ||
/// // Handle successful completion of the copy operation | ||
/// }) | ||
/// .store(in: &cancellables) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKCopyModelRequestData`` used to request the model copy. | ||
/// - Returns: A `AnyPublisher<Void, Error>` that completes when the copy operation is done. | ||
public func copyModel(data: OKCopyModelRequestData) -> AnyPublisher<Void, Error> { | ||
let request = AF.request(router.copyModel(data: data)).validate() | ||
|
||
return request.publishData() | ||
.tryMap { _ in Void() } | ||
.eraseToAnyPublisher() | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
// | ||
// OllamaKit+DeleteModel.swift | ||
// | ||
// | ||
// Created by Kevin Hermawan on 01/01/24. | ||
// | ||
|
||
import Alamofire | ||
import Combine | ||
import Foundation | ||
|
||
extension OllamaKit { | ||
/// Asynchronously requests the Ollama API to delete a specific model. | ||
/// | ||
/// This method sends a request to the Ollama API to delete a model based on the provided ``OKDeleteModelRequestData``. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let requestData = OKDeleteModelRequestData(/* parameters */) | ||
/// try await ollamaKit.deleteModel(data: requestData) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKDeleteModelRequestData`` containing the details needed to delete the model. | ||
/// - Throws: An error if the request to delete the model fails. | ||
public func deleteModel(data: OKDeleteModelRequestData) async throws -> Void { | ||
let request = AF.request(router.deleteModel(data: data)).validate() | ||
_ = try await request.serializingData().response.result.get() | ||
} | ||
|
||
/// Requests the Ollama API to delete a specific model, returning the result as a Combine publisher. | ||
/// | ||
/// This method provides a reactive approach to request a model deletion operation. It accepts ``OKDeleteModelRequestData`` and returns a Combine publisher that completes when the deletion operation is finished. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let requestData = OKDeleteModelRequestData(/* parameters */) | ||
/// | ||
/// ollamaKit.deleteModel(data: requestData) | ||
/// .sink(receiveCompletion: { completion in | ||
/// // Handle completion | ||
/// }, receiveValue: { | ||
/// // Handle successful completion of the deletion operation | ||
/// }) | ||
/// .store(in: &cancellables) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKDeleteModelRequestData`` used to request the model deletion. | ||
/// - Returns: A `AnyPublisher<Void, Error>` that completes when the deletion operation is done. | ||
public func deleteModel(data: OKDeleteModelRequestData) -> AnyPublisher<Void, Error> { | ||
let request = AF.request(router.deleteModel(data: data)).validate() | ||
|
||
return request.publishData() | ||
.tryMap { _ in Void() } | ||
.eraseToAnyPublisher() | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
// | ||
// OllamaKit+Generate.swift | ||
// | ||
// | ||
// Created by Kevin Hermawan on 02/01/24. | ||
// | ||
|
||
import Alamofire | ||
import Combine | ||
import Foundation | ||
|
||
extension OllamaKit { | ||
/// Establishes a Combine publisher for streaming responses from the Ollama API, based on the provided data. | ||
/// | ||
/// This method sets up a streaming connection using the Combine framework, allowing for real-time data handling as the responses are generated by the Ollama API. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let requestData = OKGenerateRequestData(/* parameters */) | ||
/// | ||
/// ollamaKit.generate(data: requestData) | ||
/// .sink(receiveCompletion: { completion in | ||
/// // Handle completion or error | ||
/// }, receiveValue: { generateResponse in | ||
/// // Handle each generated response | ||
/// }) | ||
/// .store(in: &cancellables) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKGenerateRequestData`` used to initiate the streaming from the Ollama API. | ||
/// - Returns: An `AnyPublisher<OKGenerateResponse, AFError>` emitting the live stream of responses from the Ollama API. | ||
public func generate(data: OKGenerateRequestData) -> AnyPublisher<OKGenerateResponse, AFError> { | ||
return Future<OKGenerateResponse, AFError> { promise in | ||
let request = AF.streamRequest(router.generate(data: data)).validate() | ||
|
||
request.responseStreamDecodable(of: OKGenerateResponse.self, using: decoder) { stream in | ||
switch stream.event { | ||
case .stream(let result): | ||
switch result { | ||
case .success(let response): | ||
promise(.success(response)) | ||
case .failure(let error): | ||
promise(.failure(error)) | ||
} | ||
case .complete(_): | ||
break | ||
} | ||
} | ||
}.eraseToAnyPublisher() | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
// | ||
// OllamaKit+ModelInfo.swift | ||
// | ||
// | ||
// Created by Kevin Hermawan on 01/01/24. | ||
// | ||
|
||
import Alamofire | ||
import Combine | ||
import Foundation | ||
|
||
extension OllamaKit { | ||
/// Asynchronously retrieves detailed information for a specific model from the Ollama API. | ||
/// | ||
/// This method accepts ``OKModelInfoRequestData`` and returns an ``OKModelInfoResponse`` containing detailed information about the requested model. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let requestData = OKModelInfoRequestData(/* parameters */) | ||
/// let modelInfo = try await ollamaKit.modelInfo(data: requestData) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKModelInfoRequestData`` used to query the API for specific model information. | ||
/// - Returns: An ``OKModelInfoResponse`` containing detailed information about the model. | ||
/// - Throws: An error if the request fails or the response can't be decoded. | ||
public func modelInfo(data: OKModelInfoRequestData) async throws -> OKModelInfoResponse { | ||
let request = AF.request(router.modelInfo(data: data)).validate() | ||
let response = request.serializingDecodable(OKModelInfoResponse.self, decoder: decoder) | ||
let value = try await response.value | ||
|
||
return value | ||
} | ||
|
||
/// Retrieves detailed information for a specific model from the Ollama API as a Combine publisher. | ||
/// | ||
/// This method provides a reactive approach to fetch detailed model information. It accepts ``OKModelInfoRequestData`` and returns a Combine publisher that emits an ``OKModelInfoResponse`` upon successful retrieval. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let requestData = OKModelInfoRequestData(/* parameters */) | ||
/// | ||
/// ollamaKit.modelInfo(data: requestData) | ||
/// .sink(receiveCompletion: { completion in | ||
/// // Handle completion | ||
/// }, receiveValue: { modelInfoResponse in | ||
/// // Handle the received model info response | ||
/// }) | ||
/// .store(in: &cancellables) | ||
/// ``` | ||
/// | ||
/// - Parameter data: The ``OKModelInfoRequestData`` used to query the API for specific model information. | ||
/// - Returns: A `AnyPublisher<OKModelInfoResponse, AFError>` that emits detailed information about the model. | ||
public func modelInfo(data: OKModelInfoRequestData) -> AnyPublisher<OKModelInfoResponse, AFError> { | ||
let request = AF.request(router.modelInfo(data: data)).validate() | ||
|
||
return request | ||
.publishDecodable(type: OKModelInfoResponse.self, decoder: decoder).value() | ||
.eraseToAnyPublisher() | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
// | ||
// OllamaKit+Models.swift | ||
// | ||
// | ||
// Created by Kevin Hermawan on 01/01/24. | ||
// | ||
|
||
import Alamofire | ||
import Combine | ||
import Foundation | ||
|
||
extension OllamaKit { | ||
/// Asynchronously retrieves a list of available models from the Ollama API. | ||
/// | ||
/// This method returns an ``OKModelResponse`` containing the details of the available models. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// let models = try await ollamaKit.models() | ||
/// ``` | ||
/// | ||
/// - Returns: An ``OKModelResponse`` object listing the available models. | ||
/// - Throws: An error if the request fails or the response can't be decoded. | ||
public func models() async throws -> OKModelResponse { | ||
let request = AF.request(router.models).validate() | ||
let response = request.serializingDecodable(OKModelResponse.self, decoder: decoder) | ||
let value = try await response.value | ||
|
||
return value | ||
} | ||
|
||
/// Retrieves a list of available models from the Ollama API as a Combine publisher. | ||
/// | ||
/// This method provides a reactive approach to fetch model data, returning a Combine publisher that emits an ``OKModelResponse`` with details of available models. | ||
/// | ||
/// ```swift | ||
/// let ollamaKit = OllamaKit(baseURL: URL(string: "http://localhost:11434")!) | ||
/// | ||
/// ollamaKit.models() | ||
/// .sink(receiveCompletion: { completion in | ||
/// // Handle completion | ||
/// }, receiveValue: { modelResponse in | ||
/// // Handle the received model response | ||
/// }) | ||
/// .store(in: &cancellables) | ||
/// ``` | ||
/// | ||
/// - Returns: A `AnyPublisher<OKModelResponse, AFError>` that emits the list of available models. | ||
public func models() -> AnyPublisher<OKModelResponse, AFError> { | ||
let request = AF.request(router.models).validate() | ||
|
||
return request | ||
.publishDecodable(type: OKModelResponse.self, decoder: decoder).value() | ||
.eraseToAnyPublisher() | ||
} | ||
} |
Oops, something went wrong.