<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>Forem: vaggeliskls</title>
    <description>The latest articles on Forem by vaggeliskls (@vaggeliskls).</description>
    <link>https://forem.com/vaggeliskls</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F572713%2F8036be41-3917-43ff-b738-17b77ab5065a.png</url>
      <title>Forem: vaggeliskls</title>
      <link>https://forem.com/vaggeliskls</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/vaggeliskls"/>
    <language>en</language>
    <item>
      <title>Self-Hosted File Servers: From FTP to WebDAV to Cloud-Native</title>
      <dc:creator>vaggeliskls</dc:creator>
      <pubDate>Sat, 28 Mar 2026 14:52:17 +0000</pubDate>
      <link>https://forem.com/vaggeliskls/self-hosted-file-servers-from-ftp-to-webdav-to-cloud-native-3i3j</link>
      <guid>https://forem.com/vaggeliskls/self-hosted-file-servers-from-ftp-to-webdav-to-cloud-native-3i3j</guid>
      <description>&lt;p&gt;Every developer hits the same question eventually: &lt;em&gt;where do I put the files?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Maybe it's backup artifacts from a CI pipeline. Maybe it's a shared folder for a small team. Maybe you're tired of paying per-seat for Dropbox and want something you actually control.&lt;/p&gt;

&lt;p&gt;The self-hosted file server space has matured a lot, but the sheer number of options can be overwhelming. This article breaks down the main approaches, when each one makes sense, and for the WebDAV path, walks you through two open-source projects I maintain that cover local and cloud storage scenarios.&lt;/p&gt;




&lt;h2&gt;
  
  
  The Landscape: How Do You Want to Serve Files?
&lt;/h2&gt;

&lt;p&gt;Before picking a tool, it helps to understand the categories. Self-hosted file sharing broadly falls into four buckets:&lt;/p&gt;

&lt;h3&gt;
  
  
  1. Traditional File Protocols (FTP/SFTP/SMB)
&lt;/h3&gt;

&lt;p&gt;The old guard. FTP and SFTP are battle-tested and universally supported. SMB (Samba) is the default for Windows network shares. They work, but they come with baggage: FTP sends credentials in plaintext (unless you configure FTPS), SMB is chatty on the network and painful to expose over the internet, and neither protocol plays well with modern auth flows like OAuth or LDAP without extra tooling.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Best for:&lt;/strong&gt; LAN-only file sharing, legacy system integration, printer/scanner destinations.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. Full-Featured Cloud Platforms (Nextcloud, Seafile, FileRun)
&lt;/h3&gt;

&lt;p&gt;These are the "replace Google Drive" solutions. Nextcloud in particular has become the go-to self-hosted platform, offering file sync, calendars, contacts, office document editing, and hundreds of plugins. Seafile focuses more narrowly on file sync with excellent delta-sync performance. FileRun takes a lighter approach, letting you manage files directly on the filesystem with a polished web UI.&lt;/p&gt;

&lt;p&gt;The trade-off is complexity. Nextcloud needs a database, a PHP runtime, and regular maintenance. Seafile's block-based storage means your files aren't directly accessible on the filesystem. These platforms are excellent when you need the full suite, but they're overkill if you just want a folder accessible over the network.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Best for:&lt;/strong&gt; Teams that need a full collaboration platform, users migrating from Google Workspace or Dropbox.&lt;/p&gt;

&lt;h3&gt;
  
  
  3. Sync-First Tools (Syncthing, Resilio)
&lt;/h3&gt;

&lt;p&gt;These aren't servers in the traditional sense. They're peer-to-peer sync engines. Syncthing is fully open-source and does one thing well: keep folders in sync across devices without a central server. There's no web UI for browsing files, no user management, no access control. It's a pipe, not a platform.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Best for:&lt;/strong&gt; Keeping personal devices in sync, distributed backups, scenarios where no central server is desired.&lt;/p&gt;

&lt;h3&gt;
  
  
  4. WebDAV
&lt;/h3&gt;

&lt;p&gt;And then there's WebDAV, the protocol that sits in the sweet spot between "too simple" and "too complex." WebDAV extends HTTP with file operations: upload, download, move, copy, lock, list directories. Every major OS supports it natively (mount it as a network drive on Windows, macOS, or Linux without installing anything). Backup tools like Rclone, Restic, and Duplicati speak WebDAV out of the box. Office applications can open and save documents directly over WebDAV URLs.&lt;/p&gt;

&lt;p&gt;Because it's just HTTP under the hood, you get all the benefits of the HTTP ecosystem: reverse proxies, TLS termination, OAuth/OIDC integration, load balancing, caching headers. All of these work without any protocol translation.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Best for:&lt;/strong&gt; Lightweight file sharing with real access control, backup destinations, CI/CD artifact storage, mobile file access, mounting remote storage as a local drive.&lt;/p&gt;




&lt;h2&gt;
  
  
  Why I Built Two WebDAV Servers
&lt;/h2&gt;

&lt;p&gt;I've been running WebDAV servers in various setups for a while. My original project, &lt;a href="https://github.com/vaggeliskls/webdav-server" rel="noopener noreferrer"&gt;webdav-server&lt;/a&gt;, started as a simple Docker container wrapping Apache httpd with WebDAV modules. Over time it grew to support per-folder permissions, multiple auth methods, and a bunch of operational features.&lt;/p&gt;

&lt;p&gt;But there was a gap: what if your files live in S3 or Google Cloud Storage? Apache's WebDAV module only works with local filesystems. So I built a second project, &lt;a href="https://github.com/vaggeliskls/cloud-webdav-server" rel="noopener noreferrer"&gt;cloud-webdav-server&lt;/a&gt;, written in Go, that presents cloud object storage as a WebDAV drive.&lt;/p&gt;

&lt;p&gt;Here's how the two compare:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;&lt;/th&gt;
&lt;th&gt;&lt;strong&gt;webdav-server&lt;/strong&gt;&lt;/th&gt;
&lt;th&gt;&lt;strong&gt;cloud-webdav-server&lt;/strong&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Runtime&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Apache httpd (Docker)&lt;/td&gt;
&lt;td&gt;Go binary (distroless Docker, ~10 MB)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Storage&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Local filesystem&lt;/td&gt;
&lt;td&gt;Local, Amazon S3/MinIO, Google Cloud Storage&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Auth&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Basic, LDAP, OAuth/OIDC, LDAP+Basic fallback&lt;/td&gt;
&lt;td&gt;Basic, LDAP, OpenID Connect (Bearer)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Permissions&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Per-folder, per-user, exclusions&lt;/td&gt;
&lt;td&gt;Per-folder, per-user, exclusions&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Kubernetes&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;OCI Helm chart&lt;/td&gt;
&lt;td&gt;OCI Helm chart&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Best for&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;On-premise file sharing, NAS replacement&lt;/td&gt;
&lt;td&gt;Cloud-native setups, S3/GCS frontends&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Both share the same &lt;code&gt;FOLDER_PERMISSIONS&lt;/code&gt; syntax, so the mental model transfers between them.&lt;/p&gt;




