Interestings
- Array.new(size, obj) vs Array.new(size) { block }
Array.new(size, obj) will duplicate the object, whereas Array.new with a block will call the block n times, resulting in different objects.
Array.new(size, obj) will duplicate the object, whereas Array.new with a block will call the block n times, resulting in different objects.
Update 07/18/2012: We have added tmux-vim autosaving support as a Vim plugin. It’s available here: https://github.com/pivotal/tmux-config
Update 07/20/2012: There is a lively discussion on Hacker News about this post in addition to the comments below.
tmux is the cool kid on the block for remote pair programming, as long as you are using a terminal based editor such as Vim or Emacs.
There is no shortage of tutorials and guides regarding how to use tmux, thus my only introduction to tmux will be this: tmux is a terminal multiplexer and supports shared terminal usage.
Our large software project used tmux regularly for remote pair programming and settled on a configuration that has worked well for our team. Read on to learn about tmux’s advantages and disadvantages vs. desktop screen sharing, why and how we used it, and how we addressed the many challenges of remote pairing using tmux.
ssh access you’re good to gossh access and thus possibly a VPNDue to network latency GUI-based desktop screen sharing was intolerably slow for coding. tmux made network latency a non issue. My personal experience was that tmux + Vim was so fast when working remotely that it was usually indistinguishable from coding locally.
We use two monitors: the iMac’s main 27″ monitor and a large (usually at least 24″) LCD rotated vertically.
We usually had iTerm running a shared tmux session on the large 27″ display and a desktop screen sharing session on the vertical display. The vertical display usually had the shared web browser visible since we were usually doing web development.

Most of our in-office developers only used tmux when remote pairing: the majority of their development was in-person pair programming using MacVim and “normal” tabbed iTerm. The occasional switch to terminal-based Vim within tmux and a bunch of tmux terminal panes was the most challenging aspect of using tmux as part of our development stack. The major difference were:
Read on to see how (or if) we addressed the above challenges.
Once you have automatic saving it’s tough to give it up. Our buffers automatically saved whenever MacVim lost focus. After quite a bit of work we were able to add automatic Vim saving support within tmux. It’s not as good as MacVim’s autosave, but it’s pretty close. Please see this Github pull request for how to set up automatic saving. (Note, I’ll update this post as the pull request progresses.)
Update 07/18/2012: Our tmux-vim automatic saving Vim plugin is available here: https://github.com/pivotal/tmux-config. We’ve also integrated it into our vim-config configuration here: https://github.com/pivotal/vim-config.
By default tmux has very little mouse support. We enabled significant mouse support within iTerm by customizing our .tmux.conf:
See this .tmux.conf template for more, but here’s the interesting section:
# ~/.tmux.conf
# Enable mouse support (works in iTerm)
set-window-option -g mode-mouse on
set-option -g mouse-select-pane on
set-option -g mouse-resize-pane on
set-option -g mouse-select-window on
Note that iTerm supports this configuration. We cannot vouch for Mac’s Terminal application’s level of mouse support.
Highlighting with the mouse triggers tmux’s text selection, which is not OS X’s highlighting, and thus ⌘+c will not copy the highlighted text. Though we never fully solved this issue there is a workaround: hold down the ⌥ key (ALT/Option) while highlighting to trigger OS X’s selection — ⌘+c will now copy the text.


