fix: minichat markdown rendering and weather temperature unit preference
- KnowledgeView minichat: render assistant messages through renderMarkdown so headers, bold, lists etc. display correctly instead of raw markdown - get_weather tool: read user's temp_unit from briefing_config and convert temperatures to °F when preferred; also include temp_unit in the returned payload so the model can label values correctly Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -3,6 +3,7 @@ import { ref, computed, watch, onMounted, onUnmounted, nextTick } from "vue";
|
|||||||
import { useRouter } from "vue-router";
|
import { useRouter } from "vue-router";
|
||||||
import { apiGet, apiPatch, transcribeAudio } from "@/api/client";
|
import { apiGet, apiPatch, transcribeAudio } from "@/api/client";
|
||||||
import { fmtCompact } from "@/utils/dateFormat";
|
import { fmtCompact } from "@/utils/dateFormat";
|
||||||
|
import { renderMarkdown } from "@/utils/markdown";
|
||||||
import { useChatStore } from "@/stores/chat";
|
import { useChatStore } from "@/stores/chat";
|
||||||
import { useSettingsStore } from "@/stores/settings";
|
import { useSettingsStore } from "@/stores/settings";
|
||||||
import { useVoiceRecorder } from "@/composables/useVoiceRecorder";
|
import { useVoiceRecorder } from "@/composables/useVoiceRecorder";
|
||||||
@@ -544,7 +545,7 @@ onUnmounted(() => {
|
|||||||
class="minichat-msg"
|
class="minichat-msg"
|
||||||
:class="msg.role === 'user' ? 'msg--user' : 'msg--assistant'"
|
:class="msg.role === 'user' ? 'msg--user' : 'msg--assistant'"
|
||||||
>
|
>
|
||||||
<div class="msg-content" v-html="msg.role === 'assistant' ? msg.content : msg.content"></div>
|
<div class="msg-content" v-html="msg.role === 'assistant' ? renderMarkdown(msg.content) : msg.content"></div>
|
||||||
</div>
|
</div>
|
||||||
<div v-if="chatStore.streaming" class="minichat-msg msg--assistant">
|
<div v-if="chatStore.streaming" class="minichat-msg msg--assistant">
|
||||||
<div class="msg-content streaming-indicator">
|
<div class="msg-content streaming-indicator">
|
||||||
|
|||||||
@@ -1914,20 +1914,34 @@ async def execute_tool(
|
|||||||
from fabledassistant.services.weather import (
|
from fabledassistant.services.weather import (
|
||||||
get_cached_weather, geocode, _fetch_open_meteo, parse_forecast
|
get_cached_weather, geocode, _fetch_open_meteo, parse_forecast
|
||||||
)
|
)
|
||||||
|
from fabledassistant.services.briefing_pipeline import _get_temp_unit
|
||||||
from datetime import timezone as _tz
|
from datetime import timezone as _tz
|
||||||
location = (arguments.get("location") or "").strip()
|
location = (arguments.get("location") or "").strip()
|
||||||
|
temp_unit = await _get_temp_unit(user_id)
|
||||||
|
|
||||||
|
def _apply_unit(days: list[dict]) -> list[dict]:
|
||||||
|
if temp_unit != "F":
|
||||||
|
return days
|
||||||
|
def _c_to_f(v: float | None) -> float | None:
|
||||||
|
return round(v * 9 / 5 + 32, 1) if v is not None else None
|
||||||
|
return [
|
||||||
|
{**d, "temp_max": _c_to_f(d.get("temp_max")), "temp_min": _c_to_f(d.get("temp_min"))}
|
||||||
|
for d in days
|
||||||
|
]
|
||||||
|
|
||||||
_known = {"home", "work", "all", ""}
|
_known = {"home", "work", "all", ""}
|
||||||
if location.lower() not in _known:
|
if location.lower() not in _known:
|
||||||
# Live geocode + fetch for arbitrary city
|
# Live geocode + fetch for arbitrary city
|
||||||
try:
|
try:
|
||||||
lat, lon, label = await geocode(location)
|
lat, lon, label = await geocode(location)
|
||||||
raw = await _fetch_open_meteo(lat, lon)
|
raw = await _fetch_open_meteo(lat, lon)
|
||||||
days = parse_forecast(raw)
|
days = _apply_unit(parse_forecast(raw))
|
||||||
return {"success": True, "data": {"locations": [{
|
return {"success": True, "data": {"locations": [{
|
||||||
"location_key": "query",
|
"location_key": "query",
|
||||||
"location_label": label,
|
"location_label": label,
|
||||||
"fetched_at": datetime.now(_tz.utc).isoformat(),
|
"fetched_at": datetime.now(_tz.utc).isoformat(),
|
||||||
"days": days,
|
"days": days,
|
||||||
|
"temp_unit": temp_unit,
|
||||||
"changes_since_last_fetch": [],
|
"changes_since_last_fetch": [],
|
||||||
}]}}
|
}]}}
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
@@ -1936,6 +1950,10 @@ async def execute_tool(
|
|||||||
locations = await get_cached_weather(user_id)
|
locations = await get_cached_weather(user_id)
|
||||||
if location.lower() not in ("all", ""):
|
if location.lower() not in ("all", ""):
|
||||||
locations = [loc for loc in locations if loc["location_key"] == location.lower()]
|
locations = [loc for loc in locations if loc["location_key"] == location.lower()]
|
||||||
|
locations = [
|
||||||
|
{**loc, "days": _apply_unit(loc.get("days", [])), "temp_unit": temp_unit}
|
||||||
|
for loc in locations
|
||||||
|
]
|
||||||
return {"success": True, "data": {"locations": locations}}
|
return {"success": True, "data": {"locations": locations}}
|
||||||
|
|
||||||
elif tool_name == "get_rss_items":
|
elif tool_name == "get_rss_items":
|
||||||
|
|||||||
Reference in New Issue
Block a user