diff --git a/src/main/java/org/olat/core/util/openxml/OpenXMLWorkbookStyles.java b/src/main/java/org/olat/core/util/openxml/OpenXMLWorkbookStyles.java
index 4885c5906b5ac7e7b64ff7f325e917f425811589..6e9b226dcc701036ee10e5bc02ebfb1a5701ce55 100644
--- a/src/main/java/org/olat/core/util/openxml/OpenXMLWorkbookStyles.java
+++ b/src/main/java/org/olat/core/util/openxml/OpenXMLWorkbookStyles.java
@@ -48,7 +48,7 @@ public class OpenXMLWorkbookStyles {
 	private List<CellStyle> cellXfs = new ArrayList<>();
 	
 	private final Font standardFont, boldFont;
-	private final Fill noneFile, gray125Fill, correctFill;
+	private final Fill noneFile, gray125Fill, lightGrayFill, correctFill;
 	private final Border noBorder, borderRight;
 	
 	/**
@@ -62,6 +62,7 @@ public class OpenXMLWorkbookStyles {
 	private final CellStyle headerStyle;
 	private final CellStyle correctStyle;
 	private final CellStyle percentStyle;
+	private final CellStyle lightGrayStyle;
 
 	public OpenXMLWorkbookStyles() {
 		standardFont = new Font(fonts.size(), "12", "1", "Calibri", "2", "minor", FontStyle.none);
@@ -73,6 +74,8 @@ public class OpenXMLWorkbookStyles {
 		fills.add(noneFile);
 		gray125Fill = new Fill(fills.size(), "gray125");
 		fills.add(gray125Fill);
+		lightGrayFill = new Fill(fills.size(), "solid", "EFEFEFEF", "64");
+		fills.add(lightGrayFill);
 		correctFill = new Fill(fills.size(), "solid", "FFC3FFC0", "64");
 		fills.add(correctFill);
 		
@@ -97,6 +100,8 @@ public class OpenXMLWorkbookStyles {
 		cellXfs.add(correctStyle);
 		percentStyle = new CellStyle(cellXfs.size(), PERCENT_FORMAT, standardFont, noneFile, borderRight, null, "1");
 		cellXfs.add(percentStyle);
+		lightGrayStyle = new CellStyle(cellXfs.size(), "0", standardFont, lightGrayFill, borderRight, null, null);
+		cellXfs.add(lightGrayStyle);
 	}
 	
 	public CellStyle getBorderRightStyle() {
@@ -135,6 +140,10 @@ public class OpenXMLWorkbookStyles {
 		return percentStyle;
 	}
 	
+	public CellStyle getLightGrayStyle() {
+		return lightGrayStyle;
+	}
+	
 	public List<Font> getFonts() {
 		return fonts;
 	}
diff --git a/src/main/java/org/olat/ims/qti21/manager/archive/QTI21ArchiveFormat.java b/src/main/java/org/olat/ims/qti21/manager/archive/QTI21ArchiveFormat.java
index ea3f5c7ce2a604064c40db2b1376ebf8d1f0ce26..b440cbe9603241cc322f7412a7fea45147e39c9a 100644
--- a/src/main/java/org/olat/ims/qti21/manager/archive/QTI21ArchiveFormat.java
+++ b/src/main/java/org/olat/ims/qti21/manager/archive/QTI21ArchiveFormat.java
@@ -22,6 +22,7 @@ package org.olat.ims.qti21.manager.archive;
 import java.io.File;
 import java.io.IOException;
 import java.io.OutputStream;
+import java.math.BigDecimal;
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.Date;
@@ -117,6 +118,10 @@ import uk.ac.ed.ph.jqtiplus.node.item.interaction.SliderInteraction;
 import uk.ac.ed.ph.jqtiplus.node.item.interaction.TextEntryInteraction;
 import uk.ac.ed.ph.jqtiplus.node.item.interaction.UploadInteraction;
 import uk.ac.ed.ph.jqtiplus.node.test.AssessmentItemRef;
+import uk.ac.ed.ph.jqtiplus.node.test.AssessmentSection;
+import uk.ac.ed.ph.jqtiplus.node.test.AssessmentTest;
+import uk.ac.ed.ph.jqtiplus.node.test.SectionPart;
+import uk.ac.ed.ph.jqtiplus.node.test.TestPart;
 import uk.ac.ed.ph.jqtiplus.resolution.ResolvedAssessmentItem;
 import uk.ac.ed.ph.jqtiplus.resolution.ResolvedAssessmentTest;
 import uk.ac.ed.ph.jqtiplus.types.Identifier;
@@ -140,8 +145,9 @@ public class QTI21ArchiveFormat {
 	private final QTI21StatisticSearchParams searchParams;
 	private ExportFormat exportConfig;
 	
+	private int numOfSections;
 	private CourseNode courseNode;
-	private List<ItemInfos> itemInfos;
+	private List<AbstractInfos> elementInfos;
 	private final Map<String, InteractionArchive> interactionArchiveMap = new HashMap<>();
 	
 	private final QTI21Service qtiService;
@@ -332,30 +338,39 @@ public class QTI21ArchiveFormat {
 		header1Row.addCell(col++, translator.translate("archive.table.header.test"), headerStyle);
 		col += 5;
 		
-		List<ItemInfos> infos = getItemInfos();
+		List<AbstractInfos> infos = getItemInfos();
 		for(int i=0; i<infos.size(); i++) {
 			int delta = col;
-			ItemInfos item = infos.get(i);
-			if (exportConfig.isResponseCols() || exportConfig.isPointCol() || exportConfig.isTimeCols() || exportConfig.isCommentCol()) {
-				List<Interaction> interactions = item.getInteractions();
-				for(int j=0; j<interactions.size(); j++) {
-					Interaction interaction = interactions.get(j);
-					col = interactionArchiveMap.get(interaction.getQtiClassName())
-							.writeHeader1(item.getAssessmentItem(), interaction, i, j, header1Row, col, workbook);
+			AbstractInfos info = infos.get(i);
+			if(info instanceof ItemInfos) {
+				ItemInfos item = (ItemInfos)info;
+				if (exportConfig.isResponseCols() || exportConfig.isPointCol() || exportConfig.isTimeCols() || exportConfig.isCommentCol()) {
+					List<Interaction> interactions = item.getInteractions();
+					for(int j=0; j<interactions.size(); j++) {
+						Interaction interaction = interactions.get(j);
+						col = interactionArchiveMap.get(interaction.getQtiClassName())
+								.writeHeader1(item.getAssessmentItem(), interaction, i, j, header1Row, col, workbook);
+					}
+				}
+				if (!exportConfig.isResponseCols()) {
+					col -= col - delta;
+				}
+				if (exportConfig.isPointCol()) {
+					col++;
+				}
+				if (exportConfig.isCommentCol()) {
+					col++;
+				}
+				if (exportConfig.isTimeCols()) {
+					col += anonymizerCallback != null ? 1 : 2;
+				}
+			} else if(numOfSections > 1 && info instanceof SectionInfos) {
+				SectionInfos section = (SectionInfos)info;
+				if(!section.getItemInfos().isEmpty()) {
+					String sectionTitle = translator.translate("archive.table.header.section", new String[] { section.getAssessmentSection().getTitle() });
+					header1Row.addCell(col++, sectionTitle, headerStyle);
 				}
 			}
-			if (!exportConfig.isResponseCols()) {
-				col -= col - delta;
-			}
-			if (exportConfig.isPointCol()) {
-				col++;
-			}
-			if (exportConfig.isCommentCol()) {
-				col++;
-			}
-			if (exportConfig.isTimeCols()) {
-				col += anonymizerCallback != null ? 1 : 2;
-			}		
 		}
 	}
 
@@ -402,28 +417,36 @@ public class QTI21ArchiveFormat {
 		}
 		header2Row.addCell(col++, translator.translate("column.header.duration"), headerStyle);
 
-		List<ItemInfos> infos = getItemInfos();
+		List<AbstractInfos> infos = getItemInfos();
 		for(int i=0; i<infos.size(); i++) {
-			ItemInfos info = infos.get(i);
-			if (exportConfig.isResponseCols()) {
-				List<Interaction> interactions = info.getInteractions();
-				for(int j=0; j<interactions.size(); j++) {
-					Interaction interaction = interactions.get(j);
-					col = interactionArchiveMap.get(interaction.getQtiClassName())
-							.writeHeader2(info.getAssessmentItem(), interaction, i, j, header2Row, col, workbook);
+			AbstractInfos info = infos.get(i);
+			if(info instanceof ItemInfos) {
+				ItemInfos item = (ItemInfos)info;
+				if (exportConfig.isResponseCols()) {
+					List<Interaction> interactions = item.getInteractions();
+					for(int j=0; j<interactions.size(); j++) {
+						Interaction interaction = interactions.get(j);
+						col = interactionArchiveMap.get(interaction.getQtiClassName())
+								.writeHeader2(item.getAssessmentItem(), interaction, i, j, header2Row, col, workbook);
+					}
 				}
-			}
-			if (exportConfig.isPointCol()) {
-				header2Row.addCell(col++, translator.translate("item.score"), headerStyle);
-			}
-			if (exportConfig.isCommentCol()) {
-				header2Row.addCell(col++, translator.translate("item.comment"), headerStyle);
-			}
-			if (exportConfig.isTimeCols()) {
-				if (anonymizerCallback == null){
-					header2Row.addCell(col++, translator.translate("item.start"), headerStyle);
+				if (exportConfig.isPointCol()) {
+					header2Row.addCell(col++, translator.translate("item.score"), headerStyle);
+				}
+				if (exportConfig.isCommentCol()) {
+					header2Row.addCell(col++, translator.translate("item.comment"), headerStyle);
+				}
+				if (exportConfig.isTimeCols()) {
+					if (anonymizerCallback == null){
+						header2Row.addCell(col++, translator.translate("item.start"), headerStyle);
+					}
+					header2Row.addCell(col++, translator.translate("item.duration"), headerStyle);
+				}
+			} else if(numOfSections > 1 && info instanceof SectionInfos) {
+				SectionInfos section = (SectionInfos)info;
+				if(!section.getItemInfos().isEmpty()) {
+					header2Row.addCell(col++, translator.translate("archive.table.header.points"), headerStyle);
 				}
-				header2Row.addCell(col++, translator.translate("item.duration"), headerStyle);
 			}
 		}
 	}
@@ -552,74 +575,126 @@ public class QTI21ArchiveFormat {
 		}
 		dataRow.addCell(col++, toDurationInMilliseconds(testSession.getDuration()), null);
 
-		List<ItemInfos> infos = getItemInfos();
+		List<AbstractInfos> infos = getItemInfos();
 		for(int i=0; i<infos.size(); i++) {
-			ItemInfos info = infos.get(i);
-			AssessmentItemRef itemRef = info.getAssessmentItemRef();
-			String itemRefIdentifier = itemRef.getIdentifier().toString();
-			AssessmentItemSession itemSession = responses.getItemSession(itemRefIdentifier);
-			
-			if (exportConfig.isResponseCols()) {
-				List<Interaction> interactions = info.getInteractions();
-				for(int j=0; j<interactions.size(); j++) {
-					Interaction interaction = interactions.get(j);
-					AssessmentResponse response = responses
-							 .getResponse(itemRefIdentifier, interaction.getResponseIdentifier());
-					col = interactionArchiveMap.get(interaction.getQtiClassName())
-								.writeInteractionData(info.getAssessmentItem(), response, interaction, j, dataRow, col, workbook);
+			AbstractInfos info = infos.get(i);
+			if(info instanceof ItemInfos) {
+				ItemInfos item = (ItemInfos)info;
+				AssessmentItemRef itemRef = item.getAssessmentItemRef();
+				String itemRefIdentifier = itemRef.getIdentifier().toString();
+				AssessmentItemSession itemSession = responses.getItemSession(itemRefIdentifier);
+				
+				if (exportConfig.isResponseCols()) {
+					List<Interaction> interactions = item.getInteractions();
+					for(int j=0; j<interactions.size(); j++) {
+						Interaction interaction = interactions.get(j);
+						AssessmentResponse response = responses
+								 .getResponse(itemRefIdentifier, interaction.getResponseIdentifier());
+						col = interactionArchiveMap.get(interaction.getQtiClassName())
+									.writeInteractionData(item.getAssessmentItem(), response, interaction, j, dataRow, col, workbook);
+					}
 				}
-			}
 			
-			//score, start, duration
-			if (itemSession == null) {
-				if (exportConfig.isPointCol()) {
-					col++;
-				}
-				if (exportConfig.isCommentCol()) {
-					col++;
-				}
-				if (exportConfig.isTimeCols()) {
-					col += anonymizerCallback != null ? 1 : 2;
-				}
-			} else {
-				if (exportConfig.isPointCol()) {
-					if(itemSession.getManualScore() != null) {
-						dataRow.addCell(col++, itemSession.getManualScore(), null);
-					} else {
-						dataRow.addCell(col++, itemSession.getScore(), null);
+				//score, start, duration
+				if (itemSession == null) {
+					if (exportConfig.isPointCol()) {
+						col++;
+					}
+					if (exportConfig.isCommentCol()) {
+						col++;
+					}
+					if (exportConfig.isTimeCols()) {
+						col += anonymizerCallback != null ? 1 : 2;
+					}
+				} else {
+					if (exportConfig.isPointCol()) {
+						if(itemSession.getManualScore() != null) {
+							dataRow.addCell(col++, itemSession.getManualScore(), null);
+						} else {
+							dataRow.addCell(col++, itemSession.getScore(), null);
+						}
+					}
+					if (exportConfig.isCommentCol()) {
+						dataRow.addCell(col++, itemSession.getCoachComment(), null);	
+					}
+					if (exportConfig.isTimeCols()) {
+						if (anonymizerCallback == null){
+							dataRow.addCell(col++, itemSession.getCreationDate(), workbook.getStyles().getTimeStyle());
+						}
+						dataRow.addCell(col++, toDurationInMilliseconds(itemSession.getDuration()), null);
 					}
 				}
-				if (exportConfig.isCommentCol()) {
-					dataRow.addCell(col++, itemSession.getCoachComment(), null);	
-				}
-				if (exportConfig.isTimeCols()) {
-					if (anonymizerCallback == null){
-						dataRow.addCell(col++, itemSession.getCreationDate(), workbook.getStyles().getTimeStyle());
+			} else if(numOfSections > 1 && info instanceof SectionInfos) {
+				SectionInfos section = (SectionInfos)info;
+				if(!section.getItemInfos().isEmpty()) {
+					BigDecimal score = calculateSectionScore(responses, section);
+					if(score != null) {
+						dataRow.addCell(col++, score, workbook.getStyles().getLightGrayStyle());
+					} else {
+						col++;
 					}
-					dataRow.addCell(col++, toDurationInMilliseconds(itemSession.getDuration()), null);
 				}
 			}
 		}
 	}
 	
+	private BigDecimal calculateSectionScore(SessionResponses responses, SectionInfos section) {
+		BigDecimal sectionScore = BigDecimal.valueOf(0l);
+		
+		for(ItemInfos item:section.getItemInfos()) {
+			AssessmentItemRef itemRef = item.getAssessmentItemRef();
+			String itemRefIdentifier = itemRef.getIdentifier().toString();
+			AssessmentItemSession itemSession = responses.getItemSession(itemRefIdentifier);
+			if(itemSession.getManualScore() != null) {
+				sectionScore = sectionScore.add(itemSession.getManualScore());
+			} else if(itemSession.getScore() != null){
+				sectionScore = sectionScore.add(itemSession.getScore());
+			}
+		}
+		
+		return sectionScore;
+	}
+	
 	private Long toDurationInMilliseconds(Long value) {
 		if(value == null || value.longValue() == 0) return null;
 		return value.longValue() / 1000l;
 	}
 	
-	private List<ItemInfos> getItemInfos() {
-		if(itemInfos == null) {
-			itemInfos = new ArrayList<>();
-			List<AssessmentItemRef> itemRefs = resolvedAssessmentTest.getAssessmentItemRefs();
-			for(AssessmentItemRef itemRef:itemRefs) {
+	private List<AbstractInfos> getItemInfos() {
+		if(elementInfos == null) {
+			numOfSections = 0;
+			elementInfos = new ArrayList<>();
+			
+			AssessmentTest assessmentTest = resolvedAssessmentTest.getRootNodeLookup().extractAssumingSuccessful();
+			for(TestPart part:assessmentTest.getTestParts()) {
+				for(AssessmentSection section:part.getAssessmentSections()) {
+					collectElementInfos(section);
+				}
+			}
+		}
+		return elementInfos;
+	}
+	
+	private void collectElementInfos(AssessmentSection section) {
+		numOfSections++;
+		SectionInfos sectionInfos = new SectionInfos(section);
+		elementInfos.add(sectionInfos);
+
+		List<SectionPart> parts = section.getChildAbstractParts();
+		for(SectionPart part:parts) {
+			if(part instanceof AssessmentItemRef) {
+				AssessmentItemRef itemRef = (AssessmentItemRef)part;
 				ResolvedAssessmentItem resolvedItem = resolvedAssessmentTest.getResolvedAssessmentItem(itemRef);
 				AssessmentItem item = resolvedItem.getRootNodeLookup().extractIfSuccessful();
 				if(item != null) {
-					itemInfos.add(new ItemInfos(itemRef, item, item.getItemBody().findInteractions()));
+					ItemInfos itemInfo = new ItemInfos(itemRef, item, item.getItemBody().findInteractions());
+					elementInfos.add(itemInfo);
+					sectionInfos.getItemInfos().add(itemInfo);
 				}
+			} else if(part instanceof AssessmentSection) {
+				collectElementInfos((AssessmentSection)part);
 			}
 		}
-		return itemInfos;
 	}
 	
 	private static class SessionResponses {
@@ -667,7 +742,28 @@ public class QTI21ArchiveFormat {
 		}
 	}
 	
-	private static class ItemInfos {
+	private static class AbstractInfos {
+		//
+	}
+	
+	private static class SectionInfos extends AbstractInfos {
+		private final AssessmentSection section;
+		private final List<ItemInfos> itemInfos = new ArrayList<>();
+		
+		public SectionInfos(AssessmentSection section) {
+			this.section = section;
+		}
+		
+		public AssessmentSection getAssessmentSection() {
+			return section;
+		}
+		
+		public List<ItemInfos> getItemInfos() {
+			return itemInfos;
+		}
+	}
+	
+	private static class ItemInfos extends AbstractInfos {
 		
 		private final AssessmentItemRef itemRef;
 		private final AssessmentItem assessmentItem;
diff --git a/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_de.properties b/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_de.properties
index 04cddbbfcbf8109a3e1817ed03f6fba38c6a3500..037467d2bc4031c2bb03919823930b4114ac98d7 100644
--- a/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_de.properties
+++ b/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_de.properties
@@ -16,6 +16,7 @@ archive.table.header.node=Kurs
 archive.table.header.node.passed=Kursbaustein bestanden
 archive.table.header.node.points=Kursbaustein Punkte
 archive.table.header.points=$\:table.header.score
+archive.table.header.section=Sektion "{0}"
 archive.table.header.test=Test
 assessment.comment.legend=Pers\u00F6nliche Notizen
 assessment.comment.legend.help=Sie k\u00F6nnen ein Kommentar hier schreiebn. Diese Notizen sind privat und werden nicht in einem Pr\u00FCfung ber\u00FCcksichtigt.
diff --git a/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_en.properties b/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_en.properties
index 5d833289106abfcdc1d81624beee897be47b1954..53747311d37e3ff5270c69914e1ff1700e3610a4 100644
--- a/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_en.properties
+++ b/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_en.properties
@@ -16,6 +16,7 @@ archive.table.header.node=Course
 archive.table.header.node.passed=Passed course element
 archive.table.header.node.points=Score course element
 archive.table.header.points=$\:table.header.score
+archive.table.header.section=Section "{0}"
 archive.table.header.test=Test
 assessment.comment.legend=Personal notes
 assessment.comment.legend.help=Please use the following text box if you need to provide any additional information, comments or feedback during this test. This notice is private and will be taken in account for an exam.
diff --git a/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_fr.properties b/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_fr.properties
index 3ea7ffe9fd7f92c80c9913023149c9481925aed8..7168ff94852bf2aca9900816d2e2be1df40279b0 100644
--- a/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_fr.properties
+++ b/src/main/java/org/olat/ims/qti21/ui/_i18n/LocalStrings_fr.properties
@@ -16,6 +16,7 @@ archive.table.header.node=Cours
 archive.table.header.node.passed=Element de cours r\u00E9ussi
 archive.table.header.node.points=Points \u00E9l\u00E9ment de cours
 archive.table.header.points=$\:table.header.score
+archive.table.header.section=Sektion "{0}"
 archive.table.header.test=Test
 assessment.comment.legend=Notes personelles
 assessment.comment.legend.help=Vous pouvez ajoutez un commentaire dans le champ de texte ci-dessous. Cette note est priv\u00E9e et il n'en sera pas tenu compte dans un test.