Skip to content

Commit ab0efab

Browse files
committed
chore(blog): figure out if there is a new post
1 parent 7a93c93 commit ab0efab

File tree

1 file changed

+156
-0
lines changed

1 file changed

+156
-0
lines changed
Lines changed: 156 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,156 @@
1+
name: Detect New Blog Post
2+
3+
on:
4+
workflow_call:
5+
inputs:
6+
content_path:
7+
description: 'Path to blog content directory (e.g., src/content/blog)'
8+
required: false
9+
type: string
10+
default: 'src/content/blog'
11+
post_filename:
12+
description: 'Blog post filename pattern (e.g., index.md)'
13+
required: false
14+
type: string
15+
default: 'index.md'
16+
site_url:
17+
description: 'Base URL for the site (e.g., https://www.example.com)'
18+
required: true
19+
type: string
20+
url_prefix:
21+
description: 'URL path prefix for blog posts (e.g., /blog)'
22+
required: false
23+
type: string
24+
default: '/blog'
25+
event_name:
26+
description: 'The triggering event name (push, schedule, workflow_dispatch)'
27+
required: true
28+
type: string
29+
categories_field:
30+
description: 'Frontmatter field name for categories/tags (e.g., categories, tags)'
31+
required: false
32+
type: string
33+
default: 'categories'
34+
outputs:
35+
has_new_post:
36+
description: 'Whether a new post was detected'
37+
value: ${{ jobs.detect.outputs.has_new_post }}
38+
post_title:
39+
description: 'Title of the new post'
40+
value: ${{ jobs.detect.outputs.post_title }}
41+
post_url:
42+
description: 'Full URL to the new post'
43+
value: ${{ jobs.detect.outputs.post_url }}
44+
post_hashtags:
45+
description: 'Categories as hashtags (e.g., #cat1 #cat2)'
46+
value: ${{ jobs.detect.outputs.post_hashtags }}
47+
48+
jobs:
49+
detect:
50+
runs-on: ubuntu-latest
51+
outputs:
52+
has_new_post: ${{ steps.check.outputs.has_new_post }}
53+
post_title: ${{ steps.check.outputs.post_title }}
54+
post_url: ${{ steps.check.outputs.post_url }}
55+
post_hashtags: ${{ steps.check.outputs.post_hashtags }}
56+
steps:
57+
- name: Checkout
58+
uses: actions/checkout@v4
59+
with:
60+
fetch-depth: 0
61+
62+
- name: Detect new blog post
63+
id: check
64+
run: |
65+
TODAY=$(date -u +"%Y-%m-%d")
66+
echo "Today's date: $TODAY"
67+
68+
CONTENT_PATH="${{ inputs.content_path }}"
69+
POST_FILENAME="${{ inputs.post_filename }}"
70+
SITE_URL="${{ inputs.site_url }}"
71+
URL_PREFIX="${{ inputs.url_prefix }}"
72+
EVENT_NAME="${{ inputs.event_name }}"
73+
CATEGORIES_FIELD="${{ inputs.categories_field }}"
74+
75+
if [ "$EVENT_NAME" == "push" ]; then
76+
echo "=== Push event: checking for new posts dated today or earlier ==="
77+
78+
# Get list of added files in this push
79+
ADDED_FILES=$(git diff --name-only --diff-filter=A HEAD~1 HEAD)
80+
81+
echo "Added files:"
82+
echo "$ADDED_FILES"
83+
84+
# Look for new blog post files
85+
NEW_POST=$(echo "$ADDED_FILES" | grep -E "^${CONTENT_PATH}/.*/${POST_FILENAME}$" | head -1)
86+
87+
if [ -z "$NEW_POST" ]; then
88+
echo "No new blog post detected"
89+
echo "has_new_post=false" >> $GITHUB_OUTPUT
90+
exit 0
91+
fi
92+
93+
echo "New post found: $NEW_POST"
94+
95+
# Extract date from frontmatter
96+
POST_DATE=$(sed -n '/^---$/,/^---$/p' "$NEW_POST" | grep -E '^date:' | sed 's/^date:[[:space:]]*//' | sed 's/["\x27]//g' | cut -dT -f1)
97+
echo "Post date: $POST_DATE"
98+
99+
# Compare dates - skip if future dated
100+
if [[ "$POST_DATE" > "$TODAY" ]]; then
101+
echo "Post is future-dated ($POST_DATE > $TODAY), skipping"
102+
echo "has_new_post=false" >> $GITHUB_OUTPUT
103+
exit 0
104+
fi
105+
106+
else
107+
echo "=== Scheduled/manual event: checking for posts dated today ==="
108+
109+
# Find all blog posts and check for ones dated today
110+
NEW_POST=""
111+
for POST_FILE in $(find "$CONTENT_PATH" -name "$POST_FILENAME" 2>/dev/null); do
112+
POST_DATE=$(sed -n '/^---$/,/^---$/p' "$POST_FILE" | grep -E '^date:' | sed 's/^date:[[:space:]]*//' | sed 's/["\x27]//g' | cut -dT -f1)
113+
114+
if [ "$POST_DATE" == "$TODAY" ]; then
115+
echo "Found post dated today: $POST_FILE"
116+
NEW_POST="$POST_FILE"
117+
break
118+
fi
119+
done
120+
121+
if [ -z "$NEW_POST" ]; then
122+
echo "No posts dated today found"
123+
echo "has_new_post=false" >> $GITHUB_OUTPUT
124+
exit 0
125+
fi
126+
fi
127+
128+
# Extract title from frontmatter
129+
TITLE=$(sed -n '/^---$/,/^---$/p' "$NEW_POST" | grep -E '^title:' | sed "s/^title:[[:space:]]*['\"]*//" | sed "s/['\"].*$//")
130+
131+
if [ -z "$TITLE" ]; then
132+
echo "Could not extract title"
133+
echo "has_new_post=false" >> $GITHUB_OUTPUT
134+
exit 0
135+
fi
136+
137+
echo "Title: $TITLE"
138+
139+
# Extract categories from frontmatter and convert to hashtags
140+
# Handles format: categories: [cat1, cat2, cat3] or categories: ["cat1", "cat2"]
141+
CATEGORIES=$(sed -n '/^---$/,/^---$/p' "$NEW_POST" | grep -E "^${CATEGORIES_FIELD}:" | sed "s/^${CATEGORIES_FIELD}:[[:space:]]*//" | tr -d '[]"' | tr ',' '\n' | sed 's/^[[:space:]]*//' | sed 's/[[:space:]]*$//' | sed 's/^/#/' | tr '\n' ' ' | sed 's/[[:space:]]*$//')
142+
echo "Hashtags: $CATEGORIES"
143+
144+
# Extract slug from path: {content_path}/{year}/{slug}/{filename} -> {year}/{slug}
145+
SLUG=$(echo "$NEW_POST" | sed "s|${CONTENT_PATH}/||" | sed "s|/${POST_FILENAME}$||")
146+
147+
# Build full URL (remove trailing slash from site_url if present, ensure url_prefix starts with /)
148+
SITE_URL="${SITE_URL%/}"
149+
POST_URL="${SITE_URL}${URL_PREFIX}/${SLUG}/"
150+
151+
echo "URL: $POST_URL"
152+
153+
echo "has_new_post=true" >> $GITHUB_OUTPUT
154+
echo "post_title=$TITLE" >> $GITHUB_OUTPUT
155+
echo "post_url=$POST_URL" >> $GITHUB_OUTPUT
156+
echo "post_hashtags=$CATEGORIES" >> $GITHUB_OUTPUT

0 commit comments

Comments
 (0)