diff --git a/config/keter.yml b/config/keter.yml index 1f4ed4f88..b6b7bd829 100644 --- a/config/keter.yml +++ b/config/keter.yml @@ -19,6 +19,13 @@ stanzas: ssl: true + forward-env: + - LDAPURI + - LDAPDN + - LDAPPW + - LDAPBN + - DUMMY_LOGIN + # Use the following to automatically copy your bundle upon creation via `yesod # keter`. Uses `scp` internally, so you can set it to a remote destination # copy-to: user@host:/opt/keter/incoming/ diff --git a/config/settings.yml b/config/settings.yml index 2cee4c70c..378f58f0f 100644 --- a/config/settings.yml +++ b/config/settings.yml @@ -18,7 +18,7 @@ approot: "_env:APPROOT:http://localhost:3000" # reload-templates: false # mutable-static: false # skip-combining: false -# auth-dummy-login : false +auth-dummy-login: "_env:DUMMY_LOGIN:false" # NB: If you need a numeric value (e.g. 123) to parse as a String, wrap it in single quotes (e.g. "_env:PGPASS:'123'") # See https://github.com/yesodweb/yesod/wiki/Configuration#parsing-numeric-values-as-strings @@ -32,6 +32,12 @@ database: database: "_env:PGDATABASE:uniworx" poolsize: "_env:PGPOOLSIZE:10" +ldap: + uri: "_env:LDAPURI:ldap://localhost:389" + dn: "_env:LDAPDN:uniworx" + password: "_env:LDAPPW:" + basename: "_env:LDAPBN:" + cryptoid-keyfile: "_env:CRYPTOID_KEYFILE:cryptoid_key.bf" copyright: Insert copyright statement here diff --git a/docker/Dockerfile b/docker/Dockerfile new file mode 100644 index 000000000..310b609cc --- /dev/null +++ b/docker/Dockerfile @@ -0,0 +1,6 @@ +FROM fpco/stack-build:lts-9.3 + +ENV DEBIAN_FRONTEND noninteractive + +RUN apt-get update +RUN apt-get install libldap2-dev libsasl2-dev \ No newline at end of file diff --git a/package.yaml b/package.yaml index 2a11a9332..536c40907 100644 --- a/package.yaml +++ b/package.yaml @@ -72,6 +72,8 @@ dependencies: - generic-deriving - blaze-html - conduit-resumablesink >=0.2 +- yesod-auth-ldap +- LDAP # The library contains all of our application code. The executable # defined below is just a thin wrapper. diff --git a/src/Foundation.hs b/src/Foundation.hs index 67e9a8933..8093fb9a1 100644 --- a/src/Foundation.hs +++ b/src/Foundation.hs @@ -17,8 +17,10 @@ import Text.Jasmine (minifym) -- Used only when in "auth-dummy-login" setting is enabled. import Yesod.Auth.Dummy +import Yesod.Auth.LDAP + +import LDAP.Data (LDAPScope(..)) -import Yesod.Auth.OpenId (authOpenId, IdentifierType (Claimed)) import Yesod.Default.Util (addStaticContentExternal) import Yesod.Core.Types (Logger) import qualified Yesod.Core.Unsafe as Unsafe @@ -280,12 +282,23 @@ instance YesodAuth UniWorX where } -- You can add other plugins like Google Email, email or OAuth here - authPlugins app = [authOpenId Claimed []] ++ extraAuthPlugins + authPlugins app = [genericAuthLDAP $ ldapConfig app] ++ extraAuthPlugins -- Enable authDummy login if enabled. where extraAuthPlugins = [authDummy | appAuthDummyLogin $ appSettings app] authHttpManager = getHttpManager +ldapConfig :: UniWorX -> LDAPConfig +ldapConfig app@(appSettings -> settings) = LDAPConfig + { usernameFilter = ("userPrincipalName=" <>) + , identifierModifier = \n _ -> n + , ldapUri = appLDAPURI settings + , initDN = appLDAPDN settings + , initPass = appLDAPPw settings + , baseDN = appLDAPBaseName settings + , ldapScope = LdapScopeDefault + } + -- | Access function to determine if a user is logged in. isAuthenticated :: Handler AuthResult isAuthenticated = do diff --git a/src/Settings.hs b/src/Settings.hs index 437985178..e595cdc59 100644 --- a/src/Settings.hs +++ b/src/Settings.hs @@ -43,6 +43,11 @@ data AppSettings = AppSettings -- ^ Get the IP address from the header when logging. Useful when sitting -- behind a reverse proxy. + , appLDAPURI :: String + , appLDAPDN :: String + , appLDAPPw :: String + , appLDAPBaseName :: Maybe String + , appDetailedRequestLogging :: Bool -- ^ Use detailed request logging system , appShouldLogAll :: Bool @@ -80,6 +85,9 @@ instance FromJSON AppSettings where appPort <- o .: "port" appIpFromHeader <- o .: "ip-from-header" + ( appLDAPURI, appLDAPDN, appLDAPPw, appLDAPBaseName ) + <- (=<< o .: "ldap") . withObject "LDAP" $ \obj -> (,,,) <$> obj .: "uri" <*> obj .: "dn" <*> obj .: "password" <*> obj .:? "basename" + appDetailedRequestLogging <- o .:? "detailed-logging" .!= defaultDev appShouldLogAll <- o .:? "should-log-all" .!= defaultDev appReloadTemplates <- o .:? "reload-templates" .!= defaultDev diff --git a/stack.yaml b/stack.yaml index e3fef1fd3..761bb647d 100644 --- a/stack.yaml +++ b/stack.yaml @@ -1,6 +1,7 @@ flags: {} docker: enable: true + image: uniworx nix: enable: false packages: [] @@ -13,6 +14,14 @@ packages: git: https://github.com/pngwjpgh/zip-stream.git commit: 9272bbed000928d500febad1cdc98d1da29d399e extra-dep: true +- location: + git: https://github.com/mlitchard/yesod-auth-ldap.git + commit: 69e08ef687ab96df3352ff4267562135453c6f02 + extra-dep: true +- location: + git: https://github.com/mlitchard/authenticate-ldap.git + commit: cc2770024766a8fa29d3086688df60aaf65fb954 + extra-dep: true extra-deps: - colonnade-1.1.1 - yesod-colonnade-1.1.0 @@ -25,4 +34,6 @@ extra-deps: - encoding-0.8.2 - regex-compat-0.93.1 + +- LDAP-0.6.11 resolver: lts-9.3