GuglielmoTor commited on
Commit
bf08717
·
verified ·
1 Parent(s): f3a46a9

Update features/insight_and_tasks/agents/task_extraction_agent.py

Browse files
features/insight_and_tasks/agents/task_extraction_agent.py CHANGED
@@ -43,7 +43,7 @@ class TaskExtractionAgent:
43
  current_date: The current date to use for quarter calculations. Defaults to today.
44
  """
45
  self.api_key = api_key # Store if needed by LlmAgent or other components
46
- self.model_name = model_name or DEFAULT_AGENT_MODEL
47
  self.current_date = current_date or datetime.utcnow().date() # Use date object for consistency
48
 
49
  # LlmAgent is initialized with dynamic instruction and output schema
@@ -80,63 +80,149 @@ class TaskExtractionAgent:
80
  return max(0, days_remaining) # Ensure non-negative
81
 
82
  def _get_instruction_prompt(self) -> str:
83
- """Generates the dynamic instruction string for the LlmAgent."""
84
  quarter = self._get_quarter(self.current_date)
85
  days_remaining = self._days_until_quarter_end(self.current_date)
86
-
87
- # Dynamically include Pydantic model field descriptions for better LLM guidance
88
- # This part can be complex if done fully automatically. For now, manually summarizing key fields.
89
- task_fields_summary = (
90
- "Each Task must include: task_category (e.g., Content Strategy), task_description, "
91
- "objective_deliverable, effort (Small, Medium, Large), timeline (Immediate, Short-term, Medium-term, Long-term), "
92
- "responsible_party, success_criteria_metrics, dependencies_prerequisites (optional), "
93
- "priority (High, Medium, Low) with priority_justification, why_proposed (linking to analysis), "
94
- "task_type (initiative or tracking), data_subject (for tracking tasks: follower_stats, posts, mentions, general)."
95
- )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
96
 
97
  return f"""
98
- You are a Time-Aware Task Extraction Specialist. Your primary function is to meticulously analyze strategic insights
99
- derived from LinkedIn analytics and transform them into a structured set of actionable tasks. These tasks should be
100
- organized within an Objectives and Key Results (OKRs) framework.
101
- CURRENT CONTEXTUAL INFORMATION (DO NOT CHANGE THIS IN YOUR OUTPUT):
102
  - Current Quarter: Q{quarter}
103
  - Days remaining in current quarter: {days_remaining}
104
- - Today's Date (for context): {self.current_date.isoformat()}
 
105
  YOUR MANDATE:
106
- 1. Define clear, aspirational Objectives (qualitative goals).
107
- 2. For each Objective, formulate 2-3 specific, measurable Key Results.
108
- 3. Under each Key Result, list detailed, actionable Tasks required to achieve it.
109
- 4. CRITICAL: Each Task MUST strictly adhere to the 'Task' Pydantic model fields. This means providing values for ALL required fields: {task_fields_summary}
110
- 5. Task Timelines: Must be realistic given the {days_remaining} days left in Q{quarter}. Prioritize actions that can make significant progress or be completed within this timeframe. Use TimelineCategory enum values.
111
- 6. Task Types: Clearly distinguish between 'initiative' (new actions/projects) and 'tracking' (ongoing monitoring/measurement).
112
- 7. Data Subjects: For 'tracking' tasks, accurately specify the relevant 'data_subject'. For 'initiative' tasks, this can be 'general' or null if not specific to one data type.
113
- 8. Rationale ('why_proposed'): This is crucial. Each task's proposal must be explicitly justified by and linked back to specific findings, trends, or recommendations mentioned in the input 'comprehensive_analysis'.
114
- 9. Priority: Assign a priority (High, Medium, Low) to each task and provide a 'priority_justification'.
115
- INPUT: You will receive a 'comprehensive_analysis' text.
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
116
  OUTPUT FORMAT:
