Social Programming

So today was pretty cool, I went from 100 lines of this:

[Skill Load (0.2ms)[SELECT * FROM “skills” WHERE (“skills”.”id” = 21)]

To 6 lines.

I ran into a problem where I was running 2(n) queries.

If “n” is the number of skills I have to keep track of, then I ran 2 queries for each one.
Meaning: if I track 100 skills, for the page to load it has to do 200 bits of work.

This was clearly unacceptable, and is generally fixed by doing “eager loading.”
Eager loading, in Rails, is just a way of saying: “I need this ahead of time, do 1 query now to fetch all 100 of them, so that you don’t get stupid and run 100 queries later.”

The problem was that, despite using this technique, Rails didn’t quite understand how to implement it with nested attributes.
Admittedly, I’m using an old version of Rails (2.3.5, latest is 3) so I’m not sure if it’s fixed or not. I’d doubt it, since it seems to be somewhat of an edge case…

I solved it by simply generating a list of names off an eager loaded query. Then spitting out that list of names in order. Luckily the order matched up perfectly to the text boxes. (When I say luckily I mean to say I totally knew that they were going to line up perfectly when I wrote that code!)

Now, I wouldn’t have had this idea if I didn’t ask the community. That’s what I mean by “social programming” — I don’t think programmers are experts in their fields anymore. I think modern programmers are more creative than they are intelligent.

That’s not to say our field is unintelligent, or that in general computer programmers aren’t smart. The thing is that algorithms for common things are already well implemented, so instead of needing the noggin to write our own algorithms, we just use a library function… or grab one off Wiki.

Furthermore, we can talk to other programmers. We have chatrooms, forums, “StackOverflow’s”, etc. We don’t work in isolation. Our noggin’s don’t need to store the answer to every common computer programming problem. They just need to figure out a crazy solution to the task at hand.

I started by going to Freenode’s #rubyonrails channel, and asked my question (how do I eager load associations on a nested attribute?) I also pasted a sample of my code (exact paste: http://pastie.org/1184878 <— this was the original, broken code)

<person>: drbawb: use DataMapper

That was all the help I got. “Use DataMapper.”
Rails comes with something called ActiveRecord.
ActiveRecord is amazing, it takes information out of a database (think really smart spreadsheet) and abstracts it to classes/methods.

So I can have a table that just stores some information about a Character (such as their name, race, gender, etc.) - and access it by doing things like:

@character = Character.find(:first)
@character.gender
(returns: male)
@character.race
(returns: human)
@character.race = “elf”
@character.save
(Now the race is an elf)

DataMapper does something similar, it’s just a different technology.
This guy was saying I should rip out what comes with Rails, and replace it with a different technology.
It’d be akin to taking my computer to a repair shop, and the repair guy says: “Install Mac OS.”
It’s not bad advice. Some would argue it’s good advice (if you like Mac OS/DataMapper) — but it’s unnecessary advice.

So, I gave up on that idea, and went to StackOverflow.
1) Here is my question: http://stackoverflow.com/questions/3035064/updating-extra-attributes-in-a-has-many-through-relationship-using-rails

2) Here is my code, now, after getting helped at StackOverflow: http://pastie.org/1185686

You can somewhat see in “stub_player_skills” that I just create a list (@skills_arr) of all the skills. Then in the view, I count an index (adding 1 to it each time we print a skill) and step along @skill_arr. 
BEHOLD IN ALL ITS GLORY, @skill_arr magically is sorted in the appropriate order! 

Don’t take this the wrong way, I’m not bashing #rubyonrails. I’ve gotten help there in the past. Also DataMapper very well could be a better tool for the job. (Just as Mac OS may be a better tool for some jobs. <insert more analogies here.>) I just don’t feel like ripping out a core part of Rails to make my application work.
I don’t think you can remove a giant part of the framework, and consider yourself a Rails app.
Just as I don’t think you can strictly call yourself a Mac user if you’re virtualizing Windows in the background. (You get demoted to “computer user.” ;D)

It is very cool though, that programming has become a social phenomenon!

© Robbie Straw, 2010.
The code referenced at pastie.org is dual-licensed under the MIT/WTFPL. Do whatever the fuck you want with it.
Lots of rights reserved. 

Short URL for this post: http://tmblr.co/ZP7OEy17h3Ul