# Git Symbolic Links Setup for Blog Content ## Overview This document explains the setup that allows the blog content to be managed in Obsidian while being properly versioned in Git. The setup uses Git hooks to automatically handle symbolic links, ensuring that actual content is committed while maintaining symbolic links for local development. ## Architecture ```mermaid graph TD A[Obsidian Vault] -->|Symbolic Links| B[Blog Repository] B -->|Pre-commit Hook| C[Convert to Content] C -->|Commit| D[Git Repository] D -->|Post-commit Hook| E[Restore Symlinks] E -->|Local Development| B ``` ## Directory Structure ### Obsidian Content Location ``` /mnt/synology/obsidian/Public/Blog/ ├── posts/ ├── projects/ ├── configurations/ ├── external-posts/ ├── configs/ ├── images/ ├── infrastructure/ └── content/ ``` ### Blog Repository Structure ``` laforceit-blog/ ├── src/content/ │ ├── posts -> /mnt/synology/obsidian/Public/Blog/posts │ ├── projects -> /mnt/synology/obsidian/Public/Blog/projects │ ├── configurations -> /mnt/synology/obsidian/Public/Blog/configurations │ └── external-posts -> /mnt/synology/obsidian/Public/Blog/external-posts └── public/blog/ ├── configs -> /mnt/synology/obsidian/Public/Blog/configs ├── images -> /mnt/synology/obsidian/Public/Blog/images ├── infrastructure -> /mnt/synology/obsidian/Public/Blog/infrastructure └── posts -> /mnt/synology/obsidian/Public/Blog/posts ``` ## Setup Instructions 1. Clone the Blog Repository ```bash git clone https://git.argobox.com/KeyArgo/laforceit-blog.git cd laforceit-blog ``` 2. Create the Scripts Directory ```bash mkdir -p scripts ``` 3. Create the Content Processing Script Create `scripts/process-content-links.sh`: ```bash #!/bin/bash # Script to handle symbolic links before commit echo "Processing symbolic links for content..." # Array of content directories to process declare -A CONTENT_PATHS # src/content directories CONTENT_PATHS["posts"]="src/content/posts" CONTENT_PATHS["projects"]="src/content/projects" CONTENT_PATHS["configurations"]="src/content/configurations" CONTENT_PATHS["external-posts"]="src/content/external-posts" # public/blog directories CONTENT_PATHS["configs"]="public/blog/configs" CONTENT_PATHS["images"]="public/blog/images" CONTENT_PATHS["infrastructure"]="public/blog/infrastructure" CONTENT_PATHS["blog-posts"]="public/blog/posts" for dir_name in "${!CONTENT_PATHS[@]}"; do dir_path="${CONTENT_PATHS[$dir_name]}" if [ -L "$dir_path" ]; then echo "Processing $dir_path..." target=$(readlink "$dir_path") rm "$dir_path" mkdir -p "$(dirname "$dir_path")" cp -r "$target" "$dir_path" git add "$dir_path" echo "Processed $dir_path -> $target" else echo "Skipping $dir_path (not a symbolic link)" fi done echo "Content processing complete!" ``` 4. Create Git Hooks ### Pre-commit Hook Create `.git/hooks/pre-commit`: ```bash #!/bin/bash # Pre-commit hook to process symbolic links echo "Running pre-commit hook for blog content..." # Get the absolute path to the script SCRIPT_PATH="$(git rev-parse --show-toplevel)/scripts/process-content-links.sh" # Check if the script exists and is executable if [ -x "$SCRIPT_PATH" ]; then bash "$SCRIPT_PATH" # Add any new or changed files resulting from the script git add -A else echo "Error: Content processing script not found or not executable at $SCRIPT_PATH" echo "Please ensure the script exists and has execute permissions" exit 1 fi ``` ### Post-commit Hook Create `.git/hooks/post-commit`: ```bash #!/bin/bash # Post-commit hook to restore symbolic links echo "Running post-commit hook to restore symbolic links..." # Array of content directories and their targets declare -A SYMLINK_TARGETS=( ["src/content/posts"]="/mnt/synology/obsidian/Public/Blog/posts" ["src/content/projects"]="/mnt/synology/obsidian/Public/Blog/projects" ["src/content/configurations"]="/mnt/synology/obsidian/Public/Blog/configurations" ["src/content/external-posts"]="/mnt/synology/obsidian/Public/Blog/external-posts" ["public/blog/configs"]="/mnt/synology/obsidian/Public/Blog/configs" ["public/blog/images"]="/mnt/synology/obsidian/Public/Blog/images" ["public/blog/infrastructure"]="/mnt/synology/obsidian/Public/Blog/infrastructure" ["public/blog/posts"]="/mnt/synology/obsidian/Public/Blog/posts" ) for dir_path in "${!SYMLINK_TARGETS[@]}"; do target="${SYMLINK_TARGETS[$dir_path]}" if [ -d "$target" ]; then echo "Restoring symlink for $dir_path -> $target" rm -rf "$dir_path" mkdir -p "$(dirname "$dir_path")" ln -s "$target" "$dir_path" else echo "Warning: Target directory $target does not exist" fi done echo "Symbolic links restored!" ``` 5. Set Proper Permissions ```bash chmod +x scripts/process-content-links.sh chmod +x .git/hooks/pre-commit chmod +x .git/hooks/post-commit ``` 6. Create Symbolic Links ```bash # Create necessary directories mkdir -p src/content public/blog # Create symbolic links for src/content ln -s /mnt/synology/obsidian/Public/Blog/posts src/content/posts ln -s /mnt/synology/obsidian/Public/Blog/projects src/content/projects ln -s /mnt/synology/obsidian/Public/Blog/configurations src/content/configurations ln -s /mnt/synology/obsidian/Public/Blog/external-posts src/content/external-posts # Create symbolic links for public/blog ln -s /mnt/synology/obsidian/Public/Blog/configs public/blog/configs ln -s /mnt/synology/obsidian/Public/Blog/images public/blog/images ln -s /mnt/synology/obsidian/Public/Blog/infrastructure public/blog/infrastructure ln -s /mnt/synology/obsidian/Public/Blog/posts public/blog/posts ``` ## Git Configuration 1. Configure Git to Handle Symbolic Links ```bash git config core.symlinks true ``` 2. Create `.gitattributes` ``` # Handle symbolic links as real content public/blog/* !symlink src/content/* !symlink # Treat these directories as regular directories even if they're symlinks public/blog/configs/ -symlink public/blog/images/ -symlink public/blog/infrastructure/ -symlink public/blog/posts/ -symlink src/content/posts/ -symlink src/content/projects/ -symlink src/content/configurations/ -symlink src/content/external-posts/ -symlink # Set text files to automatically normalize line endings * text=auto ``` ## How It Works 1. **Normal Development** - Content is edited in Obsidian - Blog repository uses symbolic links to this content - Local development works seamlessly 2. **During Commits** - Pre-commit hook activates - Symbolic links are converted to actual content - Content is committed to the repository 3. **After Commits** - Post-commit hook activates - Symbolic links are restored - Local development continues normally ## Viewing in Gitea Yes, you can view this setup in Gitea: 1. The actual content will be visible in the repository 2. The `.git/hooks` directory and scripts will be visible 3. The symbolic links will appear as regular directories in Gitea ## Troubleshooting 1. **Symbolic Links Not Working** - Check file permissions - Verify Obsidian vault location - Ensure Git symlinks are enabled 2. **Hooks Not Executing** - Check execute permissions on scripts - Verify hook files are in `.git/hooks` - Check script paths are correct 3. **Content Not Committing** - Check Git configuration - Verify pre-commit hook execution - Check file permissions ## Maintenance 1. **Adding New Content Directories** - Add to `CONTENT_PATHS` in process-content-links.sh - Add to `SYMLINK_TARGETS` in post-commit hook - Create corresponding symbolic links 2. **Changing Obsidian Location** - Update paths in post-commit hook - Update existing symbolic links 3. **Backup Considerations** - Both Obsidian content and blog repository should be backed up - Keep hooks and scripts in version control ## Security Notes 1. Keep sensitive content outside of public blog directories 2. Review content before commits 3. Use `.gitignore` for private files 4. Consider access permissions on Obsidian vault