#pragma warning restore 0649 private static void GetArticle(HttpListenerContext client, int categoryIndex) { var req = client.Request; var url = req.Url.Segments; if (url.Length < 3) { client.Error(HttpStatusCode.BadRequest); return; } if (url[url.Length - 1].Contains(".")) { client.GetFile(); return; } if (!articles[categoryIndex].ContainsKey(url[2])) { client.Error(HttpStatusCode.NotFound); return; } var article = articles[categoryIndex][url[2]]; var path = ChickenSoup.RootFolder + article.Path; if (File.Exists(path)) { var content = File.ReadAllText(path); var comments = article.GetComments(); var tree = new CommentTree(); foreach (var comment in comments) { if (!tree.Add(comment)) { throw new FormatException($"Comment file of {article.Name} has an invalid comment: {comment}"); } } var response = ArticleTemplate.Replace("{title}", article.Title) .Replace("{time}", article.Date.ToString()) .Replace("{time(O)}", article.Date.ToString("O")); Action <Article, string, string> replaceLinks = (otherArticle, replace, conditional) => { if (otherArticle != null) { response = response.Replace(replace, otherArticle.Url); response.Replace(replace, ""); response.Replace(conditional, ""); } else { var s = response.IndexOf(conditional, StringComparison.InvariantCulture); if (s < 0) { return; } var e = response.IndexOf(")}", s + conditional.Length, StringComparison.InvariantCulture) + 2; response = response.Remove(s, e - s); } }; replaceLinks(article.Next, "{next}", "{next??("); replaceLinks(article.Previous, "{previous}", "{previous??("); response = response.Replace("{content}", File.ReadAllText(path)) .Replace("{comments}", GenerateCommentHtml(tree)); client.WriteAndClose(response, "html", HttpStatusCode.OK); } else { client.Error(HttpStatusCode.NotFound); } }