Weşand li ser

Bikaranîna GitHub Actions ji bo afirandina agahdariyên derbarê weşandina postê blogê

Nivîskar

Weke Weke, Çawa Min Ji Xwe Re Bîra Nivîsandina Posteke Blogê Çêkir

Weke nivîskar, ez têgihîştinim ku çiqas girîng e ku mirov di weşandina naveroka nû de berdewam be. Lê belê, carinan jiyan di rêya me de radibe û dibe ku mirov ji bîr bike ku posteke blogê ya nû binivîse. Ji bo ku ez di plana parvekirina xwe de bimînim, min bi karanîna GitHub Actions bîreke hêsan çêkir. Di vê postê de, ez ê bi we re parve bikim ka min ev rêbaz çawa pêk anî.

GitHub Action Çi ye?

GitHub Actions amûrek bihêz e ku ji we re dihêle hûn xebatên xwe otomatîk bikin. Hûn dikarin wê ji bo avakirin, ceribandin û bicihkirina kodê xwe bikar bînin. Hûn dikarin wê ji bo pêkanîna gelek karên din, wekî şandina agahdariyan an plankirina bîranînên, bikar bînin.

Min Bîreke Ji Bo Nivîsandina Posteke Blogê Çawa Çêkir

Ji bo ku ez ji xwe re bîreke ji bo nivîsandina posteke blogê çê bikim, ez repozîtoya taybet a GitHubê README.md bikar tînim û pelê .github/workflows/blog-posts.yml lê zêde dikim. Di vê pelê de, ez xebata ku GitHub Actions dê pêk bîne, diyar dikim. Ev naveroka destpêkê ya pelê ye:

name: Blog Posts

on:
  schedule:
    - cron: '0 0 * * 0' # Her Yekşemê di saet 00:00 de dest pê bike
  workflow_dispatch:

jobs:
  update-posts:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v3
      - name: Update post list
        run: |
          sleep 1m
          curl -LO https://blog.imam.dev/feed.xml
          node src/list-posts.js
          rm feed.xml
      - name: Commit changes
        run: |
          git config --local user.email "github-actions[bot]@users.noreply.github.com"
          git config --local user.name "github-actions[bot]"
          git add -A
          git diff-index --quiet HEAD || git commit -m "Update blog posts"
      - name: Pull changes
        run: git pull -r
      - name: Push changes
        uses: ad-m/github-push-action@0fafdd62b84042d49ec0cb92d9cac7f7ce4ec79e
        with:
          github_token: ${{ secrets.GITHUB_TOKEN }}

Ev xebat her Yekşemê di saet 00:00 de dest pê dike. Piştre, ew skriptek dimeşîne ku lîsteya posteyên blogê nû dike. Skript bi JavaScript hatiye nivîsandin û RSS feed-a bloga min analîz dike. Piştre, lîsteyek ji posteyên blogê çêdike û pelê README.md nû dike. Di dawiyê de, guhertinan kom dike û wan dişîne GitHubê. Ez repozîtoya ouuan wekî referansek ji bo vê xebatê bikar tînim.

Bîranîn ji ku tê? Bi rastî di pelê list-posts.js de ye. Min bîranînek ji bo lîsteya posteyên blogê zêde kiriye. Ev naveroka pelê ye:

const { readFileSync, writeFileSync } = require('fs')

/**
 * Zimanê XML veguherîne JSON
 * @param {string} xmlString
 * @returns {object} json
 */
const xmlToJson = (xmlString) => {
  const regex = /<(\w+)([^>]*)>([\s\S]*?)<\/\1>/gm
  const matches = xmlString.matchAll(regex)
  const json = {}

  for (const match of matches) {
    const [, key, attributes, value] = match
    const subMatches = value.matchAll(regex)
    const subJson = {}

    for (const subMatch of subMatches) {
      const [, subKey, subAttributes, subValue] = subMatch

      if (subValue.match(regex)) {
        if (Array.isArray(subJson[subKey])) {
          subJson[subKey].push(
            xmlToJson(`<${subKey}${subAttributes}>${subValue}</${subKey}>`)[subKey]
          )
        } else if (subJson[subKey]) {
          subJson[subKey] = [
            subJson[subKey],
            xmlToJson(`<${subKey}${subAttributes}>${subValue}</${subKey}>`)[subKey],
          ]
        } else {
          subJson[subKey] = xmlToJson(`<${subKey}${subAttributes}>${subValue}</${subKey}>`)[subKey]
        }
      } else if (Array.isArray(subJson[subKey])) {
        subJson[subKey].push(subValue)
      } else if (subJson[subKey]) {
        subJson[subKey] = [subJson[subKey], subValue]
      } else {
        subJson[subKey] = subValue
      }
    }

    if (json[key]) {
      if (Array.isArray(json[key])) {
        json[key].push(subJson)
      } else {
        json[key] = [json[key], subJson]
      }
    } else {
      json[key] = subJson
    }
  }

  return json
}

/**
 * JSON li gorî pubDate rêz bike
 * @param {object} json
 * @returns {object} sortedJson
 */
const sortJson = (json) => {
  json.sort((a, b) => new Date(b.pubDate) - new Date(a.pubDate))
  return json
}

