• Shortcuts : 'n' next unread feed - 'p' previous unread feed • Styles : 1 2

» Publishers, Monetize your RSS feeds with FeedShow:  More infos  (Show/Hide Ads)


Date: Friday, 10 May 2013 15:30

This article is heavily styled and is best viewed at PeepCode!

by Geoffrey Grosenbach

7 Strategies Video

7 Strategies Video

Troubleshooting is a skill that transcends programming languages, frameworks, and even time.

My first few years of professional programming were full of frustration. I would frequently run into problems and have no clue about how to solve them. I treated them as unexpected and unwanted interruptions.

Now I know that encountering and fixing problems is part of the developer’s job description. It’s a rare day that ends without unexpected behavior from code, a deployment, or another library.

But with the right plan, these unexpected events can be resolved quickly. Here’s the order of events we use regularly at PeepCode:

  • Gather data
  • Isolate the fault
  • Form a hypothesis
  • Read the documentation
  • Describe the problem
  • Read the code
  • Try another angle

Free poster!

Download this free poster, print it out, and hang it on your office wall for easy reference. Works on US Letter or A4. Also available in color.

7 Strategies Poster

7 Strategies Poster

Or watch our video for explanations and stories behind these troubleshooting strategies.

Start a PeepCode subscription for $200 or renew for $109! Full access to all videos and our iOS app. Or tell your employer to contact us for a business subscription quote.

Author: "--"
Send by mail Print  Save  Delicious 
New Memes   New window
Date: Sunday, 07 Apr 2013 13:50

This article is heavily styled and is best viewed at PeepCode!

by Geoffrey Grosenbach and Paula Lavalle

Wish granted! Use the following in your presentations, status updates, meme generators, or just for laughs!

Buy the full-length Play by Play or tell your boss to buy you a PeepCode Unlimited subscription for full access to all our videos and our iOS app.

COMPUTERING

Every day we’re computering.

Every day we’re computering.

Solo Computering

“This is how I program.”

“This is how I program.”

High Five!

High five.

High five.

Bingo!

Aww yeah!

Aww yeah!

That’s the word!

“That’s the word!”

“That’s the word!”

Cold Stare

Cold stare.

Cold stare.

Stand back!

Whoa!

Whoa!

Facepalm

So the reason is…

So the reason is…

What?

What? No. No.

What? No. No.

Watch the full-length Play by Play with Aaron Patterson and Corey Haines

Did you know…if you’ve ever had a PeepCode Unlimited subscription, you can renew now for only $109! Or tell your employer to contact us for a business subscription.

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 22 Mar 2013 10:16

This article is heavily styled and is best viewed at PeepCode!

by Geoffrey Grosenbach and Paula Lavalle

From the It Just Makes Sense department

Stream to your Apple TV! We’re watching Play by Play with Corey Haines and Aaron Patterson.

Stream to your Apple TV! We’re watching Play by Play with Corey Haines and Aaron Patterson.

As a bootstrapped company, it’s not always clear what the next step is, but an iOS app for viewing PeepCode videos has been one of the longest standing requests we’ve received. Which makes sense! It’s almost as if these devices were perfectly designed for watching PeepCode videos. The new iPhone 5 is the right dimensions for displaying HD video, which is what all our new videos have been filmed in since the end of last year (and some before that).

So we (finally) took the plunge and built an iOS app. We worked with expert iOS developer (and PeepCode author) Alex Vollmer of Radiant Capsule, and while he did most of the heavy lifting we certainly put in a lot of work and learned a lot along the way.

Solving the Progress Bar Problem

Download progress shows both percentage and remaining MB.

Download progress shows both percentage and remaining MB.

Desiging a good progress bar is famously difficult. Given that our audience is technical and speaks MB and GB, we settled on a great solution that works specifically for the content we’re delivering.

We decided to combine a standard progress bar with a numerical percentage. This works well for any videos under 100MB. But large videos might appear to be stalled if we can only show 100 points of progress. If a video is 500MB, it might take a minute or more to download 1/100th of it (5MB) and show progress.

So we also show you the number of MB remaining. This gives visual feedback that’s useful for videos larger than 100MB. The end result is that for any video you’ll download, progress is frequent and keeps you updated.

Delivering Instant Gratification

The UI shows progress in two steps.

The UI shows progress in two steps.

One of the things we find frustrating about video streaming applications is all the waiting.

Starting an HTTP video stream can involve an API call, requests for 2 metadata files, and another request for a media file…all before you see a single frame of video.

We wanted to improve on that by showing you some progress along the way. So you’ll see an initial spinner when you click the “Play” button on the cover. When the first API call has completed, you’ll be taken to the video player where the video will start to stream.

Splitting progress into two visual steps makes the application feel more responsive than it would if we just sent you directly to the video player where you would have to wait for 5 or 10 seconds. It’s part of the attention we’ve put into the UI of this application to make it enjoyable to use.

Note: Video streams start at low quality while the device figures out what bandwidth is available. If you have a good Internet connection, you’ll see better quality video after a few seconds. We’re working on adding full HD streams to videos, too.

The Value of a Flaky Development Server

It’s not easy to bootstrap a multimedia application that requires client, server, and media.

Due to misbehaving third-party libraries, our first implementation of a video streaming server would sometimes monopolize 100% of the server’s CPU and hang, or never return a response at all. This was bad news for the iOS client application since it couldn’t get the data it needed to start streaming a video.

Or was it? The early flakiness forced Alex to add more error checking code to the iOS client, and better error messages for the user. And it forced us to write the server code to look for timeouts or blank API responses. Overall, it made our code more robust.

Brother Baba Budan, Melbourne

Brother Baba Budan, Melbourne

And yes, we rewrote the server so it doesn’t use 100% CPU anymore. In fact, it’s been smooth sailing since the launch.

Keeping it Simple

We’ve launched version 1.0 with a simple but straightforward feature set: PeepCode Unlimited subscribers can download or stream any video we’ve published in the last two years. We’re starting with only PeepCode Unlimited subscribers so we can fine-tune our streaming infrastructure and determine what mirrors we need around the world for a top notch download and streaming experience. So far everything has been running very well.

Anyone with a PeepCode account of any kind can use the app to stream previews of current videos.

Interesting Features

  • The app will remember the playback time of each video you’ve watched. If you have iCloud, it will sync that across all your devices. So you can watch part of Play by Play with Aaron Patterson and Corey Haines on your iPhone, then resume watching on your iPad at the same time in the video.
  • We’ve done extensive testing, literally all around the world (Seattle, Melbourne, Kauai, San Francisco). We hope to add video streaming mirrors for an even better experience.
  • Stream to your AppleTV with AirPlay. Play by Play looks fantastic on an HDTV.
  • Smart download doesn’t drain your battery if you leave the app. It resumes when you’ve re-launched the app and are back in Wi-Fi range. (Our developer tested this by walking down the street until he was out of range).
  • Download full quality videos or stream up to half resolution. Our new HD videos look amazing on the iPhone 5!
  • We built a custom, self-contained Sinatra server for streaming video. This will make it easier for us to deploy extra streaming or download servers around the world or whenever needed.
  • A series of command line scripts together with remote APIs makes it a breeze to encode video for all the necessary formats and copy it to our servers.

Try it!

We’re proud of this application, our first shipping iOS application. For a 1.0, it covers most of what’s needed for a great mobile experience.

Possibly the best evidence of how useful this application is was how much we started using it in-house! On the bus, at home streamed to an Apple TV, or on a plane. The last three months of rigorous testing and refinement have been a lot of fun.

Try it out with any PeepCode account. Or upgrade to PeepCode Unlimited for full-length streaming!

Did you know…if you’ve ever had a PeepCode Unlimited subscription, you can renew now for only $109! Or tell your employer to contact us for a business subscription.

Watch on the iPad, too!

Watch on the iPad, too!

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 22 Mar 2013 10:16

This article is heavily styled and is best viewed at PeepCode!

by Geoffrey Grosenbach

Software developers are hard to find. Good ones are even harder.

We’re fortunate to have found one.

