How to use itertools.cycle to set even and odd rows

I find code like this in a lot of web applications:

list_of_x_objects = ['a', 'b', 'c', 'd', 'e']
for i, x in enumerate(list_of_x_objects):
if i % 2: htmlclass = "odd"
else: htmlclass = "even"
print """

  • %s
  • """ % (htmlclass, x)

    Never mind the print statement. That’s just to illustrate the point without having to explain some template syntax.

    The same thing can be expressed with itertools.cycle:

    list_of_x_objects = ['a', 'b', 'c', 'd', 'e']
    for htmlclass, x in zip(itertools.cycle(['odd', 'even']), list_of_x_objects):
    print """

  • %s
  • """ % (htmlclass, x)

    I see several advantages of the second approach:

    • It’s way more flexible. I can easily switch to a style that repeats every three lines (or four, or five…).
    • I don’t create the variable i when all I really want is a class variable that toggles between values.
    • The second approach avoids the modulus operator. Since I hardly ever use the modulus operator, when I do come across it, I always have to take a second and puzzle out what’s happening.

    Dear Google

    I hate experts-exchange.com. I am tired of getting my hopes up that I found an answer to my problem, and then finding out that they want money before they’ll show me the answer.

    From now on, please filter them out of all my future searches.

    How to make sure you write more tests

    I’ve been writing way more tests for my code lately, and they’ve become the backbone of my development style.

    I used to write some web code, then play around with it in the browser and look for something to blow up. Automated testing was usually an afterthought or used for confirmation. Or maybe in some cases I would write tests dilligently at the beginning of a project, but start skipping them as deadlines approached. Following TDD has always felt like sticking to high-school abstinence pledges. I wrote tests because I thought I should do it, not because I wanted to do it.

    But now I’ve found a way to make writing tests central to getting my work done. It’s because of the computer I’m using now. It is such a crappy box that it takes about 5 minutes for firefox to start up. Then each page load takes about another 30 seconds at least. In the time it takes to click through three or four pages using firefox or epiphany, my twill scripts can run through about a hundred pages.

    There’s a scene in Star Wars: a New Hope where Obiwan trains Luke to use the light saber while blindfolded. Well, he’s not blindfolded, really, he’s wearing a helmet with the blast shield down, but the idea is the same. Luke has to use “the force” to feel out where the floating droid is, rather than relying on his vision.

    Anyway, writing web pages with this Compaq Presario 1200 feels kind of like that. It’s too frustrating to check my pages with Firefox. The only way I can make sure that anything really works is to write a test for it.

    PS: I wrote this posting with lynx.

    MVC Blasphemy

    I just put HTML code into my data model. I have a list-of-objects page. Each object is an instance of an object defined in my data model, derived from a row in a database. Each object needs a pretty link drawn that object’s detailed-view page. So I added a property on my object:
    class Message(SQLObject):
    def _get_view(self):
    "Draw a link to the view page for this message."
    return cElementTree.XML("""VIEW""" % self.id)
    # Lots of other stuff snipped out.

    This is now what my kid template looks like:

    MESSAGE STUFF

    I pass in messages and columns; messages is a list of objects and columns is a tuple of strings that map to attributes or properties, like “view”.

    I’m happy with this decision. I know I could have manipulated the messages or created some new classes in my controller, but I couldn’t really see any advantage. This way works.

    I just don’t want anyone else doing this 🙂

    Ubuntu Gutsy twill package breaks the showforms command

    On one computer named snowball, I installed the ubuntu twill package, then tried to test my webapp:

    $ twill-sh -u http://coleridge:8181/login2
    ==> at http://coleridge:8181/login2

    -= Welcome to twill! =-

    current page: http://coleridge:8181/login2
    >> showforms
    current page: http://coleridge:8181/login2
    >> show




    Login 2

    Login 2



    current page: http://coleridge:8181/login2
    >>

    The page clearly contains a form, but twill’s showforms command doesn’t display it. Fortunately, I found this post on the twill mailing list and so I didn’t waste too much time scratching my head. Then on this other box, coleridge, I installed twill using easy_install, and all was well:

    $ twill-sh -u http://localhost:8181/login2
    ==> at http://localhost:8181/login2

    -= Welcome to twill! =-

    current page: http://localhost:8181/login2
    >> showforms

    Form name=login2 (#1)
    ## ## __Name__________________ __Type___ __ID________ __Value__________________
    1 user_name text (None)
    2 passwd password (None)
    3 1 None submit (None)

    current page: http://localhost:8181/login2

    Sidenote: snowball is my new computer. She is a beaut; a 600mhz Compaq Presario with 60mb of ram, and a hard drive that makes clicking sounds when anything happens. I think Clinton was still in office when she was manufactured. I’d like to thank my son for helping decorate her with some very cool Godzilla stickers.

    Photo0250.jpg

    Installing on such an old machine meant I had to monkey a fair amount with some kernel modules, which is always a blast, and I am now much more aware of how much every program really costs in terms of CPU utilization and memory footprint.

    Response to SEO video blog by Sage Lewis

    Sage Lewis runs a website marketing firm in Akron and he posts video commentaries on YouTube. I really like how candid he is in his posts.

    Anyhow, he made one post called “Search Engines Optimization Expectations”.

    I typed out what I believe are his main points below.

    1. A brand-new domain takes six months to a year to start showing up in Google.
    2. Getting good positions in Google is really hard. The key is links pointing into your site from external sites, and that happens when you have good content.
    3. Google owes you nothing, and you can’t buy your way to the top of the rankings.
    4. You have to have content and lots of it. You have to be a resource and you have to be relevant.
    5. You have to use phrases in your content. If you want to appear in searches for the term “franchise” you need to be talking about franchises in your site.
    6. It takes as long as it takes. The more competitive, the longer the delay.
    7. You do it until. Keep working it until works.
    8. Kill off multiple domains.
    9. Don’t hide content. No white-on-white content, no hidden DHTML, etc. The key is good content.
    10. Trust SEO for at least a year. It takes a while to get results.

    I agree with most of this. There doesn’t seem to be any secret shortcut to the top of search ranks. The most reliable way there is by hosting content that other people want to find, and presenting it in a search-engine friendly format. I feel like his remarks support my belief that search engine ranking is an efficient market.

    However, I don’t think I really understand what he means by “you do it until”. Does he mean that you must keep shoveling money into the SEO consultants accounts indefinitely? That seems a little self-serving.

    Additionally, I also don’t know if it is really true that Google time-delays new domains. I started up this blog recently, and I nearly immediately started showing up at the bottom of the first page for Google searches on certain terms. Go do a search on lua metatable examples or python logging or cleveland heights hookah bar and you’ll likely find this blog somewhere high up there.

    All the search engines publish descriptions of what any web designer should do to maximize chances of getting a premium spot. What else can an honest SEO consultant offer me besides holding my hand while I implement these practices?

    If I remember my theory correctly, a firm operating in an efficient, perfectly competitive marketplace should expect to earn no better (and no worse) than any use of the same labor and capital. In other words, ZERO ECONOMIC PROFIT.

    Like I said at the beginning, Sage Lewis seems like a cool guy. I think this post is brilliant.

    Found a possible error in chapter 7 of the TurboGears book

    I bought the TurboGears book about two weeks ago, and I have been working through it. I like the book in general, but I agree with the reviewers on Amazon that complain about the number of errors. I can’t think of another programming book that I’ve read with this many errors.

    All of the errors I noticed are little glitchy typographical errors, rather than incorrect theory. The authors really do a good job of illustrating the MVC approach to web design, so I’m glad I bought it.

    Anyway, this page lists mistakes found after publication, and the community of readers seems to be doing a good job of helping each other out.

    I think I might have found another tiny error. This code appears at the bottom of page 109:

    class ProjectFields(widgets.WidgetsList):
    title = TextField(label="project", validator=validators.NotEmpty())
    client_revenue = widgets.TextField(validator=validators.Number())
    project_form = widgets.TableForm(fields=ProjectFields(), action="save_project_test")

    I don’t see the point in using both TextField and widgets.TextField. But more importantly, I think the indentation is wrong in the last line. I don’t think project_form is supposed to be an attribute of the ProjectField class.

    I think the code should look more like this:


    class ProjectFields(widgets.WidgetsList):
    title = widgets.TextField(label="project", validator=validators.NotEmpty())
    client_revenue = widgets.TextField(validator=validators.Number())

    # Moved outside the class.
    project_form = widgets.TableForm(fields=ProjectFields(), action="save_project_test")

    But maybe I’m missing something. I posted to the TurboGears Book mailing list, so hopefully I’ll find out.

    becontrary.com is a neat site built with TurboGears

    BeContrary.com is a very clever idea for a site. This debate on going dutch illustrates how the site works. And this is a good discussion of different styles of python templates.

    The site’s author, Will McGugan, wrote up a blog post describing his experience with turbogears here. He says he chose TurboGears partially because he had already worked with CherryPy and really liked it. Will made this remark after talking about SQLObject:

    Incidently, I don’t like the way that Python ORMs specify the database schema as Python code. Since the schema doesn’t change when the application is running, I would prefer a simple xml definition that would be used by the ORM to dynamically build classes for each table that could be derived from in the model code.

    I like this idea, but instead of writing XML, I would prefer to write SQL and have python parse that to build classes.

    Learning flex without spending $0.01, day one.

    I downloaded the command-line compiler and lots of documentation PDF files from here earlier today.

    Then I started working through the “getting started” tutorial PDF.

    I made a few edits to my ~/_vimrc file so that working with mxml files would be a little easier:

    ” Do some specific maps for flex files (.mxml files).
    ” F10 rebuilds the swf.
    autocmd BufNewFile,BufRead *.mxml map <F10> :! mxmlc %<CR>

    ” F11 executes the swf.
    autocmd BufNewFile,BufRead *.mxml map <F11> :! start %<.swf<CR>

    And I was able to build this do-nothing widget after about 15 minutes of goofing off:

    flex1

    That’s a screenshot of my homemade swf running above the vim session where I wrote it.

    Next stuff to figure out:

    • Where do my trace statements go?
    • I need to figure out how to pass in locations of actionscript files when I compile my mxml files into swf files.
    • I need to learn the tags in MXML. They’re different than HTML.
    • I need to learn how to talk to a webserver.