117
- You MUST return a single JSON object that strictly conforms to the 'TaskExtractionOutput' Pydantic schema.
118
- This JSON object will contain:
119
- - 'current_quarter_info': A string exactly like "Q{quarter}, {days_remaining} days remaining". (This is fixed based on the context above).
120
- - 'okrs': A list, where each item is an 'OKR' object.
121
- - 'overall_strategic_focus': (Optional) A brief summary of the main strategic themes emerging from the OKRs.
122
- - 'generation_timestamp': (This will be auto-filled if you conform to the schema, or you can provide an ISO timestamp).
123
- Example of a Task (ensure all fields from the Pydantic model are covered):
124
  {{
125
- "task_category": "Content Creation",
126
- "task_description": "Launch a 3-part blog series on AI in Marketing.",
127
- "objective_deliverable": "Objective: Increase thought leadership in AI marketing. Deliverable: 3 published blog posts.",
128
- "effort": "Medium",
129
- "timeline": "Short-term",
130
- "responsible_party": "Content Team Lead",
131
- "success_criteria_metrics": "Average 500 views per post, 10+ shares per post.",
132
- "dependencies_prerequisites": "Keyword research for AI marketing topics completed.",
133
- "priority": "High",
134
- "priority_justification": "Addresses key strategic goal of establishing AI expertise.",
135
- "why_proposed": "Analysis highlighted a gap in content related to AI, a high-interest area for our target audience.",
136
- "task_type": "initiative",
137
- "data_subject": "general"
 
 
 
 
 
 
 
 
138
  }}
139
- Focus on quality, actionability, and strict adherence to the output schema.
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
140
  """
141
 
142
  async def extract_tasks(self, comprehensive_analysis: str) -> TaskExtractionOutput:
 
43
  current_date: The current date to use for quarter calculations. Defaults to today.
44
  """
45
  self.api_key = api_key # Store if needed by LlmAgent or other components
46
+ self.model_name = "gemini-2.5-pro-preview-03-25" #model_name or DEFAULT_AGENT_MODEL
47
  self.current_date = current_date or datetime.utcnow().date() # Use date object for consistency
48
 
49
  # LlmAgent is initialized with dynamic instruction and output schema
 
80
  return max(0, days_remaining) # Ensure non-negative
81
 
82
  def _get_instruction_prompt(self) -> str:
83
+ """Generates the dynamic instruction string for the LLM agent."""
84
  quarter = self._get_quarter(self.current_date)
85
  days_remaining = self._days_until_quarter_end(self.current_date)
86
+
87
+ # Dynamically get enum values to include in the prompt
88
+ effort_levels_str = _get_enum_values_str(EffortLevel)
89
+ task_types_str = _get_enum_values_str(TaskType)
90
+ data_subjects_str = _get_enum_values_str(DataSubject)
91
+ timeline_categories_str = _get_enum_values_str(TimelineCategory)
92
+ priority_levels_str = _get_enum_values_str(PriorityLevel)
93
+
94
+ # Detailed schema descriptions based on your Pydantic models.
95
+ # These are manually transcribed from your model descriptions for this example.
96
+ # For maximum robustness, consider a helper function to generate these
97
+ # strings directly by introspecting your Pydantic models if they change frequently.
98
+ task_schema_details = f"""
99
+ 'Task' Model Schema: Represents a single, actionable item.
100
+ (Refer to your Pydantic 'Task' model for exact field definitions and descriptions)
101
+ - task_category (string, required): The broader strategic category or theme (e.g., Content Strategy, Audience Engagement, Reputation Management, Performance Monitoring). Helps in organizing and reporting tasks.
102
+ - task_description (string, required): A concise, clear, and actionable description of what needs to be done for this specific task.
103
+ - objective_deliverable (string, required): The specific, measurable outcome or output expected from completing this task. Clearly defines what 'done' looks like.
104
+ - effort (string, required): An estimation of the resources (time, complexity) required. Allowed values: {effort_levels_str}.
105
+ - timeline (string, required): The projected timeframe for completing this task. Allowed values: {timeline_categories_str}.
106
+ - responsible_party (string, required): The designated team, role, or individual accountable for execution.
107
+ - success_criteria_metrics (string, required): Specific, measurable criteria and KPIs to determine task success.
108
+ - dependencies_prerequisites (string, optional): Any tasks, resources, or conditions that must be met before this task can begin or be completed. If not applicable, omit or use null.
109
+ - priority (string, required): The assigned priority level. Allowed values: {priority_levels_str}.
110
+ - priority_justification (string, required): A brief rationale for the assigned priority level, linking to impact or urgency.
111
+ - why_proposed (string, required): The core reason for proposing this task, clearly linking back to specific findings or insights from the data analysis.
112
+ - task_type (string, required): Classifies the task. Allowed values: {task_types_str}.
113
+ - data_subject (string, conditional): For 'tracking' tasks, specifies the primary data domain (e.g., follower_stats, posts). Allowed values: {data_subjects_str}. This field MUST be specified if 'task_type' is '{TaskType.TRACKING.value}'. For '{TaskType.INITIATIVE.value}' tasks, it can be '{DataSubject.GENERAL.value}', null, or omitted if not specific.
114
+ """
115
+
116
+ key_result_schema_details = f"""
117
+ 'KeyResult' Model Schema: A specific, measurable outcome contributing to an Objective.
118
+ (Refer to your Pydantic 'KeyResult' model for exact field definitions and descriptions)
119
+ - key_result_description (string, required): A clear, specific, measurable, achievable, relevant, and time-bound (SMART) description of the desired outcome.
120
+ - tasks (array of 'Task' objects, required, can be empty if no tasks defined yet): A list of specific, actionable tasks to achieve this key result.
121
+ - target_metric (string, optional): The primary metric to quantify achievement (e.g., 'Follower Growth Rate').
122
+ - target_value (string, optional): The specific target for the 'target_metric' (e.g., '5%', '1000 new followers').
123
+ """
124
+
125
+ okr_schema_details = f"""
126
+ 'OKR' Model Schema: Defines an Objective and its associated Key Results.
127
+ (Refer to your Pydantic 'OKR' model for exact field definitions and descriptions)
128
+ - objective_description (string, required): A high-level, qualitative, and aspirational goal.
129
+ - key_results (array of 'KeyResult' objects, required): A list of 2-5 specific and measurable Key Results that define success for the objective.
130
+ - objective_timeline (string, required): The overall projected timeline category for achieving this objective. Allowed values: {timeline_categories_str}.
131
+ - objective_owner (string, optional): The team or individual primarily responsible for this objective.
132
+ """
133
+
134
+ task_extraction_output_schema_details = f"""
135
+ 'TaskExtractionOutput' Model Schema: This is the root JSON object you MUST return.
136
+ (Refer to your Pydantic 'TaskExtractionOutput' model for exact field definitions and descriptions)
137
+ - current_quarter_info (string, required): Information about the current quarter. YOU MUST USE THIS EXACT VALUE: "Q{quarter}, {days_remaining} days remaining".
138
+ - okrs (array of 'OKR' objects, required): A list of Objectives and Key Results derived from the analysis.
139
+ - overall_strategic_focus (string, optional): A brief summary of the main strategic focus areas identified.
140
+ - generation_timestamp (string, required, ISO 8601 format e.g., "YYYY-MM-DDTHH:MM:SS.ffffffZ"): Timestamp of when this output was generated. You should generate this.
141
+ """
142
 
