<?xml version="1.0" encoding="UTF-8"?>
<commit>
  <added type="array">
    <added>
      <filename>01_HelloBlog/air/src/AIRAliases.js</filename>
    </added>
    <added>
      <filename>01_HelloBlog/air/src/HelloBlog.html</filename>
    </added>
    <added>
      <filename>01_HelloBlog/air/src/application-html.xml</filename>
    </added>
    <added>
      <filename>12_TwitterClient/air/src/TC-app.xml</filename>
    </added>
    <added>
      <filename>12_TwitterClient/rails/app/models/account.rb</filename>
    </added>
    <added>
      <filename>12_TwitterClient/rails/db/migrate/001_create_accounts.rb</filename>
    </added>
    <added>
      <filename>12_TwitterClient/rails/db/schema.rb</filename>
    </added>
    <added>
      <filename>12_TwitterClient/rails/test/fixtures/accounts.yml</filename>
    </added>
    <added>
      <filename>12_TwitterClient/rails/test/unit/account_test.rb</filename>
    </added>
  </added>
  <modified type="array">
    <modified>
      <diff>@@ -1,7 +1,7 @@
-**/bin-debug/*
+bin-debug
 .DS_Store
 twitter.yml
-**/config/amazon_s3.yml
+amazon_s3.yml
 **/log/*.log
 **/tmp/**/*
 .actionScriptProperties</diff>
      <filename>.gitignore</filename>
    </modified>
    <modified>
      <diff>@@ -6,7 +6,6 @@
             - style tweets (remove xml)
             - don't retrieve if already in graph
             - better error handling
-            - toggle ControlPanel visibility
             - better defaults
 --&gt;
 &lt;mx:WindowedApplication xmlns:mx=&quot;http://www.adobe.com/2006/mxml&quot; 
@@ -33,7 +32,7 @@
             [Bindable]
             private var selectedItem:Item;  // simple click selects user, double click retrieve friends
             
-        private var graph:MyGraph = new MyGraph();
+        private var graph:Graph;
         
         // Rails server calls
         // --------------------------------------
@@ -45,8 +44,10 @@
             setupGraph();
         }
             
