Production & development

Dev teams tend to forget one thing: production management. This is quite unfortunate as a lot can be learned from.

Obvious remarks: managing production is important as this is what gets people paid. Get customers happy. Give them an easy going experience with your applications. That’s the key. Is that all anyway? Not of course because living with production only won’t give you much success either.

The other side of the coin is the development team. We are for most of us dealing with agile teams working within bounded sprints. Keeping people focused is really important to help go forward and raise overall quality so it’s pretty hard to get them out of this. But dev teams disconnected from production is a non-sense. There must be a trade off between dev and production obviously. Nevertheless, ensure dev teams are not fully staffed and have free time taking care of production.

Finding the sweet spot is really important - but to deal with production, it must be correctly monitored (you have a team in charge of that, right ?):

  • Gather metrics, build performance dashboard and compare trends - if not, priorize this with your teams
  • Have centralized logs - if not, priorize this with your teams
  • Document architecture, workflows & train peoples
  • On duty - ensure incident are correctly reported and documented to dev teams and outcomes are priorize accordingly with product managers
  • Know what you have released, where, when and who have tested this - if not.. well you know what to do

The goal is to be proactive:

  • application slowdown can be mitigated or anticipated with test-in-production
  • quickly explain incidents with facts
  • understand system limitations if any (capacity management)
  • plan impacts of future developments

Believe me, that’s a lot of work. Production is not for the faint of the heart and this can be time consuming (and destructive) if not taken seriously. That’s why people from development have to take care of, learn and follow what’s happening in production… and help!

Keep in mind

If production often breaks, you have three problems to deal with:

  • quality: you will loose your customers
  • human burn-out: you will loose your staff
  • legacy lock-in: you won’t be able to implement anything due to huge production maintenance costs

Last but not least: if production breaks repetitively for same problems again and again, go and kick butts!

Hello World (again) !

Starting again this blog. This time powered by Jekyll & GitHub (it’s so crazy easy - thanks !).

unstructured task_group sample

Example using unstructured task_group (recursive fibonacci computation). It’s pretty useless but this shows at least dynamic addition of tasks into the task_group.

#include "stdafx.h"
#include <ppl.h>
 
using namespace Concurrency;
 
void task_fibo(task_group& tasks, combinable<unsigned int>& comb, unsigned int n)
{
    if( 1 >= n )
    {
        comb.local() += n;
    }
    else
    {
        tasks.run([&, n] { task_fibo(tasks, comb, n-1); });
        tasks.run([&, n] { task_fibo(tasks, comb, n-2); });
    }
}
 
void task_fibo()
{
    unsigned int n = 30;
 
    task_group tasks;
    combinable<unsigned int> comb;
    tasks.run_and_wait([&] { task_fibo(tasks, comb, n); });
    unsigned int fibo_n = comb.combine( std::plus<unsigned int>() );
    std::cout << "Fibo(" << n << ") = " << fibo_n << std::endl;
}

PPL container sample

Sample showing some PPL containers.

#include <ppl.h>
#include <concurrent_vector.h>
#include <concurrent_queue.h>
 
using namespace Concurrency;
 
// =================================================================================================
 
void cont_concurrent_vector()
{
    concurrent_vector<int> vec;
    parallel_for((size_t)0, (size_t)1000,
                 [&](size_t i) { vec.push_back(i); });
}
 
// =================================================================================================
 
void cont_concurrent_queue()
{
    concurrent_queue<int> queue;
    parallel_for((size_t)0, (size_t)1000,
                 [&](size_t i) { queue.push(i); });
 
    std::cout << "queue has " << queue.unsafe_size() << " elements" << std::endl;
}
 
// =================================================================================================
 
void cont_combinable()
{
    int arr[] = { 1, 2, 3, 4, 5};
 
    combinable<int> comb;
    parallel_for_each(&arr[0], &arr[5], [&](int value) { comb.local() += value; });
    int res = comb.combine([&](int acc, int value) { return acc+value; });
 
    std::cout << "combinable = " << res << std::endl;
}

PPL algorithm sample

Sample showing PPL algorithms.

#include <ppl.h>
#include <concurrent_vector.h>
#include <concurrent_queue.h>
 
using namespace Concurrency;
 
// =================================================================================================
 
void algo_parallel_for(int* buffer, size_t size)
{
    parallel_for((size_t)0, size, /*(size_t)1, */
                 [&](size_t i) { buffer[i] = i*2; });
}
 
// =================================================================================================
 
void algo_parallel_for_each()
{
    std::array<int, 16> arr;
    algo_parallel_for(&arr[0], arr.size());
    parallel_for_each(arr.begin(), arr.end(),
                      [&](int value) { std::cout << value << std::endl; });
}
 
// =================================================================================================
 
void algo_parallel_invoke()
{
    std::cout << "Starting tasks" << std::endl;
    parallel_invoke( [&]() { std::cout << "0 starting" << std::endl; ::Sleep(1000*1); },
                     [&]() { std::cout << "1 starting" << std::endl; ::Sleep(1000*2); },
                     [&]() { std::cout << "2 starting" << std::endl; ::Sleep(1000*3); },
                     [&]() { std::cout << "3 starting" << std::endl; ::Sleep(1000*4); });
    std::cout << "Tasks done" << std::endl;
}