Skip to content

Commit

Permalink
fix: add test for nix module
Browse files Browse the repository at this point in the history
  • Loading branch information
brianmay committed Nov 9, 2024
1 parent e15b324 commit 3f16754
Show file tree
Hide file tree
Showing 6 changed files with 189 additions and 15 deletions.
28 changes: 28 additions & 0 deletions .commitlintrc.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
---
# The rules below have been manually copied from @commitlint/config-conventional
# and match the v1.0.0 specification:
# https://www.conventionalcommits.org/en/v1.0.0/#specification
#
# You can remove them and uncomment the config below when the following issue is
# fixed: https://github.com/conventional-changelog/commitlint/issues/613
#
# extends:
# - '@commitlint/config-conventional'
rules:
body-leading-blank: [1, always]
body-max-line-length: [2, always, 100]
footer-leading-blank: [1, always]
footer-max-line-length: [2, always, 100]
header-max-length: [2, always, 100]
subject-case:
- 2
- never
- [sentence-case, start-case, pascal-case, upper-case]
subject-empty: [2, never]
subject-full-stop: [2, never, "."]
type-case: [2, always, lower-case]
type-empty: [2, never]
type-enum:
- 2
- always
- [build, chore, ci, docs, feat, fix, perf, refactor, revert, style, test]
44 changes: 44 additions & 0 deletions flake.nix
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,51 @@
}
];
};

