Django decorators

I am developing a page with Django and I had one interesting requirement: limit the number of users. The idea is to let a fixed number of users use the site and show a message telling the others to wait. I will like to share how I did it.

We need to check in every view used by a user. Instead of repeating the same code, the easiest way is to add a decorator for each function. Is really similar to AoP.

decorators.py:

from django.conf import settings
from django.shortcuts import redirect

MAX_NUMBERS_OF_USERS = getattr(settings, 'MAX_NUMBERS_OF_USERS', 100)

def check_user(view_function):
    def _wrapped_view_func(request, *args, **kwargs):
        auth_user = request.user
        
        if auth_user.id <= MAX_NUMBERS_OF_USERS:
            return view_function(request, *args, **kwargs)
        return redirect('coming_soon')
    return _wrapped_view_func

views.py:

from app.decorators import check_user
from django.contrib.auth.decorators import login_required
from django.shortcuts import render

@login_required
@check_user
def restricted_view(request):
    #Do stuff

def coming_soon(request):
    return render(request, 'coming_soon.html', {})

And that’s it ! Easy, clean and simple ! You can do more complex stuffs like logging.

Advertisements

Django + nginx + uWSGI

I had to deploy a web application I just created using Django. I will describe the steps I followed.

  1. Make sure you have you Django setted up correctly. I followed this guide.
  2. Install uWSGI into your virtualenv:
    pip install uwsgi
    
  3. Install nginx:
    sudo aptitude install nginx
    sudo service nginx start
    
  4. Edit nginx.conf file (it is in /etc/nginx if you are using ubuntu), it should be something like this:
    upstream django {
     server unix:///path/to/your/mysite/mysite.sock;
    }
    
    server {
     listen 80 default_server;
     listen [::]:80 default_server ipv6only=on;
    
     server_name mysite.com;
    
     charset utf-8;
    
     # max upload size
     client_max_body_size 5M; # adjust to taste
    
     location /robots.txt {
     alias /path/to/your/mysite/robots.txt;
     }
    
     # Django media
     location /files {
     alias /path/to/your/mysite/files; # your Django project's media files - amend as required
     }
    
     location /static {
     alias /path/to/your/mysite/static; # your Django project's static files - amend as required
     }
    
     # Finally, send all non-media requests to the Django server.
     location / {
     uwsgi_pass django;
     include /path/to/your/mysite/uwsgi_params; # the uwsgi_params file you installed
     }
    }
    

    Make sure it matches your Django app settings.py configuration:

    PROJECT_ROOT = os.path.abspath(os.path.dirname(os.path.dirname(__file__)))
    MEDIA_ROOT = os.path.join(PROJECT_ROOT, 'files')
    MEDIA_URL = '/files/'
    STATIC_ROOT = ''
    STATIC_URL = '/static/'
    
  5. Configure you uWSGI .ini file:
    # mysite_uwsgi.ini file
    [uwsgi]
    
    # Django-related settings
    # the base directory (full path)
    chdir = /path/to/your/mysite
    # Django's wsgi file
    module = mysite.wsgi
    # the virtualenv (full path) .virtualenvs at home folder
    home = /path/to/your/mysitevirtualenv  
    
    # process-related settings
    # master
    master = true
    # maximum number of worker processes
    processes = 10
    # the socket (use the full path to be safe
    socket = /path/to/your/mysite.sock
    # ... with appropriate permissions - may be needed
    chmod-socket = 666
    # clear environment on exit
    vacuum = true
    lgger = syslog
    
  6. Add uwsgi_params file to your project:
    uwsgi_param QUERY_STRING $query_string;
    uwsgi_param REQUEST_METHOD $request_method;
    uwsgi_param CONTENT_TYPE $content_type;
    uwsgi_param CONTENT_LENGTH $content_length;
    
    uwsgi_param REQUEST_URI $request_uri;
    uwsgi_param PATH_INFO $document_uri;
    uwsgi_param DOCUMENT_ROOT $document_root;
    uwsgi_param SERVER_PROTOCOL $server_protocol;
    uwsgi_param HTTPS $https if_not_empty;
    
    uwsgi_param REMOTE_ADDR $remote_addr;
    uwsgi_param REMOTE_PORT $remote_port;
    uwsgi_param SERVER_PORT $server_port;
    uwsgi_param SERVER_NAME $server_name;
    
  7. Run in emperor mode:
    # create a directory for the vassals
    sudo mkdir /etc/uwsgi
    sudo mkdir /etc/uwsgi/vassals
    # symlink from the default config directory to your config file
    sudo ln -s /path/to/your/mysite/mysite_uwsgi.ini /etc/uwsgi/vassals/
    /usr/local/bin/uwsgi --emperor /etc/uwsgi/vassals --uid www-data --gid www-data
    

    You can run the last command on screen or when the system starts.

And thats it, hope this can be helpful. You can find more info here.

CV

This time I wanted to share my latex CV template. It took me some time to get it done and I know this can be useful to anybody.

%______________________________________________________________________________________________________________________
% @brief    LaTeX2e Resume for Federico Ponte
\documentclass[oneside,12pt,letterpaper]{article}

\usepackage{hyperref}
\usepackage{epsf}
\usepackage[pdftex]{graphicx}
\usepackage{epstopdf}
\usepackage{epsfig}
\usepackage{wrapfig}
\usepackage{fancyhdr}
\usepackage{anysize}
\usepackage{titlesec}
\usepackage{indentfirst}
\usepackage[tmargin=1in,bmargin=1in,lmargin=1.25in,rmargin=1.25in]{geometry}
\usepackage{xcolor}

\renewcommand*\rmdefault{cmss}

\definecolor{MSBlue}{rgb}{.204,.353,.541}
\definecolor{MSLightBlue}{rgb}{.31,.506,.741}

\titleformat*{\section}{\Large\bfseries\sffamily\color{MSBlue}}
\titleformat*{\subsection}{\large\bfseries\sffamily\color{MSLightBlue}}
\titleformat*{\subsubsection}{\itshape\subsubsectionfont}


\pagestyle{fancy}
\lhead{\Large Curriculum Vitae}
\rhead{Federico Ponte}
\cfoot{Software Engineer}
\setlength{\headheight}{50pt}
\marginsize{2.8cm}{3.5cm}{1.2cm}{1.2cm}