&lt;h2&gt;
  
  
  Getting Started with webdav-server
&lt;/h2&gt;

&lt;blockquote&gt;
&lt;p&gt;👉 &lt;a href="https://github.com/vaggeliskls/webdav-server" rel="noopener noreferrer"&gt;github.com/vaggeliskls/webdav-server&lt;/a&gt;&lt;br&gt;
📖 &lt;a href="https://vaggeliskls.github.io/webdav-server/" rel="noopener noreferrer"&gt;Full documentation&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The quickest way to get a WebDAV server running:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;1. Create a &lt;code&gt;.env&lt;/code&gt; file:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;BASIC_AUTH_ENABLED=true
BASIC_USERS="alice:alice123 bob:bob123"
FOLDER_PERMISSIONS="/shared:*:ro,/alice:alice:rw,/bob:bob:rw"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;2. Create a &lt;code&gt;docker-compose.yml&lt;/code&gt;:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;services&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;webdav&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;image&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;ghcr.io/vaggeliskls/webdav-server:latest&lt;/span&gt;
    &lt;span class="na"&gt;ports&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;80:8080&lt;/span&gt;
    &lt;span class="na"&gt;volumes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;./webdav-data:/var/lib/dav/data&lt;/span&gt;
    &lt;span class="na"&gt;env_file&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;.env&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;3. Run it:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;docker compose up &lt;span class="nt"&gt;-d&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it. Alice and Bob can both read &lt;code&gt;/shared&lt;/code&gt;, but each can only write to their own folder. Folders are auto-created at startup.&lt;/p&gt;

&lt;h3&gt;
  
  
  Per-Folder Access Control
&lt;/h3&gt;

&lt;p&gt;This is the feature that sets it apart from most WebDAV containers you'll find on Docker Hub. The &lt;code&gt;FOLDER_PERMISSIONS&lt;/code&gt; variable uses a simple format:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;/path:users:mode
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Where &lt;code&gt;users&lt;/code&gt; can be &lt;code&gt;public&lt;/code&gt; (no auth), &lt;code&gt;*&lt;/code&gt; (any authenticated user), specific usernames, or exclusions with &lt;code&gt;!&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# Everyone can read /public, no login needed
# All authenticated users can read /shared except charlie
# Only alice and bob can write to /projects
FOLDER_PERMISSIONS="/public:public:ro,/shared:* !charlie:ro,/projects:alice bob:rw"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Authentication Options
&lt;/h3&gt;

&lt;p&gt;You can enable one or more auth methods:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Basic Auth&lt;/strong&gt;: simplest setup, users defined in the &lt;code&gt;.env&lt;/code&gt; file with bcrypt hashing&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;LDAP&lt;/strong&gt;: connect to Active Directory or any LDAP server for centralized user management&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;OAuth/OIDC&lt;/strong&gt;: integrate with Keycloak, Okta, Azure AD, or any OpenID Connect provider&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;LDAP + Basic fallback&lt;/strong&gt;: try LDAP first, fall back to local users if LDAP auth fails&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  What's New Since v1
&lt;/h3&gt;

&lt;p&gt;Since I first wrote about this project, several features have been added:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Per-folder permissions&lt;/strong&gt; with user inclusion/exclusion&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Public folders&lt;/strong&gt; that require no authentication&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Read-only vs read-write mode&lt;/strong&gt; per folder (configurable HTTP methods)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;CORS support&lt;/strong&gt; for web clients&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Health check endpoint&lt;/strong&gt; (&lt;code&gt;/_health&lt;/code&gt;) for load balancer probes&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;LDAP + Basic fallback&lt;/strong&gt; authentication&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Security test suite&lt;/strong&gt; for validating access control&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Full documentation site&lt;/strong&gt; at &lt;a href="https://vaggeliskls.github.io/webdav-server/" rel="noopener noreferrer"&gt;vaggeliskls.github.io/webdav-server&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  Getting Started with cloud-webdav-server
&lt;/h2&gt;

&lt;blockquote&gt;
&lt;p&gt;👉 &lt;a href="https://github.com/vaggeliskls/cloud-webdav-server" rel="noopener noreferrer"&gt;github.com/vaggeliskls/cloud-webdav-server&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;If your files live in S3 or GCS, this project lets you access them over WebDAV without syncing anything locally.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Local storage (same idea, lighter runtime):&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;STORAGE_TYPE=local
LOCAL_DATA_PATH=/data
BASIC_AUTH_ENABLED=true
BASIC_USERS="alice:alice123"
FOLDER_PERMISSIONS="/files:*:rw"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Amazon S3 / MinIO:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;STORAGE_TYPE=s3
S3_BUCKET=my-bucket
S3_REGION=us-east-1
AWS_ACCESS_KEY_ID=AKIA...
AWS_SECRET_ACCESS_KEY=...
FOLDER_PERMISSIONS="/files:*:rw"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Google Cloud Storage:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;STORAGE_TYPE=gcs
GCS_BUCKET=my-bucket
GOOGLE_APPLICATION_CREDENTIALS=/run/secrets/sa.json
FOLDER_PERMISSIONS="/files:*:rw"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then just &lt;code&gt;docker compose up&lt;/code&gt; and mount &lt;code&gt;http://localhost:8080/files/&lt;/code&gt; as a network drive. Your S3 bucket is now a WebDAV folder.&lt;/p&gt;

&lt;p&gt;The Go binary compiles into a ~10 MB distroless container that runs as a non-root user, lean enough for Kubernetes sidecars or edge deployments.&lt;/p&gt;

&lt;h3&gt;
  
  
  Kubernetes Deployment with OCI Helm Charts
&lt;/h3&gt;

&lt;p&gt;Both projects ship with Kubernetes Helm charts distributed as OCI artifacts. This means you can deploy either WebDAV server to your cluster using standard Helm commands without adding a custom chart repository:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Deploy webdav-server&lt;/span&gt;
helm &lt;span class="nb"&gt;install &lt;/span&gt;webdav oci://ghcr.io/vaggeliskls/charts/webdav-server

