diff --git a/server/app/apis/__init__.py b/server/app/apis/__init__.py
index 683b61c02b3d48caf29e38470d878b3a38f62ae7..181a6dcab59ab8db61eb4c01ed7eddecac75bd69 100644
--- a/server/app/apis/__init__.py
+++ b/server/app/apis/__init__.py
@@ -55,6 +55,8 @@ def item_response(item, code=http_codes.OK):
 
 from flask_restx import Api
 
+from .alternatives import api as alternative_ns
+from .answers import api as answer_ns
 from .auth import api as auth_ns
 from .codes import api as code_ns
 from .competitions import api as comp_ns
@@ -73,6 +75,8 @@ flask_api.add_namespace(user_ns, path="/api/users")
 flask_api.add_namespace(auth_ns, path="/api/auth")
 flask_api.add_namespace(comp_ns, path="/api/competitions")
 flask_api.add_namespace(slide_ns, path="/api/competitions/<CID>/slides")
+flask_api.add_namespace(alternative_ns, path="/api/competitions/<CID>/slides/<SOrder>/questions/<QID>/alternatives")
+flask_api.add_namespace(answer_ns, path="/api/competitions/<CID>/teams/<TID>/answers")
 flask_api.add_namespace(team_ns, path="/api/competitions/<CID>/teams")
 flask_api.add_namespace(code_ns, path="/api/competitions/<CID>/codes")
 flask_api.add_namespace(question_ns, path="/api/competitions/<CID>")
diff --git a/server/app/apis/alternatives.py b/server/app/apis/alternatives.py
new file mode 100644
index 0000000000000000000000000000000000000000..8c247b40da2e33bda5cead7d28ce778f73881c6a
--- /dev/null
+++ b/server/app/apis/alternatives.py
@@ -0,0 +1,47 @@
+import app.core.http_codes as codes
+import app.database.controller as dbc
+from app.apis import check_jwt, item_response, list_response
+from app.core.dto import QuestionAlternativeDTO, QuestionDTO
+from app.core.parsers import question_alternative_parser
+from app.core.schemas import QuestionAlternativeSchema
+from app.database.controller.add import question_alternative
+from app.database.controller.get import question_alternatives
+from app.database.models import Question, QuestionAlternative
+from flask_jwt_extended import jwt_required
+from flask_restx import Resource
+
+api = QuestionAlternativeDTO.api
+schema = QuestionAlternativeDTO.schema
+list_schema = QuestionAlternativeDTO.list_schema
+
+
+@api.route("/")
+@api.param("CID, SOrder, QID")
+class QuestionAlternativeList(Resource):
+    @check_jwt(editor=True)
+    def get(self, CID, SOrder, QID):
+        items = dbc.get.question_alternatives(QID)
+        return list_response(list_schema.dump(items))
+
+    @check_jwt(editor=True)
+    def post(self, CID, SOrder, QID):
+        args = question_alternative_parser.parse_args(strict=True)
+        item = dbc.add.question_alternative(**args, question_id=QID)
+        return item_response(schema.dump(item))
+
+
+@api.route("/<AID>")
+@api.param("CID, SOrder, QID, AID")
+class QuestionAlternatives(Resource):
+    @check_jwt(editor=True)
+    def put(self, CID, SOrder, QID, AID):
+        args = question_alternative_parser.parse_args(strict=True)
+        item = dbc.get.one(QuestionAlternative, AID)
+        item = dbc.edit.question_alternative(item, **args)
+        return item_response(schema.dump(item))
+
+    @check_jwt(editor=True)
+    def delete(self, CID, SOrder, QID, AID):
+        item = dbc.get.one(QuestionAlternative, AID)
+        dbc.delete.default(item)
+        return {}, codes.NO_CONTENT
diff --git a/server/app/apis/answers.py b/server/app/apis/answers.py
new file mode 100644
index 0000000000000000000000000000000000000000..40e9407fc5d1df9cac874f7d16d28283278adf24
--- /dev/null
+++ b/server/app/apis/answers.py
@@ -0,0 +1,41 @@
+import app.core.http_codes as codes
+import app.database.controller as dbc
+from app.apis import check_jwt, item_response, list_response
+from app.core.dto import QuestionAnswerDTO
+from app.core.parsers import question_answer_edit_parser, question_answer_parser
+from app.core.schemas import QuestionAlternativeSchema
+from app.database.controller.add import question_alternative
+from app.database.controller.get import question_alternatives
+from app.database.models import Question, QuestionAlternative, QuestionAnswer
+from flask_jwt_extended import jwt_required
+from flask_restx import Resource
+
+api = QuestionAnswerDTO.api
+schema = QuestionAnswerDTO.schema
+list_schema = QuestionAnswerDTO.list_schema
+
+
+@api.route("/")
+@api.param("CID, TID")
+class QuestionAnswerList(Resource):
+    @check_jwt(editor=True)
+    def get(self, CID, TID):
+        items = dbc.get.question_answers(TID)
+        return list_response(list_schema.dump(items))
+
+    @check_jwt(editor=True)
+    def post(self, CID, TID):
+        args = question_answer_parser.parse_args(strict=True)
+        item = dbc.add.question_answer(**args, team_id=TID)
+        return item_response(schema.dump(item))
+
+
+@api.route("/<AID>")
+@api.param("CID, TID, AID")
+class QuestionAnswers(Resource):
+    @check_jwt(editor=True)
+    def put(self, CID, TID, AID):
+        args = question_answer_edit_parser.parse_args(strict=True)
+        item = dbc.get.one(QuestionAnswer, AID)
+        item = dbc.edit.question_answer(item, **args)
+        return item_response(schema.dump(item))
diff --git a/server/app/apis/questions.py b/server/app/apis/questions.py
index f486e3493b09070b5da145c48f497ea30792164e..7d16d3c89e660345c510d84dc645f111dbd7fbf4 100644
--- a/server/app/apis/questions.py
+++ b/server/app/apis/questions.py
@@ -14,7 +14,7 @@ list_schema = QuestionDTO.list_schema
 
 @api.route("/questions")
 @api.param("CID")
