<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>Imanel</title>
	
	<link>http://imanel.org</link>
	<description>Pingwin w sieci</description>
	<lastBuildDate>Wed, 03 Mar 2010 13:29:32 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/imanel-rss" /><feedburner:info uri="imanel-rss" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
		<title>Testowanie Cucumberem dla wielu użytkowników – część dalsza</title>
		<link>http://feedproxy.google.com/~r/imanel-rss/~3/aE5UBrZQpQI/</link>
		<comments>http://imanel.org/2010/03/testowanie-cucumberem-dla-wielu-uzytkownikow-czesc-dalsza/#comments</comments>
		<pubDate>Wed, 03 Mar 2010 13:29:32 +0000</pubDate>
		<dc:creator>Bernard Potocki</dc:creator>
				<category><![CDATA[Rails]]></category>
		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://imanel.org/?p=178</guid>
		<description><![CDATA[Trochę ponad miesiąc temu pisałem o testach aplikacji typu real-time za pomocą Cucumbera. Minęło trochę czasu i wydana została nowa wersja &#8211; teraz ze wsparciem dla Capybary. Jako że wcześniejsza metoda sprawiała dość dużo problemów przy przenoszeniu z systemu na system(hacki pod Snow Leoparda czasami nie działały w innych systemach) więc warto przyjrzeć się nowemu rozwiązaniu [...]]]></description>
			<content:encoded><![CDATA[<p class="dropcap-first">Trochę ponad miesiąc temu pisałem o testach aplikacji typu real-time za pomocą Cucumbera. Minęło trochę czasu i wydana została nowa wersja &#8211; teraz ze wsparciem dla <a href="http://github.com/jnicklas/capybara">Capybary</a>. Jako że wcześniejsza metoda sprawiała dość dużo problemów przy przenoszeniu z systemu na system(hacki pod Snow Leoparda czasami nie działały w innych systemach) więc warto przyjrzeć się nowemu rozwiązaniu &#8211; tym razem działającemu OOTB na każdym systemie.<br />
Ponownie nie będę się rozwodził nad instalacją i konfiguracją(jest to opisane na stronie Capybary) więc przejdźmy od razu do zastosowania w praktyce. Capybara domyślnie nie umożliwia otwarcia wielu instancji przeglądarki, a zapytany o tą funkcjonalność główny programista pluginu odpowiada że &#8220;it&#8217;s impossible by design&#8221;. Cóż powiedzieć &#8211; nie ma rzeczy niemożliwych, a Polak potrafi ;) Po przekopaniu kodu Capybary(akurat tu muszę pochwalić bardzo dużą czytelność) znalazłem parę punktów &#8220;podporu&#8221; dzięki którym można obejść zabezpieczenia twórcy przed otwarciem paru okienek przeglądarki.</p>
<p>Zacznijmy więc od początku. W features/step_definitions tworzymy sobie nowy zestaw kroków &#8211; powiedzmy &#8220;selenium_steps.rb&#8221;. Na początek przyjmijmy że chcemy otworzyć 2 przeglądarki &#8211; na razie nam to wystarczy, a jeśli w przyszłości chcieli byśmy testować więcej to bardzo łatwo to zmienić. Tworzymy sobie więc metodę sprawdzającą czy istnieją już instancje przeglądarek i (jeśli nie) tworzącą je:</p>

<div class="wp_syntax"><div class="code"><pre class="ruby" style="font-family:monospace;"><span style="color:#9966CC; font-weight:bold;">def</span> check_selenium_browsers
  Capybara.<span style="color:#9900CC;">instance_variable_set</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#996600;">'@current_driver'</span>, <span style="color:#ff3333; font-weight:bold;">:selenium</span><span style="color:#006600; font-weight:bold;">&#41;</span>
  <span style="color:#9966CC; font-weight:bold;">if</span> <span style="color:#ff6633; font-weight:bold;">$browsers</span>.<span style="color:#0000FF; font-weight:bold;">nil</span>?
    <span style="color:#ff6633; font-weight:bold;">$browsers</span> = <span style="color:#006600; font-weight:bold;">&#123;</span><span style="color:#006600; font-weight:bold;">&#125;</span>
    current_url
    <span style="color:#ff6633; font-weight:bold;">$browsers</span><span style="color:#006600; font-weight:bold;">&#91;</span><span style="color:#006666;">1</span><span style="color:#006600; font-weight:bold;">&#93;</span> = get_selenium_browser
    set_selenium_browser<span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#0000FF; font-weight:bold;">nil</span><span style="color:#006600; font-weight:bold;">&#41;</span>
    current_url
    <span style="color:#ff6633; font-weight:bold;">$browsers</span><span style="color:#006600; font-weight:bold;">&#91;</span><span style="color:#006666;">2</span><span style="color:#006600; font-weight:bold;">&#93;</span> = get_selenium_browser
    set_selenium_browser<span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#006666;">1</span><span style="color:#006600; font-weight:bold;">&#41;</span>
  <span style="color:#9966CC; font-weight:bold;">end</span>
<span style="color:#9966CC; font-weight:bold;">end</span></pre></div></div>

<p>Druga linijka służy do zapewnienia, że używamy prawidłowego silnika testów(w naszym przypadku jest to selenium) Wywołanie metody &#8220;current_url&#8221; gwarantuje nam, że przed przejściem dalej stan przeglądarki zostanie zapisany i nie ulegnie zmianie. Dalej pobieramy i zapisujemy w zmiennej aktualny stan przeglądarki po czym go zerujemy aby Capybara otworzyła następną. Dlaczego samemu tego nie robimy? Otóż Capybara używa dość sporo tricków powodujących że ciężko by było dostosować się przyszłych refaktoryzacji kodu &#8211; ta metoda całkowicie wystarcza i gwarantuje nam że przez dłuższy czas wszystko będzie działało stabilnie. Następne wywołanie &#8220;current_url&#8221; otwiera nam już drugą przeglądarkę itd. Na koniec ustawiamy jako domyślną przeglądarkę początkowy stan &#8211; dzięki temu stan wejścia i wyjścia jest identyczny.<br />
Przejdźmy więc do implementacji funkcji pobierających i zapisujących stan przeglądarki.</p>

<div class="wp_syntax"><div class="code"><pre class="ruby" style="font-family:monospace;"><span style="color:#9966CC; font-weight:bold;">def</span> get_selenium_browser
  <span style="color:#006600; font-weight:bold;">&#123;</span>
    <span style="color:#ff3333; font-weight:bold;">:session</span> =<span style="color:#006600; font-weight:bold;">&amp;</span>gt; Capybara.<span style="color:#9900CC;">current_session</span>,
    <span style="color:#ff3333; font-weight:bold;">:driver</span>  =<span style="color:#006600; font-weight:bold;">&amp;</span>gt; <span style="color:#6666ff; font-weight:bold;">Capybara::Driver::Selenium</span>.<span style="color:#9900CC;">instance_variable_get</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#996600;">'@driver'</span><span style="color:#006600; font-weight:bold;">&#41;</span>
  <span style="color:#006600; font-weight:bold;">&#125;</span>
<span style="color:#9966CC; font-weight:bold;">end</span></pre></div></div>

<p>Jak widać ta metoda jest banalna &#8211; pobiera ona jedynie obecną sesję(dla Selenium) oraz &#8220;driver&#8221;(czyli tak naprawdę referencję do instancji serwera Selenium).</p>

<div class="wp_syntax"><div class="code"><pre class="ruby" style="font-family:monospace;"><span style="color:#9966CC; font-weight:bold;">def</span> set_selenium_browser<span style="color:#006600; font-weight:bold;">&#40;</span>browser_id<span style="color:#006600; font-weight:bold;">&#41;</span>
  browser = <span style="color:#ff6633; font-weight:bold;">$browsers</span><span style="color:#006600; font-weight:bold;">&#91;</span>browser_id<span style="color:#006600; font-weight:bold;">&#93;</span> <span style="color:#006600; font-weight:bold;">||</span> <span style="color:#006600; font-weight:bold;">&#123;</span><span style="color:#006600; font-weight:bold;">&#125;</span>
  <span style="color:#9966CC; font-weight:bold;">if</span> browser<span style="color:#006600; font-weight:bold;">&#91;</span><span style="color:#ff3333; font-weight:bold;">:session</span><span style="color:#006600; font-weight:bold;">&#93;</span>.<span style="color:#0000FF; font-weight:bold;">nil</span>?
    Capybara.<span style="color:#9900CC;">instance_variable_set</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#996600;">'@session_pool'</span>, <span style="color:#006600; font-weight:bold;">&#123;</span><span style="color:#006600; font-weight:bold;">&#125;</span><span style="color:#006600; font-weight:bold;">&#41;</span>
    <span style="color:#6666ff; font-weight:bold;">Capybara::Driver::Selenium</span>.<span style="color:#9900CC;">instance_variable_set</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#996600;">'@driver'</span>, <span style="color:#0000FF; font-weight:bold;">nil</span><span style="color:#006600; font-weight:bold;">&#41;</span>
  <span style="color:#9966CC; font-weight:bold;">else</span>
    Capybara.<span style="color:#9900CC;">instance_variable_set</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#996600;">'@session_pool'</span>, <span style="color:#006600; font-weight:bold;">&#123;</span><span style="color:#996600;">&quot;selenium#{Capybara.app.object_id}&quot;</span> =<span style="color:#006600; font-weight:bold;">&amp;</span>gt; browser<span style="color:#006600; font-weight:bold;">&#91;</span><span style="color:#ff3333; font-weight:bold;">:session</span><span style="color:#006600; font-weight:bold;">&#93;</span><span style="color:#006600; font-weight:bold;">&#125;</span><span style="color:#006600; font-weight:bold;">&#41;</span>
    <span style="color:#6666ff; font-weight:bold;">Capybara::Driver::Selenium</span>.<span style="color:#9900CC;">instance_variable_set</span><span style="color:#006600; font-weight:bold;">&#40;</span><span style="color:#996600;">'@driver'</span>, browser<span style="color:#006600; font-weight:bold;">&#91;</span><span style="color:#ff3333; font-weight:bold;">:driver</span><span style="color:#006600; font-weight:bold;">&#93;</span><span style="color:#006600; font-weight:bold;">&#41;</span>
  <span style="color:#9966CC; font-weight:bold;">end</span>
<span style="color:#9966CC; font-weight:bold;">end</span></pre></div></div>

<p>Tu też nie ma żadnej magii &#8211; zapisujemy stan sesji i podmieniamy referencję do serwera Selenium. Tak zapisany kod pozwala nam na łatwe zapisanie funkcji Cucumbera zmieniających przeglądarki:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Given /^I am using first browser$/ do
  check_selenium_browsers
  set_selenium_browser(1)
end
&nbsp;
Given /^I am using second browser$/ do
  check_selenium_browsers
  set_selenium_browser(2)
end</pre></div></div>

<p>Możemy w ten sposób używać dowolnej ilości przeglądarek i testować w nich nie tylko Juggernauta, ale i WebSockets czy inne funkcjonalności(nawet zwykłą, ajaxową komunikację między użytkownikami &#8211; zaoszczędzi to nam czasu przy przelogowywaniu się pomiędzy requestami).<br />
Na koniec tylko dodam, że przy wychodzeniu z Cucumbera nie wszystkie instancje przeglądarki zostaną zamknięte(a dokładnie &#8211; zamknięta zostanie tylko obecnie aktywna) Aby &#8220;posprzątać&#8221; po sobie warto dodać w którymś z plików w inicjalizacyjnych(features/support) kod:</p>

<div class="wp_syntax"><div class="code"><pre class="ruby" style="font-family:monospace;"><span style="color:#CC0066; font-weight:bold;">at_exit</span> <span style="color:#9966CC; font-weight:bold;">do</span>
  <span style="color:#ff6633; font-weight:bold;">$browsers</span>.<span style="color:#9900CC;">each</span> <span style="color:#006600; font-weight:bold;">&#123;</span> <span style="color:#006600; font-weight:bold;">|</span>id, browser<span style="color:#006600; font-weight:bold;">|</span> browser<span style="color:#006600; font-weight:bold;">&#91;</span><span style="color:#ff3333; font-weight:bold;">:driver</span><span style="color:#006600; font-weight:bold;">&#93;</span>.<span style="color:#9900CC;">quit</span> <span style="color:#006600; font-weight:bold;">&#125;</span> <span style="color:#9966CC; font-weight:bold;">rescue</span> <span style="color:#0000FF; font-weight:bold;">nil</span>
<span style="color:#9966CC; font-weight:bold;">end</span></pre></div></div>

<img src="http://feeds.feedburner.com/~r/imanel-rss/~4/aE5UBrZQpQI" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://imanel.org/2010/03/testowanie-cucumberem-dla-wielu-uzytkownikow-czesc-dalsza/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://imanel.org/2010/03/testowanie-cucumberem-dla-wielu-uzytkownikow-czesc-dalsza/</feedburner:origLink></item>
		<item>
		<title>Nowy serwer</title>
		<link>http://feedproxy.google.com/~r/imanel-rss/~3/dNEkBa6hWEg/</link>
		<comments>http://imanel.org/2010/02/nowy-serwer/#comments</comments>
		<pubDate>Tue, 09 Feb 2010 14:50:17 +0000</pubDate>
		<dc:creator>Bernard Potocki</dc:creator>
				<category><![CDATA[Blog]]></category>

		<guid isPermaLink="false">http://imanel.org/?p=171</guid>
		<description><![CDATA[W związku z powtarzającymi się problemami z moim poprzednim właścicielem serwera dzisiaj nastąpiła przeprowadzka na nową maszynę &#8211; mam nadzieję że sprawiającą mniej problemów i dającą większe możliwości.
]]></description>
			<content:encoded><![CDATA[<p class="dropcap-first">W związku z powtarzającymi się problemami z moim poprzednim właścicielem serwera dzisiaj nastąpiła przeprowadzka na nową maszynę &#8211; mam nadzieję że sprawiającą mniej problemów i dającą większe możliwości.</p>
<img src="http://feeds.feedburner.com/~r/imanel-rss/~4/dNEkBa6hWEg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://imanel.org/2010/02/nowy-serwer/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://imanel.org/2010/02/nowy-serwer/</feedburner:origLink></item>
		<item>
		<title>Testowanie Juggernauta za pomocą Cucumbera i Selenium</title>
		<link>http://feedproxy.google.com/~r/imanel-rss/~3/xl96ldnSvLs/</link>
		<comments>http://imanel.org/2010/01/testowanie-juggernauta-za-pomoca-cucumbera-i-selenium/#comments</comments>
		<pubDate>Sun, 24 Jan 2010 14:13:21 +0000</pubDate>
		<dc:creator>Bernard Potocki</dc:creator>
				<category><![CDATA[Rails]]></category>
		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://imanel.org/?p=152</guid>
		<description><![CDATA[Zazwyczaj pisząc testy stawiamy na sprawdzone, konsolowe rozwiązania typu RSpec czy Cucumber +  Webrat &#8211; dzięki temu łączymy szybkość i wygodę. Niestety pisząc niektóre aplikacje internetowe nie da się uniknąć pobrudzenia sobie rąk. I o ile możemy sobie pozwolić na narzędzia typu Celerity jeśli operujemy wyłącznie javascriptem, o tyle kiedy dochodzą technologie typu flash czy [...]]]></description>
			<content:encoded><![CDATA[<p class="dropcap-first">Zazwyczaj pisząc testy stawiamy na sprawdzone, konsolowe rozwiązania typu <a href="http://rspec.info/">RSpec</a> czy <a href="http://cukes.info/">Cucumber</a> +  <a href="http://github.com/brynary/webrat">Webrat</a> &#8211; dzięki temu łączymy szybkość i wygodę. Niestety pisząc niektóre aplikacje internetowe nie da się uniknąć pobrudzenia sobie rąk. I o ile możemy sobie pozwolić na narzędzia typu <a href="http://celerity.rubyforge.org/">Celerity</a> jeśli operujemy wyłącznie javascriptem, o tyle kiedy dochodzą technologie typu flash czy java trzeba sięgnąć po większy kaliber. W takich momentach przychodzi nam na pomoc <a href="http://seleniumhq.org/">Selenium</a> &#8211; framework do testowania aplikacji w prawdziwych przeglądarkach. Jak połączyć Selenium z Cucumberem nie będę tu opisywał bo wszystko jest dokładnie wyjaśnione na <a href="http://wiki.github.com/aslakhellesoy/cucumber/setting-up-selenium">wiki</a> Cucumbera.</p>
<p>Domyślnie Cucumber otwiera jedną przeglądarkę i w niej wszystko testuje. Czasami jednak potrzebujemy kilku jej instancji &#8211; jak np. w przypadku stron gdzie potrzebna jest natychmiastowa komunikacja między dwoma użytkownikami. Na szczęście skrypty do Selenium w Cucumberze łatwo obejść i otworzyć drugą przeglądarkę, a potem się między nimi przełączać. Wystarczy w env.rb(albo odpowiednim pliku dla selenium) wpisać:</p>

<div class="wp_syntax"><table><tr><td class="line_numbers"><pre>1
2
3
</pre></td><td class="code"><pre class="ruby" style="font-family:monospace;"><span style="color:#ff6633; font-weight:bold;">$browser2</span> = <span style="color:#6666ff; font-weight:bold;">Webrat::SeleniumSession</span>.<span style="color:#9900CC;">new</span>.<span style="color:#9900CC;">selenium</span>
<span style="color:#ff6633; font-weight:bold;">$browser</span> = <span style="color:#0000FF; font-weight:bold;">nil</span>
<span style="color:#ff6633; font-weight:bold;">$browser1</span> = <span style="color:#6666ff; font-weight:bold;">Webrat::SeleniumSession</span>.<span style="color:#9900CC;">new</span>.<span style="color:#9900CC;">selenium</span></pre></td></tr></table></div>

<p>Druga linijka jest niezbędna aby Cucumber poprawnie zainicjalizował drugą przeglądarkę. Potem już wystarczy tylko utworzyć odpowiednie kroki dla selenium &#8211; na przykład:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Given /^I am using first browser$/ do
  if Webrat.configuration.mode == :selenium
    $browser = $browser1
  end
end
&nbsp;
Given /^I am using second browser$/ do
  if Webrat.configuration.mode == :selenium
    $browser = $browser2
  end
end</pre></div></div>

<p>Domyślnie aktywowana będzie pierwsza przeglądarka, ale należy pamiętać że ostatnio używana instancja nie jest restartowana pomiędzy poszczególnymi testami więc zawsze należy powrócić do pierwszej przeglądarki na zakończenie testu w którym zmieniamy okna. Dodatkowo przydatne są jeszcze dwa kroki:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">When /^I wait for page to load$/ do
  if Webrat.configuration.mode == :selenium
    selenium.wait_for_page_to_load
  end
end
&nbsp;
Given /^I wait for juggernaut$/ do
  if Webrat.configuration.mode == :selenium
    sleep(3)
  end
end</pre></div></div>

<p>Pierwszy zapewnia że załadowane zostaną wszystkie skrypty przed przejściem do następnych kroków, a drugi daje Juggernautowi chwilę na dostarczenie wiadomości. Z tak skonfigurowanymi testami możemy używać wszystkich kroków dostarczonych przez Cucumbera bez martwienia się o kompatybilność.</p>
<img src="http://feeds.feedburner.com/~r/imanel-rss/~4/xl96ldnSvLs" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://imanel.org/2010/01/testowanie-juggernauta-za-pomoca-cucumbera-i-selenium/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://imanel.org/2010/01/testowanie-juggernauta-za-pomoca-cucumbera-i-selenium/</feedburner:origLink></item>
		<item>
		<title>Sphinx a sprawa polska</title>
		<link>http://feedproxy.google.com/~r/imanel-rss/~3/E5mzPFDijjg/</link>
		<comments>http://imanel.org/2010/01/sphinx-a-sprawa-polska/#comments</comments>
		<pubDate>Sun, 24 Jan 2010 01:47:42 +0000</pubDate>
		<dc:creator>Bernard Potocki</dc:creator>
				<category><![CDATA[Rails]]></category>
		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://imanel.org/?p=133</guid>
		<description><![CDATA[Pisząc aplikacje internetowe czasami spotykam się z sytuacją kiedy trzeba wykorzystać full text search. W takich momentach niezastąpione są narzędzia typu Sphinx czy Ferret. Osobiście preferuję Sphinxa za jego szybkość i wygodę. Czasem jednak potrafi sprawić problemy &#8211; szczególnie z wyszukiwaniem akcentów w językach. Otóż domyślnie kodowanie UTF-8 nie jest odpowiednio konwertowane i Sphinx traktuje [...]]]></description>
			<content:encoded><![CDATA[<p class="dropcap-first">Pisząc aplikacje internetowe czasami spotykam się z sytuacją kiedy trzeba wykorzystać full text search. W takich momentach niezastąpione są narzędzia typu <a href="http://www.sphinxsearch.com/">Sphinx</a> czy <a href="http://ferret.davebalmain.com/trac/">Ferret</a>. Osobiście preferuję Sphinxa za jego szybkość i wygodę. Czasem jednak potrafi sprawić problemy &#8211; szczególnie z wyszukiwaniem akcentów w językach. Otóż domyślnie kodowanie UTF-8 nie jest odpowiednio konwertowane i Sphinx traktuje znaki z poza ASCII jako znaki rozdzielające wyrazy. W necie można znaleźć wiele stron z prostym rozwiązaniem tego problemu &#8211; wystarczy w pliku konfiguracyjnym dodać odpowiednie reguły konwersji:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">charset_table: &quot;0..9, a..z, _, A..Z-&gt;a..z, U+00C0-&gt;a, U+00C1-&gt;a, U+00C2-&gt;a, U+00C3-&gt;a, U+00C4-&gt;a, U+00C5-&gt;a, U+00C7-&gt;c, U+00C8-&gt;e, U+00C9-&gt;e, U+00CA-&gt;e, U+00CB-&gt;e, U+00CC-&gt;i, U+00CD-&gt;i, U+00CE-&gt;i, U+00CF-&gt;i, U+00D1-&gt;n, U+00D2-&gt;o, U+00D3-&gt;o, U+00D4-&gt;o, U+00D5-&gt;o, U+00D6-&gt;o, U+00D9-&gt;u, U+00DA-&gt;u, U+00DB-&gt;u, U+00DC-&gt;u, U+00DD-&gt;y, U+00E0-&gt;a, U+00E1-&gt;a, U+00E2-&gt;a, U+00E3-&gt;a, U+00E4-&gt;a, U+00E5-&gt;a, U+00E7-&gt;c, U+00E8-&gt;e, U+00E9-&gt;e, U+00EA-&gt;e, U+00EB-&gt;e, U+00EC-&gt;i, U+00ED-&gt;i, U+00EE-&gt;i, U+00EF-&gt;i, U+00F1-&gt;n, U+00F2-&gt;o, U+00F3-&gt;o, U+00F4-&gt;o, U+00F5-&gt;o, U+00F6-&gt;o, U+00F9-&gt;u, U+00FA-&gt;u, U+00FB-&gt;u, U+00FC-&gt;u, U+00FD-&gt;y, U+00FF-&gt;y, U+0100-&gt;a, U+0101-&gt;a, U+0102-&gt;a, U+0103-&gt;a, U+0104-&gt;a, U+0105-&gt;a, U+0106-&gt;c, U+0107-&gt;c, U+0108-&gt;c, U+0109-&gt;c, U+010A-&gt;c, U+010B-&gt;c, U+010C-&gt;c, U+010D-&gt;c, U+010E-&gt;d, U+010F-&gt;d, U+0112-&gt;e, U+0113-&gt;e, U+0114-&gt;e, U+0115-&gt;e, U+0116-&gt;e, U+0117-&gt;e, U+0118-&gt;e, U+0119-&gt;e, U+011A-&gt;e, U+011B-&gt;e, U+011C-&gt;g, U+011D-&gt;g, U+011E-&gt;g, U+011F-&gt;g, U+0120-&gt;g, U+0121-&gt;g, U+0122-&gt;g, U+0123-&gt;g, U+0124-&gt;h, U+0125-&gt;h, U+0128-&gt;i, U+0129-&gt;i, U+012A-&gt;i, U+012B-&gt;i, U+012C-&gt;i, U+012D-&gt;i, U+012E-&gt;i, U+012F-&gt;i, U+0130-&gt;i, U+0134-&gt;j, U+0135-&gt;j, U+0136-&gt;k, U+0137-&gt;k, U+0139-&gt;l, U+013A-&gt;l, U+013B-&gt;l, U+013C-&gt;l, U+013D-&gt;l, U+013E-&gt;l, U+0143-&gt;n, U+0144-&gt;n, U+0145-&gt;n, U+0146-&gt;n, U+0147-&gt;n, U+0148-&gt;n, U+014C-&gt;o, U+014D-&gt;o, U+014E-&gt;o, U+014F-&gt;o, U+0150-&gt;o, U+0151-&gt;o, U+0154-&gt;r, U+0155-&gt;r, U+0156-&gt;r, U+0157-&gt;r, U+0158-&gt;r, U+0159-&gt;r, U+015A-&gt;s, U+015B-&gt;s, U+015C-&gt;s, U+015D-&gt;s, U+015E-&gt;s, U+015F-&gt;s, U+0160-&gt;s, U+0161-&gt;s, U+0162-&gt;t, U+0163-&gt;t, U+0164-&gt;t, U+0165-&gt;t, U+0168-&gt;u, U+0169-&gt;u, U+016A-&gt;u, U+016B-&gt;u, U+016C-&gt;u, U+016D-&gt;u, U+016E-&gt;u, U+016F-&gt;u, U+0170-&gt;u, U+0171-&gt;u, U+0172-&gt;u, U+0173-&gt;u, U+0174-&gt;w, U+0175-&gt;w, U+0176-&gt;y, U+0177-&gt;y, U+0178-&gt;y, U+0179-&gt;z, U+017A-&gt;z, U+017B-&gt;z, U+017C-&gt;z, U+017D-&gt;z, U+017E-&gt;z, U+01A0-&gt;o, U+01A1-&gt;o, U+01AF-&gt;u, U+01B0-&gt;u, U+01CD-&gt;a, U+01CE-&gt;a, U+01CF-&gt;i, U+01D0-&gt;i, U+01D1-&gt;o, U+01D2-&gt;o, U+01D3-&gt;u, U+01D4-&gt;u, U+01D5-&gt;u, U+01D6-&gt;u, U+01D7-&gt;u, U+01D8-&gt;u, U+01D9-&gt;u, U+01DA-&gt;u, U+01DB-&gt;u, U+01DC-&gt;u, U+01DE-&gt;a, U+01DF-&gt;a, U+01E0-&gt;a, U+01E1-&gt;a, U+01E6-&gt;g, U+01E7-&gt;g, U+01E8-&gt;k, U+01E9-&gt;k, U+01EA-&gt;o, U+01EB-&gt;o, U+01EC-&gt;o, U+01ED-&gt;o, U+01F0-&gt;j, U+01F4-&gt;g, U+01F5-&gt;g, U+01F8-&gt;n, U+01F9-&gt;n, U+01FA-&gt;a, U+01FB-&gt;a, U+0200-&gt;a, U+0201-&gt;a, U+0202-&gt;a, U+0203-&gt;a, U+0204-&gt;e, U+0205-&gt;e, U+0206-&gt;e, U+0207-&gt;e, U+0208-&gt;i, U+0209-&gt;i, U+020A-&gt;i, U+020B-&gt;i, U+020C-&gt;o, U+020D-&gt;o, U+020E-&gt;o, U+020F-&gt;o, U+0210-&gt;r, U+0211-&gt;r, U+0212-&gt;r, U+0213-&gt;r, U+0214-&gt;u, U+0215-&gt;u, U+0216-&gt;u, U+0217-&gt;u, U+0218-&gt;s, U+0219-&gt;s, U+021A-&gt;t, U+021B-&gt;t, U+021E-&gt;h, U+021F-&gt;h, U+0226-&gt;a, U+0227-&gt;a, U+0228-&gt;e, U+0229-&gt;e, U+022A-&gt;o, U+022B-&gt;o, U+022C-&gt;o, U+022D-&gt;o, U+022E-&gt;o, U+022F-&gt;o, U+0230-&gt;o, U+0231-&gt;o, U+0232-&gt;y, U+0233-&gt;y, U+1E00-&gt;a, U+1E01-&gt;a, U+1E02-&gt;b, U+1E03-&gt;b, U+1E04-&gt;b, U+1E05-&gt;b, U+1E06-&gt;b, U+1E07-&gt;b, U+1E08-&gt;c, U+1E09-&gt;c, U+1E0A-&gt;d, U+1E0B-&gt;d, U+1E0C-&gt;d, U+1E0D-&gt;d, U+1E0E-&gt;d, U+1E0F-&gt;d, U+1E10-&gt;d, U+1E11-&gt;d, U+1E12-&gt;d, U+1E13-&gt;d, U+1E14-&gt;e, U+1E15-&gt;e, U+1E16-&gt;e, U+1E17-&gt;e, U+1E18-&gt;e, U+1E19-&gt;e, U+1E1A-&gt;e, U+1E1B-&gt;e, U+1E1C-&gt;e, U+1E1D-&gt;e, U+1E1E-&gt;f, U+1E1F-&gt;f, U+1E20-&gt;g, U+1E21-&gt;g, U+1E22-&gt;h, U+1E23-&gt;h, U+1E24-&gt;h, U+1E25-&gt;h, U+1E26-&gt;h, U+1E27-&gt;h, U+1E28-&gt;h, U+1E29-&gt;h, U+1E2A-&gt;h, U+1E2B-&gt;h, U+1E2C-&gt;i, U+1E2D-&gt;i, U+1E2E-&gt;i, U+1E2F-&gt;i, U+1E30-&gt;k, U+1E31-&gt;k, U+1E32-&gt;k, U+1E33-&gt;k, U+1E34-&gt;k, U+1E35-&gt;k, U+1E36-&gt;l, U+1E37-&gt;l, U+1E38-&gt;l, U+1E39-&gt;l, U+1E3A-&gt;l, U+1E3B-&gt;l, U+1E3C-&gt;l, U+1E3D-&gt;l, U+1E3E-&gt;m, U+1E3F-&gt;m, U+1E40-&gt;m, U+1E41-&gt;m, U+1E42-&gt;m, U+1E43-&gt;m, U+1E44-&gt;n, U+1E45-&gt;n, U+1E46-&gt;n, U+1E47-&gt;n, U+1E48-&gt;n, U+1E49-&gt;n, U+1E4A-&gt;n, U+1E4B-&gt;n, U+1E4C-&gt;o, U+1E4D-&gt;o, U+1E4E-&gt;o, U+1E4F-&gt;o, U+1E50-&gt;o, U+1E51-&gt;o, U+1E52-&gt;o, U+1E53-&gt;o, U+1E54-&gt;p, U+1E55-&gt;p, U+1E56-&gt;p, U+1E57-&gt;p, U+1E58-&gt;r, U+1E59-&gt;r, U+1E5A-&gt;r, U+1E5B-&gt;r, U+1E5C-&gt;r, U+1E5D-&gt;r, U+1E5E-&gt;r, U+1E5F-&gt;r, U+1E60-&gt;s, U+1E61-&gt;s, U+1E62-&gt;s, U+1E63-&gt;s, U+1E64-&gt;s, U+1E65-&gt;s, U+1E66-&gt;s, U+1E67-&gt;s, U+1E68-&gt;s, U+1E69-&gt;s, U+1E6A-&gt;t, U+1E6B-&gt;t, U+1E6C-&gt;t, U+1E6D-&gt;t, U+1E6E-&gt;t, U+1E6F-&gt;t, U+1E70-&gt;t, U+1E71-&gt;t, U+1E72-&gt;u, U+1E73-&gt;u, U+1E74-&gt;u, U+1E75-&gt;u, U+1E76-&gt;u, U+1E77-&gt;u, U+1E78-&gt;u, U+1E79-&gt;u, U+1E7A-&gt;u, U+1E7B-&gt;u, U+1E7C-&gt;v, U+1E7D-&gt;v, U+1E7E-&gt;v, U+1E7F-&gt;v, U+1E80-&gt;w, U+1E81-&gt;w, U+1E82-&gt;w, U+1E83-&gt;w, U+1E84-&gt;w, U+1E85-&gt;w, U+1E86-&gt;w, U+1E87-&gt;w, U+1E88-&gt;w, U+1E89-&gt;w, U+1E8A-&gt;x, U+1E8B-&gt;x, U+1E8C-&gt;x, U+1E8D-&gt;x, U+1E8E-&gt;y, U+1E8F-&gt;y, U+1E96-&gt;h, U+1E97-&gt;t, U+1E98-&gt;w, U+1E99-&gt;y, U+1EA0-&gt;a, U+1EA1-&gt;a, U+1EA2-&gt;a, U+1EA3-&gt;a, U+1EA4-&gt;a, U+1EA5-&gt;a, U+1EA6-&gt;a, U+1EA7-&gt;a, U+1EA8-&gt;a, U+1EA9-&gt;a, U+1EAA-&gt;a, U+1EAB-&gt;a, U+1EAC-&gt;a, U+1EAD-&gt;a, U+1EAE-&gt;a, U+1EAF-&gt;a, U+1EB0-&gt;a, U+1EB1-&gt;a, U+1EB2-&gt;a, U+1EB3-&gt;a, U+1EB4-&gt;a, U+1EB5-&gt;a, U+1EB6-&gt;a, U+1EB7-&gt;a, U+1EB8-&gt;e, U+1EB9-&gt;e, U+1EBA-&gt;e, U+1EBB-&gt;e, U+1EBC-&gt;e, U+1EBD-&gt;e, U+1EBE-&gt;e, U+1EBF-&gt;e, U+1EC0-&gt;e, U+1EC1-&gt;e, U+1EC2-&gt;e, U+1EC3-&gt;e, U+1EC4-&gt;e, U+1EC5-&gt;e, U+1EC6-&gt;e, U+1EC7-&gt;e, U+1EC8-&gt;i, U+1EC9-&gt;i, U+1ECA-&gt;i, U+1ECB-&gt;i, U+1ECC-&gt;o, U+1ECD-&gt;o, U+1ECE-&gt;o, U+1ECF-&gt;o, U+1ED0-&gt;o, U+1ED1-&gt;o, U+1ED2-&gt;o, U+1ED3-&gt;o, U+1ED4-&gt;o, U+1ED5-&gt;o, U+1ED6-&gt;o, U+1ED7-&gt;o, U+1ED8-&gt;o, U+1ED9-&gt;o, U+1EDA-&gt;o, U+1EDB-&gt;o, U+1EDC-&gt;o, U+1EDD-&gt;o, U+1EDE-&gt;o, U+1EDF-&gt;o, U+1EE0-&gt;o, U+1EE1-&gt;o, U+1EE2-&gt;o, U+1EE3-&gt;o, U+1EE4-&gt;u, U+1EE5-&gt;u, U+1EE6-&gt;u, U+1EE7-&gt;u, U+1EE8-&gt;u, U+1EE9-&gt;u, U+1EEA-&gt;u, U+1EEB-&gt;u, U+1EEC-&gt;u, U+1EED-&gt;u, U+1EEE-&gt;u, U+1EEF-&gt;u, U+1EF0-&gt;u, U+1EF1-&gt;u, U+1EF2-&gt;y, U+1EF3-&gt;y, U+1EF4-&gt;y, U+1EF5-&gt;y, U+1EF6-&gt;y, U+1EF7-&gt;y, U+1EF8-&gt;y, U+1EF9-&gt;y&quot;</pre></div></div>

<p>Okazuje się jednak że nie jest aż tak różowo &#8211; po dodaniu tego kawałka kodu polskie znaki nadal nie były poprawnie rozpoznawane. Sprawdzenie kodu, wyszukiwanie w konsoli i rozmaite testy przyniosły wreszcie powód: &#8220;ogonki&#8221; były zapisywane nie jako znaki w UTF-8 tylko jako html-owe encje. Jakie więc było moje zdziwienie gdy okazało się że na żadnych stronach opisujących ten problem nie pojawia się również to rozwiązanie. Jeśli też macie problem z brakiem możliwości wyszukiwania polskich znaków to wystarczy tylko dodać do konfiguracji linijkę:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">html_strip: 1</pre></div></div>

<p>I od razu wszystko śmiga &#8211; jedyna wada to że Sphinx ignoruje akcenty i zamienia je na znaki ASCII, ale to chyba nie jest zbyt duża cena w zamian za funkcjonalność którą nam daje.</p>
<img src="http://feeds.feedburner.com/~r/imanel-rss/~4/E5mzPFDijjg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://imanel.org/2010/01/sphinx-a-sprawa-polska/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://imanel.org/2010/01/sphinx-a-sprawa-polska/</feedburner:origLink></item>
		<item>
		<title>Buty z rubinem</title>
		<link>http://feedproxy.google.com/~r/imanel-rss/~3/_GrS7a27Vn0/</link>
		<comments>http://imanel.org/2010/01/buty-z-rubinem/#comments</comments>
		<pubDate>Sat, 02 Jan 2010 23:01:02 +0000</pubDate>
		<dc:creator>Bernard Potocki</dc:creator>
				<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://imanel.org/?p=126</guid>
		<description><![CDATA[Ostatnimi czasy pracując nad moją pracą inżynierską zacząłem się zastanawiać nad wyborem języka oraz czegoś sensownego do zrobienia interfejsu graficznego. Oczywiście pierwszą rzeczą która przyszła mi na myśl było C++ oraz QT, ale już po chwili stwierdziłem że zamiast iść na łatwiznę czas poznać coś nowego. Jako że aktualnie pracuję z Ruby więc zacząłem się [...]]]></description>
			<content:encoded><![CDATA[<p class="dropcap-first">Ostatnimi czasy pracując nad moją pracą inżynierską zacząłem się zastanawiać nad wyborem języka oraz czegoś sensownego do zrobienia interfejsu graficznego. Oczywiście pierwszą rzeczą która przyszła mi na myśl było C++ oraz QT, ale już po chwili stwierdziłem że zamiast iść na łatwiznę czas poznać coś nowego. Jako że aktualnie pracuję z Ruby więc zacząłem się zastanawiać czy nie ma jakiś sensownych bindingów dla tego języka. Poszukałem, znalazłem i stwierdziłem że to nie to. Niby fajne, niby działa, ale jakoś do mnie nie przemawia &#8211; za mało &#8220;ruby-way&#8221;, a do tego mnóstwo zabawy żeby działało u potencjalnego użytkownika(chociaż to już raczej wina samego rubiego niż QT). Poszukałem więc trochę dłużej i znalazłem jeszcze parę alternatyw &#8211; mnie lub bardziej pasujących do wymagań(ma być między-systemowe, działać OOTB i mieć jako-taką wydajność). Skończyło się na czymś spełniającym dwa pierwsze założenia i w akceptujący sposób trzecie &#8211; a mianowicie na <a title="Ruby Shoes" href="http://github.com/shoes/shoes">Ruby Shoes</a>.</p>
<p>Po wyborze czas na test &#8211; czyli nasze ukochane &#8220;hello world&#8221;. Szybka instalacja binarki dla OS X i parę linijek kodu później wielkie WOW i szybki test na maszynie wirtualnej pod Win oraz Ubuntu &#8211; wszystko działa tak jak miało. Zachwycony biorę się więc do roboty. Muszę przyznać że wszystko działa tak jak trzeba i pod każdym systemem. Do tego dochodzi generowanie pliku wykonywalnego z dołączonym Ruby Shoes więc żadne dodatkowe zależności nie są potrzebne &#8211; wszystko działa od razu, sprawnie i bez tricków specyficznych dla danego systemu. Tak więc cudo :)</p>
<p>Schody zaczęły się niestety kiedy potrzebowałem dołączyć do zależności jakieś gemy. Po testach paru wydawało mi się że wszystko będzie ok &#8211; w końcu sam instaluje gemy z sieci i jest gites. Problem jest w momencie kiedy potrzebujemy gema z rozszerzeniami natywnymi &#8211; tutaj niestety potrzebny jest kompilator, a RubyGems nie jest dostatecznie zaawansowane żeby powiedzieć dokładnie czego potrzebuje. Ale od czego jest readme &#8211; umieści się i to. Prawdziwy problem zaczął się jednak przy próbie dołączenia RMagick. Otóż po paru godzinach prób, googlowania i czytania słownie setek możliwych rozwiązań stwierdziłem że jestem w tej wąskiej grupie gdzie nawet najwięksi wyjadacze rozkładają ręce i mówią że pod Snow Leopard nie działa i nie wiadomo dlaczego. Bo w końcu wszystko się kompiluje, uruchamia itd, ale przy próbie wywołania dowolnej funkcji wywala że istniejący bundle nie istnieje i figa. Cóż &#8211; z pomocą przyszedł wysłużony VirtualBox i teraz pracuję na 2 ekrany &#8211; na jednym OS X z kodem, a na drugim Ubuntu z testami. Można? Można &#8211; potem się będę zastanawiał co mogę zrobić żeby działało na wszystkich 3 systemach &#8211; może niedługo wyjdzie patch naprawiający tą usterkę? Zobaczymy.</p>
<p>Na zakończenie krótkie podsumowanie. Jeśli potrzebujecie przenośnego frameworka dla aplikacji w Ruby to Shoes jest dla was &#8211; działa na każdym systemie, buduje binarki z samym sobą oraz automatycznie ściąga dołączone gemy. Wydajność stoi na przyzwoitym poziomie, łatwość i przyjemność programowania to jakieś 8/10 a i społeczność jest całkiem przyzwoita. Jedyny problem(poza natywnymi rozszerzeniami) to kulejąca trochę dokumentacja &#8211; połowy funkcji nie ma w plikach RDoc więc trzeba szukać na własną rękę albo w manualu(co prawda tam powinno się szukać w pierwszej kolejności, ale jak wielu użytkowników Ruby przyzwyczaiłem się do pewnych standardów;) Ale zapewniam że da się to przeboleć i wtedy dość szybko można docenić pracę autora.</p>
<img src="http://feeds.feedburner.com/~r/imanel-rss/~4/_GrS7a27Vn0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://imanel.org/2010/01/buty-z-rubinem/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://imanel.org/2010/01/buty-z-rubinem/</feedburner:origLink></item>
		<item>
		<title>Nowy blog</title>
		<link>http://feedproxy.google.com/~r/imanel-rss/~3/B6RdDrlWDtQ/</link>
		<comments>http://imanel.org/2009/12/nowy-blog/#comments</comments>
		<pubDate>Sun, 27 Dec 2009 20:36:54 +0000</pubDate>
		<dc:creator>Bernard Potocki</dc:creator>
				<category><![CDATA[Blog]]></category>

		<guid isPermaLink="false">http://imanel.org/wordpress/?p=122</guid>
		<description><![CDATA[Ostatnimi czasy patrząc na ten swój biedny blog stwierdziłem że troszeczkę tu&#8230; smutno? Tak &#8211; to chyba dobre określenie. Ale tak to już bywa kiedy bierze się za coś na szybko bo &#8220;coś podkusiło&#8221; i potem powstaje fuszerka której się nie chce dotykać bo &#8220;jeszcze się posypie&#8221;. Tak więc odczekałem od świąt i korzystając z nadmiaru czasu pomiędzy [...]]]></description>
			<content:encoded><![CDATA[<p class="dropcap-first">Ostatnimi czasy patrząc na ten swój biedny blog stwierdziłem że troszeczkę tu&#8230; smutno? Tak &#8211; to chyba dobre określenie. Ale tak to już bywa kiedy bierze się za coś na szybko bo &#8220;coś podkusiło&#8221; i potem powstaje fuszerka której się nie chce dotykać bo &#8220;jeszcze się posypie&#8221;. Tak więc odczekałem od świąt i korzystając z nadmiaru czasu pomiędzy jedną sjestą a drugą i przerzuciłem się na Wordpressa. Co prawda w pierwszej chwili byłem trochę przerażony tym ile tu jest opcji, ale jakoś się ogarnąłem i parę rzeczy poprzerabiałem &#8211; chyba teraz już będzie wszystko sensownie działać. Nauczka na przyszłość? <a href="http://github.com/mojombo/jekyll">Jeckyll</a> jest fajnym projektem, ale jeśli ma się ochotę popisać dłużej niż parę postów zanim człowieka krew zaleje to lepiej przejść na coś mniej geekowskiego&#8230;</p>
<img src="http://feeds.feedburner.com/~r/imanel-rss/~4/B6RdDrlWDtQ" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://imanel.org/2009/12/nowy-blog/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		<feedburner:origLink>http://imanel.org/2009/12/nowy-blog/</feedburner:origLink></item>
	</channel>
</rss>