&lt;span class="c"&gt;# Deploy cloud-webdav-server&lt;/span&gt;
helm &lt;span class="nb"&gt;install &lt;/span&gt;cloud-webdav oci://ghcr.io/vaggeliskls/charts/cloud-webdav-server
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;OCI-based Helm charts are pulled directly from the container registry, so you get the same versioning and distribution model as your container images. Override values with &lt;code&gt;-f values.yaml&lt;/code&gt; or &lt;code&gt;--set&lt;/code&gt; flags as usual.&lt;/p&gt;




&lt;h2&gt;
  
  
  Practical Use Cases
&lt;/h2&gt;

&lt;p&gt;Here are some real scenarios where a WebDAV server fits perfectly:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Backup destination.&lt;/strong&gt; Tools like Rclone, Restic, and Duplicati support WebDAV natively. Point them at your server and you have a self-hosted backup target with access control.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;CI/CD artifact storage.&lt;/strong&gt; Upload build artifacts with &lt;code&gt;curl -T&lt;/code&gt; after a successful build, download them in downstream jobs. Give the CI bot write access and everyone else read-only:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;FOLDER_PERMISSIONS="/artifacts:ci-bot:rw,/artifacts:*:ro"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Mobile file access.&lt;/strong&gt; Apps like Solid Explorer (Android) and Documents by Readdle (iOS) can connect to WebDAV servers directly. No app-specific sync client needed.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Network drive replacement.&lt;/strong&gt; Mount it on Windows (&lt;code&gt;net use Z: http://server/files/&lt;/code&gt;), macOS (Finder &amp;gt; Connect to Server), or Linux (&lt;code&gt;mount -t davfs&lt;/code&gt;). Native OS support, no client installation.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Document collaboration.&lt;/strong&gt; LibreOffice and Microsoft Office can open and save files directly over WebDAV URLs. No download-edit-upload cycle.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Static file distribution.&lt;/strong&gt; Serve public read-only assets (releases, datasets, documentation) without any authentication overhead. Combine with a reverse proxy for caching and HTTPS.&lt;/p&gt;




&lt;h2&gt;
  
  
  Choosing the Right Approach
&lt;/h2&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Scenario&lt;/th&gt;
&lt;th&gt;Recommended approach&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Full Google Drive replacement with office editing, calendars, etc.&lt;/td&gt;
&lt;td&gt;Nextcloud or Seafile&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Syncing folders between personal devices&lt;/td&gt;
&lt;td&gt;Syncthing&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Lightweight file sharing with access control&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;webdav-server&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Serving files from S3/GCS over WebDAV&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;cloud-webdav-server&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;LAN-only sharing with Windows machines&lt;/td&gt;
&lt;td&gt;SMB/Samba&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Legacy system integration&lt;/td&gt;
&lt;td&gt;FTP/SFTP&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;CI/CD artifacts, backup targets, mobile access&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;webdav-server&lt;/strong&gt; or &lt;strong&gt;cloud-webdav-server&lt;/strong&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;There's no single right answer. It depends on what you're storing, who needs access, and how much infrastructure you want to manage. But if you need something between "raw FTP" and "full Nextcloud deployment," WebDAV hits a sweet spot that's worth considering.&lt;/p&gt;




&lt;h2&gt;
  
  
  Links
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;webdav-server&lt;/strong&gt;: &lt;a href="https://github.com/vaggeliskls/webdav-server" rel="noopener noreferrer"&gt;github.com/vaggeliskls/webdav-server&lt;/a&gt;, Apache-based, Docker, Basic/LDAP/OAuth&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;cloud-webdav-server&lt;/strong&gt;: &lt;a href="https://github.com/vaggeliskls/cloud-webdav-server" rel="noopener noreferrer"&gt;github.com/vaggeliskls/cloud-webdav-server&lt;/a&gt;, Go-based, S3/GCS/local, ~10 MB image&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Documentation&lt;/strong&gt;: &lt;a href="https://vaggeliskls.github.io/webdav-server/" rel="noopener noreferrer"&gt;vaggeliskls.github.io/webdav-server&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you find these useful, a ⭐ on GitHub is always appreciated. Issues and PRs are welcome.&lt;/p&gt;

</description>
      <category>selfhosted</category>
      <category>docker</category>
      <category>devops</category>
      <category>kubernetes</category>
    </item>
    <item>
      <title>Deploy a Secure Containerised WebDAV Server with Docker in Minutes</title>
      <dc:creator>vaggeliskls</dc:creator>
      <pubDate>Tue, 16 Sep 2025 12:12:40 +0000</pubDate>
      <link>https://forem.com/vaggeliskls/deploy-a-secure-containerised-webdav-server-with-docker-in-minutes-20d6</link>
      <guid>https://forem.com/vaggeliskls/deploy-a-secure-containerised-webdav-server-with-docker-in-minutes-20d6</guid>
      <description>&lt;p&gt;Deploy a secure, lightweight WebDAV server with Docker in minutes. This containerised solution supports Basic, LDAP, and OAuth authentication, making it ideal for self-hosted file sharing, backups, and enterprise remote access with minimal setup.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;👉 Check it out on GitHub: &lt;a href="https://github.com/vaggeliskls/webdav-server" rel="noopener noreferrer"&gt;vaggeliskls/webdav-server&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  📖 What is WebDAV?
&lt;/h2&gt;

&lt;p&gt;WebDAV (Web Distributed Authoring and Versioning) is an extension of HTTP that lets you manage files on a server upload, download, edit, move, and share as if it were local storage. It’s widely supported across operating systems, backup tools, and mobile apps.&lt;/p&gt;

&lt;p&gt;This project provides a modern, containerised WebDAV server that’s:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Easy to deploy with Docker 🐳&lt;/li&gt;
&lt;li&gt;Flexible in authentication 🔐&lt;/li&gt;
&lt;li&gt;Ideal for self-hosting and enterprise use 🏢&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  📦 Prerequisites
&lt;/h2&gt;

&lt;p&gt;Before starting, ensure you have:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Docker&lt;/strong&gt; version &lt;strong&gt;20.0 or higher&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;Basic understanding of containers and WebDAV&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  🚀 Key Features
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Effortless Deployment&lt;/strong&gt;: Set up a fully operational WebDAV server quickly using Docker.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Flexible Authentication&lt;/strong&gt;:

&lt;ul&gt;
&lt;li&gt;Basic Authentication 🛡️&lt;/li&gt;
&lt;li&gt;LDAP Authentication 🛡️&lt;/li&gt;
&lt;li&gt;OAuth Authentication 🛡️&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;

&lt;strong&gt;Proxy-Ready&lt;/strong&gt;: Easily integrate with reverse proxies to add more authentication layers.&lt;/li&gt;

&lt;li&gt;

&lt;strong&gt;Authentication is Optional&lt;/strong&gt;: The server runs without authentication by default, allowing flexibility for your setup.&lt;/li&gt;

&lt;/ul&gt;




&lt;h2&gt;
  
  
  🔧 Authentication Setup
&lt;/h2&gt;

&lt;p&gt;You can enable various authentication mechanisms using environment variables in a &lt;code&gt;.env&lt;/code&gt; file. Here’s how to configure each one:&lt;/p&gt;

&lt;h3&gt;
  
  
  🔐 Basic Authentication
&lt;/h3&gt;

&lt;p&gt;Authentication is controlled via environment variables in a &lt;code&gt;.env&lt;/code&gt; file.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nv"&gt;BASIC_AUTH_ENABLED&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;true
&lt;/span&gt;&lt;span class="nv"&gt;BASIC_AUTH_REALM&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;WebDAV
&lt;span class="nv"&gt;BASIC_USERS&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;alice:alice123 bob:bob123
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  🔐 OAuth Authentication
&lt;/h3&gt;

&lt;p&gt;OAuth authentication (&lt;a href="https://github.com/vaggeliskls/devops-docker-projects/tree/main/charts/keycloak-webdav" rel="noopener noreferrer"&gt;example with Keycloak&lt;/a&gt;) configuration:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;OAUTH_ENABLED=true
OIDCProviderMetadataURL="http://keycloak/keycloak-auth/realms/master/.well-known/openid-configuration"
OIDCRedirectURI="http://my-domain.local/redirect_uri"
OIDCCryptoPassphrase="randomly_generated_secure_passphrase"
OIDCClientID="webdav-client"
OIDCClientSecret="ABC123def456GHI789jkl0mnopqrs"
OIDCProviderTokenEndpointAuth="client_secret_basic"
OIDCRemoteUserClaim="preferred_username"
OIDCScope="openid email profile"
OIDCXForwardedHeaders="X-Forwarded-Host"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;More examples with different identity providers can be found on the &lt;a href="https://github.com/OpenIDC/mod_auth_openidc" rel="noopener noreferrer"&gt;mod_auth_openidc&lt;/a&gt; GitHub page.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  🔐 LDAP Authentication
&lt;/h3&gt;

&lt;p&gt;LDAP integration for centralized user management:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;LDAP_ENABLED=true
LDAP_URL=ldaps://ldap.example.com
LDAP_ATTRIBUTE=uid
LDAP_BASE_DN=ou=users,dc=example,dc=com
LDAP_BIND_DN=uid=admin,ou=users,dc=example,dc=com
LDAP_BIND_PASSWORD=securepassword
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  📑 WebDAV Methods and Access Control
&lt;/h2&gt;

&lt;p&gt;Control allowed methods with the &lt;code&gt;WEBDAV_OPERATIONS&lt;/code&gt; variable.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Method&lt;/th&gt;
&lt;th&gt;Purpose&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;GET&lt;/td&gt;
&lt;td&gt;Download a file or resource&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;OPTIONS&lt;/td&gt;
&lt;td&gt;Discover server-supported methods&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PROPFIND&lt;/td&gt;
&lt;td&gt;List directory contents, get resource metadata&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PUT&lt;/td&gt;
&lt;td&gt;Upload a file&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;DELETE&lt;/td&gt;
&lt;td&gt;Delete a file or resource&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MKCOL&lt;/td&gt;
&lt;td&gt;Create a new collection (folder)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;COPY&lt;/td&gt;
&lt;td&gt;Copy a resource&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MOVE&lt;/td&gt;
&lt;td&gt;Move or rename a resource&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;LOCK&lt;/td&gt;
&lt;td&gt;Lock a resource&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;UNLOCK&lt;/td&gt;
&lt;td&gt;Unlock a resource&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PROPPATCH&lt;/td&gt;
&lt;td&gt;Set or remove resource properties&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;REPORT&lt;/td&gt;
&lt;td&gt;Query for information (advanced WebDAV clients)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PATCH&lt;/td&gt;
&lt;td&gt;Partial update of a resource&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;HEAD&lt;/td&gt;
&lt;td&gt;Retrieve headers only (no body)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;POST&lt;/td&gt;
&lt;td&gt;Submit data (rarely used in WebDAV, sometimes for locking)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;




&lt;h2&gt;
  
  
  ⚡ Usage Example
&lt;/h2&gt;

&lt;p&gt;1) Create a &lt;code&gt;.env&lt;/code&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;WEBDAV_OPERATIONS="GET OPTIONS PROPFIND"
LDAP_ENABLED=false
OAUTH_ENABLED=false
BASIC_AUTH_ENABLED=false
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;2) Create a &lt;code&gt;docker-compose.yaml&lt;/code&gt; file&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;services:
  webdav:
    image: ghcr.io/vaggeliskls/webdav-server:latest
    ports:
      - 8080:8080
    volumes:
      - ./webdav-data:/var/lib/dav/data
    env_file:
      - .env
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;3) Run the server&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;docker compose up -d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;4) Access it Open: &lt;a href="http://localhost:8080" rel="noopener noreferrer"&gt;http://localhost:8080&lt;/a&gt;&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;This example runs an &lt;strong&gt;unauthenticated server&lt;/strong&gt;. For production, enable HTTPS and authentication.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  📚 References
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://github.com/mgutt/docker-apachewebdav" rel="noopener noreferrer"&gt;Docker Apache WebDAV&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.jscape.com/blog/what-is-webdav" rel="noopener noreferrer"&gt;What is WebDAV?&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>docker</category>
      <category>devops</category>
      <category>selfhosted</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>Rehosting Bitnami Secure Images with Specific Tags</title>
      <dc:creator>vaggeliskls</dc:creator>
      <pubDate>Mon, 15 Sep 2025 12:35:30 +0000</pubDate>
      <link>https://forem.com/vaggeliskls/rehosting-bitnami-secure-images-with-specific-tags-2bfi</link>
      <guid>https://forem.com/vaggeliskls/rehosting-bitnami-secure-images-with-specific-tags-2bfi</guid>
      <description>&lt;p&gt;Bitnami recently updated its policy, restricting direct access to their secure container images (&lt;a href="https://github.com/bitnami/containers/issues/83267" rel="noopener noreferrer"&gt;discussion here&lt;/a&gt;). This change impacts automated workflows, CI/CD pipelines, and production deployments that rely on Bitnami images and Helm charts.&lt;/p&gt;

