You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

117 lines
3.5 KiB

using System;
using System.Globalization;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Web;
public class PostHandler : IHttpHandler
{
public void ProcessRequest(HttpContext context)
{
if (!context.User.Identity.IsAuthenticated || Blog.MatchesUniqueId(context))
throw new HttpException(403, "No access");
string mode = context.Request.QueryString["mode"];
string id = context.Request.Form["id"];
if (mode == "delete")
{
DeletePost(id);
}
else if (mode == "save")
{
EditPost(id, context.Request.Form["title"], context.Request.Form["content"], bool.Parse(context.Request.Form["isPublished"]), context.Request.Form["categories"].Split(','));
}
}
private void DeletePost(string id)
{
Post post = Storage.GetAllPosts().FirstOrDefault(p => p.ID == id);
if (post == null)
throw new HttpException(404, "The post does not exist");
Storage.Delete(post);
}
private void EditPost(string id, string title, string content, bool isPublished, string[] categories)
{
Post post = Storage.GetAllPosts().FirstOrDefault(p => p.ID == id);
if (post != null)
{
post.Title = title;
post.Content = content;
post.Categories = categories;
}
else
{
post = new Post() { Title = title, Content = content, Slug = CreateSlug(title), Categories = categories };
HttpContext.Current.Response.Write(post.Url);
}
SaveFilesToDisk(post);
post.IsPublished = isPublished;
Storage.Save(post);
}
private void SaveFilesToDisk(Post post)
{
foreach (Match match in Regex.Matches(post.Content, "(src|href)=\"(data:([^\"]+))\""))
{
string extension = Regex.Match(match.Value, "data:([^/]+)/([a-z]+);base64").Groups[2].Value;
byte[] bytes = ConvertToBytes(match.Groups[2].Value);
string path = Blog.SaveFileToDisk(bytes, extension);
string value = string.Format("src=\"{0}\" alt=\"\" /", path);
if (match.Groups[1].Value == "href")
value = string.Format("href=\"{0}\"", path);
post.Content = post.Content.Replace(match.Value, value);
}
}
private byte[] ConvertToBytes(string base64)
{
int index = base64.IndexOf("base64,", StringComparison.Ordinal) + 7;
return Convert.FromBase64String(base64.Substring(index));
}
public static string CreateSlug(string title)
{
title = title.ToLowerInvariant().Replace(" ", "-");
title = RemoveDiacritics(title);
title = Regex.Replace(title, @"([^0-9a-z-])", string.Empty);
if (Storage.GetAllPosts().Any(p => string.Equals(p.Slug, title)))
throw new HttpException(409, "Already in use");
return title.ToLowerInvariant();
}
static string RemoveDiacritics(string text)
{
var normalizedString = text.Normalize(NormalizationForm.FormD);
var stringBuilder = new StringBuilder();
foreach (var c in normalizedString)
{
var unicodeCategory = CharUnicodeInfo.GetUnicodeCategory(c);
if (unicodeCategory != UnicodeCategory.NonSpacingMark)
{
stringBuilder.Append(c);
}
}
return stringBuilder.ToString().Normalize(NormalizationForm.FormC);
}
public bool IsReusable
{
get { return false; }
}
}