Como montar um volume do gluster usando a biblioteca libgfapi como usuário comum (non-root)

Enquanto estava trabalhando no projeto libgfapi-python, eu encontrei um problema para montar um volume do gluster como um usuário comum. O gluster, por padrão, permite conexões de clientes somente que vem de portas privilegiadas. Veja os passos abaixo para permitir a conexão apartir de portas “não-privilegiadas” e resolver esse problema:

  1. Execute o comando: sudo gluster volume set [nome_do_volume] allow-insecure on
  2. Edite o arquivo glusterd.vol: (geralmente se encontra aqui: /etc/glusterfs)
    • Adicione a linha: option rpc-auth-allow-insecure on
  3. Lembre-se de mudar as permissões do diretório que você quer acesso para permitir o accesso apropriado para usuários comuns.

Debugando testes de unidade em python usando tox e nosetests

Tox é uma ferramenta de linha de comando que facilita o desenvolvimento orientado a testes em Python. Ele usa o virtualenv para criar um ambiente isolado, o que lhe permite testar o mesmo código contra diferentes interpretadores do Python ou configurar diferentes fases de teste, tais como testes de unidade ou de integração.
Nose é um framework de teste de unidade do Python que “estende o unittest para facilitar o processo de testes.” O Nose vem com os scripts chamado ‘nosetests‘, que é usado para executar testes.

Para fazer sentido de tudo isso junto, vou usar como exemplo uma versão simplificada do arquivo tox.ini do projeto Gluster-Swift:

[tox]
envlist = py26,py27,pep8,functest,ksfunctest

[testenv]
setenv = ...
deps = ...
commands = nosetests -v --exe {posargs}
....

Quando o tox é is chamado com um envlist, ele irá criar um ambiente virtualenv com os intérpretes corretos (por exemplo: python2.6 ou python 2.7) e executar o comando nosetests.

Tox permite passar novos parâmetros que não foram definidos no arquivo tox.ini ao comando nosetests, basta invocar o tox assim:

tox -e py27 -- [novos_parâmetetros]

O que for passado depois de --, irá ser substituído onde {posargs} for especificado  no arquivo tox.ini.

Às vezes você pode precisar debugar o teste de unidade ou o código que você está tentando testar. Para debugar quando estiver usando o tox, siga os passos abaixo:

Insira um ponto de interrupção no seu código de teste. Aqui está um exemplo:

    def test_write_metadata(self):
        import pdb; pdb.set_trace()
        path = "/tmp/foo/w"
        orig_d = {'bar': 'foo'}
        ...

Execute o tox passando o parametro -s (que irá ser passado para o nosetests).

tox -e py27 -- -s

Você também pode especificar a execução de um único módulo, classe de teste ou até mesmo método. Isto irá acelerar o seu processo de debugação, caso você tenha um grande número de testes.

  • Módulo: tox -e py27 -- -s test.unit.common.test_utils
  • Classe: tox -e py27 -- -s test.unit.common.test_utils:TestUtils
  • Método: tox -e py27 -- -s test.unit.common.test_utils:TestUtils.test_write_metadata

Alguns comandos do debugger do python:

w - print stack
s - step into
n - step over
c - continue
p - print
a - print arguments of the current function

Alias para ir para diretorio raiz de um repositório do git

Achei esse alias bastante útil quando estou trabalhando com o git. Ele permite que eu vá para a raiz do repositório de qualquer lugar (diretório) que eu esteja:

alias cdw='cd $(git rev-parse --show-toplevel)'

Exemplo:

[thiago@localhost gluster-swift]$ pwd
/home/thiago/Projects/gluster-swift
[thiago@localhost gluster-swift]$ cd gluster/swift/common/middleware/gswauth/bin
[thiago@localhost bin]$ cdw
[thiago@localhost gluster-swift]$ pwd
/home/thiago/Projects/gluster-swift

Listando dados do Vimeo em um aplicativo para Android

Verão passado eu estava em um curso de desenvolvimento para dispositivos móveis e tive a oportunidade de aprender um pouquinho sobre desenvolvimento para Android. Já se passaram alguns meses desde que terminei a classe, mas vou tentar estimular minha memória e comentar um pouco sobre o código que escrevi antes que eu esqueça tudo.

Para meu último projeto, eu tentei criar um pequeno aplicativo para minha Igreja e em uma das “Atividades”, eu mostrava uma lista com nossos videos que estão postados na nossa conta do Vimeo. É uma “atividade” com uma simples lista, o que me permitiu focar no trabalho mais interessante de fazer o download dos dados e fazer uma análise sintática  da lista do Vimeo.

