update personas to add Tone
This commit is contained in:
@@ -47,18 +47,36 @@ def setup_logging():
|
||||
if os.path.exists(LOG_FILE):
|
||||
with open(LOG_FILE, 'r') as f:
|
||||
lines = f.readlines()
|
||||
cutoff = datetime.now(timezone.utc) - timedelta(days=LOG_PRUNE_DAYS)
|
||||
pruned_lines = []
|
||||
|
||||
# Group lines into log entries based on timestamp pattern
|
||||
log_entries = []
|
||||
current_entry = []
|
||||
timestamp_pattern = re.compile(r'^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2},\d{3}')
|
||||
|
||||
for line in lines:
|
||||
if timestamp_pattern.match(line):
|
||||
if current_entry:
|
||||
log_entries.append(''.join(current_entry))
|
||||
current_entry = [line]
|
||||
else:
|
||||
current_entry.append(line)
|
||||
|
||||
if current_entry:
|
||||
log_entries.append(''.join(current_entry))
|
||||
|
||||
cutoff = datetime.now(timezone.utc) - timedelta(days=LOG_PRUNE_DAYS)
|
||||
pruned_entries = []
|
||||
for entry in log_entries:
|
||||
try:
|
||||
timestamp = datetime.strptime(line[:19], '%Y-%m-%d %H:%M:%S').replace(tzinfo=timezone.utc)
|
||||
timestamp = datetime.strptime(entry[:19], '%Y-%m-%d %H:%M:%S').replace(tzinfo=timezone.utc)
|
||||
if timestamp > cutoff:
|
||||
pruned_lines.append(line)
|
||||
pruned_entries.append(entry)
|
||||
except ValueError:
|
||||
logging.warning(f"Skipping malformed log line: {line.strip()[:50]}...")
|
||||
logging.warning(f"Skipping malformed log entry (no timestamp): {entry[:50]}...")
|
||||
continue
|
||||
|
||||
with open(LOG_FILE, 'w') as f:
|
||||
f.writelines(pruned_lines)
|
||||
f.writelines(pruned_entries)
|
||||
|
||||
logging.basicConfig(
|
||||
filename=LOG_FILE,
|
||||
|
||||
+58
-34
@@ -104,42 +104,66 @@ CTAS = [
|
||||
]
|
||||
|
||||
SUMMARY_PERSONA_PROMPTS = {
|
||||
"Visionary Editor": (
|
||||
"You’re a commanding food editor with a borderless view. Summarize this article in a polished, decisive tone, like shaping a premier food mag, but with a casual twist—think bold vibes like 'This is unreal!'. "
|
||||
"Visionary Editor": {
|
||||
"description": "a commanding food editor with a borderless view",
|
||||
"tone": "a polished and insightful tone, like 'This redefines culinary excellence.'",
|
||||
"prompt": (
|
||||
"You’re {description}. Summarize this article in {tone}. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally without mentioning the source name or URL directly in the text, with a slight Upworthy/Buzzfeed flair style. "
|
||||
"Add a bold take and end with a clickbait-y question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
),
|
||||
"Foodie Critic": (
|
||||
"You’re a seasoned foodie reviewer with a sharp eye. Summarize this article in a pro yet lively tone, like a top food mag with a playful edge—think 'This bangs!'. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally without mentioning the source name or URL directly in the text, with a slight Upworthy/Buzzfeed flair style. "
|
||||
"Add a subtle opinion and end with a clickbait-y question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
),
|
||||
"Trend Scout": (
|
||||
"You’re a forward-thinking editor obsessed with trends. Summarize this article in an enthusiastic voice, like 'This is the future, fam!'. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally without mentioning the source name or URL directly in the text, with a slight Upworthy/Buzzfeed flair style. "
|
||||
"Predict what’s next and end with a clickbait-y question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
),
|
||||
"Culture Connoisseur": (
|
||||
"You’re a cultured food writer who loves storytelling. Summarize this article in a warm, reflective tone with a kick, like 'This feels different, right?'. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally without mentioning the source name or URL directly in the text, with a slight Upworthy/Buzzfeed flair style. "
|
||||
"Add a thoughtful observation and end with a clickbait-y question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
),
|
||||
"African-American Soul Food Sage": (
|
||||
"You’re a vibrant storyteller rooted in African-American culinary heritage. Summarize this article in a soulful tone, like 'This got that heat, y’all!'. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally without mentioning the source name or URL directly in the text, with a slight Upworthy/Buzzfeed flair style. "
|
||||
"Add a heritage twist and end with a clickbait-y question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
),
|
||||
"Global Street Food Nomad": (
|
||||
"You’re an adventurous explorer of global street food. Summarize this article in a bold, gritty tone with a spin, like 'This is straight fire!'. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally without mentioning the source name or URL directly in the text, with a slight Upworthy/Buzzfeed flair style. "
|
||||
"Drop a street-level insight and end with a clickbait-y question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
"Write naturally in a refined yet engaging style, with a slight Upworthy/Buzzfeed flair, without mentioning the source name or URL directly in the text. "
|
||||
"Add a bold take and end with a thought-provoking question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
)
|
||||
},
|
||||
"Foodie Critic": {
|
||||
"description": "a seasoned foodie reviewer with a sharp eye",
|
||||
"tone": "a professional yet engaging tone, like 'This dish is a revelation.'",
|
||||
"prompt": (
|
||||
"You’re {description}. Summarize this article in {tone}. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally in a refined yet engaging style, with a slight Upworthy/Buzzfeed flair, without mentioning the source name or URL directly in the text. "
|
||||
"Add a subtle opinion and end with a thought-provoking question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
)
|
||||
},
|
||||
"Trend Scout": {
|
||||
"description": "a forward-thinking editor obsessed with trends",
|
||||
"tone": "an insightful and forward-looking tone, like 'This sets the stage for what’s next.'",
|
||||
"prompt": (
|
||||
"You’re {description}. Summarize this article in {tone}. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally in a refined yet engaging style, with a slight Upworthy/Buzzfeed flair, without mentioning the source name or URL directly in the text. "
|
||||
"Predict what’s next and end with a thought-provoking question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
)
|
||||
},
|
||||
"Culture Connoisseur": {
|
||||
"description": "a cultured food writer who loves storytelling",
|
||||
"tone": "a warm and thoughtful tone, like 'This evokes a sense of tradition.'",
|
||||
"prompt": (
|
||||
"You’re {description}. Summarize this article in {tone}. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally in a refined yet engaging style, with a slight Upworthy/Buzzfeed flair, without mentioning the source name or URL directly in the text. "
|
||||
"Add a thoughtful observation and end with a thought-provoking question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
)
|
||||
},
|
||||
"African-American Soul Food Sage": {
|
||||
"description": "a vibrant storyteller rooted in African-American culinary heritage",
|
||||
"tone": "a heartfelt and authentic tone, like 'This captures the essence of heritage.'",
|
||||
"prompt": (
|
||||
"You’re {description}. Summarize this article in {tone}. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally in a refined yet engaging style, with a slight Upworthy/Buzzfeed flair, without mentioning the source name or URL directly in the text. "
|
||||
"Add a heritage twist and end with a thought-provoking question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
)
|
||||
},
|
||||
"Global Street Food Nomad": {
|
||||
"description": "an adventurous explorer of global street food",
|
||||
"tone": "a bold and adventurous tone, like 'This takes you on a global journey.'",
|
||||
"prompt": (
|
||||
"You’re {description}. Summarize this article in {tone}. "
|
||||
"Explore a wide range of food-related topics, skip recipes. Generate exactly {num_paragraphs} paragraphs, 60-80 words each, full thoughts, with a single \n break. "
|
||||
"Write naturally in a refined yet engaging style, with a slight Upworthy/Buzzfeed flair, without mentioning the source name or URL directly in the text. "
|
||||
"Drop a street-level insight and end with a thought-provoking question like Neil Patel would do to boost engagement! Do not include emojis in the summary."
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
REDDIT_CLIENT_ID = os.getenv("REDDIT_CLIENT_ID")
|
||||
|
||||
+12
-1
@@ -339,7 +339,18 @@ def generate_title_from_summary(summary):
|
||||
def summarize_with_gpt4o(content, source_name, link, interest_score=0, extra_prompt=""):
|
||||
try:
|
||||
persona = select_best_persona(interest_score, content)
|
||||
prompt = SUMMARY_PERSONA_PROMPTS.get(persona, "Write a concise, engaging summary that captures the essence of the content for food lovers.")
|
||||
# Access the persona configuration
|
||||
persona_config = SUMMARY_PERSONA_PROMPTS.get(persona, {
|
||||
"prompt": "Write a concise, engaging summary that captures the essence of the content for food lovers.",
|
||||
"description": "a generic food writer",
|
||||
"tone": "an engaging tone"
|
||||
})
|
||||
# Format the prompt using description and tone
|
||||
prompt = persona_config["prompt"].format(
|
||||
description=persona_config["description"],
|
||||
tone=persona_config["tone"],
|
||||
num_paragraphs=determine_paragraph_count(interest_score)
|
||||
)
|
||||
logging.info(f"Using {persona} with interest_score and content")
|
||||
|
||||
full_prompt = (
|
||||
|
||||
+42
-17
@@ -62,37 +62,62 @@ X_API_CREDENTIALS = [
|
||||
]
|
||||
|
||||
X_PERSONA_PROMPTS = {
|
||||
"Visionary Editor": (
|
||||
"Craft a tweet as a commanding food editor with a bold, global view. Keep it under 280 characters, using a casual, hype tone like 'This is unreal!'. "
|
||||
"Visionary Editor": {
|
||||
"description": "a commanding food editor with a borderless view",
|
||||
"tone": "a polished and insightful tone, like 'This redefines culinary excellence.'",
|
||||
"prompt": (
|
||||
"Craft a tweet as {description}. Keep it under 280 characters, using {tone}. "
|
||||
"For article tweets, include the article title, a quirky hook, and the URL. For personal tweets, reflect on your role at InsiderFoodie or background. "
|
||||
"Avoid emojis and clichés like 'game-changer'. Return only the tweet text."
|
||||
),
|
||||
"Foodie Critic": (
|
||||
"Craft a tweet as a seasoned foodie reviewer with a sharp eye. Keep it under 280 characters, using a pro yet lively tone like 'This bangs!'. "
|
||||
)
|
||||
},
|
||||
"Foodie Critic": {
|
||||
"description": "a seasoned foodie reviewer with a sharp eye",
|
||||
"tone": "a professional yet engaging tone, like 'This dish is a revelation.'",
|
||||
"prompt": (
|
||||
"Craft a tweet as {description}. Keep it under 280 characters, using {tone}. "
|
||||
"For article tweets, include the article title, a quirky hook, and the URL. For personal tweets, reflect on your role at InsiderFoodie or background. "
|
||||
"Avoid emojis and clichés like 'game-changer'. Return only the tweet text."
|
||||
),
|
||||
"Trend Scout": (
|
||||
"Craft a tweet as a forward-thinking editor obsessed with trends. Keep it under 280 characters, using an enthusiastic tone like 'This is the future, fam!'. "
|
||||
)
|
||||
},
|
||||
"Trend Scout": {
|
||||
"description": "a forward-thinking editor obsessed with trends",
|
||||
"tone": "an insightful and forward-looking tone, like 'This sets the stage for what’s next.'",
|
||||
"prompt": (
|
||||
"Craft a tweet as {description}. Keep it under 280 characters, using {tone}. "
|
||||
"For article tweets, include the article title, a quirky hook, and the URL. For personal tweets, reflect on your role at InsiderFoodie or background. "
|
||||
"Avoid emojis and clichés like 'game-changer'. Return only the tweet text."
|
||||
),
|
||||
"Culture Connoisseur": (
|
||||
"Craft a tweet as a cultured food writer who loves storytelling. Keep it under 280 characters, using a warm, reflective tone like 'This feels different, right?'. "
|
||||
)
|
||||
},
|
||||
"Culture Connoisseur": {
|
||||
"description": "a cultured food writer who loves storytelling",
|
||||
"tone": "a warm and thoughtful tone, like 'This evokes a sense of tradition.'",
|
||||
"prompt": (
|
||||
"Craft a tweet as {description}. Keep it under 280 characters, using {tone}. "
|
||||
"For article tweets, include the article title, a quirky hook, and the URL. For personal tweets, reflect on your role at InsiderFoodie or background. "
|
||||
"Avoid emojis and clichés like 'game-changer'. Return only the tweet text."
|
||||
),
|
||||
"African-American Soul Food Sage": (
|
||||
"Craft a tweet as a vibrant storyteller rooted in African-American culinary heritage. Keep it under 280 characters, using a soulful tone like 'This got that heat, y’all!'. "
|
||||
)
|
||||
},
|
||||
"African-American Soul Food Sage": {
|
||||
"description": "a vibrant storyteller rooted in African-American culinary heritage",
|
||||
"tone": "a heartfelt and authentic tone, like 'This captures the essence of heritage.'",
|
||||
"prompt": (
|
||||
"Craft a tweet as {description}. Keep it under 280 characters, using {tone}. "
|
||||
"For article tweets, include the article title, a quirky hook, and the URL. For personal tweets, reflect on your role at InsiderFoodie or background. "
|
||||
"Avoid emojis and clichés like 'game-changer'. Return only the tweet text."
|
||||
),
|
||||
"Global Street Food Nomad": (
|
||||
"Craft a tweet as an adventurous explorer of global street food. Keep it under 280 characters, using a bold, gritty tone like 'This is straight fire!'. "
|
||||
)
|
||||
},
|
||||
"Global Street Food Nomad": {
|
||||
"description": "an adventurous explorer of global street food",
|
||||
"tone": "a bold and adventurous tone, like 'This takes you on a global journey.'",
|
||||
"prompt": (
|
||||
"Craft a tweet as {description}. Keep it under 280 characters, using {tone}. "
|
||||
"For article tweets, include the article title, a quirky hook, and the URL. For personal tweets, reflect on your role at InsiderFoodie or background. "
|
||||
"Avoid emojis and clichés like 'game-changer'. Return only the tweet text."
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
AUTHOR_BACKGROUNDS_FILE = '/home/shane/foodie_automator/author_backgrounds.json'
|
||||
X_POST_COUNTS_FILE = '/home/shane/foodie_automator/x_post_counts.json'
|
||||
|
||||
+15
-2
@@ -1,3 +1,4 @@
|
||||
# foodie_x_poster.py
|
||||
import json
|
||||
import logging
|
||||
import random
|
||||
@@ -93,7 +94,13 @@ def delete_used_post(post_title):
|
||||
logging.info(f"Deleted post '{post_title}' from recent_posts.json")
|
||||
|
||||
def generate_article_tweet(author, post, persona):
|
||||
prompt = X_PERSONA_PROMPTS[persona].replace(
|
||||
# Format the prompt using description and tone
|
||||
persona_config = X_PERSONA_PROMPTS[persona]
|
||||
base_prompt = persona_config["prompt"].format(
|
||||
description=persona_config["description"],
|
||||
tone=persona_config["tone"]
|
||||
)
|
||||
prompt = base_prompt.replace(
|
||||
"For article tweets, include the article title, a quirky hook, and the URL.",
|
||||
f"Generate an article tweet including the title '{post['title']}', a quirky hook, and the URL '{post['url']}'."
|
||||
)
|
||||
@@ -138,7 +145,13 @@ def generate_personal_tweet(author, persona):
|
||||
f"Early memory: {background['early_memory']}, Career path: {background['career_path']}."
|
||||
)
|
||||
|
||||
prompt = X_PERSONA_PROMPTS[persona].replace(
|
||||
# Format the prompt using description and tone
|
||||
persona_config = X_PERSONA_PROMPTS[persona]
|
||||
base_prompt = persona_config["prompt"].format(
|
||||
description=persona_config["description"],
|
||||
tone=persona_config["tone"]
|
||||
)
|
||||
prompt = base_prompt.replace(
|
||||
"For personal tweets, reflect on your role at InsiderFoodie or background.",
|
||||
content
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user