&lt;p&gt;To address this, the &lt;strong&gt;Bitnami Secure Hosting&lt;/strong&gt; repository provides a workflow to &lt;strong&gt;rehost and tag secure images&lt;/strong&gt; for stable, policy-compliant usage.  &lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;👉 Check it out on GitHub: &lt;a href="https://github.com/vaggeliskls/bitnami-secure-hosting" rel="noopener noreferrer"&gt;bitnami-secure-hosting&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  🔍 The Problem
&lt;/h2&gt;

&lt;p&gt;Bitnami’s new policy introduces:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;“A focused set of more hardened, more secure images. These free images are intended for development and are only available on the latest tag. You can find them at bitnamisecure on Docker Hub&lt;br&gt;
.”&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;This approach creates a major issue for developers and production teams:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;🏷️ Only latest is available — you cannot select a specific version.&lt;/li&gt;
&lt;li&gt;🔄 Reproducibility breaks — the same latest tag may change without notice.&lt;/li&gt;
&lt;li&gt;⚠️ CI/CD pipelines become unstable, since updates may introduce unexpected changes.&lt;/li&gt;
&lt;li&gt;🛑 Production systems lose reliability, because you can’t lock deployments to a tested version.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In practice, this makes the “focused, secure images” unstable and impractical for anyone who needs predictable builds, controlled upgrades, or long-term maintenance.&lt;/p&gt;