O Vimeo disponibilizou uma API simples para desenvolvedores obterem informações sobre videos, usuários, grupos, etc… A API suporta multiplos formatos de resposta. Eu usei o formato JSON e na minha Activity eu usei as classes JSONArray e JSONObject para analisar a resposta. A API está bem documentada no site do Vimeo, mas basicamente é assim:

http://vimeo.com/api/v2/username/request.output

username – id do usuário
request – Os dados que você quer.
output – Tipo de formato (JSON, PHP, XML)

A classe Activity continha uma classe privada que extendia AsyncTask.

private class LongRunningGetIO extends AsyncTask <Void, Void, String> {

Depois, dois metodos foram sobreescritos: doInBackground e onPostExecute. No doInBackground, a requisição é enviada para obter os dados.

@Override
protected String doInBackground(Void... params) {

  HttpClient httpClient = new DefaultHttpClient();
  HttpContext localContext = new BasicHttpContext();
  HttpGet httpGet = 
    new HttpGet("http://vimeo.com/api/v2/<your_username>/videos.json");
  String text = null;

  try {
    HttpResponse response = httpClient.execute(httpGet, localContext);
    HttpEntity entity = response.getEntity();

    // TODO: change and test to use: EntityUtils.toString(httpEntity);
    text = getASCIIContentFromEntity(entity);
  } catch (Exception e) {
    return e.getLocalizedMessage();
  }

  return text;
}

onPostExecute analisa a resposta e adiciona o resultado num ArrayList. Usando um SimpleAdapter, o título e as datas dos vídeos são exibidos num widget ListView. Veja o código abaixo:

protected void onPostExecute(String results) {
  if (results!=null) {
    ArrayList<HashMap<String, String>> videoList =
      new ArrayList<HashMap<String, String>>();

    // parse json response and add to a list
    try {
      JSONArray jsonVideoList = new JSONArray(results);
      for(int i = 0; i < jsonVideoList.length(); i++) {
        JSONObject video = jsonVideoList.getJSONObject(i);
        HashMap<String, String> map = new HashMap<String, String>();

        // Storing each json item
        map.put("title", video.getString("title"));
        map.put("mobile_url", video.getString("mobile_url"));

        // format the date, but adding both date formats,
        // just in case it is needed in the future
        video.getString("upload_date");
        String json_upload_date = video.getString("upload_date");
        Date date =
          new SimpleDateFormat("yyyy-MM-dd HH:mm:ss", Locale.US).
          parse(json_upload_date);
        String fDate = new SimpleDateFormat("MMM d, yyyy", Locale.US).
          format(date);
        map.put("upload_date", json_upload_date);
        map.put("upload_date_formatted", fDate);
        videoList.add(map);
      }

    } catch (Exception e) {
    }

    // add video list to ListView widget
    String from[] = {"title", "upload_date_formatted"};
    int to[] = { android.R.id.text1, android.R.id.text2 };
    ListAdapter adapter = new SimpleAdapter(SermonActivity.this,
      videoList, android.R.layout.simple_list_item_2,
      from, to);
    ListView lv= (ListView)findViewById(R.id.sermonListView);
    lv.setAdapter(adapter);

    lv.setOnItemClickListener(new AdapterView.OnItemClickListener() {

      @Override
      public void onItemClick(AdapterView<?> parent, final View view,
        int position, long id) {

        @SuppressWarnings("unchecked")
        HashMap<String, String> map = (HashMap<String, String>)
        parent.getItemAtPosition(position);

        // launch video
        startActivity(new Intent(Intent.ACTION_VIEW,
          Uri.parse(map.get("mobile_url"))));
      }
    });
  }
}

Configurando teclado no Fedora 19

Quando estou configurando uma instalação nova de um SO, uma das primeiras coisas que preciso fazer é configurar o teclado para poder digitar caracteres com acentos. Para fazer isso no Fedora 19 (e com um teclado de layout americano. Isso não aplica para outros layouts como o abnt, mas a idéia é a mesma), siga os passos abaixo:

  1. Selecione Atividades > Configurações > Região & Idioma
  2. Click no icone de adição (+)  abaixo de Fontes de entrada
  3. Selecione Inglês (Estados Unidos)
  4. Selecione Inglês (Mali, US internacional)

Nota: A maioria das pessoas no Brasil estão acostumados a digitar ' + c para obter o ç; no Fedora 19, usuários tem que segurar a tecla Alt da direita + virgula (,). Todos os outros acentos continuam o mesmo.