Немного кода, небольшой рефакторинг
- modified:
- reading: 3 minutes
Изучал тут как-то примеры книги Professional Twitter Development: With Examples in .NET 3.5, хотел разобраться как работает эта самая OAuth авторизация для твиттера. Раньше у меня на сайте было немного действий с твиттером, подгружались мой твитты, хранились, отображались, но потом твиттер что-то поменял в авторизации, вроде разрешил только OAuth, а в тот момент я что-то не шибко разобрался с этим OAuth, да и времени не было, хотя вроде еще тогда LinqToTwitter ее поддерживал (а я использовал именно эту библиотеку). В общем-то, просто в тот момент подумал, что тема OAuth авторизации интересна, и нужно бы посмотреть как она реализована в деталях попозже. Вот и набрел я тут недавно на книгу Professional Twitter Development: With Examples in .NET 3.5, точнее только на ее примеры, решил поковыряться. Код там был не из простых, и я просто тупо стал рефакторить его, чтобы разобрать что и как работает. Вот, например, одно из превращений, которое я уже правда публиковал в твиттере давно (и может быть вы уже видели):
Было:
public static string NormalizeRequestParameters
(NameValueCollection parameters)
{ var sb = new StringBuilder();
var list = new List<NameValuePair>();
foreach (var name in parameters.AllKeys)
{ var value = Uri.EscapeDataString(parameters[name]);
var item = new NameValuePair { Name = name, Value = value };
// Ensure duplicates are not included
if (list.Contains(item))
{ throw new ArgumentException(
"Cannot add duplicate parameters");
}
list.Add(item);
}
list.Sort((left, right) =>
{ if (left.Name.Equals(right.Name))
{ return left.Value.CompareTo(right.Value);
}
return left.Name.CompareTo(right.Name);
});
foreach (var item in list)
{ sb.Append(item.Name + "=" + item.Value);
if (list.IndexOf(item) < list.Count - 1)
{ sb.Append("&");
}
}
return sb.ToString();
}
Стало:
public string NormalizeRequestParameters
(NameValueCollection collection)
{ IEnumerable<string> parameters = collection.AllKeys.OrderBy(x => x)
.Select(x => string.Format("{0}={1}", x, Uri.EscapeDataString(collection[x])));
return String.Join("&", parameters);
}
На первый взгляд у меня опущено два момента: а) не бросается исключение б) сортировка другая, там order by ключ, значение, а у меня просто order by ключ.
На самом деле тут просто логика самого класса NameValueCollection, если вы инициализируете его так:
new NameValueCollection { { "test1", "value1" }, { "test1", "value2" }};
то он превратится в
new NameValueCollection { { "test1", "value1&value2" }};
А следовательно проверки и бросания исключения не нужны, да и в OrderBy нет смысла добавлять вторым параметром значение, так как там не может повториться ключ.
В общем, я только хотел сказать, что C# 4 отличный язык, позволяет делать действительно очень читабельным наш код. И это не значит, что я хочу принизить книгу, думаю она отлична и полезна для тех, кто хочет разработать свой твиттер клиент, или проинтегрировать свое приложение с твиттером, а так все пишут плохой код, а кто считает что нет, тот пишет код еще хуже ;)