diff --git a/package-lock.json b/package-lock.json
index ae6799dd5cb4006c2b35ed0f8e731019c2b3dfff..7e63fe57104ff692f203149b34f440e2cd169539 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -10,6 +10,7 @@
       "dependencies": {
         "axios": "^1.6.8",
         "bootstrap": "^5.3.3",
+        "oh-vue-icons": "^1.0.0-rc3",
         "pinia": "^2.1.7",
         "vue": "^3.4.21",
         "vue-router": "^4.3.0",
@@ -6063,6 +6064,48 @@
         "url": "https://github.com/sponsors/ljharb"
       }
     },
+    "node_modules/oh-vue-icons": {
+      "version": "1.0.0-rc3",
+      "resolved": "https://registry.npmjs.org/oh-vue-icons/-/oh-vue-icons-1.0.0-rc3.tgz",
+      "integrity": "sha512-+k2YC6piK7sEZnwbkQF3UokFPMmgqpiLP6f/H0ovQFLl20QA5V4U8EcI6EclD2Lt5NMQ3k6ilLGo8XyXqdVSvg==",
+      "dependencies": {
+        "vue-demi": "^0.12.5"
+      },
+      "peerDependencies": {
+        "@vue/composition-api": "^1.0.0-rc.1",
+        "vue": "^2.0.0 || >=3.0.0"
+      },
+      "peerDependenciesMeta": {
+        "@vue/composition-api": {
+          "optional": true
+        }
+      }
+    },
+    "node_modules/oh-vue-icons/node_modules/vue-demi": {
+      "version": "0.12.5",
+      "resolved": "https://registry.npmjs.org/vue-demi/-/vue-demi-0.12.5.tgz",
+      "integrity": "sha512-BREuTgTYlUr0zw0EZn3hnhC3I6gPWv+Kwh4MCih6QcAeaTlaIX0DwOVN0wHej7hSvDPecz4jygy/idsgKfW58Q==",
+      "hasInstallScript": true,
+      "bin": {
+        "vue-demi-fix": "bin/vue-demi-fix.js",
+        "vue-demi-switch": "bin/vue-demi-switch.js"
+      },
+      "engines": {
+        "node": ">=12"
+      },
+      "funding": {
+        "url": "https://github.com/sponsors/antfu"
+      },
+      "peerDependencies": {
+        "@vue/composition-api": "^1.0.0-rc.1",
+        "vue": "^3.0.0-0 || ^2.6.0"
+      },
+      "peerDependenciesMeta": {
+        "@vue/composition-api": {
+          "optional": true
+        }
+      }
+    },
     "node_modules/once": {
       "version": "1.4.0",
       "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
diff --git a/package.json b/package.json
index 9f52cb1c7a23f36ca3194ffe34a78eb863858028..7f62401e3056a470b8fb54afb0fc7f6634551a86 100644
--- a/package.json
+++ b/package.json
@@ -18,6 +18,7 @@
   "dependencies": {
     "axios": "^1.6.8",
     "bootstrap": "^5.3.3",
+    "oh-vue-icons": "^1.0.0-rc3",
     "pinia": "^2.1.7",
     "vue": "^3.4.21",
     "vue-router": "^4.3.0",
diff --git a/src/App.vue b/src/App.vue
index 461e3d52db193794b9b516bce015595a8eeb985d..1a140ee58a2d942ddacb457b5fbd6f5b5ad23e0b 100644
--- a/src/App.vue
+++ b/src/App.vue
@@ -1,9 +1,18 @@
 <script setup lang="ts">
 import { RouterView } from 'vue-router'
+import ErrorBoundaryCatcher from '@/components/Exceptions/ErrorBoundaryCatcher.vue';
 </script>
 
 <template>
   <main>
-    <RouterView />
+    <error-boundary-catcher>
+      <RouterView />
+    </error-boundary-catcher>
   </main>
-</template>
\ No newline at end of file
+</template>
+
+<style>
+  main {
+    font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
+  }
+</style>
\ No newline at end of file
diff --git a/src/components/Exceptions/ErrorBoundaryCatcher.vue b/src/components/Exceptions/ErrorBoundaryCatcher.vue
new file mode 100644
index 0000000000000000000000000000000000000000..3bc046fb271f7d3b3ce3acee559329d18dce53bb
--- /dev/null
+++ b/src/components/Exceptions/ErrorBoundaryCatcher.vue
@@ -0,0 +1,19 @@
+<template>
+    <error-box :error-message="errorStore.getFirstError" @update:errorMessage="errorStore.removeCurrentError" />
+    <slot />
+  </template>
+  
+  <script setup lang="ts">
+  import { onErrorCaptured } from 'vue';
+  import { useErrorStore } from '@/stores/ErrorStore';
+  import ErrorBox from '@/components/Exceptions/ErrorBox.vue';
+  import handleUnknownError from '@/components/Exceptions/unkownErrorHandler';
+  
+  const errorStore = useErrorStore();
+  
+  onErrorCaptured((err, _vm, _info): boolean => {
+    const message = handleUnknownError(err.message);
+    errorStore.addError(message); //If no openAPI axios error, use err.message
+    return false;
+  });
+  </script>
\ No newline at end of file
diff --git a/src/components/Exceptions/ErrorBox.vue b/src/components/Exceptions/ErrorBox.vue
new file mode 100644
index 0000000000000000000000000000000000000000..f6dbe0d4adfb07e7ae1b4720ecf322b08fa3de71
--- /dev/null
+++ b/src/components/Exceptions/ErrorBox.vue
@@ -0,0 +1,90 @@
+<template>
+    <div class="error-box" v-if="errorMessage" data-testid="error-box">
+      <span>
+        <v-icon name="bi-exclamation-triangle" />
+        <button @click="wrapText = !wrapText" class="error-message-button">
+          <h4>{{ errorMessage }}</h4>
+        </button>
+        <button class="error-remove-button" @click="$emit('update:errorMessage', '')" data-testid="hide-button">
+          <v-icon scale="2" name="bi-dash" />
+        </button>
+      </span>
+    </div>
+  </template>
+  
+  <script lang="ts">
+  import { defineComponent } from 'vue';
+  import { OhVueIcon, addIcons } from 'oh-vue-icons';
+  import { BiDash, BiExclamationTriangle } from 'oh-vue-icons/icons';
+  
+  addIcons(BiDash, BiExclamationTriangle);
+  
+  export default defineComponent({
+    components: {
+      'v-icon': OhVueIcon,
+    },
+    props: {
+      errorMessage: {
+        type: String,
+        default: '',
+      },
+    },
+    data() {
+      return {
+        wrapText: false,
+      };
+    },
+  });
+  </script>
+  
+  <style scoped>
+  .error-box {
+    position: fixed;
+    top: 2em;
+    left: 50%;
+    transform: translate(-50%, 0);
+    width: min(100%, 700px);
+    background-color: var(--red-color);
+    padding: 7px;
+    border-radius: 5px;
+    z-index: 1000;
+  }
+  
+  .error-box span {
+    display: flex;
+    justify-content: space-between;
+    align-items: center;
+  }
+  
+  .error-message-button {
+    white-space: v-bind('wrapText ? "normal" : "nowrap"');
+    overflow: hidden;
+    border: none;
+  }
+  
+  .error-message-button h4 {
+    overflow: hidden;
+    text-overflow: ellipsis;
+  }
+  
+  .error-box * {
+    margin: 2px;
+  }
+  
+  .error-box button {
+    background-color: transparent;
+    box-shadow: none;
+    color: black;
+    cursor: pointer;
+  }
+  
+  .error-remove-button {
+    color: rgb(79, 77, 77);
+    border: solid black 0.5px;
+    padding: 0.3em;
+  }
+  
+  .error-box button:hover {
+    color: rgb(40, 38, 38);
+  }
+  </style>
\ No newline at end of file
diff --git a/src/components/Exceptions/unkownErrorHandler.ts b/src/components/Exceptions/unkownErrorHandler.ts
new file mode 100644
index 0000000000000000000000000000000000000000..6f7b6d914edc88b03029a68b907f7ef45f05ee7e
--- /dev/null
+++ b/src/components/Exceptions/unkownErrorHandler.ts
@@ -0,0 +1,19 @@
+import { ApiError as BackendApiError } from '@/api';
+import { AxiosError } from 'axios';
+
+/**
+ * Finds the correct error message for the given error
+ * The message is then put into the error store
+ * which an error component can then display
+ * @param error The unknown error to handle
+ */
+const handleUnknownError = (error: any): string => {
+  if (error instanceof AxiosError) {
+    return error.code!!;
+  } else if (error instanceof BackendApiError) {
+    return error.body.detail ?? error.body;
+  }
+  return 'ContextErrorMessage';
+};
+
+export default handleUnknownError;
\ No newline at end of file
diff --git a/src/router/index.ts b/src/router/index.ts
index 83cc091e2226f9bdedf4ff60d45c2b9b83317778..98101c6423782c3fa0ebfca00d156b93fac31f5a 100644
--- a/src/router/index.ts
+++ b/src/router/index.ts
@@ -24,6 +24,11 @@ const routes = [
         name: 'news',
         component: () => import('@/views/NewsView.vue'),
       },
+      {
+        path: 'test',
+        name: 'test',
+        component: () => import('@/views/TestView.vue'),
+      },
     ]
   },
   {
diff --git a/src/stores/ErrorStore.ts b/src/stores/ErrorStore.ts
new file mode 100644
index 0000000000000000000000000000000000000000..32ffb91af9d857c3ad747853265724d3843f4ea4
--- /dev/null
+++ b/src/stores/ErrorStore.ts
@@ -0,0 +1,33 @@
+import { defineStore } from 'pinia';
+
+// A userstore which can be used to store several errors at the same time
+export const useErrorStore = defineStore('ErrorStore', {
+  state: () => ({
+    errors: [] as string[],
+  }),
+  actions: {
+    addError(error: string) {
+      console.log(error);
+      this.errors = [error];
+    },
+    removeCurrentError() {
+      if (this.errors.length > 0) {
+        this.errors.shift();
+      }
+    },
+  },
+  getters: {
+    getFirstError(): string {
+      if (this.errors.length > 0) {
+        return `Exceptions.${this.errors[0]}`;
+      }
+      return '';
+    },
+    getLastError(): string {
+      if (this.errors.length > 0) {
+        return `Exceptions.${this.errors[this.errors.length - 1]}`;
+      }
+      return '';
+    },
+  },
+});
\ No newline at end of file
diff --git a/src/views/TestView.vue b/src/views/TestView.vue
new file mode 100644
index 0000000000000000000000000000000000000000..a7fce444288c4df4c5f9f531c3e92e3da43935a4
--- /dev/null
+++ b/src/views/TestView.vue
@@ -0,0 +1,11 @@
+<template>
+    <div>
+        <Button1 :buttonText="hallo"></Button1>
+    </div>
+</template>
+
+<script setup lang="ts">
+    import Button1 from '@/components/Buttons/Button1.vue'
+
+    const hallo = 'Hallo'
+</script>
\ No newline at end of file