-        private function searchTwitterUser(user:String):void {
-            
+        private function searchTwitterUser(twitterUser:String):void {
+            currentUser = twitterUser;
+            user.send();
+            setupGraph();
         }    
         /*
         &lt;user&gt;
@@ -61,37 +62,27 @@
     */
             
         private function showUser(event:ResultEvent):void {
-            trace(event.result);
             var user:XML = event.result as XML;
             var item:Item = new Item(user.name);
             item.data = user;
             graph.add(item);
-            //roamer.currentItem = item;
-            roamer.dataProvider = graph;
+            roamer.dataProvider = graph; //FORCE refresh
         }    
         
         private function showFriends(event:ResultEvent):void {
             var result:XML = event.result as XML;
             var users:XMLList = result.record;
             var currentUser:Item = event.token.currentUser;
-            trace(&quot;Found friends for &quot;+currentUser.data.name);
-            graph.disableNotification();
-            try {
-                for each (var user:XML in users) {
-                    var friend:Item = new Item(user.name);
-                    friend.data = user;
-                    graph.add(friend);
-                    graph.link(currentUser, friend);
-                }
-            } finally {
-                graph.enableNotification();
+            for each (var user:XML in users) {
+                var friend:Item = new Item(user.name);
+                friend.data = user;
+                graph.add(friend);
+                graph.link(currentUser, friend);
             }
-            //roamer.currentItem = currentUser;
-            //roamer.dataProvider = graph;    
             roamer.currentItem = currentUser;    
         }
         
-        // Graph Handlig
+        // Graph Handling
         // --------------------------------------
 
             /*
@@ -103,6 +94,7 @@
                 roamer.resetHistory();
                 roamer.resetShowHide();
                 roamer.xmlNames = ['user','Edge','fromID','toID']; //['Node','Edge','fromID','toID']
+                graph = new Graph()
                 roamer.dataProvider = graph;         
             }
             
@@ -116,7 +108,6 @@
             
             public function itemClick(event: Event) : void {
                 selectedItem = event.currentTarget.data;
-                trace(&quot;Selected:&quot;+selectedItem);
             }    
         
              </diff>
      <filename>12_TwitterClient/air/src/TwitterConnections.mxml</filename>
    </modified>
    <modified>
      <diff>@@ -5,21 +5,14 @@
 	click=&quot;app().itemClick(event);&quot;
 	filters=&quot;{calcFilters(app().roamer.currentItem, data as Item)}&quot;
 &gt;	
-	&lt;!--
-	////////////////////////////////////////////////////////////////////////////////
-	//
-	//  Copyright (C) 2006 Adobe Macromedia Software LLC and its licensors.
-	//  All Rights Reserved. The following is Source Code and is subject to all
-	//  restrictions on such code as contained in the End User License Agreement
-	//  accompanying this product.
-	//
-	////////////////////////////////////////////////////////////////////////////////
-	--&gt;
+	&lt;mx:states&gt;
+		&lt;mx:State name=&quot;cached&quot;/&gt;
+	&lt;/mx:states&gt;
 	
-	&lt;!-- XMLItemView.mxml is the item renderer component for one XML item. We simply display the 'prop' 
-	     attribute of the XML item in a colored box. --&gt;
+	&lt;!-- XMLItemView.mxml is the item renderer component for one XML item. 
+		 We simply display the 'name' attribute of the XML item in a colored box. --&gt;
 				
-	&lt;mx:Text fontSize=&quot;13&quot; text=&quot;{data.data.name}&quot; color=&quot;#ffffff&quot; width=&quot;65&quot; selectable=&quot;false&quot;/&gt;	
+	&lt;mx:Text fontSize=&quot;13&quot; text=&quot;{data.data.name}&quot; color=&quot;#ffffff&quot; width=&quot;65&quot; selectable=&quot;false&quot;/&gt;
 	&lt;mx:Image source=&quot;{data.data.profile_image_url}&quot;/&gt;
 
 	&lt;mx:Script&gt;
@@ -31,7 +24,6 @@
 			import mx.core.Application;
 			
 			public function doubleClick(event: Event): void {
-				trace(&quot;doubleclicked&quot;);
 				app().itemDoubleClick(event);
 			}
 			</diff>
      <filename>12_TwitterClient/air/src/XMLItemView.mxml</filename>
    </modified>
    <modified>
      <diff>@@ -1,58 +1,63 @@
-=begin
-  Simplify code. Maybe just need to get data and send it.
-  Don't cache for first version.
-  Don't use &quot;own&quot; TwitterInstance, use explicit api Twitter::User.find(user, twitter)
-  Find easy way to convert returned Twitter::User.find(user, twitter) to xml
-=end
 class TwitterController &lt; ApplicationController
 
+  @@twitter = Twitter::Client.from_config(
+                File.join(File.dirname(__FILE__), '..', '..', 'config', 'twitter.yml'))
+
   def user
-    render :xml =&gt; get_user(params[:id])[:xml]
+    render :xml =&gt; account.user 
   end
   
   def friends    
-    render :xml =&gt; get_friends(params[:id])[:xml]
+    acc = account
+    unless acc.friends
+      u = Twitter::User.find(params[:id], @@twitter)
+      acc.update_attribute(
+                  'friends', 
+                  u.friends.collect {|f| to_hash(f) }.to_xml(:dasherize =&gt; false))
+    end
+    render :xml =&gt; acc.friends
   end
   
+  
+=begin
+  Non cached version
+  def user
+    u =  Twitter::User.find(params[:id], @@twitter)
+    render :xml =&gt; to_hash(u).to_xml(:root =&gt; :user, :dasherize =&gt; false)
+  end
+
+  def friends    
+    u = Twitter::User.find(params[:id], @@twitter)
+    f = u.friends
+    a = f.collect {|f| to_hash(f) }
+    render :xml =&gt; a.to_xml(:dasherize =&gt; false)
+  end
+=end  
+    
   protected
   
-  # user Hash with :user, :xml, :friends
-  def get_user(username)
-    unless u = @@cache[username]
-      new_u = {:user =&gt; TwitterInstance.find(username)}
-      new_u[:xml] = to_hash(new_u[:user]).to_xml(:root =&gt; :user, :dasherize =&gt; false)
-      new_u[:friends] = nil
-      u = @@cache[username] = new_u      
-    end
-    u
+  def account
+    acc = Account.find_or_initialize_by_name(params[:id])
+    if acc.new_record? #Not in db, let's retrieve and store
+      u =  Twitter::User.find(params[:id], @@twitter)
+      acc.user = to_hash(u).to_xml(:root =&gt; :user, :dasherize =&gt; false)
+      acc.save
+    end  
+    acc  
   end
   
-  # friends Hash with :array, :xml 
-  def get_friends(username)
-    u = get_user(username)
-    unless u[:friends]
-      new_f = {:array =&gt; TwitterInstance.friends(username).collect {|f| to_hash(f) }}
-      new_f[:xml] = new_f[:array].to_xml(:dasherize =&gt; false)
-      u[:friends] = new_f
-    end
-    u[:friends]
+  def to_xml(user)
+    to_hash(user)
   end  
   
-  # Poor man's user cache
-  #    name
-  #    keep user instance returned from twitter
-  #    friends - nil never retrieved - array retrieved
-  @@cache = {}
-  
-  
-  def to_hash(friend)
-    {:id  =&gt;  friend.id,
-     :profile_image_url  =&gt;  friend.profile_image_url,
-     :description  =&gt;  friend.description,
-     :url  =&gt;  friend.url,
-     :name  =&gt;  friend.name,
-     :location  =&gt;  friend.location,
-     :screen_name  =&gt;  friend.screen_name}
+  def to_hash(user)
+    {:id  =&gt;  user.id,
+     :profile_image_url  =&gt;  user.profile_image_url,
+     :description  =&gt;  user.description,
+     :url  =&gt;  user.url,
+     :name  =&gt;  user.name,
+     :location  =&gt;  user.location,
+     :screen_name  =&gt;  user.screen_name}
   end
   
 end</diff>
      <filename>12_TwitterClient/rails/app/controllers/twitter_controller.rb</filename>
    </modified>
    <modified>
      <diff></diff>
      <filename>12_TwitterClient/rails/db/development.sqlite3</filename>
    </modified>
  </modified>
  <removed type="array">
    <removed>
      <filename>12_TwitterClient/air/src/MyGraph.as</filename>
    </removed>
    <removed>
      <filename>12_TwitterClient/rails/app/models/twitter_instance.rb</filename>
    </removed>
  </removed>
  <parents type="array">
    <parent>
      <id>1d92efd7f94ced67bdf791adba7cdbe9e9b88252</id>
    </parent>
  </parents>
  <author>
    <name>Daniel Wanja</name>
    <email>d@n-so.com</email>
  </author>
  <url>http://github.com/danielwanja/railsconf2008/commit/62a31af57c547c8c0a2d717b0c0d1564e0f87741</url>
  <id>62a31af57c547c8c0a2d717b0c0d1564e0f87741</id>
  <committed-date>2008-05-27T19:47:58-07:00</committed-date>
  <authored-date>2008-05-27T19:47:58-07:00</authored-date>
  <message>Latest updates</message>
  <tree>a5babaa957ea0390b58cde5920b90e109ee88238</tree>
  <committer>
    <name>Daniel Wanja</name>
    <email>d@n-so.com</email>
  </committer>
</commit>