test = pkgs.nixosTest {
name = "penguin_memories";
nodes.machine = {...}: {
imports = [
self.nixosModules.default
];
services.penguin_memories = {
enable = true;
http_url = "http://localhost:4000";
port = 4000;
secrets = pkgs.writeText "secrets.txt" ''
export RELEASE_COOKIE="12345678901234567890123456789012345678901234567890123456"
export DATABASE_URL="postgres://penguin_memories:your_secure_password_here@localhost/penguin_memories"
export GUARDIAN_SECRET="1234567890123456789012345678901234567890123456789012345678901234"
export SECRET_KEY_BASE="1234567890123456789012345678901234567890123456789012345678901234"
export SIGNING_SALT="12345678901234567890123456789012"
export OIDC_DISCOVERY_URL="http://localhost"
export OIDC_CLIENT_ID="photos"
export OIDC_CLIENT_SECRET="12345678901234567890123456789012"
export OIDC_AUTH_SCOPE="openid profile groups"
'';
};
system.stateVersion = "24.05";

services.postgresql = {
enable = true;
extraPlugins = ps: [ps.postgis];
initialScript = pkgs.writeText "init.psql" ''
CREATE DATABASE penguin_memories;
CREATE USER penguin_memories with encrypted password 'your_secure_password_here';
ALTER DATABASE penguin_memories OWNER TO penguin_memories;
ALTER USER penguin_memories WITH SUPERUSER;
'';
};
};

testScript = ''
machine.wait_for_unit("penguin_memories.service")
machine.wait_for_open_port(4000)
machine.succeed("${pkgs.curl}/bin/curl --fail -v http://localhost:4000/_health")
'';
};
in {
checks.nixosModules = test;
packages = {
devenv-up = devShell.config.procfileScript;
default = pkg;
Expand Down
70 changes: 70 additions & 0 deletions lib/penguin_memories/release.ex
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
defmodule PenguinMemories.Release do

Check warning on line 1 in lib/penguin_memories/release.ex

View workflow job for this annotation

GitHub Actions / Setup, Build, Test / test (1.16.3, 25.1)

Modules should have a @moduledoc tag.
@app :penguin_memories

import Ecto.Query
alias PenguinMemories.Repo

def migrate do
for repo <- repos() do
{:ok, _, _} = Ecto.Migrator.with_repo(repo, &Ecto.Migrator.run(&1, :up, all: true))
end
end

def rollback(repo, version) do
for r <- repos(), r == repo do
{:ok, _, _} = Ecto.Migrator.with_repo(repo, &Ecto.Migrator.run(&1, :down, to: version))
end
end

def seconds_since_last_migration do
Repo.one(
from m in "schema_migrations",
select: fragment("EXTRACT(EPOCH FROM age(NOW(), ?::timestamp))::BIGINT", m.inserted_at),
order_by: [desc: m.inserted_at],
limit: 1
)
end

def health_check do
repos = Application.fetch_env!(@app, :ecto_repos)

migrations =
repos
|> Enum.map(&Ecto.Migrator.migrations/1)
|> List.flatten()
|> Enum.filter(fn
{:up, _, _} -> false
{_, _, _} -> true
end)

migrations =
if Enum.empty?(migrations) do
:ok
else
{:error, "Migrations pending: #{inspect(migrations)}"}
end

database =
Enum.reduce_while(repos, :ok, fn item, _acc ->
case Ecto.Adapters.SQL.query(item, "SELECT 1") do

Check warning on line 49 in lib/penguin_memories/release.ex

View workflow job for this annotation

GitHub Actions / Setup, Build, Test / test (1.16.3, 25.1)

Nested modules could be aliased at the top of the invoking module.
{:ok, %{num_rows: 1, rows: [[1]]}} ->
{:cont, :ok}

{:error, reason} ->
{:halt, {:error, inspect(reason)}}
end
end)

case {migrations, database} do
{:ok, :ok} -> :ok
{{:error, reason}, _} -> {:error, reason}
{_, {:error, reason}} -> {:error, reason}
end
end

defp repos do
Application.ensure_all_started(:ssl)
Application.load(@app)
Application.fetch_env!(@app, :ecto_repos)
end
end
17 changes: 17 additions & 0 deletions lib/penguin_memories_web/controllers/healh_check_controller.ex
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
defmodule PenguinMemoriesWeb.HealthCheckController do
use PenguinMemoriesWeb, :controller

alias PenguinMemories.Release
require Logger

def index(conn, _params) do
case Release.health_check() do
:ok ->
text(conn, "HEALTHY")

{:error, reason} ->
Logger.error("health check error: #{reason}")
conn |> put_status(500) |> text("ERROR")
end
end
end
1 change: 1 addition & 0 deletions lib/penguin_memories_web/router.ex
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,7 @@ defmodule PenguinMemoriesWeb.Router do
pipe_through [:browser, :auth]
PenguinMemoriesWeb
live "/", PageLive, :index
get "/_health", HealthCheckController, :index
post "/logout", PageController, :logout
get "/file/:id/size/:size/", RedirectController, :photo
live "/:type/", MainLive, :index
Expand Down
44 changes: 29 additions & 15 deletions module.nix
Original file line number Diff line number Diff line change
@@ -1,13 +1,18 @@
{ self }:
{ lib, pkgs, config, ... }:
with lib;
let
{self}: {
lib,
pkgs,
config,
...
}: let
inherit (lib) mkOption types mkEnableOption mkIf;

cfg = config.services.penguin_memories;

system = pkgs.stdenv.system;
penguin_memories_pkg = self.packages.${system}.default;

private_locations = lib.concatMapStringsSep ";"
private_locations =
lib.concatMapStringsSep ";"
(l: "${toString l.longitude},${toString l.latitude},${toString l.distance}")
cfg.private_locations;

Expand All @@ -27,20 +32,28 @@ let

locations = types.submodule {
options = {
longitude = mkOption { type = types.float; };
latitude = mkOption { type = types.float; };
distance = mkOption { type = types.int; };
longitude = mkOption {type = types.float;};
latitude = mkOption {type = types.float;};
distance = mkOption {type = types.int;};
};
};

in {
options.services.penguin_memories = {
enable = mkEnableOption "penguin_memories service";
secrets = mkOption { type = types.path; };
http_url = mkOption { type = types.str; };
image_dir = mkOption { type = types.path; };
private_locations = mkOption { type = types.listOf locations; };
port = mkOption { type = types.int; };
secrets = mkOption {type = types.path;};
http_url = mkOption {type = types.str;};
image_dir = mkOption {
type = types.path;
default = "/var/lib/penguin_memories";
};
private_locations = mkOption {
type = types.listOf locations;
default = [];
};
port = mkOption {
type = types.int;
default = 4000;
};
data_dir = mkOption {
type = types.str;
default = "/var/lib/penguin_memories";
Expand All @@ -56,13 +69,14 @@ in {
home = "${cfg.data_dir}";
};

users.groups.penguin_memories = { };
users.groups.penguin_memories = {};

systemd.services.penguin_memories = {
wantedBy = ["multi-user.target"];
after = ["network.target" "postgresql.service"];
serviceConfig = {
User = "penguin_memories";
ExecStartPre = ''${wrapper}/bin/penguin_memories eval "PenguinMemories.Release.migrate"'';
ExecStart = "${wrapper}/bin/penguin_memories start";
ExecStop = "${wrapper}/bin/penguin_memories stop";
ExecReload = "${wrapper}/bin/penguin_memories reload";
Expand Down

0 comments on commit 3f16754

Please sign in to comment.