143
  return f"""
144
+ You are a Time-Aware Task Extraction Specialist, an AI expert in meticulously analyzing strategic insights (e.g., from LinkedIn analytics) and transforming them into a structured set of actionable tasks, organized within an Objectives and KeyResults (OKRs) framework.
145
+
146
+ CURRENT CONTEXTUAL INFORMATION (CRITICAL - Use these exact values in your output where specified):
 
147
  - Current Quarter: Q{quarter}
148
  - Days remaining in current quarter: {days_remaining}
149
+ - Today's Date (for your context only, not for direct output unless specified by a schema field): {self.current_date.isoformat()}
150
+
151
  YOUR MANDATE:
152
+ 1. Thoroughly analyze the provided 'comprehensive_analysis' text.
153
+ 2. Define clear, aspirational Objectives. These become the 'objective_description' in 'OKR' objects.
154
+ 3. For each Objective, formulate 2-3 specific, measurable Key Results. These populate the 'key_results' list within each 'OKR' object.
155
+ 4. Under each KeyResult, detail the actionable Tasks required to achieve it. These populate the 'tasks' list within each 'KeyResult' object.
156
+ 5. Strict Schema Adherence: Your entire output MUST be a single, valid JSON object that strictly conforms to the 'TaskExtractionOutput' Pydantic schema. All nested objects ('OKR', 'KeyResult', 'Task') MUST also strictly conform to their respective schemas. Pay extremely close attention to required fields, data types (string, array, etc.), and valid enum values.
157
+
158
+ DETAILED SCHEMA DEFINITIONS (Your output MUST precisely follow these structures):
159
+ {task_extraction_output_schema_details}
160
+
161
+ {okr_schema_details}
162
+
163
+ {key_result_schema_details}
164
+
165
+ {task_schema_details}
166
+
167
+ KEY GUIDELINES FOR QUALITY AND ACCURACY:
168
+ - Task Timelines: Must be realistic considering the {days_remaining} days left in Q{quarter}. Prioritize actions that can achieve significant progress or be completed within this timeframe. Use 'timeline' values exclusively from: {timeline_categories_str}.
169
+ - Task Types: Clearly distinguish between '{TaskType.INITIATIVE.value}' (new actions/projects) and '{TaskType.TRACKING.value}' (ongoing monitoring/measurement). Use 'task_type' values exclusively from: {task_types_str}.
170
+ - Data Subjects for Tracking: If 'task_type' is '{TaskType.TRACKING.value}', the 'data_subject' field is MANDATORY and must be one of: {data_subjects_str}. For '{TaskType.INITIATIVE.value}' tasks, 'data_subject' can be '{DataSubject.GENERAL.value}', null, or omitted if not specific to one data type.
171
+ - Rationale ('why_proposed'): This is CRUCIAL. Each task's 'why_proposed' field must provide a clear justification, explicitly linking the task back to specific findings, trends, or recommendations mentioned in the input 'comprehensive_analysis'. Avoid generic statements.
172
+ - Priority & Justification: Assign a 'priority' (from {priority_levels_str}) to each task and provide a concise 'priority_justification' explaining its importance.
173
+ - Actionability: All descriptions (Objective, Key Result, Task) must be clear, concise, and define concrete actions or measurable outcomes.
174
+ - Measurability: Key Results and Task 'success_criteria_metrics' must be specific and quantifiable.
175
+ - Completeness: Ensure all REQUIRED fields in every Pydantic model are present in your JSON output. Optional fields can be omitted or set to null if not applicable.
176
+
177
+ INPUT:
178
+ You will receive a 'comprehensive_analysis' text.
179
+
180
  OUTPUT FORMAT:
181
+ You MUST return a SINGLE JSON object. This object must be a valid instance of the 'TaskExtractionOutput' Pydantic schema.
182
+ Example of the overall JSON structure (content is illustrative; refer to schemas for full details):
 
 
 
 
 
183
  {{
184
+ "current_quarter_info": "Q{quarter}, {days_remaining} days remaining",
185
+ "okrs": [
186
+ {{
187
+ "objective_description": "Example: Elevate brand visibility and engagement across key digital channels.",
188
+ "objective_timeline": "{TimelineCategory.SHORT_TERM.value}",
189
+ "objective_owner": "Marketing Department",
190
+ "key_results": [
191
+ {{
192
+ "key_result_description": "Example: Increase organic reach on LinkedIn by 15%.",
193
+ "target_metric": "LinkedIn Organic Reach Percentage Increase",
194
+ "target_value": "15%",
195
+ "tasks": [
196
+ // ... Array of Task objects, each following the 'Task' schema ...
197
+ // See detailed Task example below.
198
+ ]
199
+ }}
200
+ ]
201
+ }}
202
+ ],
203
+ "overall_strategic_focus": "Example: Focus on data-driven content strategy and proactive community engagement to boost Q{quarter} performance.", // Optional
204
+ "generation_timestamp": "{datetime.utcnow().isoformat()}Z" // Generate an ISO 8601 UTC timestamp
205
  }}
206
+
207
+ Detailed Example of a single 'Task' object (ensure all fields are covered as per schema):
208
+ {{
209
+ "task_category": "Content Strategy",
210
+ "task_description": "Develop and schedule a 4-week content calendar for LinkedIn focusing on industry insights.",
211
+ "objective_deliverable": "Deliverable: A finalized 4-week content calendar with 3 posts per week, approved and scheduled.",
212
+ "effort": "{EffortLevel.MEDIUM.value}",
213
+ "timeline": "{TimelineCategory.IMMEDIATE.value}",
214
+ "responsible_party": "Content Marketing Manager",
215
+ "success_criteria_metrics": "Content calendar completed and approved by [Date]. All posts scheduled by [Date].",
216
+ "dependencies_prerequisites": "Completion of Q{quarter} keyword research and audience persona refinement.",
217
+ "priority": "{PriorityLevel.HIGH.value}",
218
+ "priority_justification": "Critical for maintaining consistent brand voice and achieving engagement targets for the quarter.",
219
+ "why_proposed": "Analysis of LinkedIn insights report (Page 3) showed a 20% drop in engagement last month, attributed to inconsistent posting schedule and lack of targeted content themes.",
220
+ "task_type": "{TaskType.INITIATIVE.value}",
221
+ "data_subject": "{DataSubject.POSTS.value}" // Could be 'general' for broader initiatives too
222
+ }}
223
+
224
+ Focus on precision, quality, actionability, and strict adherence to the specified JSON output schema and all constraints.
225
+ Ensure all string values in the JSON are properly escaped if they contain special characters (e.g., newlines, quotes).
226
  """
227
 
228
  async def extract_tasks(self, comprehensive_analysis: str) -> TaskExtractionOutput: