Archive for the ‘Webdevelopment’ Category

Testing User Sessions with Flask Elegantly

Thursday, August 17th, 2017

There is excellent information available on testing Flask e.g. http://flask.pocoo.org/docs/0.12/testing/

One thing I ran into was the need to set up a user session for most of my test cases.
The documentation suggests something like:

with app.test_client() as c:
    with c.session_transaction() as sess:
        sess['a_key'] = 'a value'

but repeating that in every test case (especially with a bit more code to set up the session) is not really DRY.

Now the same documentation suggests a very elegant trick using context managers for setting up users on the global object:

from contextlib import contextmanager
from flask import appcontext_pushed, g

@contextmanager
def user_set(app, user):
    def handler(sender, **kwargs):
        g.user = user
    with appcontext_pushed.connected_to(handler, app):
        yield

Inspired by this, I figured that they can be combined into:

@contextmanager
def user_set(app, user):
   with app.test_client() as c:
       with c.session_transaction() as sess:
           start_user_session(sess, user)
       yield c


and then use it in a test like:

user = ...
with user_set(app, user) as client:
    client.get('/logged_in_resource')

Obsessed about monitoring

Sunday, February 10th, 2013

For the past two years, I’ve been working on one of our products: Observu,  a site and server monitoring platform.   The last year we’ve applied it to our existing sites and customers and now we feel it’s ready for others to see and use as well. It took a bit longer than anticipated, due to other projects and responsibilities taking up time, but we’ve always kept determined to get Observu ready to launch.

If you are interested in improving your availability, response times and quality of service in general, check it out at http://observu.com/

I definitely do not feel like we are done now, having it out in the open now is just the start to find out which direction we should go.  We’ve got so many ideas, but we can’t execute all of them right away. Your feedback will be greatly appreciated and help us guide further development.

5 Reasons To Release Early

Wednesday, December 15th, 2010

There has been a lot of writing about the need to release early and often already, but I feel after doing many projects, I need to write a few reasons down anyway.

1. You are building stuff nobody needs. No matter how nice a feature will be, without real users, you have no way to tell if you are spending your valuable time on something that will convince users to buy your service.

2. Nothing like real user data. Your software may work great in theory, there is nothing like real volumes of data to test it. Many things can grind to a halt if you start having serious amounts of data. ( Things like search with ‘%LIKE%’ or pages listing ALL entries of a table)

3. Nothing like real measurement data. You can ask potential users whatever you want,  there is nothing like properly measuring what they are doing and what they prefer. With real users you can use tools like  Analytics to confirm that users actually do what you need them to do.

4. Ranking in Google takes time. As soon as you’ve got something out there,  Google can start finding your site, you can start optimizing text and titles and build links. The sooner you get started, the better.

5. Enough chances on a first impression. If you are worrying about scaring your first users of, think about the vast number of internet users out there.  The changes of ruining a first impression with all your potential customers are slim. Just don’t start promoting the product till you feel confident about it. There are many ways to steer the first users, e.g. an invitation based beta program.

Why you should not rely on bug reports

Saturday, December 11th, 2010

After building websites for a few years, I’ve reached a very important conclusion:  you cannot rely on bugreports to find major bugs and flaws in your product.  Think about it, what do you do if a website has a major bug? e.g. the registration form doesn’t work? You will just go to a competitor, unless you have some special interest in helping the creator or you really really really need to use it.
The same goes for missing features or conceptual errors: users just leave if they do not like what they experience.

Users that send you feedback, only do so if they already committed to your product. Maybe they’ve already paid, maybe they just entered loads of content or maybe they just like you.  However, this will only get you so far: in most cases this will be exceptions, obscure bugs or obvious features you just didn’t get done yet.

So what do you need to do?

  • Create a list of all important user stories in your site.  For PicturePush I would write stuff down like:  signup, login, create an album, upload a photo to an album, delete the photo, delete the album,  change my profile, delete my account.
  • Test all of it in ALL major browsers. No matter how much you think you’ve made everything cross browser,  there are always subtile differences that sneak in when you add new features or fix stuff.
  • REPEAT this as often as possible. Fixing bugs and adding features, you are very likely to create new bugs, clutter and/or unclearity.
  • Measure if you can. Using Google Analytics or other tools you are able to track whether users reach certain goals. This will allow you to see if your users succeed in the most critical tasks on your website.

Furthermore you can encourage you users to send you feedback:

  • Offer rewards for feedback. You could give away a few months discount.
  • Make it easy for users to delete their account and have an easy option to indicate why they want to leave. I suggest having radio buttons for those that are in a hurry and an aditional text field for those that want to help you even more.
  • Respond quickly to all questions and bug reports, if you can fix their problem quickly they will not only become loyal customers, they will keep contacting you with feedback.

PHP: How to generate URLs in your webapps

Sunday, October 31st, 2010

