diff --git a/src/Lib/Script/Ast/IrType.cc b/src/Lib/Script/Ast/IrType.cc
index 4860a1c52533a73843d6f40beb097fbde3d48281..e95b265ee47ac6b7c92fdcf7afc7a09ae09bc2f5 100644
--- a/src/Lib/Script/Ast/IrType.cc
+++ b/src/Lib/Script/Ast/IrType.cc
@@ -4,18 +4,6 @@
 
 namespace Vivy::Script
 {
-const ::Vivy::Script::IrVariable *
-IrType::parent() const noexcept
-{
-    return dynamic_cast<const IrVariable *>(IrElement::parent());
-}
-
-::Vivy::Script::IrVariable *
-IrType::parent() noexcept
-{
-    return dynamic_cast<IrVariable *>(IrElement::parent());
-}
-
 void
 IrType::assertType(Type t) const
 {
@@ -25,6 +13,10 @@ IrType::assertType(Type t) const
 }
 }
 
+/*
+** IrTAss
+*/
+
 namespace Vivy::Script
 {
 IrType::Type
@@ -58,6 +50,10 @@ IrTAss::parse(std::vector<Token> *)
 }
 }
 
+/*
+** IrTOption
+*/
+
 namespace Vivy::Script
 {
 IrType::Type
@@ -101,9 +97,28 @@ IrTPrimitive::IrTPrimitive(const PrimitiveType type) noexcept
 {
 }
 
+void
+IrTPrimitive::setSelfInnerTypeFromToken(const Token &name)
+ {
+     name.assertType(Token::Type::SIMPLE);
+    if (name.isSimple(TOKEN_BOOL)) {
+        selfInnerType = IrType::PrimitiveType::Bool;
+    } else if (name.isSimple(TOKEN_INT)) {
+        selfInnerType = IrType::PrimitiveType::Int;
+    } else if (name.isSimple(TOKEN_FLOAT)) {
+        selfInnerType = IrType::PrimitiveType::Float;
+    } else if (name.isSimple(TOKEN_STRING)) {
+        selfInnerType = IrType::PrimitiveType::String;
+    } else if (name.isSimple(TOKEN_COLOR)) {
+        selfInnerType = IrType::PrimitiveType::Color;
+    } else {
+        throw std::logic_error("IrTPrimitive unexpected token " + name.toString());
+    }
+ }
+
 IrTPrimitive::IrTPrimitive(const Token &name)
 {
-    throw std::logic_error("IrTPrimitive " + name.toString());
+    setSelfInnerTypeFromToken(name)
 }
 
 IrType::Type
@@ -121,18 +136,70 @@ IrTPrimitive::innerType() const noexcept
 unsigned int
 IrTPrimitive::innerTypeCount() const noexcept
 {
-    return selfArraySize;
+    /* 0 is same as 1, it's not an array! */
+    return selfArraySize <= 1 : 1 : selfArraySize;
 }
 
 std::string
 IrTPrimitive::toString() const noexcept
 {
-    return "IrTPrimitive";
+    switch (selfInnerType) {
+    case IrType::PrimitiveType::Int: return std::string("INT");
+    case IrType::PrimitiveType::Float: return std::string("FLOAT");
+    case IrType::PrimitiveType::Bool: return std::string("BOOL");
+    case IrType::PrimitiveType::Color: return std::string("COLOR");
+    case IrType::PrimitiveType::String: return std::string("STRING");
+    }
 }
 
 void
-IrTPrimitive::parse(std::vector<Token> *)
-{
-    throw std::logic_error("Not implemented");
+IrTPrimitive::parse(std::vector<Token> *tokens)
+{
+    selfArraySize.clear();
+    if (tokens->size() == 0) {
+        throw std::runtime_error("Expected at least one token to parse an IrTPrimitive");
+    } else if (tokens->size() == 1) {
+        setSelfInnerTypeFromToken(getInnerTokenOpt(tokenListPop(tokens)))
+    } else {
+        const Token primToken = getInnerTokenOpt(tokenListPop(tokens));
+        setSelfInnerTypeFromToken(primToken);
+        std::vector<Token> sizeTokens tokenListPopToNextSimpleToken(tokens, TOKEN_BRACKET_RIGHT);
+
+        if (tokens->size()) {
+            throw std::runtime_error(getInnerTokenOpt(tokenListPeek(tokens)).location().toString() ": Remaining tokens for the array dimensions of the type, this is invalid. To declare an array, use `TYPE_NAME[dim1, dim2, ...]`");
+        } else if (sizeTokens->size() <= 2) {
+            throw std::runtime_error(getInnerTokenOpt(tokenListPeek(sizeTokens)).location().toString() ": Invalid array dimensions for the type. To declare an array, use `TYPE_NAME[dim1, dim2, ...]`");
+        }
+
+        bool parsedBracketOnce = false;
+        Token sizeToken = getInnerTokenOpt(tokenListPop(sizeTokens));
+        do {
+            if (sizeToken.isSimple(TOKEN_BRACKET_LEFT)) {
+                if (parsedBracketOnce) {
+                    throw std::runtime_error("Unexepcted token " + sizeToken.toString() + ", the [ must begein the size specifications, line `INT[1, 2, 3]`");
+                }
+                parsedBracketOnce = true;
+                sizeToken = getInnerTokenOpt(tokenListPop(sizeTokens));
+            } else if (sizeToken.isSimple(TOKEN_COMMA)) {
+                if (!parsedBracketOnce) {
+                    throw std::runtime_error("Unexepcted token " + sizeToken.toString() + ", the [ must begein the size specifications, line `INT[1, 2, 3]`");
+                }
+                sizeToken = getInnerTokenOpt(tokenListPop(sizeTokens));
+            } else if (sizeToken.isSimple(TOKEN_BRACKET_RIGHT)) {
+                break;
+            } else {
+                throw std::runtime_error("Unexepcted token " + sizeToken.toString());
+            }
+
+            sizeToken.assertType(Token::Type::INTEGER);
+            arraySizes.push_back(sizeToken.asInteger());
+
+            /* The [ and , are ignored, they delimit each dimensions */
+        } while (sizeToken.valueType() == Token::Type::INTEGER);
+
+        /* Must end by a ] */
+        sizeToken.assertTypeSimple(TOKEN_BRACKET_RIGHT);
+        selfArraySize = static_cast<unsigned int>(arraySizes.size());
+    }
 }
 }
diff --git a/src/Lib/Script/Ast/IrType.hh b/src/Lib/Script/Ast/IrType.hh
index 71b2b5b36842e3c43dacd2d54780d70294880a5e..c2d537a0e051ae1f5cbabe1e22a96842832d9500 100644
--- a/src/Lib/Script/Ast/IrType.hh
+++ b/src/Lib/Script/Ast/IrType.hh
@@ -16,8 +16,6 @@ public:
 public:
     virtual Type type() const noexcept = 0;
     void assertType(Type) const;
-    const IrVariable *parent() const noexcept override;
-    IrVariable *parent() noexcept override;
 };
 
 class IrTAss final : public IrType {
@@ -53,11 +51,14 @@ class IrTPrimitive final : public IrType {
 
     PrimitiveType selfInnerType;
     unsigned int selfArraySize;
+    std::vector<unsigned int> arraySizes = { 1 };
 
     IrTPrimitive(const Token &);
     IrTPrimitive(const PrimitiveType) noexcept;
     IrTPrimitive(const PrimitiveType, unsigned int) noexcept;
 
+    void IrTPrimitive::setSelfInnerTypeFromToken(const Token &name);
+
 public:
     Type type() const noexcept override;
     PrimitiveType innerType() const noexcept;
diff --git a/src/Lib/Script/FrontEnd/Tokens.hh b/src/Lib/Script/FrontEnd/Tokens.hh
index bc1d6ebbd126c8e674bff06f152fef458198e849..c06428f0dd7917956609b407130064f0d11dc417 100644
--- a/src/Lib/Script/FrontEnd/Tokens.hh
+++ b/src/Lib/Script/FrontEnd/Tokens.hh
@@ -41,6 +41,7 @@ namespace Vivy::Script
 #define TOKEN_BOOL                STRV_STATIC("BOOL")
 #define TOKEN_COLOR               STRV_STATIC("COLOR")
 #define TOKEN_VOID                STRV_STATIC("VOID")
+#define TOKEN_STRING              STRV_STATIC("STR")
 #define TOKEN_IN                  STRV_STATIC("in")
 #define TOKEN_FOR                 STRV_STATIC("for")
 #define TOKEN_AS                  STRV_STATIC("as")
@@ -60,7 +61,7 @@ namespace Vivy::Script
 
 #define TOKEN_LIST_BASE_TYPE                                       \
     {                                                              \
-        TOKEN_BOOL, TOKEN_REAL, TOKEN_INT, TOKEN_COLOR, TOKEN_VOID \
+        TOKEN_BOOL, TOKEN_REAL, TOKEN_INT, TOKEN_COLOR, TOKEN_VOID, TOKEN_STRING \
     }
 
 #define TOKEN_RULE_INT         "(+|-)?[0-9]+"
@@ -128,6 +129,7 @@ namespace Vivy::Script
                                                          TOKEN_LE,
                                                          TOKEN_GT,
                                                          TOKEN_GE,
+                                                         TOKEN_STRING,
                                                          TOKEN_ASSIGN,
                                                          TOKEN_FALSE,
                                                          TOKEN_TRUE,