-class QuestionsList(Resource):
+class QuestionList(Resource):
     @check_jwt(editor=True)
     def get(self, CID):
         items = dbc.get.question_list(CID)
@@ -23,7 +23,7 @@ class QuestionsList(Resource):
 
 @api.route("/slides/<SID>/questions")
 @api.param("CID, SID")
-class QuestionsList(Resource):
+class QuestionListForSlide(Resource):
     @check_jwt(editor=True)
     def post(self, SID, CID):
         args = question_parser.parse_args(strict=True)
@@ -37,7 +37,7 @@ class QuestionsList(Resource):
 
 @api.route("/slides/<SID>/questions/<QID>")
 @api.param("CID, SID, QID")
-class Questions(Resource):
+class QuestionById(Resource):
     @check_jwt(editor=True)
     def get(self, CID, SID, QID):
         item_question = dbc.get.question(CID, SID, QID)
diff --git a/server/app/core/dto.py b/server/app/core/dto.py
index 034826f5fb784bca39bc85c355d767ccc7ab1498..90e49d00b8062ee3afe6eac7b44e7b397ccfe45c 100644
--- a/server/app/core/dto.py
+++ b/server/app/core/dto.py
@@ -68,3 +68,15 @@ class QuestionDTO:
     api = Namespace("questions")
     schema = schemas.QuestionSchema(many=False)
     list_schema = schemas.QuestionSchema(many=True)
