Skip to content
This repository
Fetching contributors…

Octocat-spinner-32-eaf2f5

Cannot retrieve contributors at this time

file 162 lines (139 sloc) 6.627 kb
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161
{-# LANGUAGE DeriveDataTypeable #-}
-----------------------------------------------------------------------------
-- |
-- Module : Distribution.License
-- Description : The License data type.
-- Copyright : Isaac Jones 2003-2005
-- Duncan Coutts 2008
-- License : BSD3
--
-- Maintainer : cabal-devel@haskell.org
-- Portability : portable
--
-- Package descriptions contain fields for specifying the name of a software
-- license and the name of the file containing the text of that license. While
-- package authors may choose any license they like, Cabal provides an
-- enumeration of a small set of common free and open source software licenses.
-- This is done so that Hackage can recognise licenses, so that tools can detect
-- <https://en.wikipedia.org/wiki/License_compatibility licensing conflicts>,
-- and to deter
-- <https://en.wikipedia.org/wiki/License_proliferation license proliferation>.
--
-- It is recommended that all package authors use the @license-file@ or
-- @license-files@ fields in their package descriptions. Further information
-- about these fields can be found in the
-- <http://www.haskell.org/cabal/users-guide/developing-packages.html#package-descriptions Cabal users guide>.
--
-- = Additional resources
--
-- The following websites provide information about free and open source
-- software licenses:
--
-- * <http://www.opensource.org The Open Source Initiative (OSI)>
--
-- * <https://www.fsf.org The Free Software Foundation (FSF)>
--
-- = Disclaimer
--
-- The descriptions of software licenses provided by this documentation are
-- intended for informational purposes only and in no way constitute legal
-- advice. Please read the text of the licenses and consult a lawyer for any
-- advice regarding software licensing.

module Distribution.License (
    License(..),
    knownLicenses,
  ) where

import Distribution.Version (Version(Version))

import Distribution.Text (Text(..), display)
import qualified Distribution.Compat.ReadP as Parse
import qualified Text.PrettyPrint as Disp
import Text.PrettyPrint ((<>))
import qualified Data.Char as Char (isAlphaNum)
import Data.Data (Data)
import Data.Typeable (Typeable)

-- | Indicates the license under which a package's source code is released.
-- Versions of the licenses not listed here will be rejected by Hackage and
-- cause @cabal check@ to issue a warning.
data License =
    -- TODO: * remove BSD4

    -- | GNU General Public License,
    -- <https://www.gnu.org/licenses/old-licenses/gpl-2.0.html version 2> or
    -- <https://www.gnu.org/licenses/gpl.html version 3>.
    GPL (Maybe Version)

    -- | <https://www.gnu.org/licenses/agpl.html GNU Affero General Public License, version 3>.
  | AGPL (Maybe Version)

    -- | GNU Lesser General Public License,
    -- <https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html version 2.1> or
    -- <https://www.gnu.org/licenses/lgpl.html version 3>.
  | LGPL (Maybe Version)

    -- | <http://www.opensource.org/licenses/bsd-license 2-clause BSD license>.
  | BSD2

    -- | <http://www.opensource.org/licenses/bsd-3-clause 3-clause BSD license>.
  | BSD3

    -- | <http://directory.fsf.org/wiki/License:BSD_4Clause 4-clause BSD license>.
    -- This license has not been approved by the OSI and is incompatible with
    -- the GNU GPL. It is provided for historical reasons and should be avoided.
  | BSD4

    -- | <http://www.opensource.org/licenses/MIT MIT license>.
  | MIT

    -- | <https://www.mozilla.org/MPL/ Mozilla Public License, version 2.0>.
  | MPL Version

    -- | <https://www.apache.org/licenses/ Apache License, version 2.0>.
  | Apache (Maybe Version)

    -- | The author of a package disclaims any copyright to its source code and
    -- dedicates it to the public domain. This is not a software license. Please
    -- note that it is not possible to dedicate works to the public domain in
    -- every jurisdiction, nor is a work that is in the public domain in one
    -- jurisdiction necessarily in the public domain elsewhere.
  | PublicDomain

    -- | No license. The package may not be legally modified or redistributed by
    -- anyone but the rightsholder.
  | AllRightsReserved

    -- | Any other software license.
  | OtherLicense

    -- | Indicates an erroneous license name.
  | UnknownLicense String
  deriving (Read, Show, Eq, Typeable, Data)

-- | The list of all currently recognised licenses.
knownLicenses :: [License]
knownLicenses = [ GPL unversioned, GPL (version [2]), GPL (version [3])
                , LGPL unversioned, LGPL (version [2, 1]), LGPL (version [3])
                , AGPL unversioned, AGPL (version [3])
                , BSD2, BSD3, MIT
                , MPL (Version [2, 0] [])
                , Apache unversioned, Apache (version [2, 0])
                , PublicDomain, AllRightsReserved, OtherLicense]
 where
   unversioned = Nothing
   version v = Just (Version v [])

instance Text License where
  disp (GPL version) = Disp.text "GPL" <> dispOptVersion version
  disp (LGPL version) = Disp.text "LGPL" <> dispOptVersion version
  disp (AGPL version) = Disp.text "AGPL" <> dispOptVersion version
  disp (MPL version) = Disp.text "MPL" <> dispVersion version
  disp (Apache version) = Disp.text "Apache" <> dispOptVersion version
  disp (UnknownLicense other) = Disp.text other
  disp other = Disp.text (show other)

  parse = do
    name <- Parse.munch1 (\c -> Char.isAlphaNum c && c /= '-')
    version <- Parse.option Nothing (Parse.char '-' >> fmap Just parse)
    return $! case (name, version :: Maybe Version) of
      ("GPL", _ ) -> GPL version
      ("LGPL", _ ) -> LGPL version
      ("AGPL", _ ) -> AGPL version
      ("BSD2", Nothing) -> BSD2
      ("BSD3", Nothing) -> BSD3
      ("BSD4", Nothing) -> BSD4
      ("MIT", Nothing) -> MIT
      ("MPL", Just version') -> MPL version'
      ("Apache", _ ) -> Apache version
      ("PublicDomain", Nothing) -> PublicDomain
      ("AllRightsReserved", Nothing) -> AllRightsReserved
      ("OtherLicense", Nothing) -> OtherLicense
      _ -> UnknownLicense $ name ++
                                        maybe "" (('-':) . display) version

dispOptVersion :: Maybe Version -> Disp.Doc
dispOptVersion Nothing = Disp.empty
dispOptVersion (Just v) = dispVersion v

dispVersion :: Version -> Disp.Doc
dispVersion v = Disp.char '-' <> disp v
Something went wrong with that request. Please try again.