scrappy-requests-0.1.0.0: src/Scrappy/Requests/Proxies.hs
{-# LANGUAGE FlexibleContexts #-}
module Scrappy.Requests.Proxies where
import Scrappy.Scrape (runScraperOnHtml)
import Scrappy.Elem.ChainHTML (containsFirst)
import Scrappy.Elem.SimpleElemParser (el)
import Scrappy.Elem.Types (innerText')
import Text.Parsec (ParsecT, Stream, many)
import Network.HTTP.Client (Proxy, Manager, HttpException, Response, Proxy(..), responseBody, httpLbs
, parseRequest, newManager, useProxy, managerSetSecureProxy)
import Network.HTTP.Client.TLS (tlsManagerSettings)
import Control.Exception (catch)
import Data.List (isInfixOf)
import Data.Text (unpack, pack)
import Data.Text.Encoding (encodeUtf8)
import qualified Data.Text.Lazy as LazyTX (toStrict, Text)
import qualified Data.Text.Lazy.Encoding as Lazy (decodeUtf8With)
import Data.ByteString.Lazy (ByteString)
testForValidProxy :: [Proxy] -> IO (Manager)
testForValidProxy (proxy:proxies) = do
req <- parseRequest "https://hackage.haskell.org/package/base-4.15.0.0/docs/Control-Exception.html#v:catch"
trialManager <- mkManagerInternal proxy
print $ "hello"
let
f :: IO (Manager)
f = catch (httpLbs req trialManager >> return trialManager) g
g :: HttpException -> IO (Manager)
g = (\_ -> testForValidProxy proxies)
x <- f
return x
rowToProxy :: [String] -> Proxy
rowToProxy row = Proxy ((encodeUtf8 . pack) (row !! 0)) (read (row !! 1) :: Int)
mkManagerInternal :: Proxy -> IO Manager
mkManagerInternal proxy = newManager (managerSetSecureProxy (useProxy proxy) tlsManagerSettings)
mkProxdManager :: IO (Manager)
mkProxdManager = do
proxyRows <- scrapeProxyList
testForValidProxy proxyRows
-- | Table pattern should also take a Cell where data Cell = (X,Y)
scrapeProxyList :: IO [Proxy] -- becoming [[String]]
scrapeProxyList = do
response <- getHtml' "https://free-proxy-list.net/"
let
parser = el "tr" [] `containsFirst` b
b :: Stream s m Char => ParsecT s u m [String]
b = ((fmap . fmap) innerText' $ many (el "td" []))
bePicky :: [[String]] -> [[String]]
bePicky rows = filter (\x -> not $ (isInfixOf "anonymous" (x !! 4)) || (isInfixOf "elite proxy" (x !! 4))) rows
-- g :: [String] -> Proxy
-- g row = Proxy ((encodeUtf8 . pack) (row !! 0)) (read (row !! 1) :: Int)
-- mapM_ print $ fromMaybe [] $ fromRight Nothing (parse (findNaive parser) "" response)
case runScraperOnHtml parser response of
Just (rows) ->
return (fmap rowToProxy (rows))
Nothing -> ioError $ userError "proxy error: couldnt get proxy"
------
--Move to Internal module:https://stackoverflow.com/questions/8650297/haskell-recursive-circular-module-definitions
------
-- | Get html with no Proxy
getHtml' :: String -> IO String
getHtml' url = do
mgrHttps <- newManager tlsManagerSettings
requ <- parseRequest url
response <- httpLbs requ mgrHttps
return $ extractDadBod response
extractDadBod :: Response ByteString -> String
extractDadBod response = (unpack . LazyTX.toStrict . mySafeDecoder . responseBody) response
mySafeDecoder :: ByteString -> LazyTX.Text
mySafeDecoder = Lazy.decodeUtf8With (\_ _ -> Just '?')