Compare commits

...

31 Commits

Author SHA1 Message Date
John Bintz
bb85ff7641 ensure layout editing is allowed outside of tmux sessions 2012-03-06 14:25:03 -05:00
Rémi Prévost
9ad83268ee Use yard/rspec Rake tasks 2012-03-05 16:05:21 -05:00
Rémi Prévost
b083bddeeb Bump version to 0.3.2 2012-03-05 14:22:21 -05:00
Rémi Prévost
ab51679e33 Set a TEAMOCIL environment variable on all splits 2012-03-05 14:22:10 -05:00
Rémi Prévost
22e4bc1d43 Use separate files for Teamocil::Layout subclasses 2012-03-03 13:38:53 -05:00
Rémi Prévost
b6acecae20 Add new task to TODO list 2012-02-24 10:16:29 -05:00
Rémi Prévost
50f3580b96 Update copyright notice 2012-02-07 10:31:27 -05:00
Rémi Prévost
30ac196713 Update README with --list option 2012-01-25 20:52:34 -05:00
Rémi Prévost
60ccf7f035 Bump to version 0.3.1 2012-01-21 14:13:07 -05:00
Rémi Prévost
6390d0d7ed Fix encoding header in gemspec file 2012-01-21 14:10:58 -05:00
Rémi Prévost
048daa65a9 Update teamocil in Gemfile.lock 2012-01-21 14:09:41 -05:00
Rémi Prévost
7deae7eff7 Bump version to 0.3 2012-01-21 14:08:51 -05:00
Rémi Prévost
124bdb1961 Add --list option to CLI class 2012-01-21 14:08:01 -05:00
Rémi Prévost
490df3bd99 Use STDERR to output error messages 2012-01-21 14:05:18 -05:00
Rémi Prévost
a43064e439 Add spec for CLI 2012-01-21 13:47:44 -05:00
Rémi Prévost
192281392b Add Travis build status in README 2011-12-26 16:32:05 -05:00
Rémi Prévost
d053706ce6 Add custom Travis command 2011-12-26 16:22:43 -05:00
Rémi Prévost
b44303b80d Add Travis configuration file 2011-12-26 16:20:15 -05:00
Rémi Prévost
4a6abd75a8 Update README.md with GitHub-flavored Markdown syntax highlighting 2011-12-10 08:11:36 -05:00
Rémi Prévost
11af9bfe85 Merge pull request #8 from hollow/master
Fix typo in --layout handling
2011-11-18 05:42:55 -08:00
Benedikt Böhm
dbc1fc55d7 fix typo 2011-11-18 14:17:23 +01:00
Rémi Prévost
51f79bcc1e Bump to 0.2.2 2011-10-26 05:21:53 -04:00
Rémi Prévost
0068baf3cb Fix issue with index variable hoisting 2011-10-26 05:21:07 -04:00
Rémi Prévost
2a2fc58063 Refactor Window#initialize filters and options 2011-10-24 07:43:37 -04:00
Rémi Prévost
7288d0ab57 Add “pkg” to .gitignore 2011-10-23 21:42:42 -04:00
Rémi Prévost
75283ac21f Bump to 0.2.1 2011-10-23 21:41:34 -04:00
Rémi Prévost
459b971a6a Fix bug with split target 2011-10-23 21:41:06 -04:00
Rémi Prévost
68d07cd897 Add a case to check session handling 2011-10-23 20:42:48 -04:00
Rémi Prévost
f2926471bd Update the todo list 2011-10-23 20:15:54 -04:00
Rémi Prévost
cbed2f3e5b Add more specs, yeah! 2011-10-23 20:10:16 -04:00
Rémi Prévost
e4e9f2d1cd Upgrade teamocil in Gemfile 2011-10-23 19:58:40 -04:00
22 changed files with 466 additions and 240 deletions

1
.gitignore vendored
View File

@ -3,3 +3,4 @@
.local*
.yardoc
doc
pkg

2
.travis.yml Normal file
View File