Unfortunately this technique does not respect tmux’s panes and will select across the entire screen, but it’s better than nothing.
Why did MacVim and Vim have different keybindings if both use the ~/.vimrc file? The answer is the ⌘ key. To ease the transition from RubyMine and TextMate to MacVim we mapped many common ⌘-based keybinding which were unavailable in terminal-based Vim. My personal advice is to stay away from the ⌘ key if your team uses both MacVim and terminal Vim, but if that’s not possible at least make an extra <leader> KEY mapping for everything that uses ⌘.
Take a look at our sophisticated ~/.vimrc setup, including the keybindings file, where ⌘ bindings are paired with non- ⌘ keybindings.
There’s no way around this one. Though mouse support means one can avoid the tmux-pane selection and scrolling commands I highly recommend learning tmux well if you are using it consistently.
In practice we only use a handful of tmux commands often:
CTL+b % – new vertical splitCTL+b " – new horizontal splitCTL+b o – switch to other pane. Repeat to cycle through.CTL+b c – create new tmux tab/windowCTL+b n/p/l – switch to next, previous, or last tmux tab/windowsCTL+b [ – Enter scroll/copy modeHere are a couple of fun ones:
CTL+b SPACE – change arrangement of panes. Repeat to cycle through various arrangements.CTL+b w – list tmux tabs/windowsCTL+b , – rename tmux tab/windowOnce your team gets the hang of it they might even prefer the multiple tmux-pane workflow to a multi-app, multi-tab setup.
With such a plethora of remote pairing software and configurations it’s impossible to keep up. We would love to hear about your own experiences remote pairing with tmux and how you might improve upon our own techniques and configurations. Please post comments and let us know what you think.
Often we need to put certain devices on specific VLANs.
To do this, we need to know which port the device is connected to on the switch. However, in very mature and active wiring closets, it’s quite a challenge tracing cable from the patch panel to the switch port.
We have found that by using the MAC tools on our switch (knowing the MAC address of the device), we were able to determine the port the device was attached to without having to physically trace the cable.
This blog post is directed at:
We had to move an HP Color LaserJet CP5225dn printer to a separate VLAN. The cabling in the wiring closet was so tangled we couldn’t easily trace the cable from the patch panel to the switch.
We needed to determine the MAC addresses of the printers.
class Movie < ActiveRecord::Base has_one :player, :as => :content end class Player < ActiveRecord::Base belongs_to :content, :polymorphic => true end
and then, later we refactor Movie to use STI with Product…
class Product < ActiveRecord::Base ... end class Movie < Product ... end > movie = Movie.first > movie.player Player Load (1.1ms) SELECT "players".* FROM "players" WHERE "players"."content_id" = 144 AND "players"."content_type" = 'Product' LIMIT 1 => nil
because players.content_type == ‘Movie’ but polymorphism uses the base class, ‘Product’
Fix: Add a migration to change the content_type column
UPDATE players SET content_type=’Product’ WHERE content_type=’Movie’
I recently blogged about about integrating remote developers with large development teams. An important but finicky part of bridging the gap between remote developers and the rest of the team is video conferencing.
How hard can this be? It’s Skype, right? While most techies know how to use Skype to make video calls, the difficulty is managing headsets, external microphones, external speakers, and switching between all of these frequently throughout the day. Despite what Apple might tell you, it does not “just work”, especially Skype, which has a particularly baffling user interface.
Early in our large project’s history the following scene played out frequently:
Actually, it’s mostly about the audio: the video usually works fine. We needed a means to easily switch between pairing-mode and group-conversation-mode — that is, between headphones + mic and external speakers + external mic. Above all else we wanted to avoid constantly changing software preferences. We needed something as easy as pressing a button or plugging/unplugging a single jack.
So far we have found two solutions that work well:
Read on for more details.
This solution relies upon a high quality external USB mic for both pairing and group conversations. Personally this worked fine for me — the background noise in the office was actually useful, not overwhelming, and I enjoyed hearing bits of the conversations going on in the office. Others might find the background noise annoying.
Connect a high quality external mic (such as a Blue Snowball) and external speakers to the Skype machine. The speakers must have an external headphone jack.

Configure the Mac and Skype to use the Snowball mic


When pair programming: plug your headphones of choice into headphone jack on speakers

For group conversations: unplug headphones. Voilà! Speakers will be live.

