about summary refs log tree commit diff
path: root/pkgs/profpatsch/query-album-streams
diff options
context:
space:
mode:
authorProfpatsch <mail@profpatsch.de>2019-12-14 23:42:23 +0100
committerProfpatsch <mail@profpatsch.de>2019-12-14 23:42:23 +0100
commitedc6e1c59fd23400daf38b9de823e8dc0be39655 (patch)
tree11367157308425912616a8b865ad8ef2e93eeeeb /pkgs/profpatsch/query-album-streams
parentd6752d574e67c8a091b04b6c98bb7b2957be13b3 (diff)
pkgs/profpatsch/query-audio-streams: init
Diffstat (limited to 'pkgs/profpatsch/query-album-streams')
-rw-r--r--pkgs/profpatsch/query-album-streams/default.nix3
-rw-r--r--pkgs/profpatsch/query-album-streams/last-fm-api.nix87
2 files changed, 90 insertions, 0 deletions
diff --git a/pkgs/profpatsch/query-album-streams/default.nix b/pkgs/profpatsch/query-album-streams/default.nix
new file mode 100644
index 00000000..249676cb
--- /dev/null
+++ b/pkgs/profpatsch/query-album-streams/default.nix
@@ -0,0 +1,3 @@
+{ pkgs, writeExecline, getBins, writeHaskellInterpret }@attrs:
+
+import ./last-fm-api.nix attrs
diff --git a/pkgs/profpatsch/query-album-streams/last-fm-api.nix b/pkgs/profpatsch/query-album-streams/last-fm-api.nix
new file mode 100644
index 00000000..920c2bfb
--- /dev/null
+++ b/pkgs/profpatsch/query-album-streams/last-fm-api.nix
@@ -0,0 +1,87 @@
+{ pkgs, getBins, writeExecline, writeHaskellInterpret }:
+let
+
+  lib = pkgs.lib;
+  bins = getBins pkgs.httpie [ "http" ];
+
+  develop = true;
+
+  writeHaskell = name: { interpret ? false, withPackages }:
+    if interpret
+    then writeHaskellInterpret name { inherit withPackages; }
+    else pkgs.writers.writeHaskell name { libraries = withPackages pkgs.haskellPackages; };
+
+  # see https://hackage.haskell.org/package/aeson-schema-0.4.1.2/docs/Data-Aeson-Schema-Types.html#t:Schema
+  # for the schema format.
+  # The input is a json-encoding of that via quasi-quoter.
+  json-schema-validator = name: schema: writeHaskell name {
+    withPackages = hps: [ (pkgs.haskell.lib.doJailbreak (pkgs.haskell.lib.markUnbroken hps.aeson-schema)) hps.aeson ];
+    interpret = develop;
+  } ''
+    {-# language QuasiQuotes #-}
+    import qualified Data.ByteString.Lazy as BS
+    import Data.Aeson (eitherDecode')
+    import Data.Aeson.Schema
+    import System.Exit (die, exitSuccess)
+
+    main :: IO ()
+    main = do
+      stdin <- BS.getContents
+      case (eitherDecode' stdin) of
+        Left errs ->  die errs
+        Right json -> do
+          let val = validate mempty schema json
+          if val == []
+          then BS.putStr stdin >> exitSuccess
+          else die (show val)
+
+    schema :: Schema ()
+    schema = [schemaQQ| ${lib.generators.toJSON {} schema} |]
+  '';
+
+  query-lastFm-album = writeExecline "query-lastFm-album" { readNArgs = 2; } [
+    bins.http
+      "GET"
+      "https://ws.audioscrobbler.com/2.0/"
+      "--"
+      "api_key==\${1}"
+      "method==album.search"
+      "album==\${2}"
+      "format==json"
+  ];
+
+  schema = {
+    obj = { required ? true }: propsMap: {
+      type = "object";
+      inherit required;
+      properties = propsMap;
+    };
+
+    arr = { required ? true }: itemsSchema: {
+      type = "array";
+      inherit required;
+      items = itemsSchema;
+    };
+  };
+
+  validator = json-schema-validator "last-fm-album-output" (with schema; obj {} {
+    results = obj {} {
+      albummatches = obj {} {
+        album = arr {} (obj {} {
+          name = { type = "string"; };
+          artist = { type = "string"; };
+        });
+      };
+    };
+  });
+
+  query-and-validate = writeExecline "validate-lastfm-album-response" { } [
+    "pipeline" [ query-lastFm-album "$@" ]
+    "if" [ validator ]
+  ];
+
+
+# in validator
+in {
+  inherit query-lastFm-album validator query-and-validate;
+}