Jake Mitchell has degrees in Computer Science and Mathematics. He’s a polyglot programmer with experience in many languages and frameworks. Jake’s the kind of person who you’ll find implementing a TIFF image parser in CoffeeScript that renders to the HTML canvas. For fun.

Jake started working full time at PeepCode about a month ago and has already implemented some useful backend code and started on a new video series for us. If you’ve ever wanted to understand how cryptography works, you’ll want to keep an eye out for it.

You can follow Jake on Twitter here. Subscribe to PeepCode here.

Jamming at the Pioneer Valley Roller Derby in Massachusetts. Photo by Susan Farber

Jamming at the Pioneer Valley Roller Derby in Massachusetts. Photo by Susan Farber

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 02 Nov 2012 03:10

This article is heavily styled and is best viewed at PeepCode!

words Geoffrey Grosenbach

card design Paula Lavalle

Card front

While waiting in line to buy the original iPad, I gave someone my business card. He said it was an amazing card. In fact, it was the second best business card he had ever seen.

“Only the second best?” I asked. “What did the best one look like?”

“It was a plain looking card,” he said, “but if you sprinkled water on it for a week, it would grow grass in the shape of the company logo.”

I knew it was time to improve our game.

Refresh

Earlier this year we ran out of our old business cards. And PeepCode has grown since three years ago! We now have at least five people who need an awesome card to hand out at tech conferences, at nerd parties, and to random strangers.

We put our best designer on the job. We contracted Evolution Press for advice on paper, ink, foil, paint, and lead type.

Glossy black ink together with silver foil and white lettering make for a combination that can’t really be represented on screen.

Although it doesn’t contain any grass seeds (can you even take those through international customs?), we’re extremely happy with it.

We’ll be at Cascadia JS and other conferences in the next few months. Find us and ask for one!

Card edge

Card foil detail

Card glossy black ink detail

Author: "--"
Send by mail Print  Save  Delicious 
Date: Monday, 22 Oct 2012 14:48

This article is heavily styled and is best viewed at PeepCode!

The process of writing code is much different from the process of editing code. It’s easy to confuse the two since they both involve mashing buttons on a keyboard while staring at a computer screen.

Vim users know this already. Their editor works in two completely different ways depending on whether they are adding new words to a document or changing existing words.

They also know that there’s more to text editing than moving around with the arrow keys and selecting one letter at a time. But you don’t have to memorize hundreds of commands. I think only these six will handle most of the editing that you’ll do every day.

  • Delete whole words (before and after the cursor)
  • Create a newline and put the cursor there (above or below)
  • Search in a file
  • Switch files
  • Indent code automatically
  • Use completion

1. Delete Whole Words

Steve Yegge writes that it’s much faster to delete an entire word and retype it than it is to navigate to and correct a single letter (see his post on Effective Emacs).

There’s not much else to say here: learn to delete the word before the cursor and the word after the cursor. You’ll immediately find yourself using it constantly throughout the day.

This one is even built in to Mac OS X, so it works in any text editing application (Sublime Text, Pages, TextMate).

Mac OS X

Delete next word:

Delete previous word:

Vim

Delete next word:

Delete previous word:

Emacs (and Terminal)

Delete next word:

Delete previous word:

2. Add Lines

The novice learns to make a newline by moving the cursor to the end of the line and hitting the ENTER key. Or a newline above by moving the cursor up one line, to the end of that line, hitting ENTER, then indent…shouldn’t this be easier?

The Pro can add a newline above or below from any point in the line. You don’t have to move your cursor at all.

Textmate

Newline below

Vim

Newline below

Newline above

Sublime Text

Newline below

Newline above

Thanks to Joaquin Vicente

Search isn’t just for finding words. It’s an efficient way to navigate.

And live search is much faster than using a search dialog. Hit the hotkey and start typing the word. BAM! You’re there. It’s great for navigation instead of using the arrow keys to navigate within a file.

Emacs-style Ctrl-s is also available in TextMate.

Textmate

Live search

Vim

Live search

Hit n to repeat search.

Emacs

Search foward:

Search backward:

Sublime Text

Search forward:

Hit Cmd-i again to repeat search.

Programming happens in files, usually several. TextMate’s fuzzy file search revolutionized my use of my text editor. But it only searches filenames, not directory paths.

This is why I wrote PeepOpen, and I still use it every day.

I think Sublime Text has the best built-in fuzzy file finder of any current text editor. It’s not initially clear that it does this, but it searches on paths as well as filenames. The search score on the left is completely useless to me, but the file and path are a huge improvement over TextMate.

TextMate

Search by filename

Vim

Search open buffers by filename

:b filename

Emacs

Search filenames (using PeepOpen or textmate.el)

Sublime Text

Built-in fuzzy file search

5. Automatic Indentation

Now we’re getting into more advanced features, but still ones that I use constantly.

When using languages without syntactically significant whitespace (e.g. CoffeeScript), I let the editor do the formatting for me. It works 90% of the time, and for the other 10% I’d rather modify my code to work with the built-in formatting than do it manually.

Most developers would refuse to use a text editor without syntax highlighting. To me, auto-indentation is a show stopping feature.

Textmate

For some languages only

Vim

Select a range with V

Emacs

cleanup-buffer

Bound to C-c n

Sublime Text

Only available with language-specific plugins

6. Completion

Let’s admit it: the simple text-based auto-completion in open source text editors doesn’t come close to matching Microsoft Visual Studio from a decade ago.

I hope that a decade from now, I can use a text editor that understands not only the words I’m typing, but their meaning within the application. Without bogging down the rest of the editor or toasting my battery, of course!

In the meantime, I like the way Emacs completes words from all open buffers. TextMate and Sublime Text are limited to only words in the current file, which rarely includes the keywords or methods I’m looking for.

Textmate

For current file only

Vim

Next completion

Previous completion

Emacs

Using dabbrev-expand

Sublime Text

Current file only

SPACE

Conclusion

Learning these basic text manipulations has improved my editing speed. More importantly, I spend less time thinking about my text editor and more time thinking about the content of the text itself.

Try it! I bet you’ll use each of these multiple times in the first day you learn to do them.

Author: "--"
Send by mail Print  Save  Delicious 
Date: Tuesday, 16 Oct 2012 11:16

This article is heavily styled and is best viewed at PeepCode!

by Geoffrey Grosenbach

PeepCode is now 6 years old!

The last month has been a good sample of the excitement that has been happening for us this past year. In September we:

  • Published a live Play by Play design video and finished a draft of a new tutorial.
  • Moved into a small office suite in an artistic building a block from Seattle’s Pike Place Market. It’s an inspiring place shared by fashion designers, web developers, and CAD drafters.
  • Hired a full time Developer Educator to help us produce more tutorials and launch new kinds of videos. Jake Mitchell starts at PeepCode next month!
  • Gave a presentation at the new Seattle Sass Meetup.
  • Started a redesign of our website.

Vision

My title is Senior Visionary, which I take as a daily challenge.

It’s fulfilling to look back and see some of the people we’ve worked with over the last six years who have gone on to do even greater things.

  • In 2008 we published Scott Chacon’s book on Git Internals. He later went on to become a co-founder of GitHub.
  • In 2010 we launched the Play by Play series starting with Gary Bernhardt. I had watched him write code and knew that his unique skills were something that had to be experienced in real time. It was an immediate success and he went on to start his own business, Destroy All Software.
  • Earlier this year, Ben Schwarz published HTML5 Browser Caching with us and is now a member of the CSS Working Group on the W3C.

People

Two years ago, I was confident that I could run this business best if I operated on my own. Fortunately I discovered there’s a better way!

Right now, 8 employees and contractors work on PeepCode every week and I can’t imagine working without any one of them. We have skilled people who work on marketing, sales, development, finance, design, customer service, and production.

Adding their fresh ideas and hard work to my own has made a huge difference in the profitability of the business and the kinds of projects we can accomplish. Now that we’re adding our first full-time developer, we’ll be digging into our notebooks of ideas and launching some new ideas we’ve been waiting to work on!

