| import os | |
| from typing import List, Dict, Any | |
| from openai import OpenAI | |
| class OpenAILLM: | |
| def __init__(self,model_chat:str = "gpt-4o",model_translate:str = "gpt-4o", model_summarize:str = "gpt-4o"): | |
| api_key = os.environ.get("OPENAI_API_KEY2") | |
| if not api_key: | |
| raise RuntimeError("OPENAI_API_KEY2 is not set in environment variables.") | |
| self.client = OpenAI(api_key=api_key) | |
| self.model_chat = model_chat | |
| self.model_translate = model_translate | |
| self.model_summarize = model_summarize | |
| def generate_ceo_message(self,meta, kpi:Dict[str,float],esg_row:List[Dict[str,Any]])->str: | |
| prompt = ( | |
| "以下の企業情報・KPI・ESG指標をもとに、日本語で200字程度のCEOメッセージ草案を出力してください。" | |
| "投資家に伝わる簡潔なトーンで、過度な形容表現は避けてください。\n\n" | |
| f"企業情報: {meta.model_dump()}\n" | |
| f"KPI: {kpi}\n" | |
| f"ESG指標: {esg_row}\n" | |
| ) | |
| rsp = self.client.chat.completions.create( | |
| model=self.model_chat, | |
| messages=[{"role": "user", "content": prompt}], | |
| temperature=0.3, | |
| ) | |
| return rsp.choices[0].message.content.strip() | |
| def generate_risk_opportunity(self,meta,kpi:Dict[str,float],esg_row:List[Dict[str,Any]])->str: | |
| prompt = ( | |
| "以下の情報から、日本語で200字程度のリスクと機会の草案を出力してください。" | |
| "定量/定性のバランスを取り、具体的な観点を1-2点挙げてください。\n\n" | |
| f"企業情報: {meta.model_dump()}\n" | |
| f"KPI: {kpi}\n" | |
| f"ESG: {esg_row}\n" | |
| ) | |
| rsp = self.client.chat.completions.create( | |
| model=self.model_chat, | |
| messages=[{"role": "user", "content": prompt}], | |
| temperature=0.3, | |
| ) | |
| return rsp.choices[0].message.content.strip() | |
| def translate_text(self, texts:List[str], target_language: str) -> List[str]: | |
| if not texts: | |
| return texts | |
| system=( | |
| "You are precise financial/ESG translator.Preserve numbers,units,and proper nouns." | |
| "Keep tone concise,suitable for investor reports." | |
| ) | |
| SEP = "\n<<<SEP>>>\n" | |
| joined = SEP.join(texts) | |
| prompt = f"Translate the following content to {target_language}.Keep layout minimal.\n\n{joined}" | |
| rsp = self.client.chat.completions.create( | |
| model=self.model_translate, | |
| messages=[ | |
| {"role": "user", "content": system},{"role": "user", "content": prompt} | |
| ], | |
| temperature=0.2, | |
| ) | |
| out = rsp.choices[0].message.content | |
| parts = [p.strip() for p in out.split("<<<SEP>>>")] | |
| if len(parts) != len(texts): | |
| parts = [out]+texts[1:] | |
| parts = parts[:len(texts)] | |
| return parts |