@ -0,0 +1,2 @@
rvm: 1.9.2
script: "bundle exec rake spec"

View File

@ -1,13 +0,0 @@
--title "Teamocil"
--no-cache
--protected
--no-private
--markup "markdown"
--markup-provider "maruku"
--format html
"README.mkd"
"lib/**/*.rb"

View File

@ -1,7 +1,7 @@
PATH
remote: .
specs:
teamocil (0.1.11)
teamocil (0.3.2)
GEM
remote: http://rubygems.org/
@ -19,7 +19,7 @@ GEM
diff-lcs (~> 1.1.2)
rspec-mocks (2.6.0)
syntax (1.0.0)
yard (0.7.2)
yard (0.7.5)
PLATFORMS
ruby

View File

@ -1,3 +1,3 @@
Copyright 2011 Rémi Prévost.
Copyright 2011-2012 Rémi Prévost.
You may use this work without restrictions, as long as this notice is included.
The work is provided "as is" without warranty of any kind, neither express nor implied.

157
README.md
View File

@ -2,19 +2,24 @@
Teamocil is a simple tool used to automatically create sessions, windows and splits in [tmux](http://tmux.sourceforge.net/) with YAML files.
[![Build Status](https://secure.travis-ci.org/remiprev/teamocil.png)](http://travis-ci.org/remiprev/teamocil)
## Usage
$ gem install teamocil
$ mkdir ~/.teamocil
$ teamocil --edit sample
$ tmux
$ teamocil sample
```bash
$ gem install teamocil
$ mkdir ~/.teamocil
$ teamocil --edit sample
$ tmux
$ teamocil sample
```
## Options
* `--here` opens the session in the current window, it doesnt create an empty first window.
* `--layout` takes a custom file path to a YAML layout file.
* `--edit` opens the layout file (whether or not `--layout` is used) with `$EDITOR`.
* `--list` lists all available layouts.
## Layout file structure
@ -30,10 +35,12 @@ You can wrap your entire layout file in a `session` and Teamocil will rename the
#### Example
session:
name: my-awesome-session
windows:
[windows list]
```yaml
session:
name: "my-awesome-session"
windows:
[windows list]
```
### Windows
@ -49,27 +56,27 @@ If you are not using a top-level `session` key, then the first key of your layou
#### Example
windows:
- name: my-first-window
options:
synchronize-panes: true
root: ~/Projects/foo-www
filters:
before:
- "echo 'Lets use ruby-1.9.2 for each split in this window.'"
- "rvm use 1.9.2"
splits:
[splits list]
- name: my-second-window
root: ~/Projects/foo-api
filters:
after: "rvm use 1.9.2"
splits:
[splits list]
- name: my-third-window
root: ~/Projects/foo-daemons
splits:
[splits list]
```yaml
windows:
- name: "my-first-window"
options:
synchronize-panes: true
root: "~/Projects/foo-www"
filters:
before:
- "echo 'Lets use ruby-1.9.2 for each split in this window.'"
- "rvm use 1.9.2"
splits:
[splits list]
- name: "my-second-window"
root: "~/Projects/foo-api"
splits:
[splits list]
- name: "my-third-window"
root: "~/Projects/foo-daemons"
splits:
[splits list]
```
### Splits
@ -84,20 +91,22 @@ Every window must define an array of splits that will be created within it. A ve
#### Example
windows:
- name: my-first-window
root: ~/Projects/foo-www
filters:
before: "rvm use 1.9.2"
after: "echo 'I am done initializing this split.'"
splits:
- cmd: "git status"
- cmd: "bundle exec rails server --port 4000"
width: 50
- cmd:
- sudo service memcached start
- sudo service mongodb start
height: 50
```yaml
windows:
- name: "my-first-window"
root: "~/Projects/foo-www"
filters:
before: "rvm use 1.9.2"
after: "echo 'I am done initializing this split.'"
splits:
- cmd: "git status"
- cmd: "bundle exec rails server --port 4000"
width: 50
- cmd:
- "sudo service memcached start"
- "sudo service mongodb start"
height: 50
```
## Layout examples
@ -107,15 +116,16 @@ See more example files in the `examples` directory.
#### Content of `~/.teamocil/sample-1.yml`
windows:
- name: sample-two-splits
root: ~/Code/sample/www
splits:
- cmd:
- pwd
- ls -la
- cmd: rails server --port 3000
width: 50
```yaml
windows:
- name: "sample-two-splits"
root: "~/Code/sample/www"
splits:
- cmd: ["pwd", "ls -la"]
- cmd: "rails server --port 3000"
width: 50
```
#### Result of `$ teamocil sample-1`
@ -135,19 +145,21 @@ See more example files in the `examples` directory.
#### Content of `~/.teamocil/sample-2.yml`
windows:
- name: sample-four-splits
root: ~/Code/sample/www
splits:
- cmd: pwd
- cmd: pwd
width: 50
- cmd: pwd
height: 50
target: bottom-right
- cmd: pwd
height: 50
target: bottom-left
```yaml
windows:
- name: "sample-four-splits"
root: "~/Code/sample/www"
splits:
- cmd: "pwd"
- cmd: "pwd"
width: 50
- cmd: "pwd"
height: 50
target: "bottom-right"
- cmd: "pwd"
height: 50
target: "bottom-left"
```
#### Result of `$ teamocil sample-2`
@ -169,13 +181,14 @@ See more example files in the `examples` directory.
To get autocompletion when typing `teamocil <Tab>` in a zsh session, add this line to your `~/.zshrc` file:
compctl -g '~/.teamocil/*(:t:r)' teamocil
```zsh
compctl -g '~/.teamocil/*(:t:r)' teamocil
```
## Todo list
* Support tmux options for windows and splits (eg. `synchronize-panes`)
* Making sure the layout is valid before executing it
* Refactor the `Layout` class to make it “test-friendly”
* Making sure the layout is valid before executing it (ie. throw exceptions).
* Add more specs.
## Contributors
@ -184,6 +197,8 @@ Feel free to contribute and submit issues/pull requests [on GitHub](https://gith
* Samuel Garneau ([garno](https://github.com/garno))
* Jimmy Bourassa ([jbourassa](https://github.com/jbourassa))
Take a look at the `spec` folder before you do, and make sure `bundle exec rake spec` passes after your modifications :)
## License
Teamocil is © 2011 [Rémi Prévost](http://exomel.com) and may be freely distributed under the [LITL license](http://litl.info/). See the `LICENSE` file.
Teamocil is © 2011-2012 [Rémi Prévost](http://exomel.com) and may be freely distributed under the [LITL license](http://litl.info/). See the `LICENSE` file.

View File

@ -1,11 +1,28 @@
require "bundler"
Bundler.require(:development)
require "bundler/gem_tasks"
require "rspec/core/rake_task"
desc "Run specs"
task :spec do # {{{
sh "bundle exec rspec --color --format=nested #{Dir.glob(File.join(File.dirname(__FILE__), "spec/**/*_spec.rb")).join(" ")}"
task :default => :spec
desc "Run all specs"
RSpec::Core::RakeTask.new(:spec) do |task| # {{{
task.pattern = "spec/**/*_spec.rb"
task.rspec_opts = "--colour --format=documentation"
end # }}}
desc "Generate documentation"
task :doc do # {{{
sh "bundle exec yard doc"
desc "Generate YARD Documentation"
YARD::Rake::YardocTask.new do |task| # {{{
task.options = [
"-o", File.expand_path("../doc", __FILE__),
"--readme=README.md",
"--markup=markdown",
"--markup-provider=maruku",
"--no-private",
"--no-cache",
"--protected",
"--title=Teamocil",
]
task.files = ["lib/**/*.rb"]
end # }}}

View File

@ -1,5 +1,5 @@
module Teamocil
VERSION = "0.2"
VERSION = "0.3.2"
autoload :Layout, "teamocil/layout"
autoload :CLI, "teamocil/cli"
end

View File

@ -5,34 +5,44 @@ module Teamocil
# This class handles interaction with the `tmux` utility.
class CLI
attr_accessor :layout, :layouts
# Initialize a new run of `tmux`
#
# @param argv [Hash] the command line parameters hash (usually `ARGV`).
# @param env [Hash] the environment variables hash (usually `ENV`).
def initialize(argv, env) # {{{
bail "You must be in a tmux session to use teamocil" unless env["TMUX"]
parse_options! argv
layout_path = File.join("#{env["HOME"]}", ".teamocil")
if @options.include?(:list)
@layouts = get_layouts(layout_path)
return print_layouts
end
parse_options!
if @options.include?(:layout)
file = options[:layout]
file = @options[:layout]
else
file = ::File.join("#{env["HOME"]}/.teamocil", "#{argv[0]}.yml")
file = ::File.join(layout_path, "#{argv[0]}.yml")
end
if @options[:edit]
::FileUtils.touch file unless File.exists?(file)
system("$EDITOR \"#{file}\"")
Kernel.system("$EDITOR \"#{file}\"")
else
bail "There is no file \"#{file}\"" unless File.exists?(file)
bail "You must be in a tmux session to use teamocil" unless env["TMUX"]
parsed_layout = YAML.load_file(file)
layout = Teamocil::Layout.new(parsed_layout, @options)
layout.compile!
layout.execute_commands(layout.generate_commands)
@layout = Teamocil::Layout.new(parsed_layout, @options)
@layout.compile!
@layout.execute_commands(@layout.generate_commands)
end
end # }}}
# Parse the command line options
def parse_options! # {{{
def parse_options!(args) # {{{
@options = {}
opts = ::OptionParser.new do |opts|
opts.banner = "Usage: teamocil [options] <layout>
@ -47,19 +57,36 @@ module Teamocil
@options[:edit] = true
end
opts.on("--layout [LAYOUT]", "Use a specific layout file, instead of ~/.teamocil/<layout>.yml") do |layout|
opts.on("--layout [LAYOUT]", "Use a specific layout file, instead of `~/.teamocil/<layout>.yml`") do |layout|
@options[:layout] = layout
end
opts.on("--list", "List all available layouts in `~/.teamocil/`") do
@options[:list] = true
end
end
opts.parse!
opts.parse! args
end # }}}
# Return an array of available layouts
#
# @param path [String] the path used to look for layouts
def get_layouts(path) # {{{
Dir.glob(File.join(path, "*.yml")).map { |file| File.basename(file).gsub(/\..+$/, "") }.sort
end # }}}
# Print each layout on a single line
def print_layouts # {{{
STDOUT.puts @layouts.join("\n")
exit 0
end # }}}
# Print an error message and exit the utility
#
# @param msg [Mixed] something to print before exiting.
def bail(msg) # {{{
puts "[teamocil] #{msg}"
STDERR.puts "[teamocil] #{msg}"
exit 1
end # }}}

View File

@ -2,135 +2,11 @@ module Teamocil
# This class act as a wrapper around a tmux YAML layout file
class Layout
autoload :Session, "teamocil/layout/session"
autoload :Window, "teamocil/layout/window"
autoload :Split, "teamocil/layout/split"
# This class represents a session within tmux
class Session
attr_reader :options, :windows, :name
# Initialize a new tmux session
#
# @param options [Hash] the options, mostly passed by the CLI
# @param attrs [Hash] the session data from the layout file
def initialize(options, attrs={}) # {{{
@name = attrs["name"]
@windows = attrs["windows"].each_with_index.map { |window, index| Window.new(self, index, window) }
@options = options
end # }}}
# Generate commands to send to tmux
#
# @return [Array]
def generate_commands # {{{
commands = []
commands << "tmux rename-session \"#{@name}\"" unless @name.nil?
commands << @windows.map(&:generate_commands)
commands << "tmux select-pane -t 0"
commands
end # }}}
end
# This class represents a window within tmux
class Window
attr_reader :filters, :root, :splits, :options, :index, :name
# Initialize a new tmux window
#
# @param session [Session] the session where the window is initialized
# @param index [Fixnnum] the window index
# @param attrs [Hash] the window data from the layout file
def initialize(session, index, attrs={}) # {{{
@name = attrs["name"]
@root = attrs["root"]
@options = attrs["options"]
@filters = attrs["filters"]
@splits = attrs["splits"].each_with_index.map { |split, index| Split.new(self, index, split) }
@index = index
@session = session
@options ||= {}
@filters ||= {}
@filters["before"] ||= []
@filters["after"] ||= []
end # }}}
# Generate commands to send to tmux
#
# @return [Array]
def generate_commands # {{{
commands = []
if @session.options.include?(:here) and @index == 0
commands << "tmux rename-window \"#{@name}\""
else
commands << "tmux new-window -n \"#{@name}\""
end
commands << @splits.map(&:generate_commands)
@options.each_pair do |option, value|
value = "on" if value === true
value = "off" if value === false
commands << "tmux set-window-option #{option} #{value}"
end
commands
end # }}}
end
# This class represents a split within a tmux window
class Split
attr_reader :width, :height, :cmd, :index, :target
# Initialize a new tmux split
#
# @param session [Session] the window where the split is initialized
# @param index [Fixnnum] the split index
# @param attrs [Hash] the split data from the layout file
def initialize(window, index, attrs={}) # {{{
@height = attrs["height"]
@width = attrs["width"]
@cmd = attrs["cmd"]
@target = attrs["target"]
@window = window
@index = index
end # }}}
# Generate commands to send to tmux
#
# @return [Array]
def generate_commands # {{{
commands = []
# Is it a vertical or horizontal split?
unless @index == 0
if !@width.nil?
commands << "tmux split-window -h -p #{@width}"
elsif !@height.nil?
commands << "tmux split-window -p #{@height}"
else
commands << "tmux split-window"
end
commands << " -t #{@target}" unless @target.nil?
end
# Wrap all commands around filters
@cmd = [@window.filters["before"]] + [@cmd] + [@window.filters["after"]]
# If a `root` key exist, start each split in this directory
@cmd.unshift "cd \"#{@window.root}\"" unless @window.root.nil?
# Execute each split command
@cmd.flatten.compact.each do |command|
commands << "tmux send-keys -t #{@index} \"#{command}\""
commands << "tmux send-keys -t #{@index} Enter"
end
commands
end # }}}
end
attr_reader :session
# Initialize a new layout from a hash
#

View File

@ -0,0 +1,31 @@
module Teamocil
class Layout
# This class represents a session within tmux
class Session
attr_reader :options, :windows, :name
# Initialize a new tmux session
#
# @param options [Hash] the options, mostly passed by the CLI
# @param attrs [Hash] the session data from the layout file
def initialize(options, attrs={}) # {{{
@name = attrs["name"]
@windows = attrs["windows"].each_with_index.map { |window, window_index| Window.new(self, window_index, window) }
@options = options
end # }}}
# Generate commands to send to tmux
#
# @return [Array]
def generate_commands # {{{
commands = []
commands << "tmux rename-session \"#{@name}\"" unless @name.nil?
commands << @windows.map(&:generate_commands)
commands << "tmux select-pane -t 0"
commands
end # }}}
end
end
end

View File

@ -0,0 +1,64 @@
module Teamocil
class Layout
# This class represents a split within a tmux window
class Split
attr_reader :width, :height, :cmd, :index, :target
# Initialize a new tmux split
#
# @param session [Session] the window where the split is initialized
# @param index [Fixnnum] the split index
# @param attrs [Hash] the split data from the layout file
def initialize(window, index, attrs={}) # {{{
@height = attrs["height"]
@width = attrs["width"]
@cmd = attrs["cmd"]
@target = attrs["target"]
@window = window
@index = index
end # }}}
# Generate commands to send to tmux
#
# @return [Array]
def generate_commands # {{{
commands = []
# Is it a vertical or horizontal split?
init_command = ""
unless @index == 0
if !@width.nil?
init_command = "tmux split-window -h -p #{@width}"
elsif !@height.nil?
init_command = "tmux split-window -p #{@height}"
else
init_command = "tmux split-window"
end
init_command << " -t #{@target}" unless @target.nil?
commands << init_command
end
# Wrap all commands around filters
@cmd = [@window.filters["before"]] + [@cmd] + [@window.filters["after"]]
# If a `root` key exist, start each split in this directory
@cmd.unshift "cd \"#{@window.root}\"" unless @window.root.nil?
# Set the TEAMOCIL environment variable
@cmd.unshift "export TEAMOCIL=1"
# Execute each split command
@cmd.flatten.compact.each do |command|
commands << "tmux send-keys -t #{@index} \"#{command}\""
commands << "tmux send-keys -t #{@index} Enter"
end
commands
end # }}}
end
end
end

View File

@ -0,0 +1,55 @@
module Teamocil
class Layout
# This class represents a window within tmux
class Window
attr_reader :filters, :root, :splits, :options, :index, :name
# Initialize a new tmux window
#
# @param session [Session] the session where the window is initialized
# @param index [Fixnnum] the window index
# @param attrs [Hash] the window data from the layout file
def initialize(session, index, attrs={}) # {{{
@name = attrs["name"]
@root = attrs["root"]
@options = attrs["options"] || {}
@splits = attrs["splits"] || []
@splits = @splits.each_with_index.map { |split, split_index| Split.new(self, split_index, split) }
@filters = attrs["filters"] || {}
@filters["before"] ||= []
@filters["after"] ||= []
@index = index
@session = session
end # }}}
# Generate commands to send to tmux
#
# @return [Array]
def generate_commands # {{{
commands = []
if @session.options.include?(:here) and @index == 0
commands << "tmux rename-window \"#{@name}\""
else
commands << "tmux new-window -n \"#{@name}\""
end
commands << @splits.map(&:generate_commands)
@options.each_pair do |option, value|
value = "on" if value === true
value = "off" if value === false
commands << "tmux set-window-option #{option} #{value}"
end
commands
end # }}}
end
end
end

43
spec/cli_spec.rb Normal file
View File

@ -0,0 +1,43 @@
require File.join(File.dirname(__FILE__), "spec_helper.rb")
describe Teamocil::CLI do
context "executing" do
context "not in tmux" do
before do # {{{
@fake_env = { "TMUX" => 1, "HOME" => File.join(File.dirname(__FILE__), "fixtures") }
end # }}}
it "should allow editing" do # {{{
FileUtils.stub(:touch)
Kernel.should_receive(:system).with(any_args())
@cli = Teamocil::CLI.new(["--edit", "my-layout"], @fake_env)
end # }}}
end
context "in tmux" do
before do # {{{
@fake_env = { "TMUX" => 1, "HOME" => File.join(File.dirname(__FILE__), "fixtures") }
end # }}}
it "creates a layout" do # {{{
@cli = Teamocil::CLI.new(["sample"], @fake_env)
@cli.layout.session.name.should == "sample"
@cli.layout.session.windows.length.should == 2
@cli.layout.session.windows.first.name.should == "foo"
@cli.layout.session.windows.last.name.should == "bar"
end # }}}
it "lists available layouts" do # {{{
@cli = Teamocil::CLI.new(["--list"], @fake_env)
@cli.layouts.should == ["sample", "sample-2"]
end # }}}
end
end
end

10
spec/fixtures/.teamocil/sample-2.yml vendored Normal file
View File

@ -0,0 +1,10 @@
session:
name: sample-2
root: ~
windows:
- name: "foo"
splits:
- cmd: "pwd"
- name: "bar"
splits:
- cmd: "pwd"

10
spec/fixtures/.teamocil/sample.yml vendored Normal file
View File

@ -0,0 +1,10 @@
session:
name: sample
root: ~
windows:
- name: "foo"
splits:
- cmd: "pwd"
- name: "bar"
splits:
- cmd: "pwd"

View File

@ -13,6 +13,7 @@ two-windows:
- cmd:
- "echo 'bar'"
- "echo 'bar in an array'"
target: bottom-right
- cmd: "echo 'bar again'"
width: 50
@ -32,3 +33,11 @@ two-windows-with-filters:
- cmd: "echo 'foo'"
- cmd: "echo 'foo again'"
width: 50
three-windows-within-a-session:
session:
name: "my awesome session"
windows:
- name: "first window"
- name: "second window"
- name: "third window"

View File

@ -2,15 +2,19 @@ require File.join(File.dirname(__FILE__), "spec_helper.rb")
describe Teamocil::Layout do
context "initializing" do
end
context "compiling" do
before :each do # {{{
before do # {{{
@layout = Teamocil::Layout.new(layouts["two-windows"], {})
end # }}}
it "creates windows" do # {{{
session = @layout.compile!
session.windows.each do |window|
window.should be_an_instance_of Teamocil::Layout::Window
end
end # }}}
it "creates windows with names" do # {{{
session = @layout.compile!
session.windows[0].name.should == "foo"
@ -23,6 +27,13 @@ describe Teamocil::Layout do
session.windows[1].root.should == "/bar"
end # }}}
it "creates splits" do # {{{
session = @layout.compile!
session.windows.first.splits.each do |split|
split.should be_an_instance_of Teamocil::Layout::Split
end
end # }}}
it "creates splits with dimensions" do # {{{
session = @layout.compile!
session.windows.first.splits[0].width.should == nil
@ -57,5 +68,31 @@ describe Teamocil::Layout do
session.windows.first.filters["after"].last.should == "echo second after filter"
end # }}}
it "should handle blank filters" do # {{{
session = @layout.compile!
session.windows.first.filters.should have_key "after"
session.windows.first.filters.should have_key "before"
session.windows.first.filters["after"].should be_empty
session.windows.first.filters["before"].should be_empty
end # }}}
it "should handle splits without a target" do # {{{
session = @layout.compile!
session.windows.last.splits.last.target.should == nil
end # }}}
it "should handle splits with a target" do # {{{
session = @layout.compile!
session.windows.last.splits.first.target.should == "bottom-right"
end # }}}
it "should handle windows within a session" do # {{{
layout = Teamocil::Layout.new(layouts["three-windows-within-a-session"], {})
session = layout.compile!
session.windows.length.should == 3
session.name.should == "my awesome session"
end # }}}
end
end

20
spec/mock/cli.rb Normal file
View File

@ -0,0 +1,20 @@
module Teamocil
module Mock
module CLI
def self.included(base) # {{{
base.class_eval do
# Do not print anything
def print_layouts
# Nothing
end
end
end # }}}
end
end
end
Teamocil::CLI.send :include, Teamocil::Mock::CLI

20
spec/mock/layout.rb Normal file
View File

@ -0,0 +1,20 @@
module Teamocil
module Mock
module Layout
def self.included(base) # {{{
base.class_eval do
# Do not execute anything
def execute_commands(commands)
# Nothing
end
end
end # }}}
end
end
end
Teamocil::Layout.send :include, Teamocil::Mock::Layout

View File

@ -2,6 +2,8 @@ $:.unshift File.join(File.dirname(__FILE__), *%w[.. lib])
require 'yaml'
require 'teamocil'
require File.join(File.dirname(__FILE__), "./mock/layout.rb")
require File.join(File.dirname(__FILE__), "./mock/cli.rb")
module Helpers

View File

@ -1,4 +1,5 @@
# -*- encoding: utf-8 -*-
# encoding: utf-8
$:.push File.expand_path("../lib", __FILE__)
require "teamocil"
@ -24,5 +25,4 @@ spec = Gem::Specification.new do |s|
s.add_development_dependency "rspec"
s.add_development_dependency "yard"
s.add_development_dependency "maruku"
end