&lt;h2&gt;
  
  
  🎯 The Goal
&lt;/h2&gt;

&lt;p&gt;The purpose of the repository &lt;a href="https://github.com/vaggeliskls/bitnami-secure-hosting" rel="noopener noreferrer"&gt;&lt;strong&gt;bitnami-secure-hosting&lt;/strong&gt;&lt;/a&gt; is to:  &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Reverse-engineer Bitnami &lt;code&gt;latest&lt;/code&gt; tag creation&lt;/strong&gt;.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Tag each secure image with a specific version&lt;/strong&gt; for better tracking.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Enable controlled testing&lt;/strong&gt; of each image before deployment.
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;This ensures that teams can continue using Bitnami images safely without relying on a moving &lt;code&gt;latest&lt;/code&gt; tag, reducing production risks.  &lt;/p&gt;




&lt;h2&gt;
  
  
  💡 The Solution
&lt;/h2&gt;

&lt;p&gt;The &lt;strong&gt;Bitnami Secure Hosting&lt;/strong&gt; repository solves these problems by:  &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Fetching the latest secure images&lt;/strong&gt; from Bitnami's official secure registry (&lt;code&gt;docker.io/bitnamisecure&lt;/code&gt;).
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Inspecting and pinning each image&lt;/strong&gt; to a specific product version using fields like &lt;code&gt;APP_VERSION&lt;/code&gt;.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Rehosting images&lt;/strong&gt; to a self-managed registry (&lt;code&gt;ghcr.io/vaggeliskls&lt;/code&gt; by default) for secure, predictable access.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Automating the workflow&lt;/strong&gt; to ensure images remain up-to-date and safe for production.
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;This approach provides &lt;strong&gt;control, compliance, and reliability&lt;/strong&gt; for teams that cannot rely on &lt;code&gt;latest&lt;/code&gt; tags.  &lt;/p&gt;




&lt;h2&gt;
  
  
  🚀 How It Works
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Pull images&lt;/strong&gt; from the official Bitnami secure registry.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Inspect images&lt;/strong&gt; to determine the product version.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Re-tag images&lt;/strong&gt; according to their version.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Push images&lt;/strong&gt; to your self-managed registry for safe usage.
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Automated updates&lt;/strong&gt; ensure the registry stays current without manual intervention.
&lt;/li&gt;
&lt;/ol&gt;




&lt;h2&gt;
  
  
  ✅ Conclusion – My Point of View
&lt;/h2&gt;

&lt;p&gt;From my perspective, Bitnami’s new approach &lt;strong&gt;cannot be considered production-ready&lt;/strong&gt;. Even their own documentation clarifies that the free, secure images are &lt;strong&gt;intended only for development use&lt;/strong&gt;.  &lt;/p&gt;

&lt;p&gt;This policy shift feels like a &lt;strong&gt;setback for the open-source community&lt;/strong&gt;. We’ve already seen similar moves from Docker, which introduced premium hardened images — raising the same concerns.  &lt;/p&gt;

&lt;p&gt;It makes me wonder:  &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;🤔 Will official public images continue to be updated with the same &lt;strong&gt;frequency&lt;/strong&gt; and &lt;strong&gt;security focus&lt;/strong&gt;?
&lt;/li&gt;
&lt;li&gt;Or will the priority shift toward &lt;strong&gt;paid solutions&lt;/strong&gt; while the community versions stagnate?
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The open-source ecosystem we’ve relied on for years is &lt;strong&gt;starting to change&lt;/strong&gt;, and not always for the better.  &lt;/p&gt;

&lt;p&gt;While there are alternatives to Bitnami images themselves, the real impact is deeper:  &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Kubernetes deployments&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Helm charts in production&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Automated CI/CD workflows&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;All of these depend heavily on predictable, versioned images. Without them, reproducibility and reliability suffer — especially at scale.  &lt;/p&gt;

&lt;p&gt;In short, this transition doesn’t just affect images, it creates &lt;strong&gt;long-term challenges for production-grade deployments&lt;/strong&gt; in the open-source world.  &lt;/p&gt;

</description>
      <category>docker</category>
      <category>bitnami</category>
      <category>devops</category>
      <category>containers</category>
    </item>
    <item>
      <title>Buttercup Password Manager for Startups 🛡️</title>
      <dc:creator>vaggeliskls</dc:creator>
      <pubDate>Sun, 20 Oct 2024 17:24:39 +0000</pubDate>
      <link>https://forem.com/vaggeliskls/buttercup-password-manager-for-startups-46ni</link>
      <guid>https://forem.com/vaggeliskls/buttercup-password-manager-for-startups-46ni</guid>
      <description>&lt;p&gt;In today's digital age, managing passwords securely is crucial for individuals and businesses alike. The Buttercup password manager offers a versatile solution, allowing users to store their vaults locally or utilize cloud services like Dropbox and Google Drive. However, for companies seeking to host their password management in-house, a custom WebDAV server can be an ideal solution.&lt;/p&gt;

&lt;h2&gt;
  
  
  🌐 Why Choose a WebDAV Server?