%______________________________________________________________________________________________________________________
\begin{document}
    %__________________________________________________________________________________________________________________
    % Contact Information
    \section*{Personal Information}

    \begin{wrapfigure}{lhc}{0.2\textwidth}
    \vspace{-20pt}
    \centering
    \includegraphics[scale=0.51]{me.jpg}
    \end{wrapfigure}

    \noindent $6^{th}$ transversal Res. Villa Quintana, PH-A, Los Palos Grandes, Caracas 1060, Venezuela\\
    tel: +582122867498\\
    cel: +584242561666\\
    skype: fedep3\\
    email: \href{mailto:fedep3@gmail.com}{fedep3@gmail.com}\\

    {\setlength{\parindent}{22pt} I was born November 19th of 1988, in Caracas, Venezuela. There I studied and got my school and bachelor degree. I have been always interested in computers and mathematics. I like the logic behind programming, it's like a challenge to me.}

    When I am not working I enjoy sports, playing computer games or going out with my friends. I swim few days in the week near my house. Of course I like and play soccer. On the other hand my hobbies are reading and watching tv.

    My best skill, I will say is learning. I am always reading and trying to know new things.

    I find my self more in the backend development of applications. I like the challenge it envolves in terms of security, scalability and efficiency.

    My objectives are to keep learning, improving my skills and always being up to date with new technologies. Also, I like to keep swimming and try new sports, like tennis, running or bicycle.

    \textbf{Favorite quote:} "Be the change that you wish to see in the world" --Mahatma Gandhi


    %__________________________________________________________________________________________________________________
    % Education
    \section*{Education}

    \noindent\textbf{Universidad Sim\'on Bol\'ivar}, Caracas, Venezuela \vspace{2mm}\\\vspace{1mm}%
    \textsl{Computer Engineering} \hfill \textbf{ Octuber 2006 - November 2011}\vspace{-3mm}\\\vspace{-1mm}%
    \begin{itemize}
        \item[--] \textbf{Thesis  advisor:} Emely Arr\'aiz. I made it with Alexander De Sousa a carrer companion.
        \item[--] \textbf{Thesis  title:}  Clustering de Datos Num\'ericos por medio de Algoritmos Basados en Poblaci\'on e Inteligencia Colectiva (in english: Numeric Data Clustering with algorithms based on Population and Collective Intelligence). 
        \item[--] I am specialized in Computer Languages and Algorithms Design. Beside I saw three electives: Robotics, Artificial Intelligence I and Business Economics. 
    \end{itemize}\vspace{-1.5mm}
    \textbf{Colegio Santiago de Le\'on de Caracas}, Caracas, Venezuela \vspace{2mm}\\\vspace{1mm}%
    \textsl{High School Degree} \hfill \textbf{1994 - 2006}\vspace{-3mm}\\\vspace{-1mm}%

    %__________________________________________________________________________________________________________________
    % Professional Experience
    \section*{Job Experiences}
	{\setlength{\parindent}{0pt}
		\textbf{Nedra}, Caracas, Venezuela \vspace{2mm}\\\vspace{1mm}%
		\textsl{Software Engineer} \hfill \textbf{May 2012 - Present}\vspace{-3mm}\\\vspace{-1mm}\\
	}
	\begin{itemize}
		\item[--]  Created different web pages for real estate and auctions using Microsoft technology.

		\item[--]  Programmed in Java various requirements for SiteScout: video ads, web app for ads agencies, other for data migration, a server to make calls to Proximic, Peer39, etc.
	\end{itemize}
	{\setlength{\parindent}{0pt}
		\textbf{Kentriki}, Caracas, Venezuela \vspace{2mm}\\\vspace{1mm}%
		\textsl{Software Engineer} \hfill \textbf{January-April 2012}\vspace{-3mm}\\\vspace{-1mm}\\
	}
	\begin{itemize}
		\item[--] Did some test to see the feasibility of installing puppet on servers, for that i created and configure some virtual machines. Programmed page requirements (Python, HTML and jQuery)
	\end{itemize}
	{\setlength{\parindent}{0pt}
		\textbf{Novared}, Caracas, Venezuela \vspace{2mm}\\\vspace{1mm}%
		\textsl{IT Programmer} \hfill \textbf{Octuber-December 2011}\vspace{-3mm}\\\vspace{-1mm}\\
	}
	\begin{itemize}
		\item[--] Work tasks included evaluating the application written in VB to C\#, creating some RESTful web services using Java and polishing the website.
	\end{itemize}

    %__________________________________________________________________________________________________________________
    % Volunteer Experience & Causes
    \section*{Volunteer Experience and Causes}
	    {\setlength{\parindent}{0pt}
		    \textbf{TECHO}, Caracas, Venezuela \vspace{2mm}\\\vspace{1mm}%
		    \textsl{Volunteer} \hfill \textbf{2013 - Present}\vspace{-3mm}\\\vspace{-1mm}\\
	    }
	    \begin{itemize}
		    \item[--]  I helped collecting money in the streets. Also giving logistic and technical help during two of their main events.
	    \end{itemize}

    %__________________________________________________________________________________________________________________
    % Computer Skills
    \section*{Computer Software}
    I have used a lot of different softwares: snv, git, Team Fundation Server, MySQL, Oracle SQL, SQL Server, PostgreSQL, Jetty, Tomcat, Glassfish, Jersey, Django, IIS, Hadoop, Virtual Box, .NET, etc.

    \section*{Programming} 
    \begin{description}
        \item{\textbf{Advanced}} Java, Python, C
        \item{\textbf{Intermediate/Advanced}} C\#, Javascript, CSS, HTML, VB, SQL, bash
        \item{\textbf{Intermediate}} Prolog, Haskell, PHP, MatLab, Intel x86 assembly, Ruby, \LaTeX
    \end{description}

    %__________________________________________________________________________________________________________________
    % Language Skills
    \section*{Language Skills}
    \indent My native language is Spanish, but almost everything I write and read is in English both in connection to computers. Also, in my last work, I had to talk and interact with the customer directly and the language use was English.

    \textbf{TOEFL Score:} 100 

%______________________________________________________________________________________________________________________
\end{document}


%______________________________________________________________________________________________________________________
% EOF

Here is the result.

Python expressiveness

Here i will post my solution of the first two problems in the qualifying round in the Google Code Jam. Both are easy problems.

The first one is:

https://code.google.com/codejam/contest/2974486/dashboard#s=p0

#!/usr/bin/python

def read_board(row_number):
    for i in xrange(4):
        if i + 1 == row_number:
            row = map(int, raw_input().split(' '))
        else:
            raw_input()
    return row 

ncases = int(raw_input())

for ncase in xrange(ncases):
    first_row_number = int(raw_input())
    first_row = read_board(first_row_number)

    second_row_number = int(raw_input())
    second_row = read_board(second_row_number)
    match_count = 0
    number = 0
    for i in first_row:
        for j in second_row:
            if i == j:
                number = i
                match_count += 1
                break

    answer = 'Case #' + str(ncase + 1) + ': '
    if match_count == 0:
        print answer + 'Volunteer cheated!'
    elif match_count == 1:
        print answer + str(number)
    else:
        print answer + 'Bad magician!'

And the other one was https://code.google.com/codejam/contest/2974486/dashboard#s=p1:

#!/usr/bin/python

ncases = int(raw_input())

for ncase in xrange(ncases):
    data = map(float, raw_input().split(' '))
    C, F, X = tuple(data)

    if X <= C:
        print 'Case #' + str(ncase + 1) + ': ' + str(X/2.0)
    else:
        house_times = [C/2.0]
        cookies_per_second = [2.0]
        min_time = X/2.0

        for i in xrange(int(X)/int(C)):
            new_cookies_per_second = cookies_per_second[i] + F
            new_time = house_times[i] + X/new_cookies_per_second
            house_times.append(house_times[i] + C/new_cookies_per_second)
            cookies_per_second.append(new_cookies_per_second)

            min_time = min(min_time, new_time)

        print 'Case #' + str(ncase + 1) + ': ' + str(min_time)

Python 🙂

Setting up Jetty with IntelliJ IDEA

I wrote this in November of last year, I didn’t have time to share it :(.

  1. Download lastest Jetty stable version here
  2. Uncompress it (tar -zxvf jetty-distribution-9.1.0.v20131115.tar.gz)
  3. cd jetty-distribution-9.1.0.v20131115/
  4. Add the –module=jmx to start.ini archive (echo –module=jmx >> start.ini)
  5. Setup  the Default Jetty Server Local configuration
  6. Click configure and add the path to the folder you just uncompressed

  7. Click Ok and put the following:

    VM Options: -Dcom.sun.management.jmxremote= -Dcom.sun.management.jmxremote.port=1099 -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false

    Jetty Server Settings: select etc/jetty-jmx.xml and etc/jetty.xml

  8. Now just add your new Jetty configuration, for that just click on the plus sign

    and search for Jetty Server Local

  9. Go to deployment tab and add your war(s) file(s)
    step5
  10. Add the path you want to use
  11. Add the name you want
    step7
  12. Click ok

That’s all, hope this is useful!

Recommended Pages

Hello, long time I don’t write, I have been really busy!

Here are some things I want to share:

  • I tried a new (for me)  javascript framework: AngularJS

    I have used Backbone.js and Knockout, you can check my post about them here. I gotta say this one is pretty good. The code is organized and you have some cool options like the directives. The only tricky part I found is the authenticating process. The problem is that AngularJS is intended for one page apps, but it can be solved. Here is how.

    You should try it !

  • If you like Python and programming, do Design of Computer Programs course in Udacity!  Here is the link. It is taught by Peter Norvig and it is pretty interesting.

See ya!

 

Backbone.js & Knockout (English version)

I had a lot of work and things to do, so I couldn’t write.

The last year my boss asked me to look up all the libraries like Backbone.js and Knockout. The idea was to check all the options and take the more convenient.

To accomplish that I began to read and look a lot of information. Besides, I took the opportunity to try each one and feel them. For that, I made an application in Backbone.js and then observed how it would be using Knockout.

I will show you the code and then give my opinion. That way you will have a better decision.

Backbone.js

It’s really powerful and used by a lot of people, but it have an hard learning curve. You have a model and a bunch of things to define. If you follow all the conventions, the code will be easy to mantain. Here you can see more information and details.

It is ideal for REST web servicies.

Creating this application took me one noon and part of the morning.

The html:

<div>
    <fieldset>
        <legend>Person List - Using Backbone</legend>
        <div id="person-container">
            <input type="button" value= "Create New" class="Add" id="btn-create-new-person" />
            <table id="person-list">
                <tr>
                    <th>
                        Name
                    </th>
                    <th>
                        Description
                    </th>
                    <th>
                    </th>
                </tr>
            </table>
        </div>
        <script id='person-template' type='text/template'>
            <td><%=ID%></td> <td><%=FirstName%></td> <td><%=LastName%></td> <td><%=Age%></td>
            <td><input type="button" value="Edit" class="person-edit" /> | <input type="button" value="Details" class="person-detail" /> | <input type="button" value="Delete" class="person-delete" /></td>
       </script>
    </fieldset>
</div>

Javascript:

$(function () {

    // Person Model
    var Person = Backbone.Model.extend({
        urlRoot: '/Person/List/',
        initialize: function () {
            console.log('Person initialize');
        },
        defaults: {
            ID: 0,
            FirstName: 'Unknown',
            LastName: 'Unknown',
            Age : 0
        }
    });

    // Person Collection
    var PersonCollection = Backbone.Collection.extend({
        model: Person,
        url: '/Person/List/'
     });

     // Person View - el returns the template enclosed within a tr
     var PersonView = Backbone.View.extend({
         template: _.template($('#person-template').html()),
         tagName: "tr",
         initialize: function () {
             console.log('PersonView initialize');
             this.model.bind('change', this.render, this);
             this.model.bind('remove', this.unrender, this);
         },
         render: function () {
             console.log('PersonView render');
             $(this.el).html(this.template(this.model.toJSON()));
             return this;
         },
         unrender: function () {
             console.log('PersonView unrender');
             $(this.el).remove();
             return this;
         },
         events: {
             "click .person-edit": 'EditPerson',
             "click .person-delete": 'DeletePerson'
         },
         EditPerson: function () {
             console.log('PersonView EditPerson');
             this.model.set({ FirstName: 'Unknown' });
             var self = this;
             this.model.save(this.model, { success: function () {
                 $("input:button", $(self.el)).button();
             }});
        },
        DeletePerson: function () {
            console.log('PersonView DeletePerson');
            this.model.destroy();
        }
    });

    // Actual App view
    var AppView = Backbone.View.extend({
        initialize: function () {
            console.log('AppView initialize');
            this.collection.bind('add', this.AppendPerson, this);
        },
        el: '#person-container',
        counter: 3,
        events: {
            "click #btn-create-new-person": "AddNewPerson"
        },
        AddNewPerson: function () {
            console.log('AppView AddNewPerson');
            this.counter++;
            var newPerson = new Person({ ID: this.counter, FirstName: 'Unknown ' + this.counter, LastName: 'Damn ' + this.counter, Age: this.counter });
            this.collection.add(newPerson);
            newPerson.save(newPerson, { success: function () {
                $("input:button", "#person-list").button();
            }});
        },
        AppendPerson: function (person) {
            console.log('AppView AppendPerson');
            var personView = new PersonView({ model: person });
            $(this.el).find('table').append(personView.render().el);
        },
        render: function () {
            console.log('AppView render');
            if (this.collection.length > 0) {
                this.collection.each(this.AppendPerson, this);
            }
            $("input:button", "#person-list").button();
        }
    });

    var persons = new PersonCollection();
    var view = new AppView({ collection: persons });

    persons.fetch({ success: function () {
        console.log('Fetch called');
        view.render();
    }});
});

In the server (my case asp.net MVC with C#):

public class PersonController : Controller
{
    List<Person> Persons = new List<Person> {
        new Person (1, "Federico", "Ponte" , 23),
        new Person (2, "Alejandro", "Drago" , 23),
    };

    // Get Person
    [AcceptVerbs(HttpVerbs.Get)]
    public JsonResult List(int? ID)
    {
        if (ID.HasValue)
        {
            Person PersonResult = Persons.Find(p => p.ID == ID);
            return Json(PersonResult, JsonRequestBehavior.AllowGet);
        }
        return Json(Persons, JsonRequestBehavior.AllowGet);
    }

    // Update Person
    [AcceptVerbs(HttpVerbs.Put)]
    public JsonResult List(int ID, Person UpdatedPerson)
    {
        Person PersonResult = Persons.Find(p => p.ID == ID);
        PersonResult.FirstName = UpdatedPerson.FirstName;
        PersonResult.LastName = UpdatedPerson.LastName;
        PersonResult.Age = UpdatedPerson.Age;
        return Json(PersonResult, JsonRequestBehavior.DenyGet);
    }

    //Add Person
    [AcceptVerbs(HttpVerbs.Post)]
    public JsonResult List(Person CreatePerson)
    {
        Persons.Add(CreatePerson);
        return Json(CreatePerson, JsonRequestBehavior.DenyGet);
    }

    //Delete Person
    [AcceptVerbs(HttpVerbs.Delete)]
    public JsonResult List(int ID)
    {
        Person PersonResult = Persons.Find(p => p.ID == ID);
        Persons.Remove(PersonResult);
        return Json(PersonResult, JsonRequestBehavior.DenyGet);
    }
}
public class Person
{
    public Person(int _ID, string _FirstName, string _LastName, int _Age)
    {
        ID = _ID;
        FirstName = _FirstName;
        LastName = _LastName;
        Age = _Age;
    }

    public int ID { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public int Age { get; set; }
}

As you can see it is laborious, but it have advantages: highly configurable, it works on cellphones, you use web services. It is easy to scale with it.

It’s pretty tricky at the begging, but once you understand it, is simple.

Knockout

It use the pattern Model-View-View Model. It is quite easy to learn and pretty powerful. It comes with a complete template system and a lot of functions. You need to create a model and modify it directly in order to update the views. It have a pretty good documentation and it’s simple. To know more enter here.

One model would be:

function PersonModel () {
    var self = this;

    self.ID = ko.observable(0);
    self.FirstName = ko.observable('Unknown');
    self.LastName = ko.observable('Unknown');
    self.Age = ko.observable(0);
}

function PersonCollectionModel () {
    var self = this;

    self.Persons = ko.observableArray()
}

$(function (){
    ko.applyBindings(new PersonCollectionModel());
});

The functionality is pretty boring and it is not structurated. An example would be:

function PersonModel () {
    var self = this;

    self.ID = ko.observable(0);
    self.FirstName = ko.observable('Unknown');
    self.LastName = ko.observable('Unknown');
    self.Age = ko.observable(0);

    self.changeAndAlert = function (){
        self.FirstName('Hola');
        self.LastName('Chao');

        alert('Me cambie a ' + self.FirstName() + ' ' + self.LastName());
    }
}
<div>
    <fieldset>
        <legend>Person List - Using Knockout</legend>
        <div id="person-container">
            <input type="button" value= "Create New" class="Add" id="btn-create-new-person" />
            <table id="person-list">
                <tr>
                    <th>
                        Name
                    </th>
                    <th>
                        Description
                    </th>
                    <th>
                    </th>
                </tr>
                <!-- ko foreach : persons -->
                    <tr>
                        <td data-bind="text : FirstName"></td>
                        <td data-bind="text : LastName"></td>
                        <td><input type="button" data-bind="click : changeAndAlert" value="ChangeAndAlert" /></td>
                    </tr>
                <!-- /ko -->
            </table>
        </div>
    </fieldset>
</div>

The rest of the functionality in the case of Backbone is quite easy to do. With a good jQuery knowledge or another library, it just take some Ajax calls and modify the model.

Comparision

Backbone is quite tricky and hard to learn. It gives maintainability and scalability.

I have used more Knockout and it is pretty simple.

At this time I am writting this i don’t have any preferences as before. Both can do the same, the decision is on what you need.

Others

This library is sponsored by Google.

Angular JS

Dealing with Tomcat

I was modifying a project in Java with maven and Spring. In some point the need of having the application context XML outside Tomcat came out. In my case it was being loaded using the ContextLoaderListener. I tried other ways of loading it, but the issue is the same: the classpath.

pom.xml

<build>
    <resources>
        <resource>
            <directory>path/to/application/context/</directory>
            <includes>
                <include>*</include>
            </includes>
        </resource>
    </resources>

    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-war-plugin</artifactId>
            <configuration>
                <webXml>path/to/resource/web.xml</webXml>
            </configuration>
        </plugin>
    </plugins>
</build>

I wanted to change path/to/application/context.

Tomcat doesn’t give the access to any file outside where it is running, so all the classpath have to behave this way. It is done this way for security reasons. After struggling a hard time, trying different things and almost give up, I decided to read how Tomcat works. I found this page: http://www.mulesoft.com/tomcat-classpath. It have the answer to my question: add the path to the application context XML in the catalina.properties under the shared loader.

shared.loader=path/to/application/context

Hope this is useful for someone !

Annotations in Java

I am working on a new project using Java, Jersey, MongoDB with MongoJack, JUnit and maven.

As MongoDB is pretty fast the need of mockers can be avoided in tests. but the database needs to have the data.

In my case, there is a test just for that: it creates and saves all the data needed. The problems is that it has to be run before the other tests !

Instead of finding a way to give the tests an order, I just created a base class that all the testing classes extends and put a method with the annotation @Before. That method initialized all the necesary things (in my case MongoDB) and ran all the methods with @Test annontation in the class in charge of loading the data.

public abstract class BaseTest {

    @Before
    public void startMongoConnection() throws UnknownHostException, InvocationTargetException, IllegalAccessException {
        if (!MongoConnection.isActive()) {
            EntitySavingTest entitySavingTest = new EntitySavingTest();
            MongoConnection.initializeForDevelopment();
            for (Method method : entitySavingTest.getClass().getMethods()) {
                if(method.isAnnotationPresent(Test.class)) {
                    method.invoke(entitySavingTest);
                }
            }
            extraSetup();
        }
    }

    protected void extraSetup() {
    }

}

public class ATest extends BaseTest {

    @Override
    public void extraSetup() {
        //Any extra things you need to have before the test starts
    }

    @Test
    public void test() {
        //Testing code...
    }

}

Pretty simple and useful !

I got all the information about annotations here:

http://www.vogella.com/articles/JavaAnnotations/article.html

Two useful pages i found

  1. Some days ago i stumbled with this page: http://twistedoakstudios.com/blog/

    When i was coding in .NET it was quite hard to find good information. Great part of the community have a low level of programming skills. I had to look so many pages, it was stressing.

    I think the problem relies on the UI way to do thing of Microsoft. People tend to forget how things work.

    The articles in that blog are from high level programmers: they don’t only code, but understand how it works. The most interesting part is that they use C# to do advanced things.

  2. The other page i’ll like to suggest is: http://www.blueprintcss.org/

    Awesome css framework. If you live web design, you will find everything you need there.