-- Mathlib/CategoryTheory/Filtered/Final.lean
theorem isFiltered_structuredArrow_of_isFiltered_of_exists [IsFilteredOrEmpty C]
    (h₁ : ∀ d, ∃ c, Nonempty (d ⟶ F.obj c)) (h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c),
      ∃ (c' : C) (t : c ⟶ c'), s ≫ F.map t = s' ≫ F.map t) (d : D) :
    IsFiltered (StructuredArrow d F)

Proof state:
case refine_1
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
⊢ ∃ Z x x, True

Tactic:
obtain ⟨c, ⟨t, ht⟩⟩ := h₂ (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right))
    (g.hom ≫ F.map (IsFiltered.rightToMax f.right g.right))

Result:
case refine_1.intro.intro
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
c : C
t : IsFiltered.max f.right g.right ⟶ c
ht :
  (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right)) ≫ F.map t =
    (g.hom ≫ F.map (IsFiltered.rightToMax f.right g.right)) ≫ F.map t
⊢ ∃ Z x x, True

Proof state:
case refine_1.intro.intro
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
c : C
t : IsFiltered.max f.right g.right ⟶ c
ht :
  (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right)) ≫ F.map t =
    (g.hom ≫ F.map (IsFiltered.rightToMax f.right g.right)) ≫ F.map t
⊢ ∃ Z x x, True

Tactic:
refine ⟨.mk (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right ≫ t)), ?_, ?_, trivial⟩

Result:
case refine_1.intro.intro.refine_1
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
c : C
t : IsFiltered.max f.right g.right ⟶ c
ht :
  (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right)) ≫ F.map t =
    (g.hom ≫ F.map (IsFiltered.rightToMax f.right g.right)) ≫ F.map t
⊢ f ⟶ StructuredArrow.mk (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right ≫ t))

case refine_1.intro.intro.refine_2
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
c : C
t : IsFiltered.max f.right g.right ⟶ c
ht :
  (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right)) ≫ F.map t =
    (g.hom ≫ F.map (IsFiltered.rightToMax f.right g.right)) ≫ F.map t
⊢ g ⟶ StructuredArrow.mk (f.hom ≫ F.map (IsFiltered.leftToMax f.right g.right ≫ t))

Proof state:
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
⊢ IsFilteredOrEmpty (StructuredArrow d F)

Tactic:
refine ⟨fun f g => ?_, fun f g η μ => ?_⟩

Result:
case refine_1
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
⊢ ∃ Z x x, True

case refine_2
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
η μ : f ⟶ g
⊢ ∃ Z h, η ≫ h = μ ≫ h

Proof state:
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
⊢ IsFiltered (StructuredArrow d F)

Tactic:
have : Nonempty (StructuredArrow d F) := by
  obtain ⟨c, ⟨f⟩⟩ := h₁ d
  exact ⟨.mk f⟩

Result:
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
⊢ IsFiltered (StructuredArrow d F)

Proof state:
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
η μ : f ⟶ g
⊢ g.hom ≫ F.map (IsFiltered.coeqHom η.right μ.right) =
    (StructuredArrow.mk (f.hom ≫ F.map (η.right ≫ IsFiltered.coeqHom η.right μ.right))).hom

Tactic:
simp

Result:
no goals

Proof state:
case refine_2
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
η μ : f ⟶ g
⊢ ∃ Z h, η ≫ h = μ ≫ h

Tactic:
refine ⟨.mk (f.hom ≫ F.map (η.right ≫ IsFiltered.coeqHom η.right μ.right)),
  StructuredArrow.homMk (IsFiltered.coeqHom η.right μ.right) (by simp), ?_⟩

Result:
case refine_2
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
f g : StructuredArrow d F
η μ : f ⟶ g
⊢ η ≫ StructuredArrow.homMk (IsFiltered.coeqHom η.right μ.right) ⋯ =
    μ ≫ StructuredArrow.homMk (IsFiltered.coeqHom η.right μ.right) ⋯

Proof state:
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
⊢ IsFiltered (StructuredArrow d F)

Tactic:
suffices IsFilteredOrEmpty (StructuredArrow d F) from IsFiltered.mk

Result:
C : Type u₁
inst✝² : Category.{v₁, u₁} C
D : Type u₂
inst✝¹ : Category.{v₂, u₂} D
F : C ⥤ D
inst✝ : IsFilteredOrEmpty C
h₁ : ∀ (d : D), ∃ c, Nonempty (d ⟶ F.obj c)
h₂ : ∀ {d : D} {c : C} (s s' : d ⟶ F.obj c), ∃ c' t, s ≫ F.map t = s' ≫ F.map t
d : D
this : Nonempty (StructuredArrow d F)
⊢ IsFilteredOrEmpty (StructuredArrow d F)