31 Commits

Author SHA1 Message Date
Ivan Gabriele
9ad6a1dc84 ci(release): v0.14.0 2024-08-27 09:28:58 +02:00
Ivan Gabriele
7c464830ee docs(changelog): update 2024-08-27 09:28:50 +02:00
francois-caddet
161b33c725 feat(constants): update model constants (#17)
* feat(Model)!: Update model constants

- Add new models Mistral Nemo and Codestral Mamba
- Add aliases to models constant to be deserialized seemlessly from the versioned forme (e.g.: "mistral-large-2407")
- The commonly named Mistral Large 2 is now `constants::Model::MistralLargeLatest` when the old one is `Model::MistralLarge`

* tests(Model): Update the tests to check the new model variants.
2024-08-27 09:25:59 +02:00
Ivan Gabriele
79a410b298 ci(release): v0.13.0 2024-08-22 01:15:08 +02:00
Ivan Gabriele
4a45ad337f docs(changelog): update 2024-08-22 01:15:00 +02:00
Ivan Gabriele
2114916941 fix(client)!: update ModelListData struct following API changes
BREAKING CHANGE: `v1::model_list::ModelListData` struct has been updated.
2024-08-22 01:09:27 +02:00
francois-caddet
9bfbf2e9dc fix(client): remove the Content-Type from the headers of the reqwest builders. (#14)
They apparently are conflicting with reqwest internal stufs.

fix #13
2024-08-22 00:45:06 +02:00
Ivan Gabriele
67aa5bbaef ci(release): v0.12.0 2024-07-24 20:23:22 +02:00
Ivan Gabriele
415fd98167 docs(changelog): update 2024-07-24 20:23:01 +02:00
Federico G. Schwindt
8e9f7a5386 feat: mark Function trait as Send (#12)
Allow to use Client in places that are also Send.
2024-07-24 20:16:11 +02:00
Federico G. Schwindt
3afeec1d58 feat: implement the Debug trait for Client (#11)
This is useful if you want to include client::Client in your own
implementation and derive Debug.
2024-07-24 20:08:25 +02:00
Ivan Gabriele
0c097aa56d ci(release): v0.11.0 2024-06-22 14:05:11 +02:00
Ivan Gabriele
e6539c0ccf docs(changelog): update 2024-06-22 14:05:04 +02:00
Ivan Gabriele
30156c5273 test: remove useless setup in constants test 2024-06-22 14:02:52 +02:00
Ivan Gabriele
ecd0c3028f feat(constants): add OpenMixtral8x22b, MistralTiny & CodestralLatest to Model enum 2024-06-22 13:22:57 +02:00
Ivan Gabriele
0df67b1b25 fix(chat): implement Clone trait for ChatParams & ResponseFormat 2024-06-22 13:09:15 +02:00
Ivan Gabriele
f7d012b280 ci(release): v0.10.0 2024-06-07 16:55:50 +02:00
Ivan Gabriele
5b5bd2d68e docs(changelog): update 2024-06-07 16:55:39 +02:00
Xavier Gillard
2fc0642a5e feat(chat): add the 'system' and 'tool' message roles (#10)
* add the 'system' and 'tool' message roles (see: https://docs.mistral.ai/capabilities/completion/ )

* docs(chat): add offical doc link in ChatMessageRole

* ci(github): listen to pull_request event in Test workflow

---------

Co-authored-by: Ivan Gabriele <ivan.gabriele@protonmail.com>
2024-06-07 16:49:55 +02:00
Ivan Gabriele
cf68a77320 feat(chat)!: change safe_prompt, temperature & top_p to non-Option types
BREAKING CHANGE:
- `Chat::ChatParams.safe_prompt` & `Chat::ChatRequest.safe_prompt` are now `bool` instead of `Option<bool>`. Default is `false`.
- `Chat::ChatParams.temperature` & `Chat::ChatRequest.temperature` are now `f32` instead of `Option<f32>`. Default is `0.7`.
- `Chat::ChatParams.top_p` & `Chat::ChatRequest.top_p` are now `f32` instead of `Option<f32>`. Default is `1.0`.
2024-06-07 16:00:10 +02:00
Ivan Gabriele
e61ace9a18 test(chat): simplify chat response message content check to cover variations 2024-06-07 14:36:49 +02:00
Ivan Gabriele
64034402ca build(makefile): fix env file loading 2024-06-07 14:36:48 +02:00
Nick Anderson
85c3611afb feat(chat): add response_format for JSON return values 2024-06-07 14:36:37 +02:00
seurimas
da5fe54115 fix(chat): skip serializing tool_calls if null, to avoid 422 error 2024-06-07 14:12:22 +02:00
Ivan Gabriele
7a5e0679c1 ci(release): v0.9.0 2024-04-13 14:06:55 +02:00
Ivan Gabriele
99d9d099e2 docs(changelog): update 2024-04-13 13:56:20 +02:00
Ivan Gabriele
91fb775132 ci(makefile): fix conventional-changelog-cli suffix 2024-04-13 13:55:22 +02:00
Ivan Gabriele
7474aa6730 ci(makefile): prefix conventional-changelog with npx 2024-04-13 13:54:05 +02:00
Ivan Gabriele
6a99eca49c fix!: fix typo in OpenMixtral8x7b model name (#8)
BREAKING CHANGE: `Model.OpenMistral8x7b` has been renamed to `Model.OpenMixtral8x7b`.
2024-04-13 13:49:54 +02:00
renovate[bot]
fccd59c0cc fix(deps): update rust crate reqwest to 0.12.0 (#6)
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2024-04-13 13:38:35 +02:00
Ivan Gabriele
a463cb3106 docs(github): update issue templates 2024-03-10 04:36:08 +01:00
23 changed files with 303 additions and 99 deletions

View File

@@ -1,17 +1,16 @@
---
name: Bug report
about: Create a report to help us improve
title: ''
labels: ''
assignees: ''
title: ""
labels: "bug"
assignees: ""
---
**Describe the bug**
A clear and concise description of what the bug is.
...
**To Reproduce**
**Reproduction**
Steps to reproduce the behavior:
@@ -20,7 +19,7 @@ Steps to reproduce the behavior:
**Expected behavior**
A clear and concise description of what you expected to happen.
...
**Screenshots**
@@ -32,4 +31,4 @@ If applicable, what version did you use?
**Environment**
Add useful information about your configuration and environment here.
If applicable, add relevant information about your config and environment here.

View File

@@ -1,24 +1,19 @@
---
name: Feature request
about: Suggest an idea for this project
title: ''
labels: ''
assignees: ''
about: Suggest a new idea for the project.
title: ""
labels: "enhancement"
assignees: ""
---
**Is your feature request related to a problem? Please describe.**
**Is your feature request related to some problems?**
A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]
- _Ex. I'm always frustrated when..._
**Describe the solution you'd like**
**What are the solutions you'd like?**
A clear and concise description of what you want to happen.
- _Ex. A new option to..._
**Describe alternatives you've considered**
**Anything else?**
A clear and concise description of any alternative solutions or features you've considered.
**Additional context**
Add any other context or screenshots about the feature request here.
- ...

View File

@@ -1,6 +1,8 @@
name: Test
on: push
on:
pull_request:
push:
jobs:
test:

View File

@@ -1,3 +1,62 @@
## [0.14.0](https://github.com/ivangabriele/mistralai-client-rs/compare/v0.13.0...v) (2024-08-27)
### Features
* **constants:** update model constants ([#17](https://github.com/ivangabriele/mistralai-client-rs/issues/17)) ([161b33c](https://github.com/ivangabriele/mistralai-client-rs/commit/161b33c72539a6e982207349942a436df95399b7))
## [0.13.0](https://github.com/ivangabriele/mistralai-client-rs/compare/v0.12.0...v) (2024-08-21)
### ⚠ BREAKING CHANGES
* **client:** `v1::model_list::ModelListData` struct has been updated.
### Bug Fixes
* **client:** remove the `Content-Type` from the headers of the reqwest builders. ([#14](https://github.com/ivangabriele/mistralai-client-rs/issues/14)) ([9bfbf2e](https://github.com/ivangabriele/mistralai-client-rs/commit/9bfbf2e9dc7b48103ac56923fb8b3ac9a5e2d9cf)), closes [#13](https://github.com/ivangabriele/mistralai-client-rs/issues/13)
* **client:** update ModelListData struct following API changes ([2114916](https://github.com/ivangabriele/mistralai-client-rs/commit/2114916941e1ff5aa242290df5f092c0d4954afc))
## [0.12.0](https://github.com/ivangabriele/mistralai-client-rs/compare/v0.11.0...v) (2024-07-24)
### Features
* implement the Debug trait for Client ([#11](https://github.com/ivangabriele/mistralai-client-rs/issues/11)) ([3afeec1](https://github.com/ivangabriele/mistralai-client-rs/commit/3afeec1d586022e43c7b10906acec5e65927ba7d))
* mark Function trait as Send ([#12](https://github.com/ivangabriele/mistralai-client-rs/issues/12)) ([8e9f7a5](https://github.com/ivangabriele/mistralai-client-rs/commit/8e9f7a53863879b2ad618e9e5707b198e4f3b135))
## [0.11.0](https://github.com/ivangabriele/mistralai-client-rs/compare/v0.10.0...v) (2024-06-22)
### Features
* **constants:** add OpenMixtral8x22b, MistralTiny & CodestralLatest to Model enum ([ecd0c30](https://github.com/ivangabriele/mistralai-client-rs/commit/ecd0c3028fdcfab32b867eb1eed86182f5f4ab81))
### Bug Fixes
* **chat:** implement Clone trait for ChatParams & ResponseFormat ([0df67b1](https://github.com/ivangabriele/mistralai-client-rs/commit/0df67b1b2571fb04b636ce015a2daabe629ff352))
## [0.10.0](https://github.com/ivangabriele/mistralai-client-rs/compare/v0.9.0...v) (2024-06-07)
### ⚠ BREAKING CHANGES
* **chat:** - `Chat::ChatParams.safe_prompt` & `Chat::ChatRequest.safe_prompt` are now `bool` instead of `Option<bool>`. Default is `false`.
- `Chat::ChatParams.temperature` & `Chat::ChatRequest.temperature` are now `f32` instead of `Option<f32>`. Default is `0.7`.
- `Chat::ChatParams.top_p` & `Chat::ChatRequest.top_p` are now `f32` instead of `Option<f32>`. Default is `1.0`.
### Features
* **chat:** add response_format for JSON return values ([85c3611](https://github.com/ivangabriele/mistralai-client-rs/commit/85c3611afbbe8df30dfc7512cc381ed304ce4024))
* **chat:** add the 'system' and 'tool' message roles ([#10](https://github.com/ivangabriele/mistralai-client-rs/issues/10)) ([2fc0642](https://github.com/ivangabriele/mistralai-client-rs/commit/2fc0642a5e4c024b15710acaab7735480e8dfe6a))
* **chat:** change safe_prompt, temperature & top_p to non-Option types ([cf68a77](https://github.com/ivangabriele/mistralai-client-rs/commit/cf68a773201ebe0e802face52af388711acf0c27))
### Bug Fixes
* **chat:** skip serializing tool_calls if null, to avoid 422 error ([da5fe54](https://github.com/ivangabriele/mistralai-client-rs/commit/da5fe54115ce622379776661a440e2708b24810c))
## [0.9.0](https://github.com/ivangabriele/mistralai-client-rs/compare/v0.8.0...v) (2024-04-13)
### ⚠ BREAKING CHANGES
* `Model.OpenMistral8x7b` has been renamed to `Model.OpenMixtral8x7b`.
### Bug Fixes
* **deps:** update rust crate reqwest to 0.12.0 ([#6](https://github.com/ivangabriele/mistralai-client-rs/issues/6)) ([fccd59c](https://github.com/ivangabriele/mistralai-client-rs/commit/fccd59c0cc783edddec1b404363faabb009eecd6))
* fix typo in OpenMixtral8x7b model name ([#8](https://github.com/ivangabriele/mistralai-client-rs/issues/8)) ([6a99eca](https://github.com/ivangabriele/mistralai-client-rs/commit/6a99eca49c0cc8e3764a56f6dfd7762ec44a4c3b))
## [0.8.0](https://github.com/ivangabriele/mistralai-client-rs/compare/v0.7.0...v) (2024-03-09)

View File

@@ -2,7 +2,7 @@
name = "mistralai-client"
description = "Mistral AI API client library for Rust (unofficial)."
license = "Apache-2.0"
version = "0.8.0"
version = "0.14.0"
edition = "2021"
rust-version = "1.76.0"
@@ -20,7 +20,7 @@ async-trait = "0.1.77"
env_logger = "0.11.3"
futures = "0.3.30"
log = "0.4.21"
reqwest = { version = "0.11.24", features = ["json", "blocking", "stream"] }
reqwest = { version = "0.12.0", features = ["json", "blocking", "stream"] }
serde = { version = "1.0.197", features = ["derive"] }
serde_json = "1.0.114"
strum = "0.26.1"

View File

@@ -14,7 +14,7 @@ define source_env_if_not_ci
endef
define RELEASE_TEMPLATE
conventional-changelog -p conventionalcommits -i ./CHANGELOG.md -s
npx conventional-changelog-cli -p conventionalcommits -i ./CHANGELOG.md -s
git add .
git commit -m "docs(changelog): update"
git push origin HEAD
@@ -53,20 +53,20 @@ release-major:
$(call RELEASE_TEMPLATE,major)
test:
@$(source_env_if_not_ci)
@$(source_env_if_not_ci) && \
cargo test --no-fail-fast
test-cover:
@$(source_env_if_not_ci)
@$(source_env_if_not_ci) && \
cargo llvm-cov
test-doc:
@$(source_env_if_not_ci)
@$(source_env_if_not_ci) && \
cargo test --doc --no-fail-fast
test-examples:
@$(source_env_if_not_ci)
@for example in $$(ls examples/*.rs | sed 's/examples\/\(.*\)\.rs/\1/'); do \
@$(source_env_if_not_ci) && \
for example in $$(ls examples/*.rs | sed 's/examples\/\(.*\)\.rs/\1/'); do \
echo "Running $$example"; \
cargo run --example $$example; \
done
test-watch:
@source ./.env
@source ./.env && \
cargo watch -x "test -- --nocapture"

View File

@@ -7,6 +7,10 @@
Rust client for the Mistral AI API.
> [!IMPORTANT]
> While we are in v0, minor versions may introduce breaking changes.
> Please, refer to the [CHANGELOG.md](./CHANGELOG.md) for more information.
---
- [Supported APIs](#supported-apis)
@@ -102,7 +106,7 @@ fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};
@@ -134,7 +138,7 @@ async fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};
@@ -174,7 +178,7 @@ async fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};
@@ -259,7 +263,7 @@ fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
tool_choice: Some(ToolChoice::Auto),
tools: Some(tools),
@@ -336,7 +340,7 @@ async fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
tool_choice: Some(ToolChoice::Auto),
tools: Some(tools),

View File

@@ -7,6 +7,10 @@
Rust client for the Mistral AI API.
> [!IMPORTANT]
> While we are in v0, minor versions may introduce breaking changes.
> Please, refer to the [CHANGELOG.md](./CHANGELOG.md) for more information.
---
- [Supported APIs](#supported-apis)

View File

@@ -15,7 +15,7 @@ fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};

View File

@@ -16,7 +16,7 @@ async fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};

View File

@@ -53,7 +53,7 @@ fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
tool_choice: Some(ToolChoice::Auto),
tools: Some(tools),

View File

@@ -54,7 +54,7 @@ async fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
tool_choice: Some(ToolChoice::Auto),
tools: Some(tools),

View File

@@ -18,7 +18,7 @@ async fn main() {
tool_calls: None,
}];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};

View File

@@ -9,6 +9,7 @@ use crate::v1::{common, constants, tool};
pub struct ChatMessage {
pub role: ChatMessageRole,
pub content: String,
#[serde(skip_serializing_if = "Option::is_none")]
pub tool_calls: Option<Vec<tool::ToolCall>>,
}
impl ChatMessage {
@@ -29,37 +30,101 @@ impl ChatMessage {
}
}
/// See the [Mistral AI API documentation](https://docs.mistral.ai/capabilities/completion/#chat-messages) for more information.
#[derive(Clone, Debug, Eq, PartialEq, Deserialize, Serialize)]
pub enum ChatMessageRole {
#[serde(rename = "system")]
System,
#[serde(rename = "assistant")]
Assistant,
#[serde(rename = "user")]
User,
#[serde(rename = "tool")]
Tool,
}
/// The format that the model must output.
///
/// See the [API documentation](https://docs.mistral.ai/api/#operation/createChatCompletion) for more information.
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct ResponseFormat {
#[serde(rename = "type")]
pub type_: String,
}
impl ResponseFormat {
pub fn json_object() -> Self {
Self {
type_: "json_object".to_string(),
}
}
}
// -----------------------------------------------------------------------------
// Request
#[derive(Debug)]
/// The parameters for the chat request.
///
/// See the [API documentation](https://docs.mistral.ai/api/#operation/createChatCompletion) for more information.
#[derive(Clone, Debug)]
pub struct ChatParams {
/// The maximum number of tokens to generate in the completion.
///
/// Defaults to `None`.
pub max_tokens: Option<u32>,
/// The seed to use for random sampling. If set, different calls will generate deterministic results.
///
/// Defaults to `None`.
pub random_seed: Option<u32>,
pub safe_prompt: Option<bool>,
pub temperature: Option<f32>,
/// The format that the model must output.
///
/// Defaults to `None`.
pub response_format: Option<ResponseFormat>,
/// Whether to inject a safety prompt before all conversations.
///
/// Defaults to `false`.
pub safe_prompt: bool,
/// What sampling temperature to use, between `Some(0.0)` and `Some(1.0)`.
///
/// Defaults to `0.7`.
pub temperature: f32,
/// Specifies if/how functions are called.
///
/// Defaults to `None`.
pub tool_choice: Option<tool::ToolChoice>,
/// A list of available tools for the model.
///
/// Defaults to `None`.
pub tools: Option<Vec<tool::Tool>>,
pub top_p: Option<f32>,
/// Nucleus sampling, where the model considers the results of the tokens with `top_p` probability mass.
///
/// Defaults to `1.0`.
pub top_p: f32,
}
impl Default for ChatParams {
fn default() -> Self {
Self {
max_tokens: None,
random_seed: None,
safe_prompt: None,
temperature: None,
safe_prompt: false,
response_format: None,
temperature: 0.7,
tool_choice: None,
tools: None,
top_p: None,
top_p: 1.0,
}
}
}
impl ChatParams {
pub fn json_default() -> Self {
Self {
max_tokens: None,
random_seed: None,
safe_prompt: false,
response_format: None,
temperature: 0.7,
tool_choice: None,
tools: None,
top_p: 1.0,
}
}
}
@@ -74,20 +139,15 @@ pub struct ChatRequest {
#[serde(skip_serializing_if = "Option::is_none")]
pub random_seed: Option<u32>,
#[serde(skip_serializing_if = "Option::is_none")]
pub safe_prompt: Option<bool>,
pub response_format: Option<ResponseFormat>,
pub safe_prompt: bool,
pub stream: bool,
#[serde(skip_serializing_if = "Option::is_none")]
pub temperature: Option<f32>,
pub temperature: f32,
#[serde(skip_serializing_if = "Option::is_none")]
pub tool_choice: Option<tool::ToolChoice>,
#[serde(skip_serializing_if = "Option::is_none")]
pub tools: Option<Vec<tool::Tool>>,
#[serde(skip_serializing_if = "Option::is_none")]
pub top_p: Option<f32>,
// TODO Check this prop (seen in official Python client but not in API doc).
// pub tool_choice: Option<String>,
// TODO Check this prop (seen in official Python client but not in API doc).
// pub response_format: Option<String>,
pub top_p: f32,
}
impl ChatRequest {
pub fn new(
@@ -104,6 +164,7 @@ impl ChatRequest {
tool_choice,
tools,
top_p,
response_format,
} = options.unwrap_or_default();
Self {
@@ -118,6 +179,7 @@ impl ChatRequest {
tool_choice,
tools,
top_p,
response_format,
}
}
}

View File

@@ -10,6 +10,7 @@ use std::{
use crate::v1::{chat, chat_stream, constants, embedding, error, model_list, tool, utils};
#[derive(Debug)]
pub struct Client {
pub api_key: String,
pub endpoint: String,
@@ -383,7 +384,6 @@ impl Client {
let request_builder = request
.bearer_auth(&self.api_key)
.header("Accept", "application/json")
.header("Content-Type", "application/json")
.header("User-Agent", user_agent);
request_builder
@@ -398,7 +398,6 @@ impl Client {
let request_builder = request
.bearer_auth(&self.api_key)
.header("Accept", "application/json")
.header("Content-Type", "application/json")
.header("User-Agent", user_agent);
request_builder
@@ -413,7 +412,6 @@ impl Client {
let request_builder = request
.bearer_auth(&self.api_key)
.header("Accept", "text/event-stream")
.header("Content-Type", "application/json")
.header("User-Agent", user_agent);
request_builder

View File

@@ -6,14 +6,26 @@ pub const API_URL_BASE: &str = "https://api.mistral.ai/v1";
pub enum Model {
#[serde(rename = "open-mistral-7b")]
OpenMistral7b,
#[serde(rename = "open-mistral-8x7b")]
OpenMistral8x7b,
#[serde(rename = "mistral-small-latest")]
#[serde(rename = "open-mixtral-8x7b")]
OpenMixtral8x7b,
#[serde(rename = "open-mixtral-8x22b")]
OpenMixtral8x22b,
#[serde(rename = "open-mistral-nemo", alias = "open-mistral-nemo-2407")]
OpenMistralNemo,
#[serde(rename = "mistral-tiny")]
MistralTiny,
#[serde(rename = "mistral-small-latest", alias = "mistral-small-2402")]
MistralSmallLatest,
#[serde(rename = "mistral-medium-latest")]
#[serde(rename = "mistral-medium-latest", alias = "mistral-medium-2312")]
MistralMediumLatest,
#[serde(rename = "mistral-large-latest")]
#[serde(rename = "mistral-large-latest", alias = "mistral-large-2407")]
MistralLargeLatest,
#[serde(rename = "mistral-large-2402")]
MistralLarge,
#[serde(rename = "codestral-latest", alias = "codestral-2405")]
CodestralLatest,
#[serde(rename = "open-codestral-mamba")]
CodestralMamba,
}
#[derive(Clone, Debug, Eq, PartialEq, Deserialize, Serialize)]

View File

@@ -9,6 +9,7 @@ pub struct ModelListResponse {
pub data: Vec<ModelListData>,
}
/// See: https://docs.mistral.ai/api/#tag/models
#[derive(Clone, Debug, Deserialize, Serialize)]
pub struct ModelListData {
pub id: String,
@@ -16,27 +17,21 @@ pub struct ModelListData {
/// Unix timestamp (in seconds).
pub created: u32,
pub owned_by: String,
pub permission: Vec<ModelListDataPermission>,
// TODO Check this prop (seen in API responses but undocumented).
// pub root: ???,
// TODO Check this prop (seen in API responses but undocumented).
// pub parent: ???,
pub root: Option<String>,
pub archived: bool,
pub name: String,
pub description: String,
pub capabilities: ModelListDataCapabilies,
pub max_context_length: u32,
pub aliases: Vec<String>,
/// ISO 8601 date (`YYYY-MM-DDTHH:MM:SSZ`).
pub deprecation: Option<String>,
}
#[derive(Clone, Debug, Deserialize, Serialize)]
pub struct ModelListDataPermission {
pub id: String,
pub object: String,
/// Unix timestamp (in seconds).
pub created: u32,
pub allow_create_engine: bool,
pub allow_sampling: bool,
pub allow_logprobs: bool,
pub allow_search_indices: bool,
pub allow_view: bool,
pub allow_fine_tuning: bool,
pub organization: String,
pub is_blocking: bool,
// TODO Check this prop (seen in API responses but undocumented).
// pub group: ???,
pub struct ModelListDataCapabilies {
pub completion_chat: bool,
pub completion_fim: bool,
pub function_calling: bool,
pub fine_tuning: bool,
}

View File

@@ -1,6 +1,6 @@
use async_trait::async_trait;
use serde::{Deserialize, Serialize};
use std::{any::Any, collections::HashMap};
use std::{any::Any, collections::HashMap, fmt::Debug};
// -----------------------------------------------------------------------------
// Definitions
@@ -115,12 +115,16 @@ pub enum ToolType {
Function,
}
/// An enum representing how functions should be called.
#[derive(Clone, Debug, Eq, PartialEq, Deserialize, Serialize)]
pub enum ToolChoice {
/// The model is forced to call a function.
#[serde(rename = "any")]
Any,
/// The model can choose to either generate a message or call a function.
#[serde(rename = "auto")]
Auto,
/// The model won't call a function and will generate a message instead.
#[serde(rename = "none")]
None,
}
@@ -129,6 +133,12 @@ pub enum ToolChoice {
// Custom
#[async_trait]
pub trait Function {
pub trait Function: Send {
async fn execute(&self, arguments: String) -> Box<dyn Any + Send>;
}
impl Debug for dyn Function {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "Function()")
}
}

View File

@@ -16,10 +16,10 @@ async fn test_client_chat_async() {
let model = Model::OpenMistral7b;
let messages = vec![ChatMessage::new_user_message(
"Just guess the next word: \"Eiffel ...\"?",
"Guess the next word: \"Eiffel ...\"?",
)];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};
@@ -37,8 +37,12 @@ async fn test_client_chat_async() {
expect!(response.choices[0].finish_reason.clone()).to_be(ChatResponseChoiceFinishReason::Stop);
expect!(response.choices[0].message.role.clone()).to_be(ChatMessageRole::Assistant);
expect!(response.choices[0].message.content.clone())
.to_be("Tower. The Eiffel Tower is a famous landmark in Paris, France.".to_string());
expect!(response.choices[0]
.message
.content
.clone()
.contains("Tower"))
.to_be(true);
expect!(response.usage.prompt_tokens).to_be_greater_than(0);
expect!(response.usage.completion_tokens).to_be_greater_than(0);
@@ -66,7 +70,7 @@ async fn test_client_chat_async_with_function_calling() {
"What's the current temperature in Paris?",
)];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
tool_choice: Some(ToolChoice::Any),
tools: Some(tools),

View File

@@ -16,10 +16,10 @@ fn test_client_chat() {
let model = Model::OpenMistral7b;
let messages = vec![ChatMessage::new_user_message(
"Just guess the next word: \"Eiffel ...\"?",
"Guess the next word: \"Eiffel ...\"?",
)];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};
@@ -31,8 +31,12 @@ fn test_client_chat() {
expect!(response.choices.len()).to_be(1);
expect!(response.choices[0].index).to_be(0);
expect!(response.choices[0].message.role.clone()).to_be(ChatMessageRole::Assistant);
expect!(response.choices[0].message.content.clone())
.to_be("Tower. The Eiffel Tower is a famous landmark in Paris, France.".to_string());
expect!(response.choices[0]
.message
.content
.clone()
.contains("Tower"))
.to_be(true);
expect!(response.choices[0].finish_reason.clone()).to_be(ChatResponseChoiceFinishReason::Stop);
expect!(response.usage.prompt_tokens).to_be_greater_than(0);
expect!(response.usage.completion_tokens).to_be_greater_than(0);
@@ -60,7 +64,7 @@ fn test_client_chat_with_function_calling() {
"What's the current temperature in Paris?",
)];
let options = ChatParams {
temperature: Some(0.0),
temperature: 0.0,
random_seed: Some(42),
tool_choice: Some(ToolChoice::Auto),
tools: Some(tools),

View File

@@ -1,6 +1,11 @@
use jrest::expect;
use mistralai_client::v1::{client::Client, error::ClientError};
#[derive(Debug)]
struct _Foo {
_client: Client,
}
#[test]
fn test_client_new_with_none_params() {
let maybe_original_mistral_api_key = std::env::var("MISTRAL_API_KEY").ok();

View File

@@ -0,0 +1,44 @@
use jrest::expect;
use mistralai_client::v1::{
chat::{ChatMessage, ChatParams},
client::Client,
constants::Model,
};
#[test]
fn test_model_constant() {
let models = vec![
Model::OpenMistral7b,
Model::OpenMixtral8x7b,
Model::OpenMixtral8x22b,
Model::OpenMistralNemo,
Model::MistralTiny,
Model::MistralSmallLatest,
Model::MistralMediumLatest,
Model::MistralLargeLatest,
Model::MistralLarge,
Model::CodestralLatest,
Model::CodestralMamba,
];
let client = Client::new(None, None, None, None).unwrap();
let messages = vec![ChatMessage::new_user_message("A number between 0 and 100?")];
let options = ChatParams {
temperature: 0.0,
random_seed: Some(42),
..Default::default()
};
for model in models {
let response = client
.chat(model.clone(), messages.clone(), Some(options.clone()))
.unwrap();
expect!(response.model).to_be(model);
expect!(response.object).to_be("chat.completion".to_string());
expect!(response.choices.len()).to_be(1);
expect!(response.choices[0].index).to_be(0);
expect!(response.choices[0].message.content.len()).to_be_greater_than(0);
}
}

7
tests/v1_tool_test.rs Normal file
View File

@@ -0,0 +1,7 @@
use mistralai_client::v1::client::Client;
trait _Trait: Send {}
struct _Foo {
_dummy: Client,
}
impl _Trait for _Foo {}