+
+
+class QuestionAlternativeDTO:
+    api = Namespace("alternatives")
+    schema = schemas.QuestionAlternativeSchema(many=False)
+    list_schema = schemas.QuestionAlternativeSchema(many=True)
+
+
+class QuestionAnswerDTO:
+    api = Namespace("answers")
+    schema = schemas.QuestionAnswerSchema(many=False)
+    list_schema = schemas.QuestionAnswerSchema(many=True)
diff --git a/server/app/core/parsers.py b/server/app/core/parsers.py
index f5536cf2f1f0f5e0a751bb70257b9f6f35278d4e..45c0a6e34090951cffe29059cfd578b5d732de1a 100644
--- a/server/app/core/parsers.py
+++ b/server/app/core/parsers.py
@@ -60,7 +60,24 @@ question_parser.add_argument("total_score", type=int, default=None, location="js
 question_parser.add_argument("type_id", type=int, default=None, location="json")
 question_parser.add_argument("slide_id", type=int, location="json")
 
-###QUESTION####
+
+###QUESTION ALTERNATIVES####
+question_alternative_parser = reqparse.RequestParser()
+question_alternative_parser.add_argument("text", type=str, default=None, location="json")
+question_alternative_parser.add_argument("value", type=int, default=None, location="json")
+
+###QUESTION ANSWERS####
+question_answer_parser = reqparse.RequestParser()
+question_answer_parser.add_argument("data", type=dict, required=True, location="json")
+question_answer_parser.add_argument("score", type=int, required=True, location="json")
+question_answer_parser.add_argument("question_id", type=int, required=True, location="json")
+
+###QUESTION ANSWERS EDIT####
+question_answer_edit_parser = reqparse.RequestParser()
+question_answer_edit_parser.add_argument("data", type=dict, default=None, location="json")
+question_answer_edit_parser.add_argument("score", type=int, default=None, location="json")
+
+###CODE####
 code_parser = reqparse.RequestParser()
 code_parser.add_argument("pointer", type=str, default=None, location="json")
 code_parser.add_argument("view_type_id", type=int, default=None, location="json")
diff --git a/server/app/core/rich_schemas.py b/server/app/core/rich_schemas.py
index a890489e23a30aef19c41b1cfc105d9954c68d37..8852c392c4a060a065f618a66393e55b8a2627a8 100644
--- a/server/app/core/rich_schemas.py
+++ b/server/app/core/rich_schemas.py
@@ -20,7 +20,7 @@ class QuestionSchemaRich(RichSchema):
     total_score = ma.auto_field()
     slide_id = ma.auto_field()
     type_id = ma.auto_field()
-    alternatives = fields.Nested(schemas.QuestionAlternative, many=True)
+    alternatives = fields.Nested(schemas.QuestionAlternativeSchema, many=True)
 
 
 class TeamSchemaRich(RichSchema):
diff --git a/server/app/core/schemas.py b/server/app/core/schemas.py
index ff561491ac12644abda6e004efbec12a54becb77..79bdbc1c48fd7460e85fe18f13a744f45a0a57e1 100644
--- a/server/app/core/schemas.py
+++ b/server/app/core/schemas.py
@@ -62,13 +62,13 @@ class QuestionAnswerSchema(BaseSchema):
         model = models.QuestionAnswer
 
     id = ma.auto_field()
-    data = ma.auto_field()
+    data = ma.Function(lambda obj: obj.data)
     score = ma.auto_field()
     question_id = ma.auto_field()
     team_id = ma.auto_field()
 
 
-class QuestionAlternative(BaseSchema):
+class QuestionAlternativeSchema(BaseSchema):
     class Meta(BaseSchema.Meta):
         model = models.QuestionAlternative
 
diff --git a/server/app/database/controller/add.py b/server/app/database/controller/add.py
index be7a773e9e579669393dadd83527ad779726e8cc..929410fa4e22f01a8a7fa2b9e98c1cf8eb7eee0a 100644
--- a/server/app/database/controller/add.py
+++ b/server/app/database/controller/add.py
@@ -15,6 +15,8 @@ from app.database.models import (
     Media,
     MediaType,
     Question,
+    QuestionAlternative,
+    QuestionAnswer,
     QuestionType,
     Role,
     Slide,
@@ -114,6 +116,14 @@ def question(name, total_score, type_id, item_slide):
     return db_add(Question(name, total_score, type_id, item_slide.id))
 
 
+def question_alternative(text, value, question_id):
+    return db_add(QuestionAlternative(text, value, question_id))
+
+
+def question_answer(data, score, question_id, team_id):
+    return db_add(QuestionAnswer(data, score, question_id, team_id))
+
+
 def code(pointer, view_type_id):
     """ Adds a code to the database using the provided arguments. """
 
diff --git a/server/app/database/controller/copy.py b/server/app/database/controller/copy.py
index dabd0d7807025f9c908a6840e9e0a64c40b64a57..a6b408ec301e093d6e47bca359968c052ac62aa1 100644
--- a/server/app/database/controller/copy.py
+++ b/server/app/database/controller/copy.py
@@ -6,10 +6,15 @@ from app.database.controller import add, get, search, utils
 from app.database.models import Question
 
 
+def _alternative(item_old, question_id):
+    """Internal function. Makes a copy of the provided question alternative"""
+    return add.question_alternative(item_old.text, item_old.value, question_id)
+
+
 def _question(item_question_old, slide_id):
     """
     Internal function. Makes a copy of the provided question item to the
-    specified slide. Does not copy team, question answers or alternatives.
+    specified slide. Does not copy team, question answers.
     """
 
     item_question_new = add.db_add(
@@ -21,9 +26,8 @@ def _question(item_question_old, slide_id):
         )
     )
 
-    # TODO: Add question alternatives
-    # for item_alternatives in item_question_old.alternatives:
-    #     dbc.add.alternatives()
+    for item_alternative in item_question_old.alternatives:
+        _alternative(item_alternative, item_question_new.id)
 
     return item_question_new
 
@@ -48,7 +52,7 @@ def _component(item_component, item_slide_new):
 def slide(item_slide_old):
     """
     Deep copies a slide to the same competition.
-    Does not copy team, question answers or alternatives.
+    Does not copy team, question answers.
     """
 
     item_competition = get.competition(item_slide_old.competition_id)
@@ -59,7 +63,7 @@ def slide(item_slide_old):
 def slide_to_competition(item_slide_old, item_competition):
     """
     Deep copies a slide to the provided competition.
-    Does not copy team, question answers or alternatives.
+    Does not copy team, question answers.
     """
 
     item_slide_new = add.slide(item_competition)
@@ -85,7 +89,7 @@ def slide_to_competition(item_slide_old, item_competition):
 def competition(item_competition_old):
     """
     Adds a deep-copy of the provided competition.
-    Will not copy teams, question answers or alternatives.
+    Will not copy teams, question answers.
     """
 
     name = "Kopia av " + item_competition_old.name
diff --git a/server/app/database/controller/edit.py b/server/app/database/controller/edit.py
index 52471badd4edc43ff503436f4f9dbbb65a580c6c..49fcef87a4d28131501786782dbbf95fc58ac1ae 100644
--- a/server/app/database/controller/edit.py
+++ b/server/app/database/controller/edit.py
@@ -125,3 +125,31 @@ def question(item_question, name=None, total_score=None, type_id=None, slide_id=
     db.session.refresh(item_question)
 
     return item_question
+
+
+def question_alternative(item, text=None, value=None):
+
+    if text:
+        item.text = text
+
+    if value:
+        item.value = value
+
+    db.session.commit()
+    db.session.refresh(item)
+
+    return item
+
+
+def question_answer(item, data=None, score=None):
+
+    if data:
+        item.data = data
+
+    if score:
+        item.score = score
+
+    db.session.commit()
+    db.session.refresh(item)
+
+    return item
diff --git a/server/app/database/controller/get.py b/server/app/database/controller/get.py
index f7d14914957066b6ac90bad09b16745bc9a59262..45cbb6ec3a137667b74a2bba514a88685c3b3daa 100644
--- a/server/app/database/controller/get.py
+++ b/server/app/database/controller/get.py
@@ -12,6 +12,8 @@ from app.database.models import (
     ComponentType,
     MediaType,
     Question,
+    QuestionAlternative,
+    QuestionAnswer,
     QuestionType,
     Role,
     Slide,
@@ -78,6 +80,16 @@ def question(CID, SOrder, QID, required=True, error_msg=None):
     return Question.query.join(Slide, join_filters).filter(Question.id == QID).first_extended(required, error_msg)
 
 
+def question_alternatives(QID):
+    # join_filters = (Slide.competition_id == CID) & (Slide.order == SOrder)
+    return QuestionAlternative.query.filter(QuestionAlternative.question_id == QID).all()
+
+
+def question_answers(TID):
+    # join_filters = (Slide.competition_id == CID) & (Slide.order == SOrder)
+    return QuestionAnswer.query.filter(QuestionAnswer.team_id == TID).all()
+
+
 def competition(CID):
     """ Get Competition and all it's sub-entities """
     """ HOT PATH """
diff --git a/server/app/database/models.py b/server/app/database/models.py
index da9e0620b55bf20c6b2ab11bbc4b3ea4a80fe661..2063774f356fab21d53972aa31e542cb056e2bb8 100644
--- a/server/app/database/models.py
+++ b/server/app/database/models.py
@@ -160,7 +160,7 @@ class Question(db.Model):
 class QuestionAlternative(db.Model):
     id = db.Column(db.Integer, primary_key=True)
     text = db.Column(db.String(STRING_SIZE), nullable=False)
-    value = db.Column(db.Boolean, nullable=False)
+    value = db.Column(db.Integer, nullable=False)
     question_id = db.Column(db.Integer, db.ForeignKey("question.id"), nullable=False)
 
     def __init__(self, text, value, question_id):
@@ -172,8 +172,9 @@ class QuestionAlternative(db.Model):
 class QuestionAnswer(db.Model):
     __table_args__ = (db.UniqueConstraint("question_id", "team_id"),)
     id = db.Column(db.Integer, primary_key=True)
-    data = db.Column(db.Text, nullable=False)
+    data = db.Column(Dictionary(), nullable=False)
     score = db.Column(db.Integer, nullable=False, default=0)
+
     question_id = db.Column(db.Integer, db.ForeignKey("question.id"), nullable=False)
     team_id = db.Column(db.Integer, db.ForeignKey("team.id"), nullable=False)
 
diff --git a/server/populate.py b/server/populate.py
index 48ed2f955860c048ba62d1b5e4e57bf76358df4d..609193ba0dc5e5a19e3425fa25144d4aabe688d6 100644
--- a/server/populate.py
+++ b/server/populate.py
@@ -63,13 +63,16 @@ def _add_items():
             dbc.utils.commit_and_refresh(item_slide)
 
             # Add question to competition
-            dbc.add.question(
+            item_question = dbc.add.question(
                 name=f"Question {j}: {question_types_items[j].name}",
                 total_score=j,
                 type_id=question_types_items[j].id,
                 item_slide=item_slide,
             )
 
+            for i in range(3):
+                dbc.add.question_alternative(f"Alternative {i}", 0, item_question.id)
+
             # Add text components
             # TODO: Add images as components
             for k in range(3):
diff --git a/server/tests/test_db.py b/server/tests/test_db.py
index 7d162065c8857a24a137b1f55c610f969045fd60..8f211473c14977634c5332874f455b954a2124cf 100644
--- a/server/tests/test_db.py
+++ b/server/tests/test_db.py
@@ -80,9 +80,11 @@ def check_slides_copy(item_slide_original, item_slide_copy, num_slides, order):
     assert item_slide_copy.settings == item_slide_original.settings
 
     # Checks that all components were correctly copied
-    assert len(item_slide_copy.components) == len(item_slide_original.components)
-    for i, c1 in enumerate(item_slide_original.components):
-        c2 = item_slide_copy.components[i]
+    components = item_slide_original.components
+    components_copy = item_slide_copy.components
+    assert len(components) == len(components_copy)
+
+    for c1, c2 in zip(components, components_copy):
         assert c1 != c2
         assert c1.x == c2.x
         assert c1.y == c2.y
@@ -94,16 +96,28 @@ def check_slides_copy(item_slide_original, item_slide_copy, num_slides, order):
         assert c1.type_id == c2.type_id
 
     # Checks that all questions were correctly copied
-    assert len(item_slide_copy.questions) == len(item_slide_original.questions)
-    for i, q1 in enumerate(item_slide_original.questions):
-        q2 = item_slide_copy.questions[i]
+    questions = item_slide_original.questions
+    questions_copy = item_slide_copy.questions
+    assert len(questions) == len(questions_copy)
+
+    for q1, q2 in zip(questions, questions_copy):
         assert q1 != q2
         assert q1.name == q2.name
         assert q1.total_score == q2.total_score
         assert q1.type_id == q2.type_id
         assert q1.slide_id == item_slide_original.id
         assert q2.slide_id == item_slide_copy.id
-        # TODO: Assert alternatives
+
+        # Assert alternatives
+        alternatives = q1.alternatives
+        alternatives_copy = q2.alternatives
+        assert len(alternatives) == len(alternatives_copy)
+
+        for a1, a2 in zip(alternatives, alternatives_copy):
+            assert a1.text == a2.text
+            assert a1.value == a2.value
+            assert a1.quesiton_id == q1.id
+            assert a2.quesiton_id == q2.id
 
     # Checks that the copy put the slide in the database
     item_slides, total = dbc.search.slide(