UnionAll as a Type Parameter

I’m trying to build a structure that separates parametric types (UnionAll) into three categories (Gaussian Alarms, Gaussian Observations, and Reset Observations). I regularly deal with many different UnionAll types. I tried to do something like

struct ObservationStruct{T}
    alarms     :: T{GaussianAlarm}
    estimators :: T{GaussianMeas}
    resets     :: T{ResetObs}

but I get an error
LoadError: TypeError: in Type{...} expression, expected UnionAll, got a value of type TypeVar
Is there any trick here that would allow me to use a UnionAll type for T? Similarly, I want to try and extract the UnionAll type one level up

basetype(::Type{U{T}}) where {U<:UnionAll, T} = U

and I get a very similar error
TypeError: in Type{...} expression, expected UnionAll, got a value of type TypeVar

Are there any tricks with respect to handling nested parametric types? For example, an generic way to get
Dict{Symbol, Vector{T}} where T from Dict{Symbol, Vector{Float64}}
but at the same time get
Vector{Dict{Symbol, T}} where T from Vector{Dict{Symbol, Float64}}

I’m not sure I understand what you are trying to achieve. Is it something like

abstract type AbstractParametricType{T} end

struct GaussianAlarm end
struct GaussianMeas end
struct ResetObs end

struct ObservationStruct{
    GA <: AbstractParametricType{GaussianAlarm}, 
    GM <: AbstractParametricType{GaussianMeas}, 
    RO <: AbstractParametricType{ResetObs}}
    alarms ::GA 
    estimators ::GM 
    resets ::RO

struct ParametricType1{T} <: AbstractParametricType{T} end
struct ParametricType2{T} <: AbstractParametricType{T} end


I wanted to be able to have something like

ObservationStruct{ Dict{Symbol, Vector{T}} where T}()
>> ObservationStruct{ Dict{Symbol, Vector{T}} where T}(
>>     alarms       = Dict{Symbol, Vector{GaussianAlarm}}()
>>     estimators   = Dict{Symbol, Vector{GaussianEstimator}}()
>>     resets       = Dict{Symbol, Vector{ResetObs}() )

I could simply have ObservationStruct{T1, T2, T3} and then write a constructor that would use the UnionAll type, but then it would be hard for me to extract the original UnionAll
Dict{Symbol, Vector{T}} where T
that I used to construct the ObservationStruct. I also would have a hard time dispatching based on the different UnionAll values I used to construct the ObservationStruct. This is why I try hard to avoid deeply nested structs in Julia, but this time there’s no way around it and I’m trying to figure out how to do it elegantly.


struct ParametricType1{T} <: AbstractParametricType{T} 
    dict::Dict{Symbol, Vector{T}}
    ParametricType1{T}() where T = new{T}(Dict{Symbol, Vector{T}}())

we should be pretty near (modulo one indirection)?