That’s it! Toggling between pairing and group conversations is as easy as unplugging the headphones.
For a normal remote pairing scenario the computer’s audio priorities should be as follows:
Managing this audio setup would be as easy as plugging and unplugging your USB headset. When pairing with a remote developer, plug in the headset for a quiet, private pairing experience. When a group of people arrives at your desk and need to speak with both you and the remote developer, simply unplug the headset to activate the external hardware. When the group conversation is over, plug the headset back in.
Simple. Intuitive. Low-overhead.
Unfortunately, your computer doesn’t know about these priorities. Also, Skype has its own audio input/output settings independent from the computer’s OS-controlled settings.
Luckily both the Mac OS and Skype are “trainable” and will respect the above priorities if you know how to teach them. Note that Skype takes a “hint” from your Mac on how to switch inputs and outputs. Thus, we must train them both at the same time. Here’s how:
Open both the Mac Sound System Preferences and Skype’s Audio/Video preferences. No external Audio devices should be detected.
(Click for a larger image)
Plug in the external mic. Once it is detected by both the Mac and Skype select the mic in both Mac and Skype preferences.
(Click for a larger image)
Before continuing, Close, then reopen the Skype Audio/Video preferences. You know, just to make sure it sticks.
Plug in your USB headset. Once it is detected by both the Mac and Skype select the headset in both Mac and Skype preferences.
(Click for a larger image)
Close, then reopen the Skype Audio/Video preferences. Is this needed? I don’t know… maybe. It’s Skype.
Test the configuration: Unplug your USB Headset. Skype and your Mac should automatically switch to using the external mic. Plug the USB headset in again. Skype and your Mac should automatically switch to using the USB headset again.
(Click for a larger image)
If it didn’t work, unplug everything, quit System Preferences and Skype, and start over.
Overall this is my preferred audio setup, though it takes a couple of minutes to set up and can be confusing the first time. But, once it’s set up, the configuration is usually solid and you rarely have to touch it again. Also, unlike the headphones-jacked-into-speakers technique, the headset mic is fully utilized for the best audio quality. You can also plug external speakers into the computer’s headphone jack without confusing the computer or Skype.
Do you use a cool A/V setup? Tell us about it! We love to try new things. We’re still on a quest to find the best iPad-based A/V configuration. With any luck we’ll report back on that soon.
Does anyone know why maintenance mode doesn’t seem to work? Is there any way to check from the command line that we are in maintenance mode?
– (Ken) This is how I test it on heroku_san: https://github.com/fastestforward/heroku_san/blob/master/features/step_definitions/remote_steps.rb#L130
Anyone had to send a fax from Ruby/Rails? Any good SaaS you used to do it?
Dumb workaround:
def intelligent_crop
crop_to = model.crop_to
# crop_to = [left_x, top_y, width, height]
manipulate! do |img|
# guard against the second time intelligent_crop is called
if (img.columns != crop_to[2] || img.rows != crop_to[3])
img.crop!(*model.crop_to)
end
img
end
end
version :cropped_preview do
process :intelligent_crop
end
No one seems to have heard of this particular bug, unfortunately.
What is the best soft-delete gem to help you not actually delete records?
acts_as_soft_delete_by_field was recommended, however rolling your own is probably also a very reasonable idea: this is pretty closely tied to your business logic.
…because it fails if the boolean is set to false. Use
validates_inclusion_of :boolean_field, in: [true, false], allow_nil: false
instead.
Announcing Cedar target templates for Xcode 4.3.x: Getting started with Cedar has never been easier!
These templates let you quickly add Cedar targets to your iOS or Mac OS X project. It’s super simple to build and install from source now:
git clone http://github.com/pivotal/cedar --recursive && cd cedar ; rake install
If you don’t like building from source, you can also install a build of the Cedar templates from the downloads page – just untar to your home directory.
Restart Xcode after installing, open your project and add a new target. You’ll find targets for both iOS and Mac OS X. There are 2 types of targets: Suites and Bundles. A Suite target will build your tests as a separate application which you then run to execute your tests. Bundle targets work just like OCUnit testing bundles, providing closer integration with Xcode. If you do create a bundle target, make sure to edit the scheme of your application and add the new target to the list of tests.
Every template comes with a simple example which should run out of the box to help you get running.
Automatic Reference Counting setting: Don’t use it for your spec targets. Your application is free to use ARC, just don’t use it for any Cedar targets. This is because there is a flaw in the compiler that ships with Xcode (see here for the details, and if you care please feel free to use this information to file a bug with apple).
We really hope these changes help you to get started writing specs and spending less time setting up Cedar. If you have any feedback, whether it’s about these templates or something else about Cedar, please feel welcome stop by the discussion group and share your thoughts.
(Update 07/17/2012: Added link to Pair Programming Matrix Google Doc)
At Pivotal Labs we consider ourselves to be expert pair programmers, but sometimes even we need help. We identified (thanks to a retrospective) that we were being very unbalanced in our pairings: some developers seemed to pair with each other often while rarely paring with others. We wanted a lightweight means of enforcing balanced pairing. That’s when someone remembered the pairing matrix.
A blog post titled “Pair Programming Matrix” inspired us to try our own pairing matrix. It’s a grid with a cell intersecting each pair of developers. Here’s a photo from the original article:
We thought we would give it a try, only using a Google Spreadsheet with some fancy conditional formatting instead of a whiteboard
Overall the pairing matrix serves it purpose: it helps us have much more balanced pairings. We’ve been using it for several months and will likely continue using it so long as it seems useful.
It strikes me that a pairing matrix would be a good way for team new to pair programming to add a bit of helpful structure. I would hesitate to add this structure if it’s unneeded: “if it ain’t broke, don’t fix it.”
Here are some screenshots of pairing matrices at different stages. Team structures changed and thus the featured developers were not always the same, but you get the idea.





