{"id":42077029,"url":"https://github.com/nojronatron/file-limit-service","last_synced_at":"2026-01-26T09:36:04.237Z","repository":{"id":331943961,"uuid":"1132308386","full_name":"nojronatron/file-limit-service","owner":"nojronatron","description":".NET 10 service ensures maximum file count in target directory. Build targets arch64.","archived":false,"fork":false,"pushed_at":"2026-01-18T19:46:40.000Z","size":53,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-01-19T02:39:28.597Z","etag":null,"topics":["copilot","dotnet","linux","raspberry-pi"],"latest_commit_sha":null,"homepage":"","language":"C#","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/nojronatron.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2026-01-11T18:06:10.000Z","updated_at":"2026-01-18T19:01:09.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/nojronatron/file-limit-service","commit_stats":null,"previous_names":["nojronatron/file-limit-service"],"tags_count":2,"template":false,"template_full_name":null,"purl":"pkg:github/nojronatron/file-limit-service","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nojronatron%2Ffile-limit-service","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nojronatron%2Ffile-limit-service/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nojronatron%2Ffile-limit-service/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nojronatron%2Ffile-limit-service/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/nojronatron","download_url":"https://codeload.github.com/nojronatron/file-limit-service/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nojronatron%2Ffile-limit-service/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28772914,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-26T08:38:24.014Z","status":"ssl_error","status_checked_at":"2026-01-26T08:38:22.080Z","response_time":59,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["copilot","dotnet","linux","raspberry-pi"],"created_at":"2026-01-26T09:36:03.793Z","updated_at":"2026-01-26T09:36:04.222Z","avatar_url":"https://github.com/nojronatron.png","language":"C#","funding_links":[],"categories":[],"sub_categories":[],"readme":"# FileLimitService\n\nA .NET 10 C# console application that manages file count in a directory by removing the oldest files when the count exceeds a specified threshold.\n\n## Features\n\n- **Cross-platform**: Targets Windows (x64) and Linux (ARM64)\n- **Asynchronous Operation**: Efficient file operations using async/await\n- **Comprehensive Logging**: Platform-compatible logging to local directories\n  - Windows: `%LOCALAPPDATA%\\FileLimitService\\Logs`\n  - Linux: `/var/log/FileLimitService` or `~/.local/share/FileLimitService/logs`\n- **Detailed Metrics**: Logs include file counts, age statistics, and deletion details\n\n## Usage\n\n### Manual Execution\n\n```bash\n# Using command-line arguments\nFileLimitService \u003ctarget-directory\u003e \u003cmax-file-count\u003e [noui]\n\n# Using configuration file\nFileLimitService --config \u003cconfig-file-path\u003e [noui]\n```\n\n### Arguments\n\n- `target-directory`: Path to the directory to monitor and clean\n- `max-file-count`: Maximum number of files to keep in the directory (non-negative integer)\n- `--config`: Path to JSON configuration file\n- `noui`: (Optional) Suppress all console output while still logging to file\n\n### Examples\n\n```bash\n# Keep only 100 files in the logs directory\nFileLimitService /var/log/myapp 100\n\n# On Windows, keep 50 files in a backup directory\nFileLimitService \"C:\\Backups\\Daily\" 50\n\n# Run silently without console output (useful for automated jobs)\nFileLimitService /var/log/myapp 100 noui\n\n# Use configuration file\nFileLimitService --config /etc/FileLimitService/config.json\n```\n\n### Configuration File Format\n\nCreate a JSON configuration file:\n\n```json\n{\n  \"targetDirectory\": \"/var/log/myapp\",\n  \"maxFileCount\": 100,\n  \"enableLogging\": true\n}\n```\n\n- `targetDirectory`: Path to monitor (required)\n- `maxFileCount`: Maximum files to keep (required, non-negative)\n- `enableLogging`: Enable console/file logging (optional, default: true)\n\n## Building\n\n### Build for all platforms\n\n```bash\ndotnet build FileLimitService.slnx\n```\n\n### Publish for Windows (x64)\n\n```bash\ndotnet publish FileLimitService/FileLimitService.csproj -c Release -r win-x64 --self-contained false -o publish/win-x64\n```\n\n### Publish for Linux (ARM64)\n\n```bash\ndotnet publish FileLimitService/FileLimitService.csproj -c Release -r linux-arm64 --self-contained false -o publish/linux-arm64\n```\n\n### Installing from GitHub Releases\n\nTo download and use pre-built binaries from GitHub Releases:\n\n```bash\n# Download the latest release for Linux ARM64\nwget https://github.com/nojronatron/file-limit-service/releases/latest/download/FileLimitService-linux-arm64.zip\n\n# Extract the archive\nunzip FileLimitService-linux-arm64.zip\n\n# Make the binary executable\nchmod +x FileLimitService\n\n# Run the service\n./FileLimitService /path/to/target 100\n```\n\nThe release archive includes:\n- `FileLimitService` - The main executable\n- `systemd/` - Systemd service and timer unit files\n- `install-system.sh` - System-wide installation script\n\nFor automated deployment, consider setting up a [systemd service](#systemd-service-linux), [cron job](#example-cron-job-linux), or Windows Task Scheduler to run the service on a schedule.\n\n## Systemd Service (Linux)\n\nFileLimitService can run as a systemd service with automatic timer-based execution.\n\n### System-Wide Installation\n\n1. **Download and extract** the latest release:\n   ```bash\n   wget https://github.com/nojronatron/file-limit-service/releases/latest/download/FileLimitService-linux-arm64.zip\n   unzip FileLimitService-linux-arm64.zip\n   ```\n\n2. **Run the installation script**:\n   ```bash\n   sudo ./install-system.sh\n   ```\n\n3. **Edit the configuration file**:\n   ```bash\n   sudo nano /etc/FileLimitService/config.json\n   ```\n   \n   Update `targetDirectory` and `maxFileCount` for your needs.\n\n4. **Test manually** before enabling:\n   ```bash\n   /usr/local/bin/FileLimitService --config /etc/FileLimitService/config.json\n   ```\n\n5. **Enable and start the timer**:\n   ```bash\n   sudo systemctl enable filelimitservice.timer\n   sudo systemctl start filelimitservice.timer\n   ```\n\n### Service Management\n\n```bash\n# Check timer status\nsudo systemctl status filelimitservice.timer\n\n# Check service execution logs\nsudo journalctl -u filelimitservice -f\n\n# Stop the timer\nsudo systemctl stop filelimitservice.timer\n\n# Disable automatic startup\nsudo systemctl disable filelimitservice.timer\n\n# Manually trigger cleanup now\nsudo systemctl start filelimitservice.service\n```\n\n### Customizing Timer Schedule\n\nThe default timer runs every hour. To customize:\n\n```bash\n# Edit the timer unit\nsudo systemctl edit filelimitservice.timer\n```\n\nAdd an override in the editor:\n\n```ini\n[Timer]\n# Run every 2 hours\nOnUnitActiveSec=2h\n```\n\n**Timer interval options:**\n- `1h` = Every hour\n- `2h` = Every 2 hours\n- `12h` = Twice daily\n- `24h` or `1d` = Daily\n- `168h` or `7d` = Weekly\n\nSave and reload:\n\n```bash\nsudo systemctl daemon-reload\nsudo systemctl restart filelimitservice.timer\n```\n\n## Running Tests\n\n```bash\ndotnet test\n```\n\n## How It Works\n\n1. **Validation**: Checks that the target directory exists and arguments are valid\n2. **Enumeration**: Gets all files in the target directory\n3. **Analysis**: Calculates current file count, oldest and newest file ages\n4. **Cleanup**: If file count exceeds threshold, deletes oldest files first\n5. **Logging**: Records all actions with timestamps to platform-specific log directory\n\n## Logging\n\nThe service logs the following information:\n\n- Target directory and maximum file count parameters\n- Current file count before cleanup\n- Oldest and newest file ages (in days)\n- Each deleted file with its age\n- Total count of deleted files\n- Final file count after cleanup\n\nLogs are written to both the console and a timestamped log file.\n\n## Automation\n\nThe service can be automated using:\n\n- **Systemd**: Timer-based service units (Linux) - [See above](#systemd-service-linux)\n- **Cron**: Scheduled jobs (Linux/Unix)\n- **Task Scheduler**: Windows automation\n\n### Example Cron Job (Linux)\n\n```cron\n# Run every day at 2 AM to keep max 1000 files (silent mode)\n0 2 * * * /path/to/FileLimitService /var/log/myapp 1000 noui\n\n# Or use config file\n0 2 * * * /usr/local/bin/FileLimitService --config /etc/FileLimitService/config.json noui\n```\n\n## Future Development\n\n### Phase 3: User Service Support (Planned)\n\nEnable users to run FileLimitService without sudo for personal directories:\n\n- Install to `~/.local/bin/` with `install-user.sh` script\n- User systemd services in `~/.config/systemd/user/`\n- Config files in `~/.config/FileLimitService/config.json`\n- Use `loginctl enable-linger` for background operation after logout\n- Ideal for cleaning `~/Downloads`, `~/tmp`, and other user-owned directories\n\n**Benefits:**\n- No root privileges required\n- Each user manages their own cleanup rules\n- Isolated from system-wide configuration\n\n**Limitations:**\n- Cannot access system directories like `/var/log`\n- Service stops when user logs out (unless linger enabled)\n\n### Phase 4: Multi-Directory Support (Planned)\n\nMonitor multiple directories from a single configuration:\n\n**Config schema:**\n```json\n{\n  \"targets\": [\n    {\"path\": \"/var/log/app1\", \"maxFiles\": 100},\n    {\"path\": \"/var/log/app2\", \"maxFiles\": 50},\n    {\"path\": \"/tmp/cache\", \"maxFiles\": 200}\n  ],\n  \"enableLogging\": true\n}\n```\n\n**Implementation considerations:**\n- Single service execution processes all targets sequentially\n- Individual target failures don't stop processing remaining targets\n- Aggregate logging with per-target metrics\n- Backward compatible with single-directory config format\n\n**Use cases:**\n- Centralized cleanup management for multiple applications\n- Different retention policies per directory\n- Reduced systemd service overhead (one timer instead of many)\n\n## Requirements\n\n- .NET 10 Runtime or SDK\n- Read/write permissions on target directory\n- Write permissions on log directory\n\n## License\n\nSee LICENSE file for details.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnojronatron%2Ffile-limit-service","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnojronatron%2Ffile-limit-service","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnojronatron%2Ffile-limit-service/lists"}