This commit is contained in:
Mathias Gesbert 2026-01-28 18:34:16 +01:00 committed by Mathias Gesbert
parent d33db9fff8
commit bd3497b1c0
11 changed files with 37 additions and 41 deletions

2
.vscode/launch.json vendored
View file

@ -1,5 +1,5 @@
{ {
"version": "2.0.0", "version": "2.0.1",
"configurations": [ "configurations": [
{ {
"name": "ACP Server", "name": "ACP Server",

View file

@ -5,6 +5,13 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## [2.0.1] - 2026-01-28
### Fixed
- Encoding issues in Windows
## [2.0.0] - 2026-01-27 ## [2.0.0] - 2026-01-27
### Added ### Added

View file

@ -1,7 +1,7 @@
id = "mistral-vibe" id = "mistral-vibe"
name = "Mistral Vibe" name = "Mistral Vibe"
description = "Mistral's open-source coding assistant" description = "Mistral's open-source coding assistant"
version = "2.0.0" version = "2.0.1"
schema_version = 1 schema_version = 1
authors = ["Mistral AI"] authors = ["Mistral AI"]
repository = "https://github.com/mistralai/mistral-vibe" repository = "https://github.com/mistralai/mistral-vibe"
@ -11,25 +11,25 @@ name = "Mistral Vibe"
icon = "./icons/mistral_vibe.svg" icon = "./icons/mistral_vibe.svg"
[agent_servers.mistral-vibe.targets.darwin-aarch64] [agent_servers.mistral-vibe.targets.darwin-aarch64]
archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.0/vibe-acp-darwin-aarch64-2.0.0.zip" archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.1/vibe-acp-darwin-aarch64-2.0.1.zip"
cmd = "./vibe-acp" cmd = "./vibe-acp"
[agent_servers.mistral-vibe.targets.darwin-x86_64] [agent_servers.mistral-vibe.targets.darwin-x86_64]
archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.0/vibe-acp-darwin-x86_64-2.0.0.zip" archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.1/vibe-acp-darwin-x86_64-2.0.1.zip"
cmd = "./vibe-acp" cmd = "./vibe-acp"
[agent_servers.mistral-vibe.targets.linux-aarch64] [agent_servers.mistral-vibe.targets.linux-aarch64]
archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.0/vibe-acp-linux-aarch64-2.0.0.zip" archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.1/vibe-acp-linux-aarch64-2.0.1.zip"
cmd = "./vibe-acp" cmd = "./vibe-acp"
[agent_servers.mistral-vibe.targets.linux-x86_64] [agent_servers.mistral-vibe.targets.linux-x86_64]
archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.0/vibe-acp-linux-x86_64-2.0.0.zip" archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.1/vibe-acp-linux-x86_64-2.0.1.zip"
cmd = "./vibe-acp" cmd = "./vibe-acp"
[agent_servers.mistral-vibe.targets.windows-aarch64] [agent_servers.mistral-vibe.targets.windows-aarch64]
archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.0/vibe-acp-windows-aarch64-2.0.0.zip" archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.1/vibe-acp-windows-aarch64-2.0.1.zip"
cmd = "./vibe-acp.exe" cmd = "./vibe-acp.exe"
[agent_servers.mistral-vibe.targets.windows-x86_64] [agent_servers.mistral-vibe.targets.windows-x86_64]
archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.0/vibe-acp-windows-x86_64-2.0.0.zip" archive = "https://github.com/mistralai/mistral-vibe/releases/download/v2.0.1/vibe-acp-windows-x86_64-2.0.1.zip"
cmd = "./vibe-acp.exe" cmd = "./vibe-acp.exe"

View file

@ -1,6 +1,6 @@
[project] [project]
name = "mistral-vibe" name = "mistral-vibe"
version = "2.0.0" version = "2.0.1"
description = "Minimal CLI coding agent by Mistral" description = "Minimal CLI coding agent by Mistral"
readme = "README.md" readme = "README.md"
requires-python = ">=3.12" requires-python = ">=3.12"

View file

@ -25,7 +25,7 @@ class TestACPInitialize:
), ),
) )
assert response.agent_info == Implementation( assert response.agent_info == Implementation(
name="@mistralai/mistral-vibe", title="Mistral Vibe", version="2.0.0" name="@mistralai/mistral-vibe", title="Mistral Vibe", version="2.0.1"
) )
assert response.auth_methods == [] assert response.auth_methods == []
@ -48,7 +48,7 @@ class TestACPInitialize:
), ),
) )
assert response.agent_info == Implementation( assert response.agent_info == Implementation(
name="@mistralai/mistral-vibe", title="Mistral Vibe", version="2.0.0" name="@mistralai/mistral-vibe", title="Mistral Vibe", version="2.0.1"
) )
assert response.auth_methods is not None assert response.auth_methods is not None

2
uv.lock generated
View file

