/// <summary> /// Получить цитируемые посты. /// </summary> /// <param name="document">Документ.</param> /// <returns>Цитируемые посты.</returns> public static IList <ILink> GetQuotes(this IPostDocument document) { if (document?.Nodes == null) { return(new List <ILink>()); } return(document.Nodes.FlatHierarchy(n => { if (n is ICompositePostNode cn) { return cn.Children; } return null; }).OfType <IBoardLinkPostNode>().Select(l => l?.BoardLink).Where(l => l != null).ToList()); }
private void CheckPostDocumentSerialization <T>(T original, IPostDocument deserialized, Action <T, T> asserts) where T : IPostDocument { Assert.IsNotNull(deserialized, "Десериализованный объект == null"); Assert.AreNotSame(original, deserialized, "Десериализация вернула тот же объект"); Assert.IsInstanceOfType(deserialized, typeof(T), $"Тип объекта не {typeof(T).FullName}"); if (original.Nodes == null) { Assert.IsNull(deserialized.Nodes, "deserialized.Nodes должно быть не null"); } else { Assert.IsNotNull(deserialized.Nodes, "deserialized.Nodes не должно быть null"); Assert.AreNotSame(original.Nodes, deserialized.Nodes, "Должны быть разные объекты"); Assert.AreEqual(original.Nodes.Count, deserialized.Nodes.Count, "Должно быть равное количество элементов"); } asserts?.Invoke(original, (T)deserialized); }
/// <summary> /// Перевести в простой текст. /// </summary> /// <param name="tree">Дерево поста.</param> /// <returns>Текст.</returns> public static IList <string> ToPlainText(this IPostDocument tree) { var context = new { sb = new StringBuilder(), result = new List <string>() }; var rules = tree.Nodes.TreeWalk(context) .GetChildren(n => (n as ICompositePostNode)?.Children) .If(n => n is ITextPostNode, (n, ctx) => { ctx.sb.Append(((ITextPostNode)n).Text); return(ctx); }) .If(n => IsAttribute(n, PostBasicAttributes.Paragraph) || n is ILineBreakPostNode, (n, ctx) => { ctx.result.Add(ctx.sb.ToString()); ctx.sb.Clear(); return(ctx); }) .If(n => n is IBoardLinkPostNode, (n, ctx) => { var l = (IBoardLinkPostNode)n; var pl = l.BoardLink as IPostLink; var tl = l.BoardLink as IThreadLink; if (pl != null) { ctx.sb.Append(">>" + pl.GetPostNumberString()); } else if (tl != null) { ctx.sb.Append(">>" + tl.GetThreadNumberString()); } return(ctx); }) .Else((n, c) => c); rules.Run(); if (context.sb.Length > 0) { context.result.Add(context.sb.ToString()); } return(context.result); }
public static void AssertDocuments(IModuleProvider modules, IPostDocument original, IPostDocument deserialized, int[] path = null, Action <IPostNode, IPostNode> assertCallback = null) { if (original == null) { Assert.IsNull(deserialized, "Документ должен быть null"); } else { Assert.IsNotNull(deserialized, "Документ не должен быть null"); if (original.Nodes == null) { Assert.IsNull(deserialized.Nodes, "Узлы документа должны быть null"); } else { Assert.IsNotNull(deserialized.Nodes, "Узлы документа не должны быть null"); Assert.AreEqual(original.Nodes.Count, deserialized.Nodes.Count, "Количество узлов документа не совпадает"); for (var i = 0; i < original.Nodes.Count; i++) { AssertNodes(modules, original.Nodes[i], deserialized.Nodes[i], new [] { i + 1 }, assertCallback); } } } }