{-# OPTIONS --without-K #-}

-- Agda-hott library.
-- Author: Mario Román

-- Base.  Basic types of Martin-Löf type theory and some basic
-- functions.

module Base where

  open import base.Universes public
  open import base.Empty public
  open import base.Unit public

  module Basic where
  
    -- Sigma types are a particular case of records, but records can be
    -- constructed using only sigma types. Note that l ⊔ q is the maximum
    -- of two hierarchy levels l and q. This way, we define sigma types in
    -- full generality, at each universe.
    record Σ {ℓᵢ ℓⱼ} (S : Type ℓᵢ)(T : S  Type ℓⱼ) : Type (ℓᵢ  ℓⱼ) where
      constructor _,_
      field
        fst : S
        snd : T fst
    open Σ public
  
    -- Product type as a particular case of the sigma
    _×_ : ∀{ℓᵢ ℓⱼ} (S : Type ℓᵢ) (T : Type ℓⱼ)  Type (ℓᵢ  ℓⱼ)
    A × B = Σ A  _  B)

    -- Sum types as inductive types
    data _+_ {ℓᵢ ℓⱼ} (S : Type ℓᵢ) (T : Type ℓⱼ) : Type (ℓᵢ  ℓⱼ) where
      inl : S  S + T
      inr : T  S + T

    -- Boolean type, two constants true and false
    data Bool : Type0 where
      true : Bool
      false : Bool

    -- Natural numbers are the initial algebra for a constant and a
    -- successor function. The BUILTIN declaration allows us to use
    -- natural numbers in arabic notation.
    data  : Type0 where
      zero : 
      succ :   
    {-# BUILTIN NATURAL  #-}

  open Basic public

  -- Identity function
  id : ∀{} {A : Type }  A  A
  id a = a

  -- Composition
  _∘_ : ∀{ℓᵢ ℓⱼ ℓₖ} {A : Type ℓᵢ} {B : Type ℓⱼ} {C : Type ℓₖ}
         (B  C)  (A  B)  (A  C)
  (g  f) z = g (f z)

  -- Equality is defined as an inductive type. Its induction principle
  -- is the J-eliminator.
  data _==_ {} {A : Type } : A  A  Type  where
    refl : (a : A)  a == a

  -- Composition of paths
  infixl 50 _·_
  _·_ : ∀{} {A : Type }  {a b c : A}  a == b  b == c  a == c
  refl a · q = q