@ -673,7 +673,7 @@ wheels = [
[[package]] [[package]]
name = "mistral-vibe" name = "mistral-vibe"
version = "2.0.0" version = "2.0.1"
source = { editable = "." } source = { editable = "." }
dependencies = [ dependencies = [
{ name = "agent-client-protocol" }, { name = "agent-client-protocol" },

View file

@ -3,4 +3,4 @@ from __future__ import annotations
from pathlib import Path from pathlib import Path
VIBE_ROOT = Path(__file__).parent VIBE_ROOT = Path(__file__).parent
__version__ = "2.0.0" __version__ = "2.0.1"

View file

@ -49,14 +49,11 @@ class FileSystemUpdateCacheRepository(UpdateCacheRepository):
async def set(self, update_cache: UpdateCache) -> None: async def set(self, update_cache: UpdateCache) -> None:
try: try:
payload = json.dumps( payload = json.dumps({
{ "latest_version": update_cache.latest_version,
"latest_version": update_cache.latest_version, "stored_at_timestamp": update_cache.stored_at_timestamp,
"stored_at_timestamp": update_cache.stored_at_timestamp, "seen_whats_new_version": update_cache.seen_whats_new_version,
"seen_whats_new_version": update_cache.seen_whats_new_version, })
},
ensure_ascii=False,
)
await asyncio.to_thread(self._cache_file.write_text, payload) await asyncio.to_thread(self._cache_file.write_text, payload)
except OSError: except OSError:
return None return None

View file

@ -22,12 +22,12 @@ class SessionLoader:
return False return False
try: try:
with open(metadata_path) as f: with open(metadata_path, encoding="utf-8", errors="ignore") as f:
metadata = json.load(f) metadata = json.load(f)
if not isinstance(metadata, dict): if not isinstance(metadata, dict):
return False return False
with open(messages_path) as f: with open(messages_path, encoding="utf-8", errors="ignore") as f:
lines = f.readlines() lines = f.readlines()
if not lines: if not lines:
return False return False
@ -87,7 +87,7 @@ class SessionLoader:
messages_filepath = filepath / MESSAGES_FILENAME messages_filepath = filepath / MESSAGES_FILENAME
try: try:
with messages_filepath.open("r", encoding="utf-8") as f: with messages_filepath.open("r", encoding="utf-8", errors="ignore") as f:
content = f.readlines() content = f.readlines()
except Exception as e: except Exception as e:
raise ValueError( raise ValueError(
@ -117,7 +117,9 @@ class SessionLoader:
if metadata_filepath.exists(): if metadata_filepath.exists():
try: try:
with metadata_filepath.open("r", encoding="utf-8") as f: with metadata_filepath.open(
"r", encoding="utf-8", errors="ignore"
) as f:
metadata = json.load(f) metadata = json.load(f)
except json.JSONDecodeError as e: except json.JSONDecodeError as e:
raise ValueError( raise ValueError(

View file

@ -182,7 +182,9 @@ class SessionLogger:
if not messages_filepath.exists(): if not messages_filepath.exists():
messages_filepath.touch() messages_filepath.touch()
async with await AsyncPath(messages_filepath).open("a") as f: async with await AsyncPath(messages_filepath).open(
"a", encoding="utf-8"
) as f:
for message in messages: for message in messages:
await f.write(json.dumps(message, ensure_ascii=False) + "\n") await f.write(json.dumps(message, ensure_ascii=False) + "\n")
await f.flush() await f.flush()
@ -217,7 +219,9 @@ class SessionLogger:
# Read old metadata and get total_messages # Read old metadata and get total_messages
try: try:
if self.metadata_filepath.exists(): if self.metadata_filepath.exists():
async with await AsyncPath(self.metadata_filepath).open() as f: async with await AsyncPath(self.metadata_filepath).open(
encoding="utf-8", errors="ignore"
) as f:
old_metadata = json.loads(await f.read()) old_metadata = json.loads(await f.read())
old_total_messages = old_metadata["total_messages"] old_total_messages = old_metadata["total_messages"]
else: else:

View file

@ -1,14 +0,0 @@
# What's New in 2.0.0
- **Subagents**: The agent can now delegate tasks to specialized sub-agents for more complex workflows.
- **Interactive Questions**: The agent can now ask you clarifying questions as it works.
- **Slash Commands**: You can now define your own custom slash commands through skills.
- **Auto-Update**: Vibe will now keep itself up to date automatically. Disable with `enable_auto_update = false` in `config.toml`.
- **MCP Servers**: Configurations now support environment variables and custom timeouts.
- **Agents System**: Modes have been replaced by a more flexible agents system.
### ⚠️ Breaking Changes
- Custom modes must be migrated to the new agent format.
- `workdir` setting in `config.toml` is no longer supported.
- `instructions.md` files are no longer supported.
- Heuristic regex matching is removed. To use a regex in `enabled_tools`, `disabled_tools`, `enabled_skills`, or `disabled_skills`, prefix it with `re:` (e.g., `re:serena.*`).