{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "##  Retrieving shell command output in IPython"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "This demonstration shows how to capture the outputs of Linux commands executed from the Jupyter notebook and store them as Python variables.\n",
    "\n",
    "We begin by getting the IP address of our host with a Linux command and assigning it to a Python variable. Next we explore the special SList type of the returned results. Then we show how to use one of the special attributes of the SList type to print a formatted directory listing returned by executing the system shell ls -al command.\n",
    "\n",
    "To execute a Linux command in a code cell we must preface the Linux command with the bang character, !. This tells the IPython REPL to route the command that comes after the '!' to the OS shell.\n",
    "\n",
    "For example, we can get the hostname of our platform as follows:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": false
   },
   "outputs": [],
   "source": [
    "!hostname"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Or if we want the full Internet address, we can execute the following:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": false
   },
   "outputs": [],
   "source": [
    "!hostname -I"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "To capture our host name as a Python variable is straightforward:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "host_name = !hostname\n",
    "host_name"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Note the type of the host_name variable returned is special. It is of type SList or to give it its full name IPython.utils.text.SList:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "type(host_name)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "We can ask for more details about the host_name object as follows:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": false
   },
   "outputs": [],
   "source": [
    "host_name?"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The following message appears in a separate window:\n",
    "\n",
    "```\n",
    "Type:        SList\n",
    "String form: ['plpynqz1']\n",
    "Length:      1\n",
    "File:        /usr/local/lib/python3.4/dist-packages/IPython/utils/text.py\n",
    "Docstring:  \n",
    "List derivative with a special access attributes.\n",
    "\n",
    "These are normal lists, but with the special attributes:\n",
    "\n",
    "* .l (or .list) : value as list (the list itself).\n",
    "* .n (or .nlstr): value as a string, joined on newlines.\n",
    "* .s (or .spstr): value as a string, joined on spaces.\n",
    "* .p (or .paths): list of path objects (requires path.py package)\n",
    "\n",
    "Any values which require transformations are computed only once and\n",
    "cached.\n",
    "```\n",
    "\n",
    "The key observation here is that the SList type is simply a\n",
    "> List derivative with special access attributes\n",
    "\n",
    "If we execute a shell command which returns multi-line output, type SList captures the output as a list of strings:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "dir_list = !ls -al\n",
    "dir_list"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "So to print dir_list, as a list of strings, separated by newlines, we can run the following:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "print(dir_list.n)"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python [Root]",
   "language": "python",
   "name": "Python [Root]"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.5.2"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 0
}
