diff --git a/src/main/kotlin/org/openpolicyagent/ideaplugin/ide/typing/RegoBraceMatcher.kt b/src/main/kotlin/org/openpolicyagent/ideaplugin/ide/typing/RegoBraceMatcher.kt
new file mode 100644
index 0000000..06d7753
--- /dev/null
+++ b/src/main/kotlin/org/openpolicyagent/ideaplugin/ide/typing/RegoBraceMatcher.kt
@@ -0,0 +1,32 @@
+/*
+ * Use of this source code is governed by the MIT license that can be
+ * found in the LICENSE file.
+ */
+
+package org.openpolicyagent.ideaplugin.ide.typing
+
+import com.intellij.lang.BracePair
+import com.intellij.lang.PairedBraceMatcher
+import com.intellij.psi.PsiFile
+import com.intellij.psi.tree.IElementType
+import org.openpolicyagent.ideaplugin.lang.psi.RegoTypes
+
+/**
+ * Defines the brace matching for Rego language (ie allow to auto close  brace, bracket and parenthesis when typed, also
+ * color matching braces, brackets...)
+ */
+class RegoBraceMatcher: PairedBraceMatcher {
+    override fun getPairs() = PAIRS
+
+    override fun isPairedBracesAllowedBeforeType(lbraceType: IElementType, contextType: IElementType?): Boolean = true
+
+    override fun getCodeConstructStart(file: PsiFile, openingBraceOffset: Int): Int = openingBraceOffset
+
+    companion object {
+        private val PAIRS: Array<BracePair> = arrayOf(
+            BracePair(RegoTypes.LBRACE, RegoTypes.RBRACE, true),
+            BracePair(RegoTypes.LBRACK, RegoTypes.RBRACK, false),
+            BracePair(RegoTypes.LPAREN, RegoTypes.RPAREN, false)
+        )
+    }
+}
diff --git a/src/main/resources/META-INF/opa-core.xml b/src/main/resources/META-INF/opa-core.xml
index e7b57f0..6990194 100644
--- a/src/main/resources/META-INF/opa-core.xml
+++ b/src/main/resources/META-INF/opa-core.xml
@@ -33,6 +33,9 @@
         <todoIndexer filetype="Rego file" implementationClass="org.openpolicyagent.ideaplugin.ide.todo.RegoLexerBasedTodoIndexer"/>
         <indexPatternBuilder implementation="org.openpolicyagent.ideaplugin.ide.todo.RegoTodoIndexPatternBuilder"/>
 
+        <!-- Typing -->
+        <lang.braceMatcher language="rego" implementationClass="org.openpolicyagent.ideaplugin.ide.typing.RegoBraceMatcher"/>
+
         <toolWindow id="OPA Console"
                         anchor="bottom"
                         icon="/icons/opa_13_13.svg"
diff --git a/src/test/kotlin/org/openpolicyagent/ideaplugin/ide/typing/RegoBraceMatcherTest.kt b/src/test/kotlin/org/openpolicyagent/ideaplugin/ide/typing/RegoBraceMatcherTest.kt
new file mode 100644
index 0000000..6b3e3fb
--- /dev/null
+++ b/src/test/kotlin/org/openpolicyagent/ideaplugin/ide/typing/RegoBraceMatcherTest.kt
@@ -0,0 +1,124 @@
+/*
+ * Use of this source code is governed by the MIT license that can be
+ * found in the LICENSE file.
+ */
+
+package org.openpolicyagent.ideaplugin.ide.typing
+
+import com.intellij.codeInsight.highlighting.BraceMatchingUtil
+import org.openpolicyagent.ideaplugin.OpaTestBase
+import org.openpolicyagent.ideaplugin.lang.RegoFileType
+
+class RegoBraceMatcherTest: OpaTestBase() {
+
+    fun `test parenthesis are paired`()= doTest(
+        """
+            package main
+            a := sprinft<caret>
+        """.trimIndent(),
+        '(',
+        """
+            package main
+            a := sprinft(<caret>)
+        """.trimIndent()
+    )
+
+
+    fun `test brackets are paired`()= doTest(
+        """
+            package main
+            a := <caret>
+        """.trimIndent(),
+        '[',
+        """
+            package main
+            a := [<caret>]
+        """.trimIndent()
+    )
+
+
+    fun `test braces are paired`()= doTest(
+        """
+            package main
+            rule_1<caret>
+        """.trimIndent(),
+        '{',
+        """
+            package main
+            rule_1{<caret>}
+        """.trimIndent()
+    )
+
+    fun `test parenthesis deletion`()= doTest(
+        """
+            package main
+            a := sprinft(<caret>)
+        """.trimIndent(),
+        '\b',
+        """
+            package main
+            a := sprinft<caret>
+        """.trimIndent()
+    )
+    fun `test brackets deletion`()= doTest(
+        """
+            package main
+            a := [<caret>]
+        """.trimIndent(),
+        '\b',
+        """
+            package main
+            a := <caret>
+        """.trimIndent()
+    )
+
+    fun `test braces deletion`()= doTest(
+        """
+            package main
+            rule_1{<caret>}
+        """.trimIndent(),
+        '\b',
+        """
+            package main
+            rule_1<caret>
+        """.trimIndent()
+    )
+
+    fun `test parenthesis match` () = doMatch(
+        """
+            package main
+            a: = sprintf<caret>("hello %v", name[x])
+        """.trimIndent(),
+        ")"
+    )
+
+    fun `test brackets match` () = doMatch(
+        """
+            package main
+            a: = sprintf("hello %v", name<caret>[x])
+        """.trimIndent(),
+        "]"
+    )
+
+    fun `test braces match` () = doMatch(
+        """
+            package main
+            rule_1 <caret>{                
+                a: = sprintf("hello %v", name[x])            
+            }
+        """.trimIndent(),
+        "}"
+    )
+    private fun doTest(before: String, type: Char, after: String) {
+        myFixture.configureByText(RegoFileType, before)
+        myFixture.type(type)
+        myFixture.checkResult(after)
+    }
+
+    private fun doMatch(source: String, coBrace: String) {
+        myFixture.configureByText(RegoFileType, source)
+        val expected = source.replace("<caret>", "").lastIndexOf(coBrace)
+        check(BraceMatchingUtil.getMatchedBraceOffset(myFixture.editor, true, myFixture.file) == expected)
+    }
+
+}