&lt;/h2&gt;

&lt;p&gt;WebDAV (Web Distributed Authoring and Versioning) is a protocol that enables clients to manage files on remote servers. By setting up your own WebDAV server, you gain greater control over your data, enhancing security and privacy while ensuring compliance with organizational policies.&lt;/p&gt;

&lt;h2&gt;
  
  
  🔑 Key Features
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Custom Authentication&lt;/strong&gt;: The Buttercup WebDAV server supports both &lt;strong&gt;LDAP&lt;/strong&gt; and &lt;strong&gt;Basic static authentication&lt;/strong&gt;, making it suitable for small to medium-sized companies that need robust user management.management.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Docker Support&lt;/strong&gt;: Deploying the WebDAV server with Docker is straightforward, allowing for quick setup and scalability. This ensures that your environment can grow with your business needs.&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  📥 Download the Buttercup Client
&lt;/h2&gt;

&lt;p&gt;Before deploying the WebDAV server, don’t forget to download the Buttercup client from the &lt;a href="https://buttercup.pw/" rel="noopener noreferrer"&gt;official website&lt;/a&gt;. This client allows you to access and manage your vault seamlessly.&lt;/p&gt;

&lt;h2&gt;
  
  
  🚀 Getting Started
&lt;/h2&gt;

&lt;p&gt;To deploy your Buttercup WebDAV server:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Clone the Repository&lt;/strong&gt;: Start by cloning the &lt;a href="https://github.com/vaggeliskls/buttercup-webdav-server" rel="noopener noreferrer"&gt;Buttercup WebDAV server repository&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Configure Environment Variables&lt;/strong&gt;: Edit the .env file to customize your setup. This includes configuring your authentication methods and any specific settings for your environment.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Launch the Server&lt;/strong&gt;: Use Docker Compose to bring your server online with a simple command, enabling easy management of containers.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Access Your Vault&lt;/strong&gt;: Open the Buttercup client, enter your server's URL, and authenticate with your chosen credentials. This grants you access to your securely stored passwords.&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  🔒 Secure Your Connection
&lt;/h2&gt;

&lt;p&gt;For secure access, it's advisable to configure TLS/HTTPS using a reverse proxy like Traefik. This adds an extra layer of security, ensuring that your data remains safe during transmission and protects against potential attacks.&lt;/p&gt;

&lt;h2&gt;
  
  
  🎉 Conclusion
&lt;/h2&gt;

&lt;p&gt;The Buttercup WebDAV server is a powerful tool for businesses looking to manage passwords securely in-house. By leveraging Docker and customizable authentication methods, you can create a tailored solution that meets your company's needs.&lt;/p&gt;

&lt;p&gt;For more details and to get started, check out the &lt;a href="https://github.com/vaggeliskls/buttercup-webdav-server" rel="noopener noreferrer"&gt;GitHub repository&lt;/a&gt; and explore the &lt;a href="https://github.com/vaggeliskls/webdav-server" rel="noopener noreferrer"&gt;WebDAV server documentation&lt;/a&gt;.&lt;/p&gt;

</description>
      <category>buttercup</category>
      <category>tutorial</category>
      <category>devops</category>
      <category>opensource</category>
    </item>
    <item>
      <title>Pull images from private docker registry in Kubernetes cluster 🐳</title>
      <dc:creator>vaggeliskls</dc:creator>
      <pubDate>Sat, 22 Jun 2024 20:49:26 +0000</pubDate>
      <link>https://forem.com/vaggeliskls/pull-images-from-private-docker-registry-in-kubernetes-cluster-25al</link>
      <guid>https://forem.com/vaggeliskls/pull-images-from-private-docker-registry-in-kubernetes-cluster-25al</guid>
      <description>&lt;p&gt;When working with Kubernetes, especially for deploying applications, authenticating with private image repositories is often necessary. This process is crucial for AWS ECR registries and other Docker-related registries. This post introduces a Helm chart designed to simplify and streamline this authentication process, making your workflow smoother.&lt;/p&gt;

&lt;p&gt;📦 Helm Chart Repository: &lt;code&gt;oci://registry-1.docker.io/vaggeliskls/k8s-registry-auth&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Remember to star ⭐ this Helm chart if you find it useful! More info available at &lt;a href="https://github.com/vaggeliskls/k8s-registry-auth"&gt;GitHub&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Supported Image Registries 🌐
&lt;/h2&gt;

&lt;p&gt;This Helm chart mainly supports AWS ECR registries, but it also includes support for other popular registries. Specifically, it has been tested with the following registries:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Amazon ECR&lt;/li&gt;
&lt;li&gt;JFrog Artifactory&lt;/li&gt;
&lt;li&gt;Nexus&lt;/li&gt;
&lt;li&gt;Docker Hub&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;While it has not yet been tested with the following registries, initial support is available:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Harbor&lt;/li&gt;
&lt;li&gt;IBM Cloud Container Registry&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Furthermore, future support is planned for:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Google Artifact Registry&lt;/li&gt;
&lt;li&gt;Azure Container Registry&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;It's important to note for those using AWS ECR registries that re-authentication is required every 12 hours. To address this, the Helm chart includes a cronjob that refreshes the login automatically, ensuring you are always authenticated to your registry.&lt;/p&gt;

&lt;h2&gt;
  
  
  Prerequisites 🛠️
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://helm.sh/docs/intro/install/"&gt;Helm version 3&lt;/a&gt; or higher must be installed on your system before proceeding.&lt;/p&gt;

&lt;h2&gt;
  
  
  Using the Helm Chart 🚀
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Configuration
&lt;/h3&gt;

&lt;p&gt;Configure the registry field to specify the target registry for authentication. You can set registry credentials in two ways:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;Using an Existing Secret&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Providing Static Username and Password in values.yaml&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;For &lt;a href="https://github.com/vaggeliskls/k8s-registry-auth/wiki/Examples"&gt;examples&lt;/a&gt; for both AWS ECR and generic Docker registries, see the dedicated examples section.&lt;/p&gt;

&lt;h2&gt;
  
  
  Examples
&lt;/h2&gt;

&lt;h3&gt;
  
  
  AWS ECR
&lt;/h3&gt;