Place

I like variety. In addition to traveling to and speaking at conferences, I enjoyed working without a fixed office for several years. It seemed like the way to go when running an online business with remote contractors.

But now that we have a consistent space to work from, I realize its value. Planning is much easier (every day starts at the office). And even though much of our work happens on screen, it still helps to have a fixed place to record drafts of new tutorials before they go out for transcription.

If you’re freelancing, working remotely, or starting a business, I highly recommend finding an office space to work from, even if only occasionally.

Our Supporters!

Thank you for subscribing to PeepCode and supporting our original productions over these years. We’re proud of the people we’ve promoted, the ideas we’ve brought to light, and the explanations we’ve delivered. Your support has made it happen!

Author: "--"
Send by mail Print  Save  Delicious 
Date: Tuesday, 25 Sep 2012 03:30

This article is heavily styled and is best viewed at PeepCode!

DISCLAIMER: Reg Braithwaite delivered this quote in a completely different context1, but I think it’s applicable to the design of almost any software API. Illustration by Mike Rohde.

The Rails router has been written and rewritten at least four times2, including a recent rewrite for the upcoming Rails 3. The syntax is now more concise.

But never mind making it shorter! It’s time for a final rewrite: Let’s get rid of it altogether!

Let’s get rid of the seven controller actions: index, show, new, create, edit, update and delete. Their meaning is blurred in the context of REST. They’re an unhelpful layer between programmer and protocol.

Let’s get rid of the trivial but cumbersome mental translation you have to do everytime you want to think about the HTTP GET method, the URL, the index action, and the plural_path URL helper.

Let’s get rid of duplicate functionality already implemented in the controller. If you need to redirect, take action based on the user agent, or examine headers, that should be done in a controller!

And let’s start thinking in URLs, resources, and APIs instead of doing image caching in models or asset bundling in view helpers. That’s the controller’s job. It scales better, too.

  • Routes are unnecessary configuration.
  • The seven standard controller actions are legacy.
  • Become intimate with your URLs – don’t abstract them away.
  • Decrease the distance between thought and implementation.
  • Let the controller do its job.

Get Back to Thinking in URLs

A big part of the problem with a routing layer is that it abstracts the developer away from the URLs that define the application. This leads to poor API designs and convoluted solutions to otherwise easy problems.

This epiphany came while writing a few Sinatra applications. The exact URL for a handler sits right in front of my eyes as I write the code for it. I can’t ignore it.

As a result, I find myself spending more time thinking about how my URLs are designed. Should I be serving JSON from the same controller that serves the HTML interface, or should it be organized separately?

In contrast, you can write an entire Rails application without ever looking at a URL. The design of URLs is delegated to the framework, out of sight and out of mind.

This isn’t to say that we need to lose the good parts of how Rails works with URLs. URL helper methods like pancake_path(:id) are a great idea for reducing duplication and typos. They could be implemented apart from any router.

“I love URLs. I dream about them at night. I think about them before I think about anything else.” — Adrian Holovaty, co-creator of Django

* From Webstock 2009

Retire the Seven Action Names

It has been three years since the seven controller actions had any immediate meaning. The API no longer adds to the programmer’s understanding of the tasks at hand.

Experienced programmers know that inline comments mark code that’s too confusing or too clever.

Yet every Rails controller is generated with two lines of repetitive comments for every action. That’s a code smell! And a failure of API design.

Every Rails developer must memorize the table at right, mapping HTTP method and URL to the controller action name. If we can get rid of the action name, the rest of the table is already self-explanatory.

So instead of going through this extra syntactical layer, let’s deal directly with GET, POST, PUT, and DELETE. (Suggestions follow.)

You can tell this is a great idea because it’s the way unit tests already work! Let’s bring this syntax back to the controller and complete the API.

Method URL Action Helper
GET /pancakes index pancakes_path
GET /pancakes/:id show pancake_path(:id)
GET /pancakes/new new new_pancake_path
POST /pancakes create pancakes_path
GET /pancakes/:id/edit edit edit_pancake_path(:id)
PUT /pancakes/:id update pancake_path(:id)
DELETE /pancakes/:id destroy pancake_path(:id)
# GET /pancakes
# GET /pancakes.xml
def index
end

# POST /pancakes
# POST /pancakes.xml
def create
end
test "should create pancake" do
  post :create
  assert_redirected_to pancake_path(1)
end

Assets Are Resources

Thinking in URLs helps you solve web-related problems in the right way.

Exhibit A: If you deploy to a site whose view fragments are already cached in memcached, it’s likely that Rails’ asset caching view helpers will not be called and CSS bundles will not be generated.

# Caching shouldn't happen here
stylesheet_link_tag("a", "b", "c",
                    :cache => true)

This whole problem is easily solved by using controllers to do what they do best. Views and helpers should not generate URL-based resources.

The task of combining several CSS files into one file and caching them to disk is exactly the kind of task controllers are built to do3.

Controllers should generate and cache assets, not view helpers.

Controllers should generate and cache assets, not view helpers.

Idea 1: Sinatra

There are many ways the controller API could be improved. Existing attempts have failed to achieve wide adoption because they have tried to handle controllers, views, and models all at once4.

Instead, I think a more limited, controller-only approach could work better.

The first is already in wide use: Sinatra.

# Sinatra-style handler
get "/api/v1/report/:id" do |id|
  # ...
end

Sinatra is arguably the most widely replicated Ruby web framework, having inspired implementations in Node.js, Clojure, PHP, Scala, and many other languages.

Part of the problem with writing a routing API is finding a way to describe multiple URLs in a single string. This problem is solved if you handle each URL on its own.

There’s no middle routing layer with arbitrary action names. HTTP method and URL are all you need (but handlers can filter on the user agent or other header information).

Thanks to Rack, Sinatra apps can be embedded in Rails applications. Or, Carl Lerche is writing a Rails 3 plugin that provides this syntax to Rails controllers5.

Idea 2: Method, Member, Collection

Jamis Buck introduced an implementation of REST as a plugin four years ago. Yet unlike other areas of Rails that have seen massive improvements, Rails’ implementation of REST is basically the same as it was in Rails 1.2.

A halfway approach could combine elements of the Rails 3 router syntax with the class method style of configuration that’s already familiar to Rails developers.

# Class method and HTTP-style methods.
class ReportsController < AppController
  before_filter :authenticate
  resource "/api/v1/reports(/:id)"

  get(:collection) do
  end

  get(:member) do |id|
  end

  put(:member) do |id|
  end

end

Variations on this syntax could easily accomodate nested resources, singleton resources, or other custom URL schemes.

Conclusion

For several years, Rails has charged forward and defined new, innovative syntaxes for writing web applications. It’s time for it to happen again.

An improved syntax could get rid of stale controller actions, reduce confusion, reduce duplication, and improve the way we think about solving technical problems with web applications.

Reactions

Thanks to Reg Braithwaite and Ben Hoskings for feedback on this article.

Ben Hoskings said

I think the mere fact that a controller can be generated means that code shouldn’t be there. There’s no intelligence in code that can be generated from a single resource name.