With SEO becoming more and important, it is critical that you produce the exact same URL from the same piece of content everywhere.  Furthermore, the URL structure is often decided upon only after you’ve started development. Our experiences from the last few years have led me to believe that the ultimate method for generating the proper URLs time and time again is to use a separate function for each different URL  in th following pattern:

function my_url($data_object, $context=array()){
  return root_url(    
           "my_url_page/".$context['category']['name']
           ."/".$data_object['seo_slug']
          );
}

This has the following advantages:

  • If you decide you need different fields from your data object to generate the URL, you only need to change it in one place
  • If you need extra context information,  it is easy to search where you call this function
  • One place to check if you are properly urlencoding everything
  • Avoids generating multiple urls for the same page

Because we also want it to be easy to remember, we put them together into an object:

class My_URL{
  function root($str=""){ return "/".$str; }
  function my($data_object, $context=array()){
    return $this->root(    
                    "my_url_page/".$context['category']['name']
                    ."/".$data_object['seo_slug']
                   );
  }
}
function urls(){ return new My_URL(); }

$myurl = urls()->my($data_object, array('category'=>$category) );

To  make it a bit more fancy and less work,  you can create a bit of magic for common cases:

class My_URL{
   // ... same as above. Plus: ...
   function __call($method,$args){
     $url = $this->root($method);
     if(sizeof($args)>0) $url.="?id=".urlencode($args[0]['id']);
     return $url;
   }
}

You can make it as fancy as you want, for example in some projects we have one big __call function that uses a configuration file to determine the urls based on the method name and data objects. Furthermore you can use functions to normalize urls like upper/lowercase conversion and anything else that will help you generating better and more consistent URLs.

Evaluating Basecamp

Tuesday, June 30th, 2009

At MovingLabs we really believe in creating all our tools, but as we need many, most are not really finished. Fine for us, but not so much if we need to collaborate with others.  We do have our own project tools like  TeamSpinner and FlexLists, but not everyone likes them in their current state.    Therefore we decided to sign up for the 30 day evaluation of Basecamp. Something that receives so much positive attention must be spectacular , right?

What I expected,  from what I’ve read and heard, was a clean and simple interface where those parts that are there are quick, effective and perfect.    The clean and simple part is definitely true,  there is no visual waste and I can quicly find stuff.  However speed, effectiveness and perfection are the things that I can’t find.

The first thing I noticed is that it’s actually quite slow,  maybe because it’s servers are in the US, but in terms of speed it feels like the  Java Enterprise intranet application that I worked on years ago.

Second thing is that it still has many rough edges that I would have expected to be fixed by now:

  • No error or resubmit, just forever ‘busy’  when the connection drops while doing an ajax submit ( Gmail set the standards high on this stuff)
  • The main page title is not clickable
  • On the message entry form there is not a hint that I can actually use the wiki like syntax
  • I can’t click on users anywhere to get some details about them, like which projects I share, what their e-mail is,  etc.

Finally I just miss a very important thing:  I want to set my todo’s  to  ‘busy’ .   I’m just way too used to doing that.

Besides these points it does work fairly well, I do like the way it takes into account that you want to collaborate with multiple parties.  However,  it’s not nearly good enough to cure the  ‘not invented here’ feeling.  Luckily the party we tried to collaborate with agrees with us, so seems like we need to fix TeamSpinner after all…

Available

Thursday, July 31st, 2008

The last three years I have been busy  graduating and working on some interesting projects.  Allthough these are very interesting I have decided to make myself available for design and webdevelopment projects again.  Something that I have done the years before.   So if you believe you can use my help designing or developing something  (Especially if it involves website design, website review, HTML, CSS, JavaScript or PHP)  don’t hesitate to contact me to discuss your project.

Weird JavaScript/Browser quirks

Tuesday, March 4th, 2008

The use of JavaScript has evolved over the years.  In the early days we would address a form element using:  myform.elementname .      Nowadays we prefer to use myform.elements[‘elementname’].   A related problem I ran into and only solved yesterday was, why    myform.submit();  was not working. Google presents the answer as the first result: www.thescripts.com/forum/thread542837.html for the query form.submit does not work.

Because my button was named “submit”    myform.submit refers to the button instead of the function.

Today I encountered a similar but harder problem.    Imagine this form:

<form id=”f1″ action=”go.php” onsubmit=”return ajaxSubmit(this);”><input type=”hidden” name=”action” value=”something” /> ….</form>

So I use  document.getElementById(“f1”).getAttribute(“action”);   to get the action and submit using AJAX.   Which works perfectly well in Firefox… and not in IE…

Apparently  IE does not really get you the action attribute but simply  object.action…. which in turn is the input element instead of the action attribute, similar to the first problem.  Unfortunately I can’t come up with a way to fix the script, so I had to replace the HTML all over the place.  (removing the action named input element by defining the action as action=”do.php?action=something”).