mirror of
https://github.com/jcreek/AutomatedAssessmentFeedbackAgent.git
synced 2026-07-13 02:53:49 +00:00
feat(*): Improve the display of tool usage
This commit is contained in:
@@ -1,7 +1,13 @@
|
||||
import { ToolUtility } from '@azure/ai-projects';
|
||||
|
||||
export const conceptVerifierToolMeta = {
|
||||
key: 'verifyConceptCoverage',
|
||||
userDescription: 'Checking for required concepts from the rubric',
|
||||
icon: '📋',
|
||||
};
|
||||
|
||||
export const conceptVerifierTool = ToolUtility.createFunctionTool({
|
||||
name: 'verifyConceptCoverage',
|
||||
name: conceptVerifierToolMeta.key,
|
||||
description: 'Checks which rubric‑listed concepts appear (or are missing) in the submission.',
|
||||
parameters: {
|
||||
type: 'object',
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
import { ToolUtility } from '@azure/ai-projects';
|
||||
|
||||
export const essayAnalyzerToolMeta = {
|
||||
key: 'analyzeEssay',
|
||||
userDescription: 'Analyzing essay structure and argument quality',
|
||||
icon: '📝',
|
||||
};
|
||||
|
||||
export const essayAnalyzerTool = ToolUtility.createFunctionTool({
|
||||
name: 'analyzeEssay',
|
||||
name: essayAnalyzerToolMeta.key,
|
||||
description: 'Analyzes an essay for structure, argument, and evidence.',
|
||||
parameters: {
|
||||
type: 'object',
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
import { ToolUtility } from '@azure/ai-projects';
|
||||
|
||||
export const feedbackGeneratorToolMeta = {
|
||||
key: 'generateFeedback',
|
||||
userDescription: 'Generating personalized feedback for the student',
|
||||
icon: '🌟',
|
||||
};
|
||||
|
||||
export const feedbackGeneratorTool = ToolUtility.createFunctionTool({
|
||||
name: 'generateFeedback',
|
||||
name: feedbackGeneratorToolMeta.key,
|
||||
description: 'Produces two praise points and two actionable “try next time” suggestions based on submission and rubric.',
|
||||
parameters: {
|
||||
type: 'object',
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
export { rubricMatcherTool } from './rubricMatcherTool';
|
||||
export { essayAnalyzerTool } from './essayAnalyzerTool';
|
||||
export { conceptVerifierTool } from './conceptVerifierTool';
|
||||
export { feedbackGeneratorTool } from './feedbackGeneratorTool';
|
||||
export { metacognitiveReflectionPromptTool } from './metacognitiveReflectionPromptTool';
|
||||
export { selfAssessmentTool } from './selfAssessmentTool';
|
||||
export { spellingAndGrammarCheckerTool } from './spellingAndGrammarCheckerTool';
|
||||
export { rubricMatcherTool, rubricMatcherToolMeta } from './rubricMatcherTool';
|
||||
export { essayAnalyzerTool, essayAnalyzerToolMeta } from './essayAnalyzerTool';
|
||||
export { conceptVerifierTool, conceptVerifierToolMeta } from './conceptVerifierTool';
|
||||
export { feedbackGeneratorTool, feedbackGeneratorToolMeta } from './feedbackGeneratorTool';
|
||||
export { metacognitiveReflectionPromptTool, metacognitiveReflectionPromptToolMeta } from './metacognitiveReflectionPromptTool';
|
||||
export { selfAssessmentTool, selfAssessmentToolMeta } from './selfAssessmentTool';
|
||||
export { spellingAndGrammarCheckerTool, spellingAndGrammarCheckerToolMeta } from './spellingAndGrammarCheckerTool';
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
import { ToolUtility } from '@azure/ai-projects';
|
||||
|
||||
export const metacognitiveReflectionPromptToolMeta = {
|
||||
key: 'generateReflectionPrompts',
|
||||
userDescription: 'Suggesting ways the student can improve next time',
|
||||
icon: '💭',
|
||||
};
|
||||
|
||||
export const metacognitiveReflectionPromptTool = ToolUtility.createFunctionTool({
|
||||
name: 'generateReflectionPrompts',
|
||||
name: metacognitiveReflectionPromptToolMeta.key,
|
||||
description: 'Based on rubric shortfalls, generates prompts like “How could you strengthen your evidence in paragraph 2?”',
|
||||
parameters: {
|
||||
type: 'object',
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
import { ToolUtility } from '@azure/ai-projects';
|
||||
|
||||
export const rubricMatcherToolMeta = {
|
||||
key: 'matchRubric',
|
||||
userDescription: 'Assessing the submission against the provided rubric',
|
||||
icon: '📊',
|
||||
};
|
||||
|
||||
export const rubricMatcherTool = ToolUtility.createFunctionTool({
|
||||
name: 'matchRubric',
|
||||
name: rubricMatcherToolMeta.key,
|
||||
description: 'Matches a submission to a rubric and returns a score/criteria breakdown.',
|
||||
parameters: {
|
||||
type: 'object',
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
import { ToolUtility } from '@azure/ai-projects';
|
||||
|
||||
export const selfAssessmentToolMeta = {
|
||||
key: 'createSelfAssessment',
|
||||
userDescription: 'Creating self-reflection questions for the student',
|
||||
icon: '🔎',
|
||||
};
|
||||
|
||||
export const selfAssessmentTool = ToolUtility.createFunctionTool({
|
||||
name: 'createSelfAssessment',
|
||||
name: selfAssessmentToolMeta.key,
|
||||
description: 'Generates 3 short questions that prompt the student to reflect on their own work based on rubric gaps.',
|
||||
parameters: {
|
||||
type: 'object',
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
import { ToolUtility } from '@azure/ai-projects';
|
||||
|
||||
export const spellingAndGrammarCheckerToolMeta = {
|
||||
key: 'checkSpellingAndGrammar',
|
||||
userDescription: 'Checking for spelling and grammar mistakes',
|
||||
icon: '📝',
|
||||
};
|
||||
|
||||
export const spellingAndGrammarCheckerTool = ToolUtility.createFunctionTool({
|
||||
name: 'checkSpellingAndGrammar',
|
||||
name: spellingAndGrammarCheckerToolMeta.key,
|
||||
description: 'Identifies spelling, punctuation, and syntax issues in the submission and suggests corrections.',
|
||||
parameters: {
|
||||
type: 'object',
|
||||
|
||||
@@ -0,0 +1,145 @@
|
||||
<script lang="ts">
|
||||
import {
|
||||
rubricMatcherToolMeta,
|
||||
essayAnalyzerToolMeta,
|
||||
conceptVerifierToolMeta,
|
||||
feedbackGeneratorToolMeta,
|
||||
metacognitiveReflectionPromptToolMeta,
|
||||
selfAssessmentToolMeta,
|
||||
spellingAndGrammarCheckerToolMeta
|
||||
} from '$lib/agent/tools';
|
||||
|
||||
export let toolEvents: Array<{ tool: string, time: string }> = [];
|
||||
|
||||
// Map keys to meta objects for lookup
|
||||
const TOOL_META_MAP: Record<string, { userDescription: string; icon: string }> = {
|
||||
[rubricMatcherToolMeta.key]: rubricMatcherToolMeta,
|
||||
[essayAnalyzerToolMeta.key]: essayAnalyzerToolMeta,
|
||||
[conceptVerifierToolMeta.key]: conceptVerifierToolMeta,
|
||||
[feedbackGeneratorToolMeta.key]: feedbackGeneratorToolMeta,
|
||||
[metacognitiveReflectionPromptToolMeta.key]: metacognitiveReflectionPromptToolMeta,
|
||||
[selfAssessmentToolMeta.key]: selfAssessmentToolMeta,
|
||||
[spellingAndGrammarCheckerToolMeta.key]: spellingAndGrammarCheckerToolMeta
|
||||
};
|
||||
|
||||
// Build steps from toolEvents, filling in status, icon, and userDescription
|
||||
$: steps = toolEvents.map((event, idx) => {
|
||||
const meta = TOOL_META_MAP[event.tool];
|
||||
return {
|
||||
description: meta ? meta.userDescription : event.tool,
|
||||
icon: meta ? meta.icon : '🤖',
|
||||
status: idx < toolEvents.length - 1 ? 'done' : 'running',
|
||||
time: event.time
|
||||
};
|
||||
});
|
||||
// If no events yet, show agent 'thinking'
|
||||
$: agentThinking = toolEvents.length === 0;
|
||||
$: statusMessage = agentThinking
|
||||
? 'The AI Agent is analyzing your submission and selecting the best tools...'
|
||||
: 'The AI Agent is now processing your submission...';
|
||||
$: liveMessage = agentThinking
|
||||
? statusMessage
|
||||
: steps.length > 0
|
||||
? steps[steps.length - 1].description
|
||||
: statusMessage;
|
||||
</script>
|
||||
|
||||
<style>
|
||||
.agent-container {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
margin-top: 2rem;
|
||||
}
|
||||
.agent-avatar {
|
||||
font-size: 3rem;
|
||||
margin-bottom: 1rem;
|
||||
user-select: none;
|
||||
}
|
||||
.status-message {
|
||||
font-weight: 600;
|
||||
margin-bottom: 1.5rem;
|
||||
text-align: center;
|
||||
}
|
||||
.progress-bar-bg {
|
||||
width: 100%;
|
||||
max-width: 400px;
|
||||
height: 10px;
|
||||
background: #e0e7ef;
|
||||
border-radius: 5px;
|
||||
margin-bottom: 2rem;
|
||||
overflow: hidden;
|
||||
}
|
||||
.progress-bar-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(90deg, #5b9df9 0%, #4ade80 100%);
|
||||
transition: width 0.5s;
|
||||
}
|
||||
ul.steps {
|
||||
list-style: none;
|
||||
padding: 0;
|
||||
width: 100%;
|
||||
max-width: 400px;
|
||||
}
|
||||
li.step {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
padding: 0.75rem 0.5rem;
|
||||
border-radius: 6px;
|
||||
margin-bottom: 0.5rem;
|
||||
background: #f8fafc;
|
||||
font-size: 1.05rem;
|
||||
outline: none;
|
||||
}
|
||||
li.step[aria-current="step"] {
|
||||
background: #e0f2fe;
|
||||
font-weight: bold;
|
||||
}
|
||||
.step-icon {
|
||||
margin-right: 1rem;
|
||||
font-size: 1.5rem;
|
||||
min-width: 2rem;
|
||||
text-align: center;
|
||||
}
|
||||
.visually-hidden {
|
||||
position: absolute;
|
||||
left: -9999px;
|
||||
width: 1px;
|
||||
height: 1px;
|
||||
overflow: hidden;
|
||||
}
|
||||
</style>
|
||||
|
||||
<div class="agent-container" role="region" aria-label="Submission Processing">
|
||||
<div class="agent-avatar" aria-hidden="true">🤖</div>
|
||||
<div class="status-message" id="agent-status">{statusMessage}</div>
|
||||
<div class="progress-bar-bg" aria-hidden="true">
|
||||
<div
|
||||
class="progress-bar-fill"
|
||||
style="width: {steps.length ? ((steps.filter(s => s.status === 'done').length) / (steps.length)) * 100 : 0}%"
|
||||
></div>
|
||||
</div>
|
||||
<div aria-live="polite" class="visually-hidden">{liveMessage}</div>
|
||||
<ul class="steps" aria-label="Processing steps">
|
||||
{#if agentThinking}
|
||||
<li class="step" aria-current="step">
|
||||
<span class="step-icon" aria-hidden="true">💡</span>
|
||||
<span>AI Agent is analyzing your submission…</span>
|
||||
</li>
|
||||
{:else}
|
||||
{#each steps as step, idx}
|
||||
<li class="step {step.status}">
|
||||
<span class="step-icon" aria-hidden="true">{step.icon}</span>
|
||||
<span class="step-desc">{step.description}</span>
|
||||
<span class="step-time">{new Date(step.time).toLocaleTimeString()}
|
||||
{step.status === 'done'
|
||||
? '✅'
|
||||
: step.status === 'running'
|
||||
? '⏳'
|
||||
: '🛠️'}
|
||||
</span>
|
||||
</li>
|
||||
{/each}
|
||||
{/if}
|
||||
</ul>
|
||||
</div>
|
||||
Reference in New Issue
Block a user