internal List <PluralsightCourseAuthor> GetCourseAuthors(IEnumerable <INode> authorNodes, PluralsightCourse course, AuthorsParseResult authorsParseResult) { var courseAuthors = new List <PluralsightCourseAuthor>(); foreach (var node in authorNodes) { if (_nodeParser.IsCoAuthorNode(node)) { var coAuthors = _nodeParser.ParseCoAuthors(node); // ReSharper disable once LoopCanBeConvertedToQuery foreach (var coAuthor in coAuthors) { var courseAuthor = GetCourseCoAuthor(course, coAuthor, authorsParseResult.AllAuthorsByFullNameExceptFullnamesakesContainer, authorsParseResult.FullnamesakesAuthorsContainer); courseAuthors.Add(courseAuthor); } } else { var author = _nodeParser.ParseAuthor(node); // get author from container (preserve reference integrity) author = authorsParseResult.AllAuthorsExceptWhoseUrlNullContainer[author]; var courseAuthor = new PluralsightCourseAuthor { Course = course, Author = author, IsAuthorCoAuthor = false, // explicit set HasFullnamesake = false // explicit set }; courseAuthors.Add(courseAuthor); } } return(courseAuthors); }
internal AuthorsParseResult ParseAuthors() { var authorsByUrlNameSet = new HashSet <PluralsightAuthor>(UrlNameNaturalKeyEqualityComparer <IAuthorUrlNameNaturalKey> .Instance); var coAuthorsByFullNameSet = new HashSet <PluralsightAuthor>(FullNameNaturalKeyEqualityComparer <IAuthorFullNameNaturalKey> .Instance); var authorNodes = _nodeSelector.SelectAuthorNodes(); foreach (var node in authorNodes) { if (_nodeParser.IsCoAuthorNode(node)) { var coAuthors = _nodeParser.ParseCoAuthors(node); coAuthorsByFullNameSet.UnionWith(coAuthors); } else { var author = _nodeParser.ParseAuthor(node); authorsByUrlNameSet.Add(author); } } var fullnamesakesAuthorsList = authorsByUrlNameSet .GroupBy(x => x.FullName) .Where(x => x.Count() > 1) .SelectMany(x => x).ToList(); var fullnamesakesAuthorDictionary = fullnamesakesAuthorsList .GroupBy(x => x.FullName) .Select(x => new PluralsightAuthor { FullName = x.Key, SiteUrl = string.Join(";", x.OrderBy(n => n.UrlName).Select(a => a.SiteUrl)), UrlName = string.Join(";", x.OrderBy(n => n.UrlName).Select(a => a.UrlName)) }).ToDictionary(x => x, x => x, FullNameNaturalKeyEqualityComparer <IAuthorFullNameNaturalKey> .Instance); var allAuthorsExceptWhoseUrlNullDictionary = authorsByUrlNameSet.ToDictionary(x => x, x => x, UrlNameNaturalKeyEqualityComparer <IAuthorUrlNameNaturalKey> .Instance); // remove authors with urlName != null coAuthorsByFullNameSet.ExceptWith(authorsByUrlNameSet); // remove fullnamesakes from authorsByUrlNameSet authorsByUrlNameSet.ExceptWith(fullnamesakesAuthorsList); var allAuthorsByFullNameExceptFullnamesakesContainer = authorsByUrlNameSet .Concat(coAuthorsByFullNameSet) .ToDictionary(x => x, x => x, FullNameNaturalKeyEqualityComparer <IAuthorFullNameNaturalKey> .Instance); var authorsParseResult = new AuthorsParseResult { FullnamesakesAuthorsContainer = fullnamesakesAuthorDictionary, AllAuthorsByFullNameExceptFullnamesakesContainer = allAuthorsByFullNameExceptFullnamesakesContainer, AllAuthorsExceptWhoseUrlNullContainer = allAuthorsExceptWhoseUrlNullDictionary }; return(authorsParseResult); }
internal List <PluralsightCourse> ParseCoursesForCategory(PluralsightCategory category, AuthorsParseResult authorsParseResult) { int courseCount; var courseNodes = _nodeSelector.SelectCourseNodes(category.UrlName, out courseCount); var courses = new List <PluralsightCourse>(courseCount); foreach (var courseNode in courseNodes) { var infoNode = _nodeSelector.SelectInfoNode(courseNode); var featureNode = _nodeSelector.SelectClosedCaptionsNode(courseNode); var authorNodes = _nodeSelector.SelectAuthorNodes(courseNode); var levelNode = _nodeSelector.SelectLevelNode(courseNode); var ratingNode = _nodeSelector.SelectRatingNode(courseNode); var durationNode = _nodeSelector.SelectDurationNode(courseNode); var releaseDateNode = _nodeSelector.SelectReleaseDateNode(courseNode); if (infoNode == null || authorNodes == null || levelNode == null || ratingNode == null || durationNode == null || releaseDateNode == null) { // TODO: Log issue continue; } var info = _nodeParser.ParseCourseInfo(infoNode); var hasClosedCaptions = featureNode != null; var level = _nodeParser.ParseCourseLevel(levelNode); var rating = _nodeParser.ParseCourseRating(ratingNode); var duration = _nodeParser.ParseCourseDuration(durationNode); var releaseDate = _nodeParser.ParseCourseReleaseDate(releaseDateNode); var course = new PluralsightCourse { Title = info.Name, SiteUrl = info.SiteUrl, UrlName = info.UrlName, Description = info.Description, HasClosedCaptions = hasClosedCaptions, Level = level, Duration = duration, Rating = rating, ReleaseDate = releaseDate, Category = category }; course.CourseAuthors = GetCourseAuthors(authorNodes, course, authorsParseResult); courses.Add(course); } return(courses); }