Skip to content

Commit

Permalink
ci: add a schedule task to update icons
Browse files Browse the repository at this point in the history
  • Loading branch information
moecasts committed Oct 31, 2024
1 parent 8620b1f commit e3aa064
Show file tree
Hide file tree
Showing 3 changed files with 172 additions and 3 deletions.
42 changes: 42 additions & 0 deletions .github/workflows/update-icons.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
name: update-icons

on:
schedule:
- cron: '0 0 * * *' # 每天午夜触发一次
workflow_dispatch: # 允许手动触发

jobs:
build-and-update:
runs-on: ubuntu-latest

steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: setup-environment
uses: ./.github/actions/setup-environment

- name: fetch remote icons
run: pnpm --filter '@casts/icons' run build:update-raw

- name: Check for changes
id: check-changes
run: |
git diff --exit-code > /dev/null || echo "::set-output name=has-changes::true"
- name: build icons
if: steps.check-changes.outputs.has-changes == 'true'
run: |
pnpm --filter '@casts/icons' run build:icons
- name: create pull request if changes detected
if: steps.check-changes.outputs.has-changes == 'true'
uses: peter-evans/create-pull-request@v7
with:
token: ${{ secrets.GITHUB_TOKEN }}
commit-message: 'feat(icons): update icons'
title: '[icons] update icons'
body: 'This PR is automatically created to update the icons files.'
branch: update-raw-branch-${{ github.run_id }}-${{ github.run_number }}
delete-branch: true
base: main
7 changes: 4 additions & 3 deletions packages/casts-icons/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,11 @@
"scripts": {
"dev": "father dev",
"build": "father build",
"build:icons": "svgr --config-file ./svgr.config.js -d ./src/icons ./assets/raw && eslint ./src --fix && npm run build:index && npm run build:exampleIconList",
"build:exampleIconList": "ts-node ./scripts/create-examples-icon-list.ts",
"build:icons": "svgr --config-file ./svgr.config.js -d ./src/icons ./assets/raw && eslint ./src --fix && npm run build:index && npm run build:example-icon-list",
"build:example-icon-list": "ts-node ./scripts/create-examples-icon-list.ts",
"build:index": "ts-node ./scripts/create-root-index.ts",
"build:deps": "father prebundle",
"build:update-raw": "ts-node ./scripts/update-icon-raw.ts",
"prepublishOnly": "father doctor && pnpm run build",
"test": "vitest",
"test:coverage": "vitest run --coverage"
Expand Down Expand Up @@ -58,4 +59,4 @@
"sideEffects": [
"**/*.{css,scss,sass}"
]
}
}
126 changes: 126 additions & 0 deletions packages/casts-icons/scripts/update-icon-raw.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
import { exec } from 'child_process';
import * as fs from 'fs';
import * as path from 'path';

// Define the source repository and target directory
const repoUrl = 'https://github.com/Remix-Design/RemixIcon.git';

// Create a temporary directory path
const tempDir = path.join(__dirname, '../temp-remix-icon');
const sourceDir = path.join(tempDir, 'icons');
const targetDir = path.join(__dirname, '../assets/raw');

/**
* Replace '&' with '_' in subfolder names within a folder
* @param {string} dirPath The folder path
*/
function replaceAmpersandInFolderNames(dirPath: string) {
// Read the folder contents
const entries = fs.readdirSync(dirPath, { withFileTypes: true });

// Iterate through the contents and process folders
for (const entry of entries) {
if (entry.isDirectory()) {
const oldFolderPath = path.join(dirPath, entry.name);
const newFolderName = entry.name.replace(/\s*&\s*/g, '_');
const newFolderPath = path.join(dirPath, newFolderName);

// If the folder name has changed, rename the folder
if (oldFolderPath !== newFolderPath) {
fs.renameSync(oldFolderPath, newFolderPath);
}

// Recursively process subfolders
replaceAmpersandInFolderNames(newFolderPath);
}
}
}

function copyRecursively(src: string, dest: string) {
// Check if the source path exists
if (!fs.existsSync(src)) {
throw new Error(`Source path does not exist: ${src}`);
}

// Check if the source path is a file or directory
const stats = fs.statSync(src);
if (stats.isDirectory()) {
// If the target directory does not exist, create it
if (!fs.existsSync(dest)) {
fs.mkdirSync(dest, { recursive: true });
}
const entries = fs.readdirSync(src, { withFileTypes: true });
for (const entry of entries) {
const srcPath = path.join(src, entry.name);
const destPath = path.join(dest, entry.name);
if (entry.isDirectory()) {
// Recursively copy directories
copyRecursively(srcPath, destPath);
} else {
// Copy files
fs.copyFileSync(srcPath, destPath);
}
}
} else {
// Ensure the target directory exists
const destDir = path.dirname(dest);
if (!fs.existsSync(destDir)) {
fs.mkdirSync(destDir, { recursive: true });
}
// Copy files
fs.copyFileSync(src, dest);
}
}

/**
* Clear a folder
* @param {string} dirPath The folder path
*/
function cleanDirectory(dirPath: string) {
// Read the folder contents
const entries = fs.readdirSync(dirPath);

// Iterate through the contents and delete files or subdirectories
for (const entry of entries) {
const fullPath = path.join(dirPath, entry);
const stats = fs.statSync(fullPath);

if (stats.isFile()) {
// If it's a file, delete it directly
fs.unlinkSync(fullPath);
} else if (stats.isDirectory()) {
// If it's a directory, recursively clear it
cleanDirectory(fullPath);
// Delete the empty directory
fs.rmdirSync(fullPath);
}
}
}

const run = () => {
// Clone the repository to a temporary directory
exec(`git clone ${repoUrl} ${tempDir} --depth=1`, (err) => {
if (err) {
console.error('Error cloning repository:', err);
return;
}

// Repository cloned successfully, move icons folder contents to the target directory

// Ensure the target directory exists
if (!fs.existsSync(targetDir)) {
fs.mkdirSync(targetDir, { recursive: true });
}

cleanDirectory(targetDir);

copyRecursively(sourceDir, targetDir);

replaceAmpersandInFolderNames(targetDir);

// Delete the temporary repository directory
fs.rmSync(tempDir, { recursive: true });
});
};

run();

0 comments on commit e3aa064

Please sign in to comment.