&lt;p&gt;Assuming your Helm is set up correctly, use one of the following commands:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;For existing secrets:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;helm upgrade --install k8s-registry-auth oci://registry-1.docker.io/vaggeliskls/k8s-registry-auth  --set registry=123456789123.dkr.ecr.region.amazonaws.com --set awsEcr.enabled=true --set secretConfigName=secret-name
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;For static credentials:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;helm upgrade --install k8s-registry-auth oci://registry-1.docker.io/vaggeliskls/k8s-registry-auth  --set registry=123456789123.dkr.ecr.region.amazonaws.com --set awsEcr.enabled=true --set registryUsername=username --set registryPassword=password
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;Replace &lt;code&gt;123456789123.dkr.ecr.region.amazonaws.com&lt;/code&gt; with your own AWS ECR registry URL. If you're using a specific version of this OCI repository, add &lt;code&gt;--version 1.0.1&lt;/code&gt;.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  Docker Based Registries Examples
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;For existing secrets:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;helm upgrade --install k8s-registry-auth oci://registry-1.docker.io/vaggeliskls/k8s-registry-auth  --set registry=yourdomain.com --set docker.enabled=true --set secretConfigName=secret-name
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;For static credentials:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;helm upgrade --install k8s-registry-auth oci://registry-1.docker.io/vaggeliskls/k8s-registry-auth  --set registry=yourdomain.com --set docker.enabled=true --set registryUsername=username --set registryPassword=password
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;Replace &lt;code&gt;yourdomain.com&lt;/code&gt; with your registry's domain name.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;Authenticating image registries doesn't have to be a painful process when deploying applications on Kubernetes. With this Helm chart, you can easily manage and automate this process&lt;/p&gt;

</description>
      <category>kubernetes</category>
      <category>authentication</category>
      <category>cloud</category>
      <category>helm</category>
    </item>
    <item>
      <title>Windows GitHub Self Hosted Runner inside a Linux Container</title>
      <dc:creator>vaggeliskls</dc:creator>
      <pubDate>Sat, 18 May 2024 15:00:30 +0000</pubDate>
      <link>https://forem.com/vaggeliskls/windows-github-self-hosted-runner-inside-a-linux-container-g5m</link>
      <guid>https://forem.com/vaggeliskls/windows-github-self-hosted-runner-inside-a-linux-container-g5m</guid>
      <description>&lt;p&gt;With ever-increasing advancements in the world of CI/CD pipelines, innovation is inevitable. Welcome to the exploration of an efficient, cost-effective, and innovative approach to deploying self hosted GitHub Runner. This runner operates in a containerized Windows OS (x64) environment on a Linux system.&lt;/p&gt;

&lt;p&gt;The approach leverages the strengths of Vagrant VM, libvirt, and Docker Compose, allowing seamless management of a Windows instance just like any Docker container. The takeaway is the creation of a plug-and-play solution, significantly enhancing convenience, optimizing resource allocation, and integrating flawlessly with existing workflows.&lt;/p&gt;

&lt;p&gt;For those working in various dev-ops environments, this strategy provides a smooth and comprehensive solution that does not require prior knowledge of VM creation.&lt;/p&gt;

&lt;p&gt;This guide is built upon the &lt;a href="https://github.com/vaggeliskls/windows-github-custom-runner" rel="noopener noreferrer"&gt;https://github.com/vaggeliskls/windows-github-custom-runner&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  📋 Prerequisites
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Docker version 24 or higher&lt;/li&gt;
&lt;li&gt;Docker-compose version 1.18 or higher&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  🚥 Authentication Methods for Self-Hosted
&lt;/h2&gt;

&lt;p&gt;To authenticate your custom self-hosted runners, two methods are available:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;Personal Access Token (&lt;code&gt;PAT&lt;/code&gt;): A static, manually created token that provides long-term and secure access to GitHub. This token requires Read and Write access to the GitHub organization’s self-hosted runners.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Registration Token (&lt;code&gt;TOKEN&lt;/code&gt;): A dynamic, short-lived token that is automatically generated by GitHub when creating a new self-hosted runner. This method offers a temporary but immediate solution for authentication.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;⚠ Note:&lt;/strong&gt; Only one of these authentication methods is needed. Choose the one that best suits your requirements.&lt;/p&gt;

&lt;h2&gt;
  
  
  🚀 Deployment Guide
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;1)&lt;/strong&gt; Create/Update the environmental file .env&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;PAT&lt;/code&gt;: Personal access token from GitHub&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;TOKEN&lt;/code&gt;: Short lived Github token&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;RUNNER_URL&lt;/code&gt;: The URL of the GitHub that the runner connects to&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;RUNNERS&lt;/code&gt;: Number of runners&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;MEMORY&lt;/code&gt;: Amount of memory for the Vagrant image (in MB)&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;CPU&lt;/code&gt;: Number of CPUs for the Vagrant image&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;DISK_SIZE&lt;/code&gt;: Disk size for the Vagrant image (in GB)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Example with PAT&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# Runner settings
PAT=&amp;lt;Your Personal access token&amp;gt;
RUNNER_URL=&amp;lt;runner url&amp;gt;
RUNNERS=1
# Vagrant image settings
MEMORY=8000 # 8GB
CPU=4
DISK_SIZE=100

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Example with TOKEN&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# Runner settings
TOKEN=&amp;lt;Your short lived acess token&amp;gt;
RUNNER_URL=&amp;lt;runner url&amp;gt;
RUNNERS=1
# Vagrant image settings
MEMORY=8000 # 8GB
CPU=4
DISK_SIZE=100
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;2)&lt;/strong&gt; Create &lt;code&gt;docker-compose.yml&lt;/code&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;version: "3.9"

services:
  windows-github-runner-vm:
    image: docker.io/vaggeliskls/windows-github-custom-runner:latest
    env_file: .env
    stdin_open: true
    tty: true
    privileged: true
    ports:
      - 3389:3389
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;3)&lt;/strong&gt; Run: &lt;code&gt;docker-compose up -d&lt;/code&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  🌐 Access via Remote Desktop
&lt;/h2&gt;

&lt;p&gt;For debugging purposes or testing you can always connect to the VM with remote desktop softwares.&lt;/p&gt;

&lt;p&gt;Some software that used when developed was&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Linux: &lt;code&gt;rdesktop rdesktop &amp;lt;ip&amp;gt;:3389&lt;/code&gt; or &lt;a href="https://remmina.org/" rel="noopener noreferrer"&gt;remina&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;MacOS: &lt;a href="https://apps.apple.com/us/app/microsoft-remote-desktop/id1295203466?mt=12" rel="noopener noreferrer"&gt;Windows remote desktop&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Windows: buildin &lt;code&gt;Remote Windows Connection&lt;/code&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  🔑 User Login
&lt;/h2&gt;

&lt;p&gt;The default users based on vagrant image are&lt;/p&gt;

