immich.nix 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596
  1. { config, lib, pkgs, ... }:
  2. let
  3. cfg = config.services.immich;
  4. domain = "photos.t5.st";
  5. go-avahi-cname = lib.getExe pkgs.unstable.go-avahi-cname;
  6. in
  7. {
  8. services.immich = {
  9. enable = true;
  10. host = "0.0.0.0";
  11. openFirewall = true;
  12. mediaLocation = "/mnt/storage/immich";
  13. group = "storage";
  14. accelerationDevices = [ "/dev/dri/renderD128" ];
  15. # environment = {
  16. # INFO: Not needed but left for reference
  17. # ENCODED_VIDEO_LOCATION = "/var/cache/immich/encoded-video";
  18. # MPLCONFIGDIR = "/var/cache/immich/mpl";
  19. # PROFILE_LOCATION = "/var/cache/immich/profile";
  20. # THUMB_LOCATION = "/var/cache/immich/thumbs";
  21. # };
  22. settings = {
  23. metadata.faces.import = true;
  24. newVersionCheck.enabled = false;
  25. server.externalDomain = "https://${domain}";
  26. storageTemplate = {
  27. enabled = true;
  28. hashVerificationEnabled = true;
  29. template = "{{y}}/{{MM}}/{{dd}}/{{filename}}";
  30. };
  31. # TODO: add smtp authentication to environment
  32. # notifications.smtp.enabled = true;
  33. # notifications.smtp.from = "Odin Photos <[email protected]>";
  34. };
  35. };
  36. services.cloudflared.tunnels."71c89a7f-2467-444c-9fda-4864860dc8c4" = {
  37. credentialsFile =
  38. config.age.secrets."odin/services/cloudflared-tunnel".path;
  39. default = "http_status:404";
  40. ingress."${domain}".service =
  41. "http://${cfg.host}:${toString cfg.port}";
  42. };
  43. services.caddy.virtualHosts.immich = {
  44. hostName = "http://photos.odin.local";
  45. serverAliases = [ "photos.odin.t5.st" ];
  46. extraConfig = ''
  47. encode gzip zstd
  48. reverse_proxy ${cfg.host}:${toString cfg.port}
  49. '';
  50. };
  51. systemd.services.photos-local = {
  52. description = "Avahi photos.odin.local domain";
  53. wantedBy = [ "multi-user.target" ];
  54. after = [
  55. "network.target"
  56. "avahi-daemon.service"
  57. ];
  58. requires = [ "avahi-daemon.service" ];
  59. serviceConfig = {
  60. Type = "simple";
  61. User = "root";
  62. ExecStart = "${go-avahi-cname} cname photos";
  63. Restart = "always";
  64. RestartSec = "10";
  65. };
  66. };
  67. systemd.tmpfiles.rules = [
  68. "d /mnt/storage/immich 0770 immich storage - -"
  69. "d /var/cache/immich 0770 immich storage - -"
  70. "d /var/cache/immich/mpl 0700 immich storage - -"
  71. "d /var/cache/immich/encoded-video 0700 immich storage - -"
  72. "d /var/cache/immich/profile 0700 immich storage - -"
  73. "d /var/cache/immich/thumbs 0700 immich storage - -"
  74. ];
  75. system.activationScripts.createSymlink = ''
  76. ln -sf /var/cache/immich/encoded-video /mnt/storage/immich/encoded-video
  77. ln -sf /var/cache/immich/profile /mnt/storage/immich/profile
  78. ln -sf /var/cache/immich/thumbs /mnt/storage/immich/thumbs
  79. '';
  80. services.samba.settings = {
  81. christine-photos = {
  82. "path" = "/mnt/storage/immich/library/3aaaf0a1-011e-450d-a47c-4a320deb93e5";
  83. "browseable" = "yes";
  84. "read only" = "yes";
  85. "valid users" = "christine";
  86. "force user" = "immich";
  87. };
  88. };
  89. }