ldap-client-0.2.0: src/Ldap/Asn1/Type.hs
module Ldap.Asn1.Type where
import Data.ByteString (ByteString)
import Data.Int (Int8, Int32)
import Data.List.NonEmpty (NonEmpty)
import Data.Text (Text)
-- | Message envelope. (Section 4.1.1.)
data LdapMessage op = LdapMessage
{ ldapMessageId :: !Id
, ldapMessageOp :: !op
, ldapMessageControls :: !(Maybe Controls)
} deriving (Show, Eq)
-- | Every message being processed has a unique non-zero integer ID. (Section 4.1.1.1.)
newtype Id = Id { unId :: Int32 }
deriving (Show, Eq, Ord)
-- | Client requests. The RFC doesn't make a difference between 'ProtocolClientOp'
-- and 'ProtocolServerOp' but it's useful to distinguish between them in Haskell.
data ProtocolClientOp =
BindRequest !Int8 !LdapDn !AuthenticationChoice
| UnbindRequest
| SearchRequest !LdapDn !Scope !DerefAliases !Int32 !Int32 !Bool !Filter !AttributeSelection
| ModifyRequest !LdapDn ![(Operation, PartialAttribute)]
| AddRequest !LdapDn !AttributeList
| DeleteRequest !LdapDn
| ModifyDnRequest !LdapDn !RelativeLdapDn !Bool !(Maybe LdapDn)
| CompareRequest !LdapDn !AttributeValueAssertion
| ExtendedRequest !LdapOid !(Maybe ByteString)
deriving (Show, Eq)
-- | Server responses. The RFC doesn't make a difference between 'ProtocolClientOp'
-- and 'ProtocolServerOp' but it's useful to distinguish between them in Haskell.
data ProtocolServerOp =
BindResponse !LdapResult !(Maybe ByteString)
| SearchResultEntry !LdapDn !PartialAttributeList
| SearchResultReference !(NonEmpty Uri)
| SearchResultDone !LdapResult
| ModifyResponse !LdapResult
| AddResponse !LdapResult
| DeleteResponse !LdapResult
| ModifyDnResponse !LdapResult
| CompareResponse !LdapResult
| ExtendedResponse !LdapResult !(Maybe LdapOid) !(Maybe ByteString)
| IntermediateResponse !(Maybe LdapOid) !(Maybe ByteString)
deriving (Show, Eq)
-- | Not really a choice until SASL is supported.
data AuthenticationChoice =
Simple !ByteString
| Sasl !SaslMechanism !(Maybe Text)
deriving (Show, Eq)
-- | SASL Mechanism, for now only SASL EXTERNAL is supported
data SaslMechanism =
External
deriving (Show, Eq)
-- | Scope of the search to be performed.
data Scope =
BaseObject -- ^ Constrained to the entry named by baseObject.
| SingleLevel -- ^ Constrained to the immediate subordinates of the entry named by baseObject.
| WholeSubtree -- ^ Constrained to the entry named by baseObject and to all its subordinates.
deriving (Show, Eq)
-- | An indicator as to whether or not alias entries (as defined in
-- [RFC4512]) are to be dereferenced during stages of the Search
-- operation.
data DerefAliases =
NeverDerefAliases -- ^ Do not dereference aliases in searching or in locating the base object of the Search.
| DerefInSearching -- ^ While searching subordinates of the base object, dereference any alias within the search scope.
| DerefFindingBaseObject -- ^ Dereference aliases in locating the base object of the Search.
| DerefAlways -- ^ Dereference aliases both in searching and in locating the base object of the Search.
deriving (Show, Eq)
-- | Conditions that must be fulfilled in order for the Search to match a given entry.
data Filter =
And !(NonEmpty Filter) -- ^ All filters evaluate to @TRUE@
| Or !(NonEmpty Filter) -- ^ Any filter evaluates to @TRUE@
| Not !Filter -- ^ Filter evaluates to @FALSE@
| EqualityMatch !AttributeValueAssertion -- ^ @EQUALITY@ rule returns @TRUE@
| Substrings !SubstringFilter -- ^ @SUBSTR@ rule returns @TRUE@
| GreaterOrEqual !AttributeValueAssertion -- ^ @ORDERING@ rule returns @FALSE@
| LessOrEqual !AttributeValueAssertion -- ^ @ORDERING@ or @EQUALITY@ rule returns @TRUE@
| Present !AttributeDescription -- ^ Attribute is present in the entry
| ApproxMatch !AttributeValueAssertion -- ^ Same as 'EqualityMatch' for most servers
| ExtensibleMatch !MatchingRuleAssertion
deriving (Show, Eq)
data SubstringFilter = SubstringFilter !AttributeDescription !(NonEmpty Substring)
deriving (Show, Eq)
data Substring =
Initial !AssertionValue
| Any !AssertionValue
| Final !AssertionValue
deriving (Show, Eq)
data MatchingRuleAssertion = MatchingRuleAssertion !(Maybe MatchingRuleId) !(Maybe AttributeDescription) !AssertionValue !Bool
deriving (Show, Eq)
-- | Matching rules are defined in Section 4.1.3 of [RFC4512]. A matching
-- rule is identified in the protocol by the printable representation of
-- either its <numericoid> or one of its short name descriptors
-- [RFC4512], e.g., 'caseIgnoreMatch' or '2.5.13.2'. (Section 4.1.8.)
newtype MatchingRuleId = MatchingRuleId LdapString
deriving (Show, Eq)
newtype AttributeSelection = AttributeSelection [LdapString]
deriving (Show, Eq)
newtype AttributeList = AttributeList [Attribute]
deriving (Show, Eq)
newtype PartialAttributeList = PartialAttributeList [PartialAttribute]
deriving (Show, Eq)
newtype Controls = Controls [Control]
deriving (Show, Eq)
data Control = Control !LdapOid !Bool !(Maybe ByteString)
deriving (Show, Eq)
data LdapResult = LdapResult !ResultCode !LdapDn !LdapString !(Maybe ReferralUris)
deriving (Show, Eq)
-- | LDAP operation's result.
data ResultCode =
Success
| OperationError
| ProtocolError
| TimeLimitExceeded
| SizeLimitExceeded
| CompareFalse
| CompareTrue
| AuthMethodNotSupported
| StrongerAuthRequired
| Referral
| AdminLimitExceeded
| UnavailableCriticalExtension
| ConfidentialityRequired
| SaslBindInProgress
| NoSuchAttribute
| UndefinedAttributeType
| InappropriateMatching
| ConstraintViolation
| AttributeOrValueExists
| InvalidAttributeSyntax
| NoSuchObject
| AliasProblem
| InvalidDNSyntax
| AliasDereferencingProblem
| InappropriateAuthentication
| InvalidCredentials
| InsufficientAccessRights
| Busy
| Unavailable
| UnwillingToPerform
| LoopDetect
| NamingViolation
| ObjectClassViolation
| NotAllowedOnNonLeaf
| NotAllowedOnRDN
| EntryAlreadyExists
| ObjectClassModsProhibited
| AffectsMultipleDSAs
| Other
deriving (Show, Eq)
newtype AttributeDescription = AttributeDescription LdapString
deriving (Show, Eq)
newtype AttributeValue = AttributeValue ByteString
deriving (Show, Eq)
data AttributeValueAssertion = AttributeValueAssertion !AttributeDescription !AssertionValue
deriving (Show, Eq)
newtype AssertionValue = AssertionValue ByteString
deriving (Show, Eq)
data Attribute = Attribute !AttributeDescription !(NonEmpty AttributeValue)
deriving (Show, Eq)
data PartialAttribute = PartialAttribute !AttributeDescription ![AttributeValue]
deriving (Show, Eq)
-- | An LDAPDN is defined to be the representation of a Distinguished Name
-- (DN) after encoding according to the specification in [RFC4514].
newtype LdapDn = LdapDn LdapString
deriving (Show, Eq)
-- | A RelativeLDAPDN is defined to be the representation of a Relative
-- Distinguished Name (RDN) after encoding according to the
-- specification in [RFC4514].
newtype RelativeLdapDn = RelativeLdapDn LdapString
deriving (Show, Eq)
newtype ReferralUris = ReferralUris (NonEmpty Uri)
deriving (Show, Eq)
newtype Uri = Uri LdapString
deriving (Show, Eq)
data Operation =
Add
| Delete
| Replace
deriving (Show, Eq)
-- | The LDAPString is a notational convenience to indicate that, although
-- strings of LDAPString type encode as ASN.1 OCTET STRING types, the
-- [ISO10646] character set (a superset of [Unicode]) is used, encoded
-- following the UTF-8 [RFC3629] algorithm. (Section 4.1.2.)
newtype LdapString = LdapString Text
deriving (Show, Eq)
-- | The LDAPOID is a notational convenience to indicate that the
-- permitted value of this string is a (UTF-8 encoded) dotted-decimal
-- representation of an OBJECT IDENTIFIER. Although an LDAPOID is
-- encoded as an OCTET STRING, values are limited to the definition of
-- \<numericoid\> given in Section 1.4 of [RFC4512].
newtype LdapOid = LdapOid Text
deriving (Show, Eq)