By popular demand, I have made a blank, read-only copy of our pairing matrix, complete with conditional formatting. Feel free to duplicate it and modify the copy. Please post your own modifications and optimizations in the comments.
I’m obsessed with remote pair programming and remote collaboration. I’ve even given tech talks about remote pair programming. Most teams with which I’ve worked remotely are small — usually around four to six team members total — but for the past 10 months I have remote paired on a project of up to 30 developers. While the majority of the team was co-located in our NYC office, five of us were remote. Over that time we have tried many different remote collaboration and pairing setups and feel we’ve settled on a configuration that supports daily pair rotation with minimum overhead.
We set up a team Skype account and paid for Skype group video. Each morning the team would gather for standup in a large conference room and call us from the group video account.

It can be difficult for the remote members to hear everyone in such a large room. We used a Blue Snowball mic to aid with this, and it worked well so long as nobody unplugged it.
We had a team whiteboard where we would list technical tips, tricks, and cries for help. Every day someone would send the group a photo of the board. I’m sure we could have come up with a more technical solution but this has worked well for us, though it does take some extra effort.

If remote team members had items for the standup board they would simply speak up towards the end of the meeting; a scribe was taking notes and emailed them to everyone afterwards.
We settled on having dedicated remote pairing workstations in the NYC office, one for each remote developer. This is a departure from the norm. At Pivotal we swich pairing stations frequently and nobody (or everybody) “owns” a particular machine. For practical reasons the remote person really needed to own a single station to make remote pairing as efficient as possible.
Remote pair programming often requires a bit of setup: configuring Screen Sharing, setting up tmux, launching and logging in to Skype, etc. With dedicated remote pairing stations this setup can be done once early in the project and (usually) left alone. Time spent on this overhead is minimized, and pairing could start immediately.
At Pivotal Labs, our offices have an open floor plan. To find someone you need only stand up and look around for them. But what about when you need to talk to Joe-in-Atlanta? Who’s he pairing with today?
A dedicated workstation for each remote developer becomes their virtual presence in the office. Everyone on the team knows where to find Joe-in-Atlanta. This is important not only for other developers, but also for product manager, project managers, designers — the entire team. My station was called “Little Atlanta” and we referenced it often in conversations: “Joe, I need to talk to you after standup today. I’ll meet you at Little Atlanta in a few minutes.”
Occasionally two remote developers would remote pair for the day. What did we do then? We usually chose one of our dedicated NYC office stations and paired through that machine rather than our local (that is, home) machines. Why? Just as if we were physically in the office we wanted other developers to be able to see what we were doing and help us if needed.
We made ourselves available by setting up a group Skype call between ourselves and the workstation “Skype laptop” and letting everyone know where we could be found. This worked very well. Using this video conference we could ask for help and team members could seek us out as well.

We’d like to do happy path end-end testing for an iOS project. What’s the state of the art?
We saw frank: https://github.com/moredip/Frank
If you want your ruby to read like bash:
if true then
puts "For Sure"
end