I think it’s doubly important because once you free the controller from having to implement the specifics of each action (like models doesn’t have to implement the specifics of #save), you have a lot more room to raise the abstraction level and start getting declarative.

I think making the controller more declarative is probably the end goal. Instead of the bulk of each action being an imperative mess, the controller can be heavier on the class-level configuration that’s really proven itself in the model (associations, scopes, plugin configuration, etc.).

The provides class-level configuration directive in Merb/Rails 3 is a signal that controllers can head in this direction.

Kyle Neath gives several useful guidelines in detail for thinking about URL design.

Author: "--"
Send by mail Print  Save  Delicious 
Date: Thursday, 16 Feb 2012 21:48

This article is heavily styled and is best viewed at PeepCode!

Dear Christian Neukirchen,

The first time I saw you, I was too shy to talk to you. Then you taught me how to use zsh. Now I use it every day.

One would think that the author of products used by millions of people would get some respect (the tumblelog and Rack). But most developers don’t even know your name, much less pronounce it correctly.

You promote your open source software as loudly as a ninja traverses a busy street. You launch your ideas silently and wait a few years for people to realize their brilliance.

I think about you every time I type rackup config.ru.

Geekily Yours,
Geoffrey Grosenbach

Send To:

Dear Jeremy Ashkenas,

An athlete with as many successes as you’ve had would be checked for performance enhancing drugs.

Backbone.js, CoffeeScript, Jammit, Docco, The Shoebox. The list goes on.

You’re doing real work that’s changing the world.

Keep on.

Indenting daily,
Geoffrey Grosenbach

Send To:

Dear Reginald Braithwaite,

I’m glad you didn’t get the notice that tech geeks don’t blog anymore.

Half the stuff you talk about confuses me. What the hell is a K-combinator? I have no idea but now I’m going to find out.

And then I find out that you do my favorite sport. Rock on.

XOXOX,
Geoffrey Grosenbach

Send To:

Dear Blake Mizerany,

It takes a true visionary to make simple tools that can do everything.

Maybe even more impressive than the individual success of Sinatra is that it’s always the first to be implemented in every other language that sprouts up.

But that didn’t stop you from building other mind-bending tools that most other developers wouldn’t even attempt. In a language you learned for the first time while writing it.

Here’s to you,
Geoffrey Grosenbach

Send To:

Dear Elise Worthy,

Most people would give up after trying to learn something for a few weeks. You’ve kept on with programming for several years and are getting better at it all the time.

Yet you’re an incredible teacher too. And working with you has irrevocably changed the way I think about business.

Best of luck at Living Social,
Geoffrey Grosenbach

Send To:

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 06 Jan 2012 05:22

This article is heavily styled and is best viewed at PeepCode!

by Geoffrey Grosenbach & Paula Lavalle

Command Line Prompt
Current Path
More
Last Command Status
More
Uncommitted Git Changes
More
RVM Config
More
Git Branch
More

Advanced Git!

One hour video.
Only $12! More Info…

Your Command Line Dashboard

In 10 years you’ll probably be writing code in a different language, building web apps with a different framework, and wearing a different pair of underwear.

But the command line prompt you use today could still be serving you well.

Many of the elements of my command prompt were snitched from other developers (Christian Neukirchen, Pat Allan, and Ben Hoskings). Here are my goals for my command prompt.

Goals

  • Fast: If I can tell there’s a pause when I open a window or change directories, it’s too slow.
  • Terse: Only show information that will change frequently between projects or between commands. If I always used the same version of Ruby, I would probably remove the Ruby version from my prompt.
  • Mine: I don’t hesitate to customize a script that I copied from someone else. The prompt is not the place to worry about reusable or generalized code. It should be easy to read and change when I need to.

Why ZSH?

I switched to zsh after receiving a one-on-one tutorial from Christian Neukirchen. It has some nice features:

  • Separate prompt for the right and left side of the screen.
  • Inline completion of directories, Git branch names, Rake task names, etc.
  • Easy loop syntax: for f (`ls`) echo $f

Try the source to a simple version of my prompt on GitHub. Or read the explanation below and build your own.

Implementation

Setup

The following configuration directives should be in ~/.zshrc. See the full source for the complete setup.

Run these commands to load zsh’s color variables. You’ll be able to use readable values like $fg[black] instead of cryptic ones like \e[0m.

# Colors
autoload -U colors
colors
setopt prompt_subst

Last Command Status

I first saw this technique in Pat Allan’s shell. If the last command exited with a nonzero value, it will print a red Unicode frown: . Successful commands will show a green smiley:

It’s a nice way to quickly see if tests failed or a compilation aborted.

And you’re not limited to ASCII! Use the Unicode snowman, a skull and crossbones, or any other dingbats character.

# Save a smiley to a local variable if the last command exited with success.
local smiley="%(?,%{$fg[green]%}☺%{$reset_color%},%{$fg[red]%}☹%{$reset_color%})"

Current Path

On my local machine I want to show only what’s necessary. So I don’t show the current user, hostname, or anything other than the relative path that I’m currently in.

In zsh, that’s %~.

Assign it to PROMPT to set the left-hand part of the prompt. It occupies two lines: the path is on one line and the previously saved smiley is on the next. $reset_color is a zsh variable that restores your default text color.

# Show the relative path on one line, then the smiley.
PROMPT='
%~
${smiley}  %{$reset_color%}'

Git Branch, SHA & Dirty Status

It’s surprisingly difficult to get Git to tell you what branch it’s on. I’ve tried several scripts, including the multi-SCM vcprompt (which worked well).

My current favorite is a Ruby script that prints all kinds of useful information about your Git setup:

  • Current branch name
  • The current SHA (7 characters of it). Useful for anytime you need to get out of trouble with git reset --hard. See the PeepCode Advanced Git video for this and other Git tips.
  • Rebase status (to know if you’re in the middle of a rebase)
  • Dirty status Have any tracked files been edited? A Unicode ✗ is displayed if changes have been made but not committed.

The original script is from Ben Hoskings(requires Ruby 1.9). I edited it to work on Ruby 1.8 and used a brief git-current-branch script (source). The relevant edit is on the last three lines where it specifies a format and colors for the final display.

RPROMPT='%{$fg[white]%} $(~/.rvm/bin/rvm-prompt)$(~/bin/git-cwd-info.rb)%{$reset_color%}'

I chose to make the more important metadata stand out more. The Git branch name and dirty status are more important to me than the Ruby version or the current SHA, so they are a darker shade of grey. Ben uses an @ sign before the SHA, but I replaced it with whitespace.

Ruby & Git metadata.

Ruby & Git metadata.

RVM Config

The name of the current Ruby version as configured by RVM is actually in the previous snippet. It calls ~/.rvm/bin/rvm-prompt and displays it at the left side of the right hand prompt.

Put it Together

The combined prompt looks like this.

# Combined left and right prompt configuration.
local smiley="%(?,%{$fg[green]%}☺%{$reset_color%},%{$fg[red]%}☹%{$reset_color%})"

PROMPT='
%~
${smiley}  %{$reset_color%}'

RPROMPT='%{$fg[white]%} $(~/.rvm/bin/rvm-prompt)$(~/bin/git-cwd-info.rb)%{$reset_color%}'

The important thing is to customize your own prompt and make it work the way you want it to!

Learn the command line, Git, and other great stuff!

Check out our Meet the Command Line and Advanced Command Line screencasts, plus our newest Advanced Git tutorial.

Command Line

Get started.
Only $12! More Info…

Adv Command

Master it.
Only $12! More Info…

Advanced Git

One hour video.
Only $12! More Info…

Author: "--"
Send by mail Print  Save  Delicious 
Date: Wednesday, 14 Dec 2011 08:44

This article is heavily styled and is best viewed at PeepCode!

We’ve all seen the geek gift guides put out by major publications. Somehow all geeks, regardless of their connection to technology, like star wars legos, rubix cubes, and light-up keychains. Seriously? Not here. Not us.

Many geeks appreciate well-designed, thoughtful products. We know this because it’s our bottom line. So here’s our gift guide for classy geeks.

Gifts from $1-20

Single PeepCode Gift Card

$12 A single screencast for your developer friends or that up-and-coming youngster in your family who wants to get started with programming.

The IT Crowd, Season 1

$10 Unfortunately, this is about stereotypical nerds. Fortunately, it’s awesomely hilarious.

Worther Shorty Mechanical Pencil

$14 Writing is much more fun with a beautiful pencil. Available in black, grey, or yellow.

Field Notes

$10 Now that smartphones have abandoned the stylus, there's nothing like paper and pen for brainstorming. Whether your field is a coffee shop or a bus, Field Notes are convenient and stylish.

The Wisdom of Crowds

$11 Both a classic and a quick read, this entertaining book is for entrepreneurs, sociologists, and deep thinkers of all kinds.

Milo

$15 An elegant stand for any smartphone with a smooth, hard surface.

Branch Earphone Splitter

$10 Split your music between three people. Useful for those cramped international plane flights to the next tech conference.

Whisky Stones

$20 These bad boys will keep your whisky chilled without watering it down? Oh, buddy.

How to Booze

$20 Exquisite Cocktails and other Unsound Advice humorously suggests matching beverages for any social situation.

Gifts from $20-60

5-Pack Gift Card

$55 Give five screencasts to anyone, redeemable at any time.

CoffeeScript T-Shirt

$26 For that friend who loves CoffeeScript, or even just coffee.

Chris Wanstrath T-Shirt

$26 This one's a bit niche, but that's what makes the best gifts, right? A t-shirt featuring Chris Wanstrath, co-founder of GitHub.

PowerCup Mobile Inverter

$26 Until Apple makes a power adapter for your car, this is the best way to stay energized on the road.

Juice Pack Reserver

$35 We don't mind a keychain when it's this useful! Carry an extra charge for your portable Apple products.

UBoard Smart

$49 Keeping your desk orderly isn't quite as important as having a place for your phone, coffee, tea, and three USB devices.

MOSHI MOSHI Pop Black

$40 Make those serious business calls even more official. Also available in red, pink, green, and yellow.

Braid Wood Puzzle

$34 A brain teaser in 6 or 12 pieces.

Pig's Nose 5 Year Scotch

$44 Not all scotch has to be serious. Recommended by our marketing department.

Gifts from $60-100

10-Pack Gift Card

$99 This gift won't collect dust in the bottom drawer!

Wood iPad 2 Case

$79 Nothing goes together like machined aluminum and solid wood.

Four Scrabble Letter Pillows

$98 With letters in solid black felt.

Gifts from $100-200

Unlimited Subscription Gift Card

$199 This one will keep a friend or family member occupied (and maybe even employed) until next year!

Tetris L-Shape Pouch

$165 "Extremely supple leather" and "lined in red velvet" should be all you need to know.

To:Ca Wood LED Clock

$150 A natural contrast to all the stainless steel, titanium, and adamantium in your home.

Gifts from $200-800

Revo Renaissance Radio

$357 The ceiling of the Sistine Chapel may have turned out differently if Michaelangelo had access to thousands of Internet radio stations (plus a docking port).

Bowers & Wilkins P5 Headphones

$300 Soft and cushy on the ears, tiny for travel, beautiful looking, and noise isolating. Yes, yes, and yes.

Link LED Task Lamp

$350 Move this guy anywhere. With 360° swivel, 15 high-power LED lights, and only 7.5 watts.

Espresso Machine with Integrated Grinder

$800 Run it on automatic for a cup in the morning and graduate to manual for an evening sip. An integrated grinder means maximum flavor every time.

 
Author: "--"
Send by mail Print  Save  Delicious 
Date: Thursday, 17 Nov 2011 23:52

This article is heavily styled and is best viewed at PeepCode!

Front-end Prototyping

When we started the Play by Play series, we wanted not only to learn how skilled back-end developers work, but also how front-end developers get work done.

Ryan Singer of 37signals was at the top of our list and he certainly delivered. We did an hour of sketching and an hour of prototyping with HTML and CSS (and even a bit of Rails 3.1).

Ryan’s process is an incredible mix of back-end theory (such as test-driven development) and front-end utility (sketching and prototyping). It has already changed the way we do things at PeepCode and we think you’ll like it too.

View a free ten minutes from the sketching session in the video above.

production by Geoffrey Grosenbach & Paula Lavalle

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

Style

Each post is uniquely styled within a grid.

Sinatra

Generates static pages and graphics. Styles code samples.

No SQL

Not even a database! File-based metadata.

Haml

Powers article templates and markup.

SASS/CSS

Comprehensive and reusable styling.

JavaScript

Taking it further…custom behavior & graphics.

Style

Before there were blogs we had websites. Beautiful, random websites that felt more like a zine — one page looking nothing like the one before or after it.

Greg Storey, Airbag Industries1

Many developments in computer science have nothing to do with the capabilities of computers, but with the way we use them.

A few years ago, an article on Airbag Industries1 inspired me to think about writing a blog with a unique design per post.

There are many benefits:

  • It encourages creativity both at the computer and away from it
  • It’s like a code kata for design
  • You can easily experiment with cutting-edge CSS3 features or just learn CSS2
  • You’ll learn how to build a style foundation for other designs in other applications

On the downside, it takes more time than simply writing prose.

Building an art-directed blog may seem as easy as dropping an extra CSS link tag into every blog post, but a little extra work upfront makes it a lot easier.

First, I started with a layout grid in CSS. Grids have been used extensively in print design but have only recently become popular in website design. I like Tyler Tate’s 1kb grid2 because it’s the simplest thing necessary to accomplish the task.

In standard website design, elements can be placed anywhere on a page. In contrast, a grid defines boundaries in regular increments, limiting the possibilities. Instead of stifling creativity, it encourages experimentation by making it easier to think about a finite number of widths for text or images.

I use a 12 column grid (double-click anywhere on this page to see it). Twelve columns are easily divided into other increments: 12 · 6+6 · 2+5+5 · 4+4+4 · 3+3+3+3

Sinatra

The Sinatra web framework has a beautiful REST API, can be extremely powerful, and is super fast.

It’s easily deployed with Phusion Passenger alongside my other Rack-based web applications.

I started with the Nesta4 blog engine and enhanced it with the additional CSS and graphic generation features I needed. All pages are cached statically with Sinatra::Cache5 for even greater speed. Although this blog could be generated with a static site generator, I find it more natural to write it in a dynamic style.

One example is the generation of text headline images with the Textorize6 renderer from Thomas Fuchs. I reference the images by URL in my CSS files. Sinatra generates the graphic on the fly when that URL is accesed (then caches it). Sinatra keeps URLs at the forefront of the web developer’s mind — where they should be!

Other resources are generated at the view level when needed. Code snippets are formatted by the Pygments7 command-line script via a special RedCloth tag implemented as a Haml filter.

textorize

Textorize (right half) renders text edges smoothly.

No SQL

heading: About this Blog
heading-font: Klavika-BoldCondensed
heading-color: #000
heading-background: transparent
published: December 30 2019 at 6pm
categories: meta design
summary: An article about...
format: haml

.column.article
  %h2 Bacon

  :custom
    Haml and textile together...

It’s much easier to debug a visual design in development on the local machine, check the whole thing into Git, and deploy when ready. No need to write an authentication system or an article preview mechanism.

Article files are stored on disk with a bit of YAML-esque metadata at the top. Each article can be in Textile format, or can use the full power of Haml for more complicated markup.

Early on I needed to store information about the title’s font size and color. Later I needed to add other custom fields for additional tagging. With an ORM this would have meant writing a migration and installing a plugin to manage tags.

There was no such problem here! I just added a few key-value pairs to the article’s metadata and started using them in the application immediately.

Haml

Not only does each post get its own CSS, it can also specify its own HTML, via Haml8.

When I’m designing visually in the browser, I’m thinking primarily about blocks of text and images, and how they will be styled. I don’t want to be thinking about HTML boilerplate or need to hunt to find a matching end tag.

Haml decreases the mental distance between HTML and CSS. I work directly with CSS selectors no matter what file I happen to be in.

But Haml isn’t well suited to working with inline text. Fortunately, there’s Textile9 for that!

The differences between the basic syntaxes of Textile and Markdown are negligible. Where it pulls away from Markdown is when you add new tags of your own. You can write view helpers that take a simple string and turn it into a group of HTML tags. It’s not only faster to type, but I can build reusable elements for movie links, syntax-highlighted code snippets, pull quotes, and product boxes.

Textile enhancements are easily used inline within any Haml document. In RedCloth 4, the steps are:

  • Write a module with methods for each of the tags you want to use (such as movie at right).
  • In each method, examine the :text key in the options, then build and return an HTML string. I build links for the mov and m4v versions of each movie.
  • Write a Haml filter. The name of your module will be used as the name of the filter.
  • Extend RedCloth with your custom module.
  • Add more methods to your tags module as needed.

The code samples at right were built this way. I specify a path to a source file and it runs it through pygmentize. It also prepends a link to the source file itself.

The end result is a text system customized for writing about code, but it looks great, too! I can’t imagine using a CMS that was any less powerful than this.

.column.article

  %h2 Custom Filter Sample
 
  :custom_red_cloth

    movie. http://example.com/movie.mov

    source. /blog/code.rb

    buy. http://peepcode.com/products
module CustomTags
  
  def movie(opts)
    my_text = opts[:text]
    # Build an HTML string around my_text
    # ...
    return my_text
  end
  
end
module Haml
  module Filters

    # Renders custom textile.    
    module CustomRedCloth
      include ::Haml::Filters::Base
      lazy_require 'custom_tags'

      def render(text)
        red_cloth = ::RedCloth.new(text)
        red_cloth.hard_breaks = false
        red_cloth.extend CustomTags
        red_cloth.to_html
      end
    end
  end
end

SASS/CSS

@import page_util
@import pygments_pastie

@include masthead-reset
@include dark-logo
@include dark-masthead-menu

$base_color: #d1e3ff

.prose
  @include grid_6
  float: left
  margin:
    left: $grid_gutter_width
    top:  $line_height * 5

Archives page with screenshots

In a recent copy of Print Magazine11, someone talked about designing a “style sheet” for the magazine back in the 70’s. For some reason, the extra space jolted my brain into thinking differently. Style. Sheet.

A stylesheet isn’t supposed to be a receptacle into which one tosses a bunch of unrelated visual directives. It’s a coherent guideline for how things should look. It should be planned and reusable. And like backend code, it may take several iterations of use in the real world to get it right.

SASS is a huge part of achieving that concept in this blog.

People get emotional when they hear about SASS. Either they see it as a threat to traditional CSS (used only by hacks who haven’t taken the time to learn it) or they welcome it as the best thing to happen to the Internet.

After working with this blog for a few months, I’m in the second camp.

As an example, any page can be designed with a light or a dark background. A few mixins at the top automatically adjust the page background, logo color (implemented as an image sprite), and menu colors. All these are contained in the stylesheet and don’t require any modification of the page’s HTML.

The technical parts of the grid and vertical rhythm are also wired into my SASS stylesheets. I can give elements meaningful names in HTML, then specify +grid_6 in SASS to make the element six columns wide (alternately, I could have used arguments like grid(6)).

Variables like grid_gutter_width and line_height are available to the whole application. I rarely type a number; instead I use meaningful variables to add margins or manipulate elements into position.

And if I’m going to spend that much time in the powder room, I want to show it off. The archives page uses webkit2png.py10 to take a screenshot of each page and display it in a grid.

JavaScript

A unique design for each post is great, but how about unique JavaScript for each post?

For my Rails 3 upgrade screencast, I wanted to show a timeline of Rails release dates. I’ve recently become enamored with RaphaelJS12 and it took only a few lines of code to import a JavaScript file for posts that want one.

I wrote a custom Timeline function that plots dates as large dots.

Conclusion

As with many features of this blog, it will take a while to figure out how to use them all fully. In the meantime, it’s a great learning experience and a fun output for creativity.

I haven’t published the source yet and may never. But now you have the ideas…implement them on your own blog!

In an earlier post, RaphaelJS was used to chart Rails release dates.

jQuery(function () {

  var paper = Raphael("graph", 940, 81),
    timeline;

  timeline = new Timeline(paper, [
    {date:"06/25/2004", version:"0.5"},
    {date:"12/13/2005", version:"1.0.0"},
    {date:"12/07/2007", version:"2.0.0"},
    {date:"6/10/2010",  version:"3.0 ?"}
  ]);

});

1 Airbag Industries wrote on the old days when blogs were designed like zines.

2 The 1kb grid is the simplest thing necessary to get the job done. I convert it to SASS with the included css2sass command.

3 With a hack to ruby-mode in Emacs, I can easily jump to any Sinatra URL handler in a file.

4 Nesta is a minimal blog engine by Graham Ashton (but easy to extend). It’s built on the Sinatra web framework.

5 Sinatra::Cache source code

6 Textorize text renderer

7 Pygments is the best syntax highlighter out there. When you view diffs and code at GitHub, you’re viewing pygments. Pipe code to it on the command line.

8 The Haml template engine is available for Ruby and other languages.

9 Textile is a syntax for formatting prose.

10 webkit2png.py is a capable screenshot capturing script for Mac OS X. There’s a Ruby port, but the original works well enough that I don’t see the need. I’ve wrapped it in the osxscreenshot gem.

11 Print Magazine is a classic (over 70 years in publication). Baseline Magazine is a more academic European counterpart. I recently bought a subscription to both.

12 RaphaelJS is a JavaScript-based SVG drawing library.

13 The Plainview web browser is a full-screen browser, useful not only for HTML-based presentations.

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

Thanks for making 2010 the biggest year yet at PeepCode!

We’re excited about keeping you informed and on top of your game. We’ve got big plans for 2011!

Author: "--"
Send by mail Print  Save  Delicious 
My Avatar   New window
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

by Geoffrey Grosenbach & Paula Lavalle

  • Avatar
  • Avatar
  • Avatar
  • Avatar
  • Avatar
  • Avatar

The Hooligan

In 2004 I worked at a grade school that hosted a highly anticipated field day every year. I decided to paint my face with my team’s flag for that year: South Africa.

For the next few weeks, kindergarteners told me they had nightmares because of it.

The following year, I coached the team representing the USA. I carefully painted a flag on my face, only later to realize that I had put the stars on the wrong side (damn mirrors!). Fortunately no one noticed since I had started a trend. Almost every kid arrived with some kind of paint splashed on their face: stars, hearts, stripes, camouflage.

I used a photo from that day as my avatar for the next few years, but I managed to lose the original. Instead of adopting an entirely new avatar, I decided it was time to recreate it…but better.

A studio flash, a digital SLR, and some face crayons solved the problem. I’m now the owner of what may be the world’s first studio photograph taken purely for the purpose of being displayed at 48×48 on Twitter, Facebook, GitHub, and other services.

People frequently tell me “You look nothing like your avatar.” Hopefully that’s a little less true now.

Geoffrey Grosenbach (@topfunky)

Colophon

CSS Masks

In order to achieve excruciatingly crisp curves around the images, we used CSS masks with SVG paths.

24-bit PNG images can be saved with transparency without the need for masks, but JPG photos can’t. Using a compressed JPG image with a CSS mask gives you the best of both worlds.

Webkit

Webkit’s masking is more full-featured than Firefox (see notes below). It can use SVG files straight from Adobe Illustrator and can stretch masks dynamically.

CSS image mask

The HTML markup references square images (seen at left). A circular mask is applied. The result is an image that is opaque in the black parts of the mask and transparent in the other parts.

  • An element can be masked directly, or an outer element can mask all the elements inside it.
<li>
  <img src="face.jpg" />
</li>
  • In Adobe Illustrator or another graphics application, draw a black shape and “Save As” SVG. You can use it directly in Webkit with no further modification.
  • Use the -webkit-mask-box-image directive in CSS to specify the path to the SVG file. We found it easiest to use the stretch option to expand the mask to fill the area covered by the element being masked. This also works better for animation since the mask grows as the image is resized.
li {
  -webkit-mask-box-image: url(mask.svg) 0 stretch;
}

Firefox

Firefox needs a slightly different SVG file and can’t stretch the mask.

  • Make a copy of the SVG file you used with Webkit. Open it in a text editor. Modify it to include a mask element around the drawing directives. The mask element should have an id so you can refer to it in the next step (we used avatar-mask).
<!-- Note: Simplified for educational purposes.  -->
<svg>
  <mask id="avatar-mask">
    <circle cx="100" cy="100" r="100" fill="white" />
  </mask>
</svg>
  • You also need to specify fill="white" for the drawing directives (such as the circle above).
  • Add a line to your CSS. Ask for a mask and include the URL of the Firefox mask file. Append the id of the mask element (avatar-mask in this example).
li {
  -webkit-mask-box-image: url(mask.svg) 0 stretch;
  /* Non-Webkit browsers */
  mask: url(mask-firefox.svg#avatar-mask);
}

Because Firefox masks won’t stretch with the element, we made a larger mask for the big version of the avatar. It makes the animation less elegant than the Webkit version, but it looks the same once the animation has completed.

CSS Animation

We started out thinking that we would need to use jQuery or Scriptaculous to animate the circles into the center when clicked. It turns out that CSS animations are supported in most modern browsers and make the code much easier.

CoffeeScript

Now that we know it, why not use CoffeeScript? We used it with jQuery to listen for a click on any of the images and add a CSS class. The class repositions the item to the center and makes it larger.

jQuery ->
  $('#circles li').click (event) ->
    $('#circles li').removeClass 'bigun'
    $(@).addClass 'bigun'

Animation

Until two days ago, we thought CSS animation was a complicated system that would take weeks to figure out.

Animating it only took two lines.

li {
  -webkit-transition-property: all;
  -webkit-transition-duration: 1s;
}

The easiest way is to specify all properties. When you add a CSS class to an element, all the new properties will animate. Otherwise, you can use a comma-delimited list of only the properties you want to animate: opacity,left,right, etc.

You can also add the same directives for Firefox and Opera:

li {
  /* Webkit */
  -webkit-transition-property: all;
  -webkit-transition-duration: 1s;

  /* Firefox */
  -moz-transition-property: all;
  -moz-transition-duration: 1s;

  /* Opera */
  -o-transition-property: all;
  -o-transition-duration: 1s;
}

See also

Other

Sass was instrumental in positioning the list items in a circular pattern. After calculating everything, we were able to change the radius of the hexagon and even the sizes of the circles until they fit.

li#circle1
  top: $cy - $hexagon_radius*0.866 - $radius
  left: $cx + $hexagon_radius/2 - $radius

Oh, and some photographs. We fitted a Nikon D7000 camera with a 50mm lens and hooked it to an inexpensive studio strobe and umbrella from AlienBees.

And of course, some face paint!

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

Files should be navigable by file, class, or method name and show metadata useful for distinguishing between similar files (mockup).

Files should be navigable by file, class, or method name and show metadata useful for distinguishing between similar files (mockup).

If I had no experience with computers and were to guess which group of people had the best software tools to do their job, I would guess “computer programmers.”

And if I were to guess what task would have been extensively optimized, I would guess “opening files.”

If you are a programmer, you know that I would be wrong.

Last summer, Dave Peck wrote about his hopes for a modern, progressive, text editor.1 I’d like to focus on one missing feature that’s absolutely possible today: powerful file navigation.

Keyboard

Perform any navigation task without touching the mouse.

Fuzzy Search

Find files by typing only a few letters.

Paths

Search includes folder names (relative to the project).

Metadata

File modification date and SCM status aid in file picking.

Beautiful

Terminal raster graphics don’t count! I want GUI beauty.

As every Vim user knows, most of one’s time spent in a text editor is spent editing, not writing (this is why Normal mode in Vim is the one you use for navigation and editing).

For most programming tasks, editing involves opening several files at once and switching between them (e.g. HTML/JavaScript/CSS).

I’m talking about three tasks:

  • Open any file on the computer.
  • Open any file in the current project.
  • Activate a file that’s already open in another tab.

And yet most text editors offload these important tasks to the operating system or implement half-hearted custom solutions. Even worse, third-party plugins frequently implement file-jumping functionality for different frameworks with unique, cryptic key mappings (e.g. between implementation and test or controller and view template).

This is a core task! Editors should approach it with the same innovation and care they spend on basic text entry.

TextMate
Keyboard
Fuzzy
Beautiful

Command-T with fuzzy search was revolutionary and was one of the main reasons I bought a copy of TextMate. But it breaks down for projects with many files of the same name (such as Ruby on Rails).

There’s no way to filter by directory.

There’s no way to filter by directory.

Tabs are even worse. I frequently open more tabs than can fit on my screen, which means that both usability and the extra tabs get thrown out the window. The tab menu can only be accessed with the mouse and becomes a human-powered binary search of an unsorted list.2

Xcode
Keyboard
Beautiful

Xcode’s Open Quickly command (Command-Shift-D) only works with the exact file name starting with the first letter.

Xcode’s Open Quickly dialog

Xcode’s Open Quickly dialog

Many Cocoa developers store all their code files in the root directory of the project and rely on Xcode’s virtual directories for organization, which is the only reason it’s even barely usable.

Emacs
Keyboard
Fuzzy
Path

Emacs is the closest to satisfying my requirements.

The ido-menu provides fuzzy search, including pathnames. Chris Wanstrath’s textmate.el plugin3 wraps it in even more useful functionality, such as autodiscovery of a project root based on the existence of a .git directory.

Open buffers (similar to tabs) can be searched for by name (C-x b) or in a list (C-x C-b).

But the inline menu is an ugly paragraph.

A powerful search hidden behind a mess of text.

A powerful search hidden behind a mess of text.

“The only solution I can think of, so far,
Is to smash out the windows with a crowbar.” — Buck 65

Once you start thinking about making file navigation better, the ideas flow freely. Could a dialog search on class or method names instead of just filenames? What about a free-form search for times and classes such as “yesterday Bacon#save”?

This article started with pain, developed into an idea, and ended up as an unexpected prototype implemented in MacRuby. I’m using it daily and am fine-tuning the interaction, visuals, features, and performance.

The app is now available as PeepOpen with a beautiful icon. Works with TextMate, Emacs, and MacVim.

For other updates, follow @peepcode on Twitter here.

The initial prototype performs a fuzzy search on paths and lists file modification dates.

The initial prototype performs a fuzzy search on paths and lists file modification dates.

You can contribute your own froth over the design and content of this article with the Neanderthals at Hacker News.

1 Dave Peck sends supplication to the text editor gods.

2 The RubyAMP bundle for TextMate shows a simple list of open windows, but without fuzzy search.

3 Chris Wanstrath’s textmate.el

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

San Pueblan Milksnake

The very things I find ugly in Ruby are what make amazing Ruby software like RSpec possible, and that Python could never have (given the current implementation). Gary Bernhardt
I think Ruby's syntax is ugly until they do something glorious and beautiful with it like Rake, then I think "damn it!" Unidentified Attendee
Q: Does Ruby have a better inheritance system than Python?
A: I find inheritance distasteful. That's like asking me whether I would rather eat grasshoppers or tree bark. Gary Bernhardt

My perspective on Ruby was rocked last weekend at Northwest Python Day in Seattle.

Compared to other programming languages, Python and Ruby are so similar that hearing arguments between them is like trying to figure out which identical twin is more handsome.

But there are differences, and not only in the languages! The Seattle Python community represented there was almost painfully polite. People sat silently for 3-5 minutes between talks while the speaker plugged in to the projector. I rudely whispered to my neighbor, eager to discuss the ideas presented.

During the talks, people mostly sat and listened to the speaker. Many Ruby conferences in the USA are half full of hackers with laptops open, coding away at a project and jeering the speaker over IRC. Not here.

I later learned that this may be an attribute unique to Seattle Python developers. After all, we’re the city that gave the world the Uptight Seattleite and where drivers with the right-of-way stop to let cyclists turn left in front of them.

Python vs. Ruby, A Battle to the Death

The main attraction (and last presentation) was from my friend Gary Bernhardt1. Gary spent a few months contracting on a Rails project for four hours in the morning and a Django project for four hours in the afternoon. So when he speaks of either, it’s not in ignorance.

At the end, I couldn’t find a single criticism of Ruby that I disagreed with. I did pick up a new appreciation for unique features of the Ruby language that I previously took for granted.

Matz Idolizes Larry Wall!

There was an audible gasp from the audience when Gary posted a slide with this quote from Matz:

Ruby inherited the Perl philosophy of having more than one way to do the same thing. I inherited that philosophy from Larry Wall, who is my hero actually.2

I’m not sure if the shock was from hearing someone embrace TIMTOWTDI or from learning that someone considers Larry Wall to be a hero.

If you open a python prompt and type

>>> import this

you’ll see the Zen of Python, 19 guidelines that Python programmers live by. One is “There should be one—and preferably only one—obvious way to do it.”

I do appreciate that Ruby is flexible enough to be used in many ways. That’s what makes the creativity and richness of Ruby libraries like Hpricot and Rake possible.

Parentheses Are Optional!

Gary pointed out that in most languages, appending parentheses to a variable that references a function, calls the function.

my_method = Proc.new { ... }

# ERROR: You can't do this in Ruby
my_method()

In Ruby, parentheses are a vestigial appendage. You could write an entire Ruby application without parentheses (and some do!). To Python developers, this is shameful.3

# In Ruby, you must use the call method
my_method.call()

I’m on the line here. I always use parentheses when defining methods, but use them infrequently when calling methods.

One’s aesthetic reaction to the following code snippets distinguishes the Rubyist from the Pythonista:

attr_accessor(:title, :slug, :body)
belongs_to(:article)
before_save(:encrypt_password)

get("/articles") do
  haml(:article)
end

And yet our repulsion at too many parentheses contrasts with Lisp’s influence on Ruby (which will be mentioned later).

They Monkey-Patch Object!

It’s well known that Pythonistas abhor monkey patching, a.k.a. duck punching,4 i.e. adding methods to existing classes.

They have a point. You can do a lot of damage in a few lines. Previous versions of ActiveRecord monkey-patched Logger, making it almost unusable for other applications that expected it to work in the standard way (it now behaves more civilly).

But without monkey patching, you can’t insert should and should_not into Object:

describe MySum do
  it "performs a sum" do
    sum = MyClass.add(1, 1)
    sum.should == 2
  end
end

So Python can’t implement the smooth syntax of RSpec.

Namespaces Run Amok!

The last line of the Zen of Python is

Namespaces are one honking great idea — let’s do more of those!

Python’s import statement gives you a high level of control over what code you’re bringing in to your application.

from django.db import models

In contrast, a Ruby require often slurps in other classes that seem entirely unrelated to the code you requested.

require 'active_record'
# => ActiveSupport is now in the global namespace

Having more control over the global namespace would be useful, but it seems to me that it would require a re-architecting of nearly the entire Ruby language.

Can I Have A Chainsaw Without So Much Lisp In It

My favorite quote of the whole presentation:

Ruby takes full advantage of the Lisp chainsaw.

Can I have that on a t-shirt?5

Python has no comparable equivalent to Ruby’s do end block. Python lambdas are limited to one line and can’t contain statements (for, if, def, etc.). Which leaves me wondering, what’s the point?

Without powerful blocks and lambdas, you can’t have Rake. You can’t have RSpec. You can’t have Sinatra’s clear REST syntax.

Without yield, you can’t have RailsCamp.

So the very features that make Ruby complicated to parse and potentially Perlish are the same features that can make it incredibly descriptive and flexible.

Not to mention the free Lisp chainsaw without all the parentheses!6

A Hacker News discussion about this article has over 200 comments here.

1 Gary blogs at blog.extracheese.org and recently posted the audio and slides of the talk.

2 From an interview at Artima

3 You can also call a Ruby proc with square brackets, but the crowd found that even more revolting.

4 Wikipedia on duck punching

5 Or just Lisp Chainsaw Massacre. Apparently this is a reference to Perl as a “Swiss army chainsaw.”

6 Personally, I don’t mind the parentheses. They can be rather comforting like a pillow.

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

In Motion

Learn it!

One hour video.
Only $12! More Info…

A snippet of code
COFFEESCRIPT:
jQuery ->
  $('#entry').focus()
JAVASCRIPT:
jQuery(function () { 
  $('#entry').focus();
});

1. A simple function

 

Engineering + Creativity

In his book Rise of the Creative Class, Richard Florida defines a list of creative professions that includes graphic designers, sculptors, architects, and…software writers.

It’s hard to think of a better place to see creativity and engineering than in CoffeeScript, a little language that compiles to JavaScript.

CoffeeScript is beautiful. It’s sensibly designed around syntactic indentation. It adds useful features to JavaScript. Most importantly, it’s a very thin layer over JavaScript. For any line of CoffeeScript, one can easily predict the line of JavaScript that the compiler will emit.

CoffeeScript invents some good ideas and steals many others. The number one source I could identify for the most useful ideas in CoffeeScript? Perl.

Yes, Perl. The language that’s guaranteed to produce an audible gasp if mentioned in civilized programming circles today. Yet for ten solid years, Perl was a petri dish of syntactic innovation. Extended regular expressions, destructuring assignment.

Which is why it’s exciting to see syntactic experimentation happening with such vigor in CoffeeScript.

In these video snippets, you’ll see how JavaScript and CoffeeScript compare.

— Geoffrey Grosenbach
Design & Motion Graphics by Paula Lavalle
 

2. Jasmine’s ‘describe’ function with args

A snippet of code
COFFEESCRIPT:
describe "constructor", ->
JAVASCRIPT:
describe("constructor", function () {

});

3. The @ syntax for instance properties

A snippet of code
COFFEESCRIPT:
beforeEach ->
  @dish = new Dish 'Steak $18.99'
JAVASCRIPT:
beforeEach(function () {
  this.dish = new Dish('Steak $18.99');
});
“Everybody shows off
And wants to look presentable
But the fact of the matter
Is that accidents are preventable.” — Buck 65

4. An instance method

A snippet of code
COFFEESCRIPT:
add: (dish) ->
  @dishes.push dish
JAVASCRIPT:
Meal.prototype.add = function(dish) {
  this.dishes.push(dish);
};

5. A full class with constructor

A snippet of code
COFFEESCRIPT:
class Money
  constructor: (rawString) ->
    @cents = @parseCents rawString
JAVASCRIPT:
Money = (function() {
  function Money(rawString) {
    this.cents = this.parseCents(rawString);
  }
  return Money;
})();

6. Object literal

A snippet of code
COFFEESCRIPT:
toJSON: ->
  title: @title
  price: @price.toString()
JAVASCRIPT:
function toJSON() {
  return {
    title: this.title,
    price: this.price.toString()
  };
}

Intrigued? Buy the 75 minute video at PeepCode!

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

The hash rocket is dead. In Ruby 1.9, hashes whose keys are symbols can be built with a single colon.

{
  key: "value",
  dr_nic: "The Comedian",
  ttl: 42
}

No longer will you need to remember different syntax when switching between JavaScript and Ruby (or even Python!). And you’ll save at least three characters every time.

It’s one more reason to start using Ruby 1.9!

Please update your code accordingly.

Learn more about Ruby 1.9 at PeepCode.

Inspiration from the opening panels of The Watchmen.

Comment on this post at Hacker News.

Author: "--"
Send by mail Print  Save  Delicious 
Date: Friday, 07 Oct 2011 19:02

This article is heavily styled and is best viewed at PeepCode!

Rails release dates plotted with SVG. Javascript by Geoffrey Grosenbach (using RaphaelJS ). Data from Mike Gunderloy.

Rails 3 Upgrade Handbook PDF

All You Need to Know
Only $12! More info…

NOTE This screencast covers an unreleased version of Rails 3 run from the source. Rails 3 Release Candidate 1 has been released and we’ll update this screencast when the final version is available.

For several months people have wondered, “Where can I download a video that features a developer stumbling through an upgrade of a Rails 2 app to Rails 3?”

I’m proud to say that an answer is now available!

In only 25 minutes, I convert my news screenshot site from Rails 2.x to Rails 3 (prerelease, from source).

It features the newest bundler (0.9.0.pre), Jeremy McAnally’s rails-upgrade script, new routes, Arel-based ActiveRecord queries, and more.

Stay tuned for the explosions at the end!

Resources

Attached Media: video/x-m4v (73 153 ko)
Author: "--"
Send by mail Print  Save  Delicious 
Next page
» You can also retrieve older items : Read
» © All content and copyrights belong to their respective authors.«
» © FeedShow - Online RSS Feeds Reader