<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	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/"
	>

<channel>
	<title>Dr Nic &#187; Unix</title>
	<atom:link href="http://drnicwilliams.com/category/unix/feed/" rel="self" type="application/rss+xml" />
	<link>http://drnicwilliams.com</link>
	<description>Ruby makes Rails, Javascript makes Ajax, Dr Nic makes Magic</description>
	<lastBuildDate>Sat, 12 Nov 2011 01:05:17 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.1.3</generator>
		<item>
		<title>Capistrano variables</title>
		<link>http://drnicwilliams.com/2007/04/10/capistrano-variables/</link>
		<comments>http://drnicwilliams.com/2007/04/10/capistrano-variables/#comments</comments>
		<pubDate>Tue, 10 Apr 2007 20:20:44 +0000</pubDate>
		<dc:creator>Dr Nic</dc:creator>
				<category><![CDATA[Rake]]></category>
		<category><![CDATA[Ruby]]></category>
		<category><![CDATA[Unix]]></category>

		<guid isPermaLink="false">http://drnicwilliams.com/2007/04/10/capistrano-variables/</guid>
		<description><![CDATA[Here&#8217;s an example of how you can pass variables to your capistrano actions via the cap command. desc "Returns last lines of log file. Usage: cap log [-s lines=100] [-s rails_env=production]" task :log do lines = configuration.variables[:lines] &#124;&#124; 100 rails_env = configuration.variables[:rails_env] &#124;&#124; 'production' run "tail -n #{lines} #{app_dir}/log/#{rails_env}.log" do &#124;ch, stream, out&#124; puts out [...]


Related posts:<ol><li><a href='http://drnicwilliams.com/2007/04/12/magic-multi-connections-a-facility-in-rails-to-talk-to-more-than-one-database-at-a-time/' rel='bookmark' title='Permanent Link: Magic Multi-Connections: A &#8220;facility in Rails to talk to more than one database at a time&#8221;'>Magic Multi-Connections: A &#8220;facility in Rails to talk to more than one database at a time&#8221;</a> <small>At this point in time there’s no facility in Rails...</small></li></ol>]]></description>
			<content:encoded><![CDATA[<p>Here&#8217;s an example of how you can pass variables to your capistrano actions via the <code>cap</code> command.</p>
<textarea name="code" class="ruby" cols="60" rows="10">
desc "Returns last lines of log file. Usage: cap log [-s lines=100] [-s rails_env=production]"
task :log do
  lines     = configuration.variables[:lines] || 100
  rails_env = configuration.variables[:rails_env] || 'production'
  run "tail -n #{lines} #{app_dir}/log/#{rails_env}.log" do |ch, stream, out|
    puts out
  end
end
</textarea>
<p>So, the above action could be called as follows:</p>
<pre>
cap log
cap log -s lines=1000
cap log -s rails_env=test
</pre>
<p>For reference, you pass values to Rake tasks via environment variables:</p>
<pre>
rake db:migrate RAILS_ENV=test
</pre>
<p>Inside the db:migrate task, you&#8217;d retrieve the value &#8216;test&#8217; via <code>ENV['RAILS_ENV'].</p>
<p>And further more, this then compares to how you'd normally pass option values into normal command-line apps:</p>
<pre>
tail -n 1000 log/production.log
</pre>
<p>Who said the unix command line wasn't easy peasy. Bah.</p>


<p>Related posts:<ol><li><a href='http://drnicwilliams.com/2007/04/12/magic-multi-connections-a-facility-in-rails-to-talk-to-more-than-one-database-at-a-time/' rel='bookmark' title='Permanent Link: Magic Multi-Connections: A &#8220;facility in Rails to talk to more than one database at a time&#8221;'>Magic Multi-Connections: A &#8220;facility in Rails to talk to more than one database at a time&#8221;</a> <small>At this point in time there’s no facility in Rails...</small></li></ol></p>]]></content:encoded>
			<wfw:commentRss>http://drnicwilliams.com/2007/04/10/capistrano-variables/feed/</wfw:commentRss>
		<slash:comments>10</slash:comments>
		</item>
		<item>
		<title>Remote Shell with Ruby</title>
		<link>http://drnicwilliams.com/2006/09/22/remote-shell-with-ruby/</link>
		<comments>http://drnicwilliams.com/2006/09/22/remote-shell-with-ruby/#comments</comments>
		<pubDate>Fri, 22 Sep 2006 10:22:50 +0000</pubDate>
		<dc:creator>Dr Nic</dc:creator>
				<category><![CDATA[Composite Keys]]></category>
		<category><![CDATA[Ruby]]></category>
		<category><![CDATA[Tutorial]]></category>
		<category><![CDATA[Unix]]></category>

		<guid isPermaLink="false">http://drnicwilliams.com/2006/09/22/remote-shell-with-ruby/</guid>
		<description><![CDATA[I wrote Composite Primary Keys and Dr Nic&#8217;s Magic Models because we have a 50+ table legacy database and I am terrorised by explicit SQL statements on a daily basis. I have a dirty secret &#8211; I don&#8217;t use either of them at work. We&#8217;ve been unsuccessful installing Ruby on our HP-UX box, then time [...]


Related posts:<ol><li><a href='http://drnicwilliams.com/2010/06/01/validate-and-save-your-ruby-in-textmate-with-secret-rubinus-superpowers/' rel='bookmark' title='Permanent Link: Validate and Save your Ruby in TextMate &#8211; with secret Rubinus superpowers'>Validate and Save your Ruby in TextMate &#8211; with secret Rubinus superpowers</a> <small>In some TextMate bundles, if you save a file it...</small></li><li><a href='http://drnicwilliams.com/2008/12/11/future-proofing-your-ruby-code/' rel='bookmark' title='Permanent Link: Future proofing your Ruby code. Ruby 1.9.1 is coming.'>Future proofing your Ruby code. Ruby 1.9.1 is coming.</a> <small> Bugger. I&#8217;m a Ruby monogamist. I use the Ruby...</small></li><li><a href='http://drnicwilliams.com/2008/07/04/unit-testing-iphone-apps-with-ruby-rbiphonetest/' rel='bookmark' title='Permanent Link: Unit Testing iPhone apps with Ruby: rbiphonetest'>Unit Testing iPhone apps with Ruby: rbiphonetest</a> <small> Everything to love about Ruby: the concise, powerful language;...</small></li></ol>]]></description>
			<content:encoded><![CDATA[<p>I wrote Composite Primary Keys and Dr Nic&#8217;s Magic Models because we have a 50+ table legacy database and I am terrorised by explicit SQL statements on a daily basis. <span class="pullquote">I have a dirty secret &#8211; I don&#8217;t use either of them</span> at work. We&#8217;ve been unsuccessful installing Ruby on our HP-UX box, then time passed, life moved on for the people involved, and so no Ruby. Ergo, SQL hell for Nicholas.</p>
<p>Until today. No, we still don&#8217;t have Ruby installed on our HP box, but I do have it installed everywhere else in my life. So I guess I can still access the database remotely&#8230; that&#8217;s what the TCP/IP internet protocol is for&#8230; and for executing shell commands why not remote shell into the box?</p>
<p>Let&#8217;s skip over why I never thought of either of these until now. Its bad for my ego. The upside of this minor revelation is that the Composite Primary Keys project will have Oracle support soon.</p>
<h3>Remote Shell</h3>
<p>The point of this article though is to discuss the wonders of using remote ssh (aka remote shell) to invoke shell commands via ruby without having ruby installed locally. </p>
<p>I made it work, it rocks and <span class="pullquote">I shall briefly sing the praises for Jamis Buck</span>. Jamis, you rock. <code>net-ssh</code> is a lovely API for performing <a href="http://net-ssh.rubyforge.org/chapter-1.html">remote shell commands</a> all from ruby.  Here&#8217;s a demo of what I can do (excluding the setup code which is discussed later):</p>
<pre>
>> print shell.pwd.stdout
/home/senwilli
>> shell.cd 'demo'
=> #&lt;struct Net::SSH::Service::Shell::SyncShell::CommandOutput stdout="", stderr=nil, status=0&gt;
>> out = shell.ls '-lart'; print out.stdout
total 16
drwxr-xr-x   2 senwilli   sv              96 Sep 22 11:56 .
drwxr-xr-x   5 senwilli   sv            8192 Sep 22 11:56 ..
>> out = shell.send_command 'ls -lart'; print out.stdout
total 16
drwxr-xr-x   2 senwilli   sv              96 Sep 22 11:56 .
drwxr-xr-x   5 senwilli   sv            8192 Sep 22 11:56 ..
</pre>
<p>I&#8217;ve deliberately been inconsistent in the way I called the shell commands and how I handled the responses to show you some interesting things.</p>
<p><code>shell</code> is our shell object (which we&#8217;ll cover in a bit) and it has delightfully overridden <code>method_missing</code> so I can send it any old shell command I like. In the example above, I call the commands: <code>pwd</code>, <code>cd</code> and <code>ls</code> using this method. The first parameter is the arguments you&#8217;d like to pass to the command. An optional second parameter is for any <code>stdin</code> you&#8217;d like to pass to the process during its execution.</p>
<p>The last command is a duplicate of the previous command, showing that you can explicitly pass a complete shell expression string via the <code>send_command</code> method.</p>
<p>The result of all shell commands is a struct containing <code>stdout</code> and <code>stderr</code> strings. So, to return the response of the command to the user or logger, you&#8217;ll need to store the response object (as per the <code>out</code> variable above) and use <code>stdout?</code> to test if <code>stdout</code> has anything in it.</p>
<p>In the example above, all these commands are executedly being executed synchronously, so I&#8217;m getting the stdout/stderr results back before the next command is executed. This is due to the way I created the Shell object. So, let&#8217;s look at that.</p>
<h3>Creating your Shell object</h3>
<p>First you&#8217;ll need to install the following gems (from rubyforge.org) in this order: <code>needle</code>, <code>oepnssl</code>, and <code>net-ssh</code>.</p>
<p>In your ruby script/console:</p>
<pre>
require 'net/ssh'

session = Net::SSH.start( 'host', 'user', 'passwd' )
</pre>
<p>To create our <a href="http://net-ssh.rubyforge.org/chapter-5.html#s4">synchronous shell</a>:</p>
<pre>
shell = session.shell.sync
</pre>
<p>And you&#8217;re off and racing.</p>
<p>Jamis has provided lots of useful syntatic sugar (for example, you can pass Net::SSH.start a block with session as its argument, and reading all the <a href="http://net-ssh.rubyforge.org/chapter-2.html">docco</a> is a clever thing to do next.</p>
<h3>Using sudo?</h3>
<p>The only thing I couldn&#8217;t immediately figure out is how to invoke <code>sudo su - envname</code> and then continue to control my shell as per normal. All commands just blocked.</p>
<p>Luckily there is a <a href="http://net-ssh.rubyforge.org/chapter-1.html#s5">mailing list</a> for me to loiter in&#8230;</p>


<p>Related posts:<ol><li><a href='http://drnicwilliams.com/2010/06/01/validate-and-save-your-ruby-in-textmate-with-secret-rubinus-superpowers/' rel='bookmark' title='Permanent Link: Validate and Save your Ruby in TextMate &#8211; with secret Rubinus superpowers'>Validate and Save your Ruby in TextMate &#8211; with secret Rubinus superpowers</a> <small>In some TextMate bundles, if you save a file it...</small></li><li><a href='http://drnicwilliams.com/2008/12/11/future-proofing-your-ruby-code/' rel='bookmark' title='Permanent Link: Future proofing your Ruby code. Ruby 1.9.1 is coming.'>Future proofing your Ruby code. Ruby 1.9.1 is coming.</a> <small> Bugger. I&#8217;m a Ruby monogamist. I use the Ruby...</small></li><li><a href='http://drnicwilliams.com/2008/07/04/unit-testing-iphone-apps-with-ruby-rbiphonetest/' rel='bookmark' title='Permanent Link: Unit Testing iPhone apps with Ruby: rbiphonetest'>Unit Testing iPhone apps with Ruby: rbiphonetest</a> <small> Everything to love about Ruby: the concise, powerful language;...</small></li></ol></p>]]></content:encoded>
			<wfw:commentRss>http://drnicwilliams.com/2006/09/22/remote-shell-with-ruby/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>