&lt;p&gt;1) Administrator&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Username: Administrator&lt;/li&gt;
&lt;li&gt;Password: vagrant&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;2) User&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Username: vagrant&lt;/li&gt;
&lt;li&gt;Password: vagrant&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  📚 Further Reading and Resources
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://github.com/vaggeliskls/windows-in-docker-container" rel="noopener noreferrer"&gt;Windows in docker container&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/SecurityWeekly/vulhub-lab" rel="noopener noreferrer"&gt;Windows Vagrant Tutorial&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://app.vagrantup.com/peru/boxes/windows-server-2022-standard-x64-eval" rel="noopener noreferrer"&gt;Vagrant image: peru/windows-server-2022-standard-x64-eval&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.vagrantup.com/" rel="noopener noreferrer"&gt;Vagrant by HashiCorp&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/axon-technologies/installing-a-windows-virtual-machine-in-a-linux-docker-container-c78e4c3f9ba1" rel="noopener noreferrer"&gt;Windows Virtual Machine in a Linux Docker Container&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>github</category>
      <category>devops</category>
      <category>windows</category>
      <category>vagrant</category>
    </item>
    <item>
      <title>Windows VM Inside a Linux Docker Container</title>
      <dc:creator>vaggeliskls</dc:creator>
      <pubDate>Sat, 21 Oct 2023 13:05:27 +0000</pubDate>
      <link>https://forem.com/vaggeliskls/windows-vm-inside-a-linux-docker-container-54ol</link>
      <guid>https://forem.com/vaggeliskls/windows-vm-inside-a-linux-docker-container-54ol</guid>
      <description>&lt;p&gt;When it comes to creating reproducible and isolated development environments, two leading technologies reign: Docker and Vagrant. Docker facilitates containerization by bundling applications and dependencies together, making the applications platform-independent. On the other hand, Vagrant is a tool for virtual environments, allowing the creation and management of virtual machines (VMs). Running a Vagrant VM, particularly a Windows VM, inside a Docker container creates a unique combination that can offer remarkable benefits, especially in the field of Continuous Integration (CI) and Continuous Deployment (CD). 🔂 🚀&lt;/p&gt;

&lt;p&gt;Today, we'll tap into an existing GitHub repository that demonstrates how to implement a Windows VM within this Docker/Vagrant setup. The repository can be found at the following URL: &lt;a href="https://github.com/vaggeliskls/windows-in-docker-container" rel="noopener noreferrer"&gt;https://github.com/vaggeliskls/windows-in-docker-container&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Prerequisites 📑
&lt;/h2&gt;

&lt;p&gt;Before proceeding, the following tools should be installed on your system:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://docs.docker.com/engine/install/" rel="noopener noreferrer"&gt;Docker&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://docs.docker.com/compose/install/" rel="noopener noreferrer"&gt;Docker-compose&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  How to Use It 🛠️
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;Create an environmental file &lt;strong&gt;.env&lt;/strong&gt; with VMs specifications
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# Vagrant image settings
MEMORY=8000 # 8GB
CPU=4
DISK_SIZE=100
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Create a &lt;code&gt;docker-compose.yml&lt;/code&gt; file
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;version: "3.9"

services:
  win10:
    image: docker.io/vaggeliskls/windows-in-docker-container:latest
    env_file: .env
    stdin_open: true
    tty: true
    privileged: true
    cgroup: host
    restart: always
    ports:
      - 3389:3389
      - 2222:2222
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Run: &lt;code&gt;docker-compose up -d&lt;/code&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmkvvl922ql58nox2sge9.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmkvvl922ql58nox2sge9.png" alt="Windows vm screenshot" width="800" height="483"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Remote Desktop 🖥️
&lt;/h2&gt;

&lt;p&gt;For debugging purposes or testing, you can always connect to the VM with remote desktop software products. Some software that used when developed was:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Linux: &lt;a href="http://www.rdesktop.org/" rel="noopener noreferrer"&gt;rdesktop&lt;/a&gt; IP:3389 or &lt;a href="https://remmina.org/" rel="noopener noreferrer"&gt;remina&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;macOS: &lt;a href="https://apps.apple.com/fr/app/microsoft-remote-desktop/id1295203466?mt=12" rel="noopener noreferrer"&gt;Windows remote desktop&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Windows: build in Remote Windows Connection&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  User login 👤
&lt;/h2&gt;

&lt;p&gt;The default users based on vagrant image are&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Administrator

&lt;ul&gt;
&lt;li&gt;Username: Administrator&lt;/li&gt;
&lt;li&gt;Password: vagrant&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;li&gt;User

&lt;ul&gt;
&lt;li&gt;Username: vagrant&lt;/li&gt;
&lt;li&gt;Password: vagrant&lt;/li&gt;
&lt;/ul&gt;


&lt;/li&gt;

&lt;/ul&gt;

&lt;h2&gt;
  
  
  Conclusion 👋
&lt;/h2&gt;

&lt;p&gt;Running a Vagrant Windows VM inside a Docker container merges the benefits of Docker's platform-independent containerization with Vagrant's controlled, easy-to-manage development environments. Although such a setup won't fulfill every use case, understanding how Docker and Vagrant operate and interact is highly beneficial for DevOps professionals.&lt;/p&gt;

&lt;p&gt;Remember, different configurations exist and this setup can be tweaked to suit specific application requirements. Be aware that running a VM inside a Docker container can be resource-intensive, so always check your system's specifications before proceeding. 📝&lt;/p&gt;

&lt;p&gt;Happy coding!&lt;/p&gt;

&lt;h2&gt;
  
  
  References 📚
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://github.com/SecurityWeekly/vulhub-lab" rel="noopener noreferrer"&gt;Windows Vagrant Tutorial&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://app.vagrantup.com/peru/boxes/windows-server-2022-standard-x64-eval" rel="noopener noreferrer"&gt;Vagrant image: peru/windows-server-2022-standard-x64-eval&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.vagrantup.com/" rel="noopener noreferrer"&gt;Vagrant by HashiCorp&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/axon-technologies/installing-a-windows-virtual-machine-in-a-linux-docker-container-c78e4c3f9ba1" rel="noopener noreferrer"&gt;Windows Virtual Machine in a Linux Docker Container&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/vaggeliskls/windows-github-custom-runner" rel="noopener noreferrer"&gt;Windows GitHub action runner&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/vaggeliskls/windows-in-docker-container" rel="noopener noreferrer"&gt;Windows in container&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>devops</category>
      <category>windows</category>
      <category>cicd</category>
      <category>docker</category>
    </item>
  </channel>
</rss>
