Reporting issues in YouTrack automatically

Problem

When working on my side-project for my client, I often require some specific data to address reported issue. It could be a specific request with its body, logged exception with a stack trace or authenticated user's context. I've learned, that expecting someone to paste all necessary data when reporting an error, always fails - remembering each time what you have to include is both tiresome and burdersome. Fortunately there's a possibility to automate things.

Solution

Currently I am using YouTrack so I'll stick to this issue tracker only. YouTrack exposes a REST API, which allows you to easily create, delete and manage reported issues. A reference to this API can be found here. Although it is possible to write your own client, I decided to use YouTrackSharp library - for my expectations it is a reasonable choice.

For now I've been missing following data in most issue reporting cases:

  • lack of full request's body - how to reproduce a problem without knowing what was sent to the server, especially when Jil sometimes goes crazy during deserialization
  • lack of user's context - how to reproduce problem without knowing who exactly performed a request
  • lack of headers sent and all request related data

Because I've already been catching all unhandled exceptions to log them, finding a place to call my "CreateYouTrackIssue" method is a piece of a cake. To be honest, I could take advantage of using EventStore and just raise an event, which will be further proceeded - maybe in the future I recreate it this way.

Whole method could look like this:

private static void CreateYouTrackIssue(Exception ex, Stream body)
{
      using (var reader = new StreamReader(body))
      {
            var conn = new Connection("host", 8080);
            conn.Authenticate("user", "password");

            var json = reader.ReadToEnd();

            dynamic issue = new Issue();
            issue.ProjectShortName = "SOME_NAME";
            issue.Summary = "API error - " + ex.Message;
            issue.Description = string.Format(
                    "An API error occuredd: :\r\nJSON: {0}\r\nStackTrace: {1}",
                    json,
                    ex.StackTrace);
            issue.Assignee = "root";
            issue.Type = "Bug";
            issue.State = "New";

            var im = new IssueManagement(conn);
            im.CreateIssue(issue);

            conn.Logout();
      }
}

This is just a sketch so it doesn't contain all mentioned features but note few things:

  • I'm passing stream to read its content - to get all necessary data passing some request's context would be more practical
  • I'm not handling HTTP connections - YouTrackSharp takes care of it
  • I'm assigning each feature to the root user - you can select whatever user you want

Because Issue() is dynamic, you can pass every custom field you created in YouTrack.

Summary

Above solution has already saved me some time when trying to reproduce reported error. What is more, it makes my client happy - he knows, that each time he sees a red error alert, issue has been created and I have been notified about it.

Automate everything

I'm a huge fan of automation. I don't like repeating things and I don't like doing everything manually. Everything can be automated - code generation, deployments and migrations. You can script how your application is being built, how it is being packed and how to notify everyone interested in this fact. After few months of work it saves even days of your priceless time. You can hardly believe in that? Let's see(all below examples are real functionalities prepared for my side-project):

  • Using command line to generate modules or features in your application

Most applications are based on very simple CRUD modules, which allow users to manage the data. No one likes to write such code - just query the database, do some validation, return a success or an error. Such modules or features, developed by many devs, tend to evolve into some kind of "an-app-inside-an-app" - everyone uses different conventions, code is formatted differently, the very same functionalities are structured using different patterns. Even when you are creating an application on your own, you sometimes change your style and approach. To get rid of this problem I've created a simple command line tool, which creates whole feature structure using only given feature name(of course it generates both handlers for API and AngularJS controllers and factories). I think, it saves me about one hour of writing the same code all over again per each feature. I have around 20 features so far.

  • Generating AngularJS factories based on requests data using Fody

It's a similar feature to previous one but it extends it rather than overrides it. When I have my structure created, it is obvious, that in some point in the future, I will have to add something new to my features. Because requests, which are a part of my API, are also used by factories in AngularJS(at least in terms of URL structure/HTTP verb), I don't want to change something in my JS code each time server-side code changes. That's why I'm using Fody(or Mono.Cecil if you wish) to generate this kind of client-side code.

  • Notifying users about new deployment/delivery using EventStore

I wanted to notify each user about the fact, that a new version of the application has been delivered. Because I extensively use TeamCity and psake, I decided, that my build script should just send an event to EventStore, which will be processed and respective action will be taken. I don't think about it, it just happens.

  •  Packing and deploying application using TeamCity + psake

Although I haven't got Octopus yet, I really wanted to pack and deploy my application automatically. It's the biggest problem for most companies - automate your deployment/delivery process so human factor is minimized. I decided, that everything necessary can be zipped by psake and just deployed to the destination server. Because psake is basically PowerShell, I was able to shut down the old version of my application, deploy new version and start it much faster, than doing it manually. No mistake is possible.

  • Creating issues in YouTrack automatically when not handled exception occurs

This is something unusual, but I realized that it's a real pain in the ass. Working with your client can be difficult sometimes, especially when you're trying to get some details about error he or she mentioned. Yes, you have logs and some general idea what was the flow but sometimes, you need a whole context. You can implement audit of each operation performed in you application(and this is not a bad idea). I decided to do something more interesting from my point of view - to automatically report an issue in my YouTrack when a HTTP 500 error occurs. It saves my time, it saves my client's time and that makes him happy.

Personally I think, that automating things - in development, in your process, in management - is a great opportunity to try and test your ideas. Initially you have to invest some time in making all those things, but after few months, when you just write

--create -featureName=Foo

instead of writing boilerplate code again and again, you will now it was worth it.