diff --git a/server/agent/simple_manager.go b/server/agent/simple_manager.go
new file mode 100644
index 0000000..27d522d
--- /dev/null
+++ b/server/agent/simple_manager.go
@@ -0,0 +1,565 @@
+package agent
+
+import (
+	"context"
+	"fmt"
+	"log"
+	"os"
+	"os/exec"
+	"path/filepath"
+	"strings"
+	"time"
+
+	"github.com/iomodo/staff/assignment"
+	"github.com/iomodo/staff/config"
+	"github.com/iomodo/staff/git"
+	"github.com/iomodo/staff/llm"
+	"github.com/iomodo/staff/tm"
+)
+
+// SimpleAgent represents a simplified AI agent for MVP
+type SimpleAgent struct {
+	Name         string
+	Role         string
+	Model        string
+	SystemPrompt string
+	Provider     llm.LLMProvider
+	MaxTokens    *int
+	Temperature  *float64
+}
+
+// SimpleAgentManager manages multiple AI agents with basic Git operations
+type SimpleAgentManager struct {
+	config       *config.Config
+	agents       map[string]*SimpleAgent
+	taskManager  tm.TaskManager
+	autoAssigner *assignment.AutoAssigner
+	prProvider   git.PullRequestProvider
+	cloneManager *git.CloneManager
+	isRunning    map[string]bool
+	stopChannels map[string]chan struct{}
+}
+
+// NewSimpleAgentManager creates a simplified agent manager
+func NewSimpleAgentManager(cfg *config.Config, taskManager tm.TaskManager) (*SimpleAgentManager, error) {
+	// Create auto-assigner
+	autoAssigner := assignment.NewAutoAssigner(cfg.Agents)
+
+	// Create GitHub PR provider
+	githubConfig := git.GitHubConfig{
+		Token: cfg.GitHub.Token,
+	}
+	prProvider := git.NewGitHubPullRequestProvider(cfg.GitHub.Owner, cfg.GitHub.Repo, githubConfig)
+
+	// Create clone manager for per-agent Git repositories
+	repoURL := fmt.Sprintf("https://github.com/%s/%s.git", cfg.GitHub.Owner, cfg.GitHub.Repo)
+	workspacePath := filepath.Join(".", "workspace")
+	cloneManager := git.NewCloneManager(repoURL, workspacePath)
+
+	manager := &SimpleAgentManager{
+		config:       cfg,
+		agents:       make(map[string]*SimpleAgent),
+		taskManager:  taskManager,
+		autoAssigner: autoAssigner,
+		prProvider:   prProvider,
+		cloneManager: cloneManager,
+		isRunning:    make(map[string]bool),
+		stopChannels: make(map[string]chan struct{}),
+	}
+
+	// Initialize agents
+	if err := manager.initializeAgents(); err != nil {
+		return nil, fmt.Errorf("failed to initialize agents: %w", err)
+	}
+
+	return manager, nil
+}
+
+// initializeAgents creates agent instances from configuration
+func (am *SimpleAgentManager) initializeAgents() error {
+	for _, agentConfig := range am.config.Agents {
+		agent, err := am.createAgent(agentConfig)
+		if err != nil {
+			return fmt.Errorf("failed to create agent %s: %w", agentConfig.Name, err)
+		}
+		am.agents[agentConfig.Name] = agent
+	}
+	return nil
+}
+
+// createAgent creates a single agent instance
+func (am *SimpleAgentManager) createAgent(agentConfig config.AgentConfig) (*SimpleAgent, error) {
+	// Load system prompt
+	systemPrompt, err := am.loadSystemPrompt(agentConfig.SystemPromptFile)
+	if err != nil {
+		return nil, fmt.Errorf("failed to load system prompt: %w", err)
+	}
+
+	// Create LLM provider
+	llmConfig := llm.Config{
+		Provider: llm.ProviderOpenAI,
+		APIKey:   am.config.OpenAI.APIKey,
+		BaseURL:  am.config.OpenAI.BaseURL,
+		Timeout:  am.config.OpenAI.Timeout,
+	}
+	
+	provider, err := llm.CreateProvider(llmConfig)
+	if err != nil {
+		return nil, fmt.Errorf("failed to create LLM provider: %w", err)
+	}
+
+	agent := &SimpleAgent{
+		Name:         agentConfig.Name,
+		Role:         agentConfig.Role,
+		Model:        agentConfig.Model,
+		SystemPrompt: systemPrompt,
+		Provider:     provider,
+		MaxTokens:    agentConfig.MaxTokens,
+		Temperature:  agentConfig.Temperature,
+	}
+
+	return agent, nil
+}
+
+// loadSystemPrompt loads the system prompt from file
+func (am *SimpleAgentManager) loadSystemPrompt(filePath string) (string, error) {
+	content, err := os.ReadFile(filePath)
+	if err != nil {
+		return "", fmt.Errorf("failed to read system prompt file %s: %w", filePath, err)
+	}
+	return string(content), nil
+}
+
+// StartAgent starts an agent to process tasks in a loop
+func (am *SimpleAgentManager) StartAgent(agentName string, loopInterval time.Duration) error {
+	agent, exists := am.agents[agentName]
+	if !exists {
+		return fmt.Errorf("agent %s not found", agentName)
+	}
+
+	if am.isRunning[agentName] {
+		return fmt.Errorf("agent %s is already running", agentName)
+	}
+
+	stopChan := make(chan struct{})
+	am.stopChannels[agentName] = stopChan
+	am.isRunning[agentName] = true
+
+	go am.runAgentLoop(agent, loopInterval, stopChan)
+	
+	log.Printf("Started agent %s (%s) with %s model", agentName, agent.Role, agent.Model)
+	return nil
+}
+
+// StopAgent stops a running agent
+func (am *SimpleAgentManager) StopAgent(agentName string) error {
+	if !am.isRunning[agentName] {
+		return fmt.Errorf("agent %s is not running", agentName)
+	}
+
+	close(am.stopChannels[agentName])
+	delete(am.stopChannels, agentName)
+	am.isRunning[agentName] = false
+
+	log.Printf("Stopped agent %s", agentName)
+	return nil
+}
+
+// runAgentLoop runs the main processing loop for an agent
+func (am *SimpleAgentManager) runAgentLoop(agent *SimpleAgent, interval time.Duration, stopChan <-chan struct{}) {
+	ticker := time.NewTicker(interval)
+	defer ticker.Stop()
+
+	for {
+		select {
+		case <-stopChan:
+			log.Printf("Agent %s stopping", agent.Name)
+			return
+		case <-ticker.C:
+			if err := am.processAgentTasks(agent); err != nil {
+				log.Printf("Error processing tasks for agent %s: %v", agent.Name, err)
+			}
+		}
+	}
+}
+
+// processAgentTasks processes all assigned tasks for an agent
+func (am *SimpleAgentManager) processAgentTasks(agent *SimpleAgent) error {
+	// Get tasks assigned to this agent
+	tasks, err := am.taskManager.GetTasksByAssignee(agent.Name)
+	if err != nil {
+		return fmt.Errorf("failed to get tasks for agent %s: %w", agent.Name, err)
+	}
+
+	for _, task := range tasks {
+		if task.Status == tm.StatusPending || task.Status == tm.StatusInProgress {
+			if err := am.processTask(agent, task); err != nil {
+				log.Printf("Error processing task %s: %v", task.ID, err)
+				// Mark task as failed
+				task.Status = tm.StatusFailed
+				if err := am.taskManager.UpdateTask(task); err != nil {
+					log.Printf("Error updating failed task %s: %v", task.ID, err)
+				}
+			}
+		}
+	}
+
+	return nil
+}
+
+// processTask processes a single task with an agent
+func (am *SimpleAgentManager) processTask(agent *SimpleAgent, task *tm.Task) error {
+	ctx := context.Background()
+
+	log.Printf("Agent %s processing task %s: %s", agent.Name, task.ID, task.Title)
+
+	// Mark task as in progress
+	task.Status = tm.StatusInProgress
+	if err := am.taskManager.UpdateTask(task); err != nil {
+		return fmt.Errorf("failed to update task status: %w", err)
+	}
+
+	// Generate solution using LLM
+	solution, err := am.generateSolution(ctx, agent, task)
+	if err != nil {
+		return fmt.Errorf("failed to generate solution: %w", err)
+	}
+
+	// Create Git branch and commit solution
+	branchName := am.generateBranchName(task)
+	if err := am.createAndCommitSolution(branchName, task, solution, agent); err != nil {
+		return fmt.Errorf("failed to commit solution: %w", err)
+	}
+
+	// Create pull request
+	prURL, err := am.createPullRequest(ctx, task, solution, agent, branchName)
+	if err != nil {
+		return fmt.Errorf("failed to create pull request: %w", err)
+	}
+
+	// Update task as completed
+	task.Status = tm.StatusCompleted
+	task.Solution = solution
+	task.PullRequestURL = prURL
+	task.CompletedAt = &time.Time{}
+	*task.CompletedAt = time.Now()
+
+	if err := am.taskManager.UpdateTask(task); err != nil {
+		return fmt.Errorf("failed to update completed task: %w", err)
+	}
+
+	log.Printf("Task %s completed by agent %s. PR: %s", task.ID, agent.Name, prURL)
+	return nil
+}
+
+// generateSolution uses the agent's LLM to generate a solution
+func (am *SimpleAgentManager) generateSolution(ctx context.Context, agent *SimpleAgent, task *tm.Task) (string, error) {
+	prompt := am.buildTaskPrompt(task)
+
+	req := llm.ChatCompletionRequest{
+		Model: agent.Model,
+		Messages: []llm.Message{
+			{
+				Role:    llm.RoleSystem,
+				Content: agent.SystemPrompt,
+			},
+			{
+				Role:    llm.RoleUser,
+				Content: prompt,
+			},
+		},
+		MaxTokens:   agent.MaxTokens,
+		Temperature: agent.Temperature,
+	}
+
+	resp, err := agent.Provider.ChatCompletion(ctx, req)
+	if err != nil {
+		return "", fmt.Errorf("LLM request failed: %w", err)
+	}
+
+	if len(resp.Choices) == 0 {
+		return "", fmt.Errorf("no response from LLM")
+	}
+
+	return resp.Choices[0].Message.Content, nil
+}
+
+// buildTaskPrompt creates a detailed prompt for the LLM
+func (am *SimpleAgentManager) buildTaskPrompt(task *tm.Task) string {
+	return fmt.Sprintf(`Task: %s
+
+Priority: %s
+Description: %s
+
+Please provide a complete solution for this task. Include:
+1. Detailed implementation plan
+2. Code changes needed (if applicable)
+3. Files to be created or modified
+4. Testing considerations
+5. Any dependencies or prerequisites
+
+Your response should be comprehensive and actionable.`,
+		task.Title,
+		task.Priority,
+		task.Description)
+}
+
+// generateBranchName creates a Git branch name for the task
+func (am *SimpleAgentManager) generateBranchName(task *tm.Task) string {
+	// Clean title for use in branch name
+	cleanTitle := strings.ToLower(task.Title)
+	cleanTitle = strings.ReplaceAll(cleanTitle, " ", "-")
+	cleanTitle = strings.ReplaceAll(cleanTitle, "/", "-")
+	// Remove special characters
+	var result strings.Builder
+	for _, r := range cleanTitle {
+		if (r >= 'a' && r <= 'z') || (r >= '0' && r <= '9') || r == '-' {
+			result.WriteRune(r)
+		}
+	}
+	cleanTitle = result.String()
+	
+	// Limit length
+	if len(cleanTitle) > 40 {
+		cleanTitle = cleanTitle[:40]
+	}
+	
+	return fmt.Sprintf("%s%s-%s", am.config.Git.BranchPrefix, task.ID, cleanTitle)
+}
+
+// createAndCommitSolution creates a Git branch and commits the solution using per-agent clones
+// Each agent works in its own Git clone, eliminating concurrency issues
+func (am *SimpleAgentManager) createAndCommitSolution(branchName string, task *tm.Task, solution string, agent *SimpleAgent) error {
+	ctx := context.Background()
+	
+	// Get agent's dedicated Git clone
+	clonePath, err := am.cloneManager.GetAgentClonePath(agent.Name)
+	if err != nil {
+		return fmt.Errorf("failed to get agent clone: %w", err)
+	}
+	
+	log.Printf("Agent %s working in clone: %s", agent.Name, clonePath)
+
+	// Refresh the clone with latest changes
+	if err := am.cloneManager.RefreshAgentClone(agent.Name); err != nil {
+		log.Printf("Warning: Failed to refresh clone for agent %s: %v", agent.Name, err)
+	}
+
+	// All Git operations use the agent's clone directory
+	gitCmd := func(args ...string) *exec.Cmd {
+		return exec.CommandContext(ctx, "git", append([]string{"-C", clonePath}, args...)...)
+	}
+
+	// Ensure we're on main branch before creating new branch
+	cmd := gitCmd("checkout", "main")
+	if err := cmd.Run(); err != nil {
+		// Try master branch if main doesn't exist
+		cmd = gitCmd("checkout", "master")
+		if err := cmd.Run(); err != nil {
+			return fmt.Errorf("failed to checkout main/master branch: %w", err)
+		}
+	}
+
+	// Create branch
+	cmd = gitCmd("checkout", "-b", branchName)
+	if err := cmd.Run(); err != nil {
+		return fmt.Errorf("failed to create branch: %w", err)
+	}
+
+	// Create solution file in agent's clone
+	solutionDir := filepath.Join(clonePath, "tasks", "solutions")
+	if err := os.MkdirAll(solutionDir, 0755); err != nil {
+		return fmt.Errorf("failed to create solution directory: %w", err)
+	}
+
+	solutionFile := filepath.Join(solutionDir, fmt.Sprintf("%s-solution.md", task.ID))
+	solutionContent := fmt.Sprintf(`# Solution for Task: %s
+
+**Agent:** %s (%s)  
+**Model:** %s  
+**Completed:** %s
+
+## Task Description
+%s
+
+## Solution
+%s
+
+---
+*Generated by Staff AI Agent System*
+`, task.Title, agent.Name, agent.Role, agent.Model, time.Now().Format(time.RFC3339), task.Description, solution)
+
+	if err := os.WriteFile(solutionFile, []byte(solutionContent), 0644); err != nil {
+		return fmt.Errorf("failed to write solution file: %w", err)
+	}
+
+	// Stage files
+	relativeSolutionFile := filepath.Join("tasks", "solutions", fmt.Sprintf("%s-solution.md", task.ID))
+	cmd = gitCmd("add", relativeSolutionFile)
+	if err := cmd.Run(); err != nil {
+		return fmt.Errorf("failed to stage files: %w", err)
+	}
+
+	// Commit changes
+	commitMsg := am.buildCommitMessage(task, agent)
+	cmd = gitCmd("commit", "-m", commitMsg)
+	if err := cmd.Run(); err != nil {
+		return fmt.Errorf("failed to commit: %w", err)
+	}
+
+	// Push branch
+	cmd = gitCmd("push", "-u", "origin", branchName)
+	if err := cmd.Run(); err != nil {
+		return fmt.Errorf("failed to push branch: %w", err)
+	}
+
+	log.Printf("Agent %s successfully pushed branch %s", agent.Name, branchName)
+	return nil
+}
+
+// buildCommitMessage creates a commit message from template
+func (am *SimpleAgentManager) buildCommitMessage(task *tm.Task, agent *SimpleAgent) string {
+	template := am.config.Git.CommitMessageTemplate
+	
+	replacements := map[string]string{
+		"{task_id}":    task.ID,
+		"{task_title}": task.Title,
+		"{agent_name}": agent.Name,
+		"{solution}":   "See solution file for details",
+	}
+
+	result := template
+	for placeholder, value := range replacements {
+		result = strings.ReplaceAll(result, placeholder, value)
+	}
+
+	return result
+}
+
+// createPullRequest creates a GitHub pull request
+func (am *SimpleAgentManager) createPullRequest(ctx context.Context, task *tm.Task, solution string, agent *SimpleAgent, branchName string) (string, error) {
+	title := fmt.Sprintf("Task %s: %s", task.ID, task.Title)
+	
+	// Build PR description from template
+	description := am.buildPRDescription(task, solution, agent)
+	
+	options := git.PullRequestOptions{
+		Title:       title,
+		Description: description,
+		HeadBranch:  branchName,
+		BaseBranch:  "main",
+		Labels:      []string{"ai-generated", "staff-agent", strings.ToLower(agent.Role)},
+		Draft:       false,
+	}
+
+	pr, err := am.prProvider.CreatePullRequest(ctx, options)
+	if err != nil {
+		return "", fmt.Errorf("failed to create PR: %w", err)
+	}
+
+	return fmt.Sprintf("https://github.com/%s/%s/pull/%d", am.config.GitHub.Owner, am.config.GitHub.Repo, pr.Number), nil
+}
+
+// buildPRDescription creates PR description from template
+func (am *SimpleAgentManager) buildPRDescription(task *tm.Task, solution string, agent *SimpleAgent) string {
+	template := am.config.Git.PRTemplate
+	
+	// Truncate solution for PR if too long
+	truncatedSolution := solution
+	if len(solution) > 1000 {
+		truncatedSolution = solution[:1000] + "...\n\n*See solution file for complete details*"
+	}
+	
+	replacements := map[string]string{
+		"{task_id}":          task.ID,
+		"{task_title}":       task.Title,
+		"{task_description}": task.Description,
+		"{agent_name}":       fmt.Sprintf("%s (%s)", agent.Name, agent.Role),
+		"{priority}":         string(task.Priority),
+		"{solution}":         truncatedSolution,
+		"{files_changed}":    fmt.Sprintf("- `tasks/solutions/%s-solution.md`", task.ID),
+	}
+
+	result := template
+	for placeholder, value := range replacements {
+		result = strings.ReplaceAll(result, placeholder, value)
+	}
+
+	return result
+}
+
+// AutoAssignTask automatically assigns a task to the best matching agent
+func (am *SimpleAgentManager) AutoAssignTask(taskID string) error {
+	task, err := am.taskManager.GetTask(taskID)
+	if err != nil {
+		return fmt.Errorf("failed to get task: %w", err)
+	}
+
+	agentName, err := am.autoAssigner.AssignTask(task)
+	if err != nil {
+		return fmt.Errorf("failed to auto-assign task: %w", err)
+	}
+
+	task.Assignee = agentName
+	if err := am.taskManager.UpdateTask(task); err != nil {
+		return fmt.Errorf("failed to update task assignment: %w", err)
+	}
+
+	explanation := am.autoAssigner.GetRecommendationExplanation(task, agentName)
+	log.Printf("Auto-assigned task %s to %s: %s", taskID, agentName, explanation)
+
+	return nil
+}
+
+// GetAgentStatus returns the status of all agents
+func (am *SimpleAgentManager) GetAgentStatus() map[string]SimpleAgentStatus {
+	status := make(map[string]SimpleAgentStatus)
+	
+	for name, agent := range am.agents {
+		status[name] = SimpleAgentStatus{
+			Name:      agent.Name,
+			Role:      agent.Role,
+			Model:     agent.Model,
+			IsRunning: am.isRunning[name],
+		}
+	}
+	
+	return status
+}
+
+// SimpleAgentStatus represents the status of an agent
+type SimpleAgentStatus struct {
+	Name      string `json:"name"`
+	Role      string `json:"role"`
+	Model     string `json:"model"`
+	IsRunning bool   `json:"is_running"`
+}
+
+// IsAgentRunning checks if an agent is currently running
+func (am *SimpleAgentManager) IsAgentRunning(agentName string) bool {
+	return am.isRunning[agentName]
+}
+
+// Close shuts down the agent manager
+func (am *SimpleAgentManager) Close() error {
+	// Stop all running agents
+	for agentName := range am.isRunning {
+		if am.isRunning[agentName] {
+			am.StopAgent(agentName)
+		}
+	}
+
+	// Close all LLM providers
+	for _, agent := range am.agents {
+		if err := agent.Provider.Close(); err != nil {
+			log.Printf("Error closing provider for agent %s: %v", agent.Name, err)
+		}
+	}
+
+	// Cleanup all agent Git clones
+	if err := am.cloneManager.CleanupAllClones(); err != nil {
+		log.Printf("Error cleaning up agent clones: %v", err)
+	}
+
+	return nil
+}
\ No newline at end of file
