From 5e400b5b2478fa59a84cc9a69c525ada4be6f0c3 Mon Sep 17 00:00:00 2001 From: Profpatsch Date: Sat, 8 Apr 2023 12:59:01 +0200 Subject: chore(users/Profpatsch): bring reverse-haskell-deps into shape Add a cabal file and move into subdir. Use MyPrelude & fix a few linter warnings. Change-Id: I19d5ba47be789fc24f8e02ee8721f73c706ae3e9 Reviewed-on: https://cl.tvl.fyi/c/depot/+/8465 Reviewed-by: Profpatsch Autosubmit: Profpatsch Tested-by: BuildkiteCI --- .../reverse-haskell-deps/ReverseHaskellDeps.hs | 76 ++++++++++++++++++++++ users/Profpatsch/reverse-haskell-deps/default.nix | 32 +++++++++ .../reverse-haskell-deps.cabal | 16 +++++ 3 files changed, 124 insertions(+) create mode 100644 users/Profpatsch/reverse-haskell-deps/ReverseHaskellDeps.hs create mode 100644 users/Profpatsch/reverse-haskell-deps/default.nix create mode 100644 users/Profpatsch/reverse-haskell-deps/reverse-haskell-deps.cabal (limited to 'users/Profpatsch/reverse-haskell-deps') diff --git a/users/Profpatsch/reverse-haskell-deps/ReverseHaskellDeps.hs b/users/Profpatsch/reverse-haskell-deps/ReverseHaskellDeps.hs new file mode 100644 index 0000000000..0e18ce8a6b --- /dev/null +++ b/users/Profpatsch/reverse-haskell-deps/ReverseHaskellDeps.hs @@ -0,0 +1,76 @@ +{-# LANGUAGE LambdaCase #-} +{-# LANGUAGE MultiWayIf #-} +{-# LANGUAGE OverloadedStrings #-} +{-# LANGUAGE ScopedTypeVariables #-} + +module Main where + +import Data.ByteString qualified as ByteString +import Data.Either +import Data.List qualified as List +import Data.Maybe +import Data.Text (Text) +import Data.Text qualified as Text +import Data.Text.Encoding qualified +import MyPrelude +import Numeric.Natural +import Text.HTML.TagSoup qualified as Tag +import Text.Nicify +import Text.Read qualified as Read + +parseNat :: Text -> Maybe Natural +parseNat = Read.readMaybe . textToString + +printNice :: Show a => a -> IO () +printNice = putStrLn . nicify . show + +type Tag = Tag.Tag Text + +main = do + reverseHtml <- readStdinUtf8 + printNice $ List.sortOn snd $ packagesAndReverseDeps reverseHtml + where + readStdinUtf8 = bytesToTextUtf8Lenient <$> ByteString.getContents + +-- | reads the table provided by https://packdeps.haskellers.com/reverse +-- figuring out all sections (starting with the link to the package name), +-- then figuring out the name of the package and the first column, +-- which is the number of reverse dependencies of the package +packagesAndReverseDeps :: Text -> [(Text, Natural)] +packagesAndReverseDeps reverseHtml = do + let tags = Tag.parseTags reverseHtml + let sections = Tag.partitions (isJust . reverseLink) tags + let sectionName [] = "" + sectionName (sect : _) = sect & reverseLink & fromMaybe "" + let sectionNames = map sectionName sections + mapMaybe + ( \(name :: Text, sect) -> do + reverseDeps <- firstNaturalNumber sect + pure (sectionPackageName name sect, reverseDeps) :: Maybe (Text, Natural) + ) + $ zip sectionNames sections + where + reverseLink = \case + Tag.TagOpen "a" attrs -> findMaybe attrReverseLink attrs + _ -> Nothing + + attrReverseLink = \case + ("href", lnk) -> + if + | "packdeps.haskellers.com/reverse/" `Text.isInfixOf` lnk -> Just lnk + | otherwise -> Nothing + _ -> Nothing + + sectionPackageName :: Text -> [Tag] -> Text + sectionPackageName sectionName = \case + (_ : Tag.TagText name : _) -> name + (_ : el : _) -> sectionName + xs -> sectionName + + firstNaturalNumber :: [Tag] -> Maybe Natural + firstNaturalNumber = + findMaybe + ( \case + Tag.TagText t -> parseNat t + _ -> Nothing + ) diff --git a/users/Profpatsch/reverse-haskell-deps/default.nix b/users/Profpatsch/reverse-haskell-deps/default.nix new file mode 100644 index 0000000000..704b7f229b --- /dev/null +++ b/users/Profpatsch/reverse-haskell-deps/default.nix @@ -0,0 +1,32 @@ +{ depot, pkgs, ... }: + +# Parses https://packdeps.haskellers.com/reverse +# and outputs the amount of reverse dependencies of each hackage package. + +let + + rev = depot.nix.writeExecline "reverse-haskell-deps" { } [ + "pipeline" + [ + "${pkgs.curl}/bin/curl" + "-L" + "https://packdeps.haskellers.com/reverse" + ] + rev-hs + + ]; + + rev-hs = pkgs.writers.writeHaskell "revers-haskell-deps-hs" + { + libraries = [ + depot.users.Profpatsch.my-prelude + pkgs.haskellPackages.nicify-lib + pkgs.haskellPackages.tagsoup + ]; + + } + ./ReverseHaskellDeps.hs; + + +in +rev diff --git a/users/Profpatsch/reverse-haskell-deps/reverse-haskell-deps.cabal b/users/Profpatsch/reverse-haskell-deps/reverse-haskell-deps.cabal new file mode 100644 index 0000000000..d8dd5cbe5a --- /dev/null +++ b/users/Profpatsch/reverse-haskell-deps/reverse-haskell-deps.cabal @@ -0,0 +1,16 @@ +cabal-version: 2.4 +name: reverse-haskell-deps +version: 0.1.0.0 +author: Profpatsch +maintainer: mail@profpatsch.de + +library + exposed-modules: ReverseHaskellDeps.hs + + build-depends: + base >=4.15 && <5, + my-prelude, + tagsoup, + nicify-lib + + default-language: Haskell2010 -- cgit 1.4.1