YERS! get in there! Rails 3.0 FtW 166

Posted by Peter Morris Mon, 08 Feb 2010 08:48:00 GMT

For the last 5 years I have classed myself as a Ruby on Rails developer. More recently, I realise I might possibly not be able to say that. I have been using Django a lot. I love RoR, but Django has some nice features. One of them is its ORM query mechanism, but things are changing....

Python and Ruby, siblings? 40

Posted by Peter Morris Tue, 29 Dec 2009 11:38:00 GMT

I have written code in many languages (Basic, dBase, C, Sculptor 4GL, Assembler(many flavours) Perl, VBA, Javascript, Ruby and finally, Python.

For much of my experience of Ruby, I viewed Python as a sibling language. I thought Ruby and Python where rough equals in capability and complexity.

It took me about 3 months of Python coding to realise that this is very far from the truth.

Ruby and Python are not compadres, they are not friends, they don't work at the same level.

Ruby is much simpler than Python, it has far less 'language' there. For a start, python is a compiled bytecode language (you do notice all those PYC files all over the place don't you?).

That and its explicit binding mechanism (all those import statements at the head of a python file just make my ruby sensibilities scream!) make for a much quicker language than Ruby.

When you add to that all this stuff about decorators, metaclasses etc, that takes some getting used to. The whole idea that methods associated with an instance are actually method instances that need calling (forgetting @property for the moment).

When I read about that, my mouth started watering, there must be some REALLY interesting uses for that! But then I let it stew for a while.

Really, all that does is force the coder to recognise that there are properties and then there are methods, and to require the user to know the difference.

With ruby, you don't need that. Well, really, with ruby, there are really ONLY ever methods, this forces encapsulation much more completely than Pythons default behaviour does.

Looking more deeply into decorators and metaclasses, I realise that they are trying to give the same sort of versatility to Python that Rubys blocks give to it.

Blocks affect EVERY aspect of Ruby, without blocks ruby is a rather dull, flat language. With them, it is a rich, expressive language that allows for some truely lovely DSL applications. Python tries to get the same functionality from metaclasses, decorators etc, but it just feels that much more forced. Having to use several different but interlocking constructs to ALMOST do what Rubys blocks do. This MIGHT be as a consequence of limitations enforced on the language by its bytecode underpinnings, I don't know enough yet to be able to say.

So, I suppose my final word on the issue is that Ruby is NOT a sibling of Python, its probably more of a teenager to Pythons twentysomething. There is a LOT more depth to Python than there is to Ruby, but thats not because the depth brings anything extra, it's more because Rubys simplicity is sufficient for the task. Python IS faster though, and probably always will be.

The later the binding, the slower the runtime performance.

All hail, Django models. 14

Posted by Peter Morris Tue, 29 Dec 2009 11:27:00 GMT

I have been spending a lot of time writing Django code (as you have probably noticed). In the past, I have been quite derisory about Django, there are many things that I don't like. Djangos ORM is NOT one of the problems. Well, fundamentally, it isn't. On the surface it stinks. So, lets get the nasty out of the way first. Some examples. In Rails, how do I find a particular instance if I know the ID? instance = Model.find(123) in Django instance = Model.objects.get(pk=123) Thats UGLY. This whole idea of managers, is a nice idea, but it is not entirely pretty. Now for the good thing. in Ruby if you do... object_list = Model.find(:all) you will get a big array filled with instances of all the objects in the database. Needless to say, this can SWALLOW your system. So, you have to be careful with AcriveRecord::Base, you get what you ask for, and if you ask for the moon, your system will fall to its knees and die. in Django if you do.... object_list = Model.objects.all() You will get an object that pretends to be an array, and only when you access chunks of it will it actually go over to the DB and pull back the required information. Thats NICE. BUT, it means you have to be a bit more careful, as it lulls you into a false sense of security. You have to remember that if you DO ask for the list of objects, you WILL get them. So, you have to remember. In rails, you know up front that you have to be careful, so its not quite as nice, but you aren't coddled. So, I do like Django models, it works in a more scalable fashion than Rails' ActiveRecord:Base. This leads me down the road of drawing comparisons between Ruby and Python. But thats the subject of a whole nother post.

Web development frameworks and SQL ghettos. 2

Posted by Peter Morris Fri, 20 Jun 2008 09:34:00 GMT

My platform of choice is Ruby on Rails.

In an early project, I implemented some reports by coding special purpose sql statements embedded within model methods. This worked well, and allowed the reports to run reasonably speedily.

As I continued to maintain the application and requirements changed, I found that I was reluctant to change the way the model objects interacted as it would require not only changing the model code, but sifting through the mounds of complex and convoluted sql.

What had been an efficient way to handle a problem (generating the reports quickly but in coding time and in runtime) had resulted in ‘scar tissue’, or maybe a fossilisation of my object model structure within the body of the sql.

Over time, this caused me to change the way I was altering the design, by forcing me to add layers around classes instead of refactoring within them.

After I finished on that project, I reviewed what I had done and vowed never to create sql ghettos again.

I think it is an apt term ‘sql ghetto’. An area in your application that you almost dare not go. that hinders future development, forcing it to work around it.

Resist the temptation to make ghettos, for they will surely come back to haunt you.

Rails to_xml, thar be dragons.

Posted by Peter Morris Wed, 30 Apr 2008 09:45:00 GMT

Ok, so I have been using to_xml to handle generating xml serialised lists for a restful xml interface.

I came across this interesting situation.

If you are serialising a collection which is implemented as a set of subclasses using STI, the to_xml will generate different xml depending on which class of items it sees first.

For instance, if you start the list with an instance of the base class, it will generate a list encapsulated with the plural name of the class name, and each element will be a singular of the class name for the base class, irrespective of which classes each of the objects are.

BUT, if the first item in the list is one of the subclasses, the to_xml call will see that it is a heterogenious list (presumably because the successive items don’t all return ‘true’ for .kind_of? of the class of the first item, and will generate a xml list encapsulated as <record> entities within a <records> list.

Oh, that makes me SOO happy.

Doctest, a 'gateway drug'?

Posted by Peter Morris Mon, 14 Apr 2008 03:18:00 GMT

I am quite a proponent of TDD/BDD, my framework of choice being RSPEC within Rails

But, I also understand that for people unused to TDD, the upfront investment seems daunting. So, I was very interested to be told about…

DOCTEST

This seems to be a nice light introduction into TDD. I can see that for extensive test coverage it is going to be a bit of a problem, there being no concept of fixtures etc. But I can definitely see someone adopting DOCTEST and then moving on to Unit testing or RSPEC later.

If you do not already embrace TDD, and recoil at its apparent heaviness, give doctest a look, but remember, tdd can be habit forming.

Bug, Buuuug, *BUG*!!!! I KNEW it.

Posted by Peter Morris Mon, 22 Oct 2007 02:50:00 GMT

I am a stalwart follower of the PEEPCODE screencasts.

I particularly liked the series about RSPEC.

But, in reviewing the code for it, and using the code subsequently, I found this little gem.

class Hash
  def except(*keys)
    self.reject{|k, v| keys.include?(k || k.to_sym)}
  end
end

Now, I don’t know where this code came from, but its wrong.

WRONG, WRONG WRONG

that “keys.include?(a || b)”, I see that, and know exactly what it WANTS to do, but it does not do it.

it will NOT return true if either a or b is in the keys, it WILL return true if a is in keys or a is null and b is in keys.

to get the desired effect you would have to

‘keys.include?(a) || keys.include?(b)’

not as pretty, and my mind says that it likes the other version, but that does not stop it being WRONG.

Anyway, go to Peepcode, buy screencasts and marvel at the information density.

in_batches_of

Posted by Peter Morris Mon, 22 Oct 2007 01:41:00 GMT

Rails is nice. Rails is REAL nice, but, you would expect me to say that, I am a rails developer.

One thing that rails is not nice about is efficiency.
It’s elegant, its compact, but, the simplest things can have unforseen consequences unless you understand at a fundamental level, whats going on.

The persistence layer of Rails is a class called ActiveRecord (Specifically, most of it is tied up in ActiveRecord::Base)

When you want to do something with every row in a table, or with a subset of rows, you want to do something like this…

ModelClass.find(:all).each do |item|
  ... do stuff ...
end

Take it from me, that would be bad.

What it would do is instantiate every row in the table as an object and build an array of those objects in memory. Thats fine if you have 10, 100, 1000 rows in that table, but what happens when you have 100000 or a million? Well, we would be in for a long wait.

Agile ain't about FAST.... 3

Posted by Peter Morris Thu, 06 Sep 2007 04:48:00 GMT

… it’s about GOOD.

Using Agile techniques, Rails for instance, or any of the other new frameworks popping up more quickly than mushrooms on a cowturn in a darkened room, and things like TDD, BDD, SPEC driven whatever, is NOT about writing code FASTER than previously.

Its about writing code in an acceptable timescale that is maintainable, extensible and more easily supportable.

Sure, if you develop in rails and forgo all the speccing, test script converage etc, you can write code more quickly than the guy in the next cubicle, but what about the poor bloke (possibly you) who has to support it into the future.

Writing in Rails with good test/spec coverage, and careful design, takes time. But the framework itself saves you enough time with respect to other platforms that this extra time is actually saved from other activities.

Expecting a well written RAILS development to be VASTLY quicker than using some other set of tools AND to expect it to be better quality and easier to support is wishing for your cake and eating it too.

Good code takes TIME, it takes THOUGHT.

A Peepshow anyone? 1

Posted by Peter Morris Thu, 06 Sep 2007 03:52:00 GMT

Nudge Nudge, Wink Wink, Say NO MOWER!

or so the old sketch goes.

Well, here is a peepshow that even a mother could love.