/// <summary> /// Disables accessibility resources for special cases: /// - ASL is disabled by itemMetadata flag /// - Calculator is disabled if metadata flag or resource is disabled /// - GlobalNotes is only enabled for performance task items /// - EnglishDictionary and Thesaurus are only enabled for WER items /// </summary> public static AccessibilityResource ApplyFlags( this AccessibilityResource resource, ItemDigest itemDigest, string interactionType, bool isPerformanceTask, List <string> dictionarySupportedItemTypes, IEnumerable <string> supportedBraille, Claim claim, bool aslSupported) { if (itemDigest == null || resource.Disabled) { return(resource); } bool isUnsupportedAsl = !aslSupported && resource.ResourceCode == "AmericanSignLanguage"; bool isUnsupportedCalculator = (!itemDigest.AllowCalculator || resource.Disabled) && resource.ResourceCode == "Calculator"; bool isUnsupportedGlobalNotes = !isPerformanceTask && resource.ResourceCode == "GlobalNotes"; bool isUnsupportedDictionaryThesaurus = !dictionarySupportedItemTypes.Any(s => s == interactionType) && (resource.ResourceCode == "EnglishDictionary" || resource.ResourceCode == "Thesaurus"); bool isUnsupportedClosedCaptioning = !(claim?.ClaimNumber == "3" && itemDigest.SubjectCode == "ELA") && resource.ResourceCode == "ClosedCaptioning"; if (isUnsupportedAsl || isUnsupportedCalculator || isUnsupportedGlobalNotes || isUnsupportedDictionaryThesaurus || isUnsupportedClosedCaptioning) { var newResource = resource.ToDisabled(); return(newResource); } else if (resource.ResourceCode == "BrailleType") { return(resource.DisableUnsupportedBraille(supportedBraille)); } return(resource); }
public static ImmutableArray <Rubric> GetRubrics(ItemDigest digest, AppSettings settings) { int?maxPoints = digest.MaximumNumberOfPoints; var rubrics = digest.Contents.Select(c => c.ToRubric(maxPoints, settings)).Where(r => r != null).ToImmutableArray(); return(rubrics); }
public static ImmutableArray <AccessibilityResourceGroup> GetAccessibilityResourceGroups( ItemDigest itemDigest, IList <MergedAccessibilityFamily> resourceFamilies, GradeLevels grade, bool isPerformance, bool aslSupported, Claim claim, InteractionType interactionType, ImmutableArray <string> brailleItemCodes, AppSettings settings) { var family = resourceFamilies.FirstOrDefault(f => f.Grades.Contains(grade) && f.Subjects.Contains(itemDigest.SubjectCode)); var flaggedResources = family?.Resources .Select(r => r.ApplyFlags( itemDigest, interactionType?.Code, isPerformance, settings.SettingsConfig.DictionarySupportedItemTypes, brailleItemCodes, claim, aslSupported)) .ToImmutableArray() ?? ImmutableArray <AccessibilityResource> .Empty; var groups = settings.SettingsConfig.AccessibilityTypes .Select(accType => GroupItemResources(accType, flaggedResources)) .OrderBy(g => g.Order) .ToImmutableArray(); return(groups); }
public void TestToStandardIdentifierGoodDigest() { ItemDigest digest = ItemDigestTranslation.ToItemDigest(metadata, contents, appSettings); StandardIdentifier identifier = StandardIdentifierTranslation.ToStandardIdentifier(digest, new string[] { "SBAC-MA-v1" }); Assert.NotNull(identifier); Assert.Equal(digest.SubjectCode, identifier.SubjectCode); Assert.Equal("1", identifier.Claim); Assert.Equal("3.NBT.2", identifier.CommonCoreStandard); Assert.Equal("NBT", identifier.ContentDomain); Assert.Equal("E-3", identifier.Target); }
public void TestDisableCalculatorWithMetadataAndResource() { var itemDigest = new ItemDigest() { AslSupported = true, AllowCalculator = false }; var resource = getResourceWithCode("Calculator", true); var resModified = resource.ApplyFlags(itemDigest, "", false, new List <string>(), new List <string>(), null, false); Assert.NotNull(resModified); Assert.Equal(resModified.Disabled, true); }
public static bool AslSupported(ItemDigest digest) { if (!digest.Contents.Any()) { return(digest.AslSupported ?? false); } bool foundAslAttachment = AslSupportedContents(digest.Contents); bool foundStimAslAttachment = AslSupportedContents(digest.StimulusDigest?.Contents); bool aslAttachment = foundAslAttachment || foundStimAslAttachment; bool aslSupported = (digest.AslSupported.HasValue) ? (digest.AslSupported.Value && aslAttachment) : aslAttachment; return(aslSupported); }
public void TestDoNotDisableAslFlag() { var itemDigest = new ItemDigest() { AslSupported = true, AllowCalculator = false }; var resource = getResourceWithCode("AmericanSignLanguage", false); var resModified = resource.ApplyFlags(itemDigest, "", false, new List <string>(), new List <string>(), null, true); Assert.NotNull(resModified); Assert.Equal(resModified.Disabled, false); }
public static ImmutableArray <string> GetBraillePassageCodes(ItemDigest itemDigest, IList <BrailleFileInfo> brailleFileInfo) { ImmutableArray <string> braillePassageCodes; if (itemDigest.AssociatedPassage.HasValue) { braillePassageCodes = brailleFileInfo .Where(f => f.ItemKey == itemDigest.AssociatedPassage.Value) .Select(b => b.BrailleType).ToImmutableArray(); } else { braillePassageCodes = ImmutableArray.Create <string>(); } return(braillePassageCodes); }
public void TestEnableGlobalNotes() { string itemType = "SA"; var itemDigest = new ItemDigest() { AslSupported = false, AllowCalculator = false }; var resource = getResourceWithCode("GlobalNotes", false); var resModified = resource.ApplyFlags(itemDigest, itemType, true, new List <string> { "MC" }, new List <string>(), null, false); Assert.NotNull(resModified); Assert.Equal(resModified.Disabled, false); }
public void TestDisableDictionary() { string itemType = "ER"; var itemDigest = new ItemDigest() { AslSupported = true, AllowCalculator = false }; var resource = getResourceWithCode("EnglishDictionary", false); var resModified = resource.ApplyFlags(itemDigest, itemType, false, new List <string> { "WER" }, new List <string>(), null, false); Assert.NotNull(resModified); Assert.Equal(resModified.Disabled, true); }
/// <summary> /// Gets the standard identifier from the given item metadata /// </summary> public static StandardIdentifier ToStandardIdentifier(ItemDigest digest, string[] supportedPubs) { try { var primaryStandard = digest.StandardPublications .Where(s => !s.PrimaryStandard.EndsWith("Undesignated") && supportedPubs.Any(p => p.Equals(s.Publication))) .FirstOrDefault() ?.PrimaryStandard; var identifier = StandardStringToStandardIdentifier(primaryStandard); return(identifier); } catch (InvalidOperationException ex) { throw new SampleItemsContextException( $"Publication field for item {digest.BankKey}-{digest.ItemKey} is empty.", ex); } }
/// <summary> /// Digests a collection of ItemMetadata objects and a collection of ItemContents objects into a collection of ItemDigest objects. /// Matches the ItemMetadata and ItemContents objects based on their ItemKey fields. /// </summary> public static IReadOnlyCollection <ItemDigest> ToItemDigests( IReadOnlyCollection <ItemMetadata> itemMetadata, IReadOnlyCollection <ItemContents> itemContents, AppSettings settings) { BlockingCollection <ItemDigest> digests = new BlockingCollection <ItemDigest>(); Parallel.ForEach(itemMetadata, metadata => { if (metadata.Metadata?.InteractionType == "Stimulus") { return; } var matchingItems = itemContents.Where(c => c.Item?.ItemKey == metadata.Metadata?.ItemKey); var itemsCount = matchingItems.Count(); var stimContents = itemContents.FirstOrDefault(c => metadata.Metadata?.AssociatedStimulus == c.Passage?.ItemKey); var stimMeta = itemMetadata.FirstOrDefault(c => metadata.Metadata?.AssociatedStimulus == c.Metadata?.ItemKey); StimulusDigest stimDigest = null; if (stimContents != null && stimMeta != null) { stimDigest = ToStimulusDigest(stimMeta, stimContents); } if (itemsCount == 1) { ItemDigest itemDigest = ToItemDigest(metadata, matchingItems.First(), settings, stimDigest); digests.Add(itemDigest); } else if (itemsCount > 1) { throw new SampleItemsContextException("Multiple ItemContents with ItemKey: " + metadata.Metadata.ItemKey + " found."); } }); return(digests); }
/// <summary> /// Translates metadata, itemcontents and lookups to item digest /// </summary> public static ItemDigest ToItemDigest( ItemMetadata itemMetadata, ItemContents itemContents, AppSettings settings, StimulusDigest stimulusDigest = null) { if (itemMetadata == null) { throw new ArgumentNullException(nameof(itemMetadata)); } if (itemMetadata.Metadata == null) { throw new ArgumentNullException(nameof(itemMetadata.Metadata)); } if (itemContents == null) { throw new ArgumentNullException(nameof(itemContents)); } if (itemContents.Item == null) { throw new ArgumentNullException(nameof(itemContents.Item)); } if (itemContents.Item.ItemKey != itemMetadata.Metadata.ItemKey) { throw new SampleItemsContextException("Cannot digest items with different ItemKey values.\n" + $"Content Item Key: {itemContents.Item.ItemKey} Metadata Item Key:{itemMetadata.Metadata.ItemKey}"); } string itemType = itemContents.Item.ItemType ?? string.Empty; string interactionCode = itemMetadata.Metadata.InteractionType ?? string.Empty; var oldToNewInteraction = settings?.SettingsConfig?.OldToNewInteractionType; if (oldToNewInteraction != null && oldToNewInteraction.ContainsKey(itemType)) { settings.SettingsConfig.OldToNewInteractionType.TryGetValue(itemType, out itemType); } if (oldToNewInteraction != null && oldToNewInteraction.ContainsKey(interactionCode)) { settings.SettingsConfig.OldToNewInteractionType.TryGetValue(interactionCode, out interactionCode); } ItemDigest digest = new ItemDigest() { ItemType = itemType, ItemKey = itemContents.Item.ItemKey, BankKey = itemContents.Item.ItemBank, TargetAssessmentType = itemMetadata.Metadata.TargetAssessmentType, SufficentEvidenceOfClaim = itemMetadata.Metadata.SufficientEvidenceOfClaim, AssociatedStimulus = itemMetadata.Metadata.AssociatedStimulus, AslSupported = itemMetadata.Metadata.AccessibilityTagsASLLanguage.AslSupportedStringToBool(), AllowCalculator = itemMetadata.Metadata.AllowCalculator == "Y", DepthOfKnowledge = itemMetadata.Metadata.DepthOfKnowledge, Contents = itemContents.Item.Contents, InteractionTypeCode = interactionCode, AssociatedPassage = itemContents.Item.AssociatedPassage, GradeCode = itemMetadata.Metadata.GradeCode, MaximumNumberOfPoints = itemMetadata.Metadata.MaximumNumberOfPoints, StandardPublications = itemMetadata.Metadata.StandardPublications, SubjectCode = itemMetadata.Metadata.SubjectCode, ItemMetadataAttributes = itemContents.Item.ItemMetadataAttributes, StimulusDigest = stimulusDigest, SmarterAppItemDescriptor = itemMetadata.Metadata.SmarterAppItemDescriptor }; return(digest); }
public void TestItemToItemDigest() { int testItemKey = 1; int testItemBank = 2; string testGrade = "5"; ItemMetadata metadata = new ItemMetadata(); ItemContents contents = new ItemContents(); metadata.Metadata = new SmarterAppMetadataXmlRepresentation(); contents.Item = new ItemXmlFieldRepresentation(); metadata.Metadata.ItemKey = testItemKey; metadata.Metadata.GradeCode = testGrade; metadata.Metadata.TargetAssessmentType = "Test target string"; metadata.Metadata.SufficientEvidenceOfClaim = "Test claim string"; metadata.Metadata.InteractionType = "EQ"; metadata.Metadata.SubjectCode = "MATH"; metadata.Metadata.StandardPublications = new List <StandardPublication>(); metadata.Metadata.StandardPublications.Add( new StandardPublication { PrimaryStandard = "SBAC-ELA-v1:3-L|4-6|6.SL.2" }); contents.Item.ItemKey = testItemKey; contents.Item.ItemBank = testItemBank; contents.Item.Contents = new List <Content>(); var interactionTypes = new List <InteractionType> { new InteractionType(code: "EQ", label: "", description: "", order: 0) }; var subjects = new List <Subject> { new Subject( code: "MATH", label: string.Empty, shortLabel: string.Empty, claims: ImmutableArray.Create <Claim>(), interactionTypeCodes: ImmutableArray.Create <string>()) }; var placeholderText = new RubricPlaceHolderText { RubricPlaceHolderContains = new string[0], RubricPlaceHolderEquals = new string[0] }; var settings = new SettingsConfig { SupportedPublications = new string[] { "" } }; AppSettings appSettings = new AppSettings { SettingsConfig = settings, RubricPlaceHolderText = placeholderText }; ItemDigest digest = ItemDigestTranslation.ToItemDigest(metadata, contents, appSettings); Assert.Equal(testItemKey, digest.ItemKey); Assert.Equal(testItemBank, digest.BankKey); Assert.Equal(GradeLevels.Grade5, GradeLevelsUtils.FromString(digest.GradeCode)); Assert.Equal("Test target string", digest.TargetAssessmentType); Assert.Equal("Test claim string", digest.SufficentEvidenceOfClaim); Assert.Equal("MATH", digest.SubjectCode); Assert.Equal("EQ", digest.InteractionTypeCode); }
/// <summary> /// Translates metadata, itemcontents and lookups to item digest /// </summary> public static SampleItem ToSampleItem( ItemDigest itemDigest, CoreStandardsXml standardsXml, IList <Subject> subjects, IList <InteractionType> interactionTypes, IList <MergedAccessibilityFamily> resourceFamilies, IList <ItemPatch> patches, IList <BrailleFileInfo> brailleFileInfo, AppSettings settings) { var supportedPubs = settings.SettingsConfig.SupportedPublications; var rubrics = GetRubrics(itemDigest, settings); var brailleItemCodes = GetBrailleItemCodes(itemDigest.ItemKey, brailleFileInfo); var braillePassageCodes = GetBraillePassageCodes(itemDigest, brailleFileInfo); var interactionType = interactionTypes.FirstOrDefault(t => t.Code == itemDigest.InteractionTypeCode); var grade = GradeLevelsUtils.FromString(itemDigest.GradeCode); var patch = patches.FirstOrDefault(p => p.ItemId == itemDigest.ItemKey); var copiedItemPatch = patches.FirstOrDefault(p => p.BrailleCopiedId == itemDigest.ItemKey.ToString()); var subject = subjects.FirstOrDefault(s => s.Code == itemDigest.SubjectCode); var depthOfKnowledge = itemDigest.DepthOfKnowledge; var itemType = itemDigest.ItemType; var fieldTestUseAttribute = itemDigest.ItemMetadataAttributes?.FirstOrDefault(a => a.Code == "itm_FTUse"); var fieldTestUse = FieldTestUse.Create(fieldTestUseAttribute, itemDigest.SubjectCode); StandardIdentifier identifier = StandardIdentifierTranslation.ToStandardIdentifier(itemDigest, supportedPubs); CoreStandards coreStandards = StandardIdentifierTranslation.CoreStandardFromIdentifier(standardsXml, identifier); int?copiedFromItem = null; if (patch != null) { int tmp; copiedFromItem = int.TryParse(patch.BrailleCopiedId, out tmp) ? (int?)tmp : null; depthOfKnowledge = !string.IsNullOrEmpty(patch.DepthOfKnowledge) ? patch.DepthOfKnowledge : depthOfKnowledge; itemType = !string.IsNullOrEmpty(patch.ItemType) ? patch.ItemType : itemType; coreStandards = ApplyPatchToCoreStandards(identifier, coreStandards, standardsXml, patch); } if (copiedItemPatch != null) { var copyBrailleItemCodes = GetBrailleItemCodes(copiedItemPatch.ItemId, brailleFileInfo); brailleItemCodes = brailleItemCodes.Concat(copyBrailleItemCodes).Distinct().ToImmutableArray(); } if (patch != null && !string.IsNullOrEmpty(patch.QuestionNumber)) { fieldTestUse = ApplyPatchFieldTestUse(fieldTestUse, patch); } var claim = subject?.Claims.FirstOrDefault(t => t.ClaimNumber == coreStandards.ClaimId); bool brailleOnly = copiedFromItem.HasValue; bool isPerformance = fieldTestUse != null && itemDigest.AssociatedPassage.HasValue; if (itemDigest.AssociatedPassage.HasValue) { braillePassageCodes = brailleFileInfo .Where(f => f.ItemKey == itemDigest.AssociatedPassage.Value) .Select(b => b.BrailleType).ToImmutableArray(); } else { braillePassageCodes = ImmutableArray.Create <string>(); } bool aslSupported = AslSupported(itemDigest); var groups = GetAccessibilityResourceGroups(itemDigest, resourceFamilies, grade, isPerformance, aslSupported, claim, interactionType, brailleItemCodes, settings); string interactionTypeSubCat = ""; settings.SettingsConfig.InteractionTypesToItem.TryGetValue(itemDigest.ToString(), out interactionTypeSubCat); SampleItem sampleItem = new SampleItem( itemType: itemType, itemKey: itemDigest.ItemKey, bankKey: itemDigest.BankKey, targetAssessmentType: itemDigest.TargetAssessmentType, depthOfKnowledge: depthOfKnowledge, sufficentEvidenceOfClaim: itemDigest.SufficentEvidenceOfClaim, associatedStimulus: itemDigest.AssociatedStimulus, aslSupported: aslSupported, allowCalculator: itemDigest.AllowCalculator, isPerformanceItem: isPerformance, accessibilityResourceGroups: groups, rubrics: rubrics, interactionType: interactionType, subject: subject, claim: claim, grade: grade, coreStandards: coreStandards, fieldTestUse: fieldTestUse, interactionTypeSubCat: interactionTypeSubCat, brailleItemCodes: brailleItemCodes, braillePassageCodes: braillePassageCodes, brailleOnlyItem: brailleOnly, copiedFromitem: copiedFromItem); return(sampleItem); }
public SampleItemTranslationTests() { rubricEntries = new List <RubricEntry>() { new RubricEntry { Scorepoint = "0", Name = "TestName", Value = "TestValue" }, new RubricEntry { Scorepoint = "1", Name = "TestName1", Value = "TestValue1" } }; var sampleResponces = new List <SampleResponse>() { new SampleResponse() { Purpose = "TestPurpose", ScorePoint = "0", Name = "TestName", SampleContent = "TestSampleContent" }, new SampleResponse() { Purpose = "TestPurpose1", ScorePoint = "1", Name = "TestName1", SampleContent = "TestSampleContent1" } }; rubricSamples = new List <RubricSample>() { new RubricSample { MaxValue = "MaxVal", MinValue = "MinVal", SampleResponses = sampleResponces }, new RubricSample { MaxValue = "MaxVal1", MinValue = "MinVal1", SampleResponses = new List <SampleResponse>() } }; rubricList = new RubricList() { Rubrics = rubricEntries, RubricSamples = rubricSamples }; Resources = new List <AccessibilityResource> { AccessibilityResource.Create( resourceCode: "ACC1", order: 1, disabled: false, defaultSelection: "ACC1_SEL1", currentSelectionCode: "ACC1_SEL1", label: "Accessibility 1", description: "Accessibility Selection One", resourceType: "Acc1Type", selections: ImmutableArray.Create( new AccessibilitySelection( code: "ACC1_SEL1", order: 1, disabled: false, label: "Selection 1", hidden: false))), AccessibilityResource.Create( resourceCode: "ACC2", order: 2, disabled: false, defaultSelection: "ACC2_SEL2", currentSelectionCode: "ACC2_SEL2", label: "Accessibility 2", description: "Accessibility Selection Two", resourceType: "Acc2Type", selections: ImmutableArray.Create( new AccessibilitySelection( code: "ACC2_SEL1", order: 1, disabled: false, label: "Selection 1", hidden: false), new AccessibilitySelection( code: "ACC2_SEL2", order: 2, disabled: false, label: "Selection 2", hidden: false))) }; accessibilityType = new AccessibilityType(); accessibilityType.Id = "Acc1Type"; accessibilityType.Label = "Accessibility 1"; accessibilityType.Order = 1; int testItemKey = 1; int testItemBank = 2; string testGrade = "5"; metadata = new ItemMetadata(); contents = new ItemContents(); metadata.Metadata = new SmarterAppMetadataXmlRepresentation(); contents.Item = new ItemXmlFieldRepresentation(); metadata.Metadata.ItemKey = testItemKey; metadata.Metadata.GradeCode = testGrade; metadata.Metadata.TargetAssessmentType = "Test target string"; metadata.Metadata.SufficientEvidenceOfClaim = "Test claim string"; metadata.Metadata.InteractionType = "2"; metadata.Metadata.SubjectCode = "MATH"; metadata.Metadata.MaximumNumberOfPoints = 2; metadata.Metadata.StandardPublications = new List <StandardPublication>(); metadata.Metadata.StandardPublications.Add( new StandardPublication { PrimaryStandard = "SBAC-ELA-v1:3-L|4-6|6.SL.2", Publication = "SupportedPubs" }); contents.Item.ItemKey = testItemKey; contents.Item.ItemBank = testItemBank; contents.Item.Contents = new List <Content>(); var placeholderText = new RubricPlaceHolderText { RubricPlaceHolderContains = new string[] { "RubricSampleText", "RubricSampleText1" }, RubricPlaceHolderEquals = new string[0] }; settings = new SettingsConfig { SupportedPublications = new string[] { "SupportedPubs" }, AccessibilityTypes = new List <AccessibilityType>() { accessibilityType }, InteractionTypesToItem = new Dictionary <string, string>(), DictionarySupportedItemTypes = new List <string>(), LanguageToLabel = new Dictionary <string, string>() }; appSettings = new AppSettings { SettingsConfig = settings, RubricPlaceHolderText = placeholderText }; digest = ItemDigestTranslation.ToItemDigest(metadata, contents, appSettings); }