// Pelê XML bixwîne û veguherîne JSON
const xmlString = readFileSync('feed.xml', 'utf8')
const feeds = sortJson(xmlToJson(xmlString).rss.channel.item)

// Lîsteya posteyên Markdown çêbike
const posts = feeds
  .slice(0, 5)
  .map(
    (item) =>
      `- ${new Date(item.pubDate).toISOString().split('T')[0]} [${item.title}](${
        item.link
      }?utm_source=GitHubProfile)`
  )

// README.md nû bike eger posteyên guhertine,
// Wekî din, çewtiyê biavêje ji bo ku bîra min bike ku posteke blogê binivîsim
const readme = readFileSync('README.md', 'utf8')
if (readme.includes(posts.join('\n'))) {
  throw new Error('No new blog posts')
} else {
  const updatedReadme = readFileSync('README.md', 'utf8').replace(
    /(?<=<!--START_SECTION:blog-posts-->\n)[\s\S]*(?=\n<!--END_SECTION:blog-posts-->)/,
    posts.join('\n')
  )
  writeFileSync('README.md', updatedReadme)

  console.log('Updated README.md')
}

Skript RSS feed-a bloga min dixwîne û lîsteyek ji posteyên blogê çêdike. Piştre, ew pelê README.md bi lîsteya posteyên blogê nû dike. Eger posteyên nû tune bin, ew çewtiyê diavêje ji bo ku bîra min bike ku posteke blogê binivîsim.

Ew tenê çewtiyek e ku dê were avêtin dema ku skript tê bicihkirin dema ku posteyên hîn jî wekî xwe ne û ew bîranînek nine ku dê ji bo min were şandin e-nameyekê yan tiştek din ku ji min re xuya be. Ji ber vê yekê, min biryar da ku agahdariyê ji bo her xebata ku bi ser neketiye vebikim. Ev çawa tê kirin:

  1. Li ser quncika rastê jorîn a rûpelê biklike û Settings hilbijêre.

  2. Li ser tabloya çepê Notifications hilbijêre.

  3. Li ser Actions biklike.

  4. Send notifications for failed workflows only hilbijêre.

Niha, ez ê agahdariyek bistînim dema ku skript tê bicihkirin û posteyên nû tune ne. Ez dikarim agahdarî li ser malpera GitHub-ê jî bibînim.

Rêyek Din ku Ez Lêkolîn Kirim

Xebata berê ku ez ji we re behsa wê dikim, guhertoyeke guhertî ye, da ku README.md min her dem nû be. Ez rêyek din jî lêkolîn kir ku ji xwe re bîreke ji bo nivîsandina posteke blogê çê bikim. Lê belê, ew tenê bîranîneke safî ye bêyî mekanîzmaya nûkirina README.md, tenê bîranînek.

Ji bo ku ez ji xwe re bîreke ji bo nivîsandina posteke blogê çê bikim, min repozîtoya nû ya GitHubê çêkir û pelê .github/workflows/remind.yml lê zêde kir. Di vê pelê de, ez xebata ku GitHub Actions dê pêk bîne, diyar dikim. Ev naveroka pelê ye:

name: Reminder to write a blog post

on:
  schedule:
    - cron: '0 10 * * 1-5'

jobs:
  remind:
    runs-on: ubuntu-latest
    steps:
      - name: Send a reminder
        uses: dawidd6/action-send-mail@v3.1.0
        with:
          server_address: smtp.gmail.com
          server_port: 465
          username: ${{ secrets.EMAIL_USERNAME }}
          password: ${{ secrets.EMAIL_PASSWORD }}
          subject: 'Reminder to write a new blog post'
          body: "Don't forget to write a new blog post today!"
          to: my-email@example.com

Ev xebat her roj di saet 10:00 de, ji bo ku bîra min bike ku posteke blogê ya nû binivîsim, ji min re e-nameyekê dişîne. Min ji bo şandina e-nameyê, dawidd6/action-send-mail-ê, çalakiyek ji aliyê sêyemîn ve bikar anî. Ez agahiyên e-nameya xwe wekî razên GitHub pêşkêş kirim, da ku ew di pelê xebatê de xuya nebin.

Encam

Min du rêbaz lêkolîn kir ku ji xwe re bîreke ji bo nivîsandina posteke blogê çê bikim. Rêbaza yekem nûkirina pelê README.md yê profîla min a GitHubê ye. Rêbaza duyemîn şandina bîranînek bi e-nameyê ye. Ez niha rêbaza yekem bikar tînim ji ber ku ew ji rêbaza duyemîn xuya tir e. Her gava ku ez serdana profîla xwe ya GitHubê dikim, ez dikarim bîranînê bibînim.

Çêkirina bîranînek ji bo nivîsandina posteke blogê bi karanîna GitHub Actions, rêyek hêsan û bi bandor e ku hûn di plana nivîsandina bloga xwe de bimînin. Bi vê xebatê re, hûn ê careke din ji bîr nekin ku posteke nû binivîsin. Eger hûn dixwazin xebata xwe ya bîranînê çê bikin, ji bo ku hûn zêdetir fêr bibin, pê ewle bin ku belgeyên GitHub Actions binihêrin. Nivîsandina bloga we baş be!