Category Archives: Software Development

This category contains all my posts about software development. Tutorials, solutions to problems I’ve met, interesting things I’ve stumbled over, code samples, stuff I don’t want to forget, et cetera.

Ignoring files and folders in Sublime Text

I love the file search (ctrl+shift+f) and quick navigate (ctrl+p) in Sublime Text. What can be annoying however is when these present you with library code in your project, files related to source control, binary files or minified files.

Since I keep forgetting how to clean that up, here’s a note to self (and others) on how to clean that up. Easy peasy.

  1. Save as project (if you haven’t already)
  2. Edit project file
  3. Add file_exclude_patterns and/or folder_exclude_patterns to the folders section.

Below is an example from one of my current projects which excludes the git repo folder, a cache folder, minified files and some binary files.

{
    "folders":
    [
        {
            "file_exclude_patterns":
            [
                "*.mp3",
                "*.ogg",
                "*.pdf",
                "*.min.*"
            ],
            "folder_exclude_patterns":
            [
                ".git",
                ".cache"
            ],
            "path": "/D/dev/www/sdaweb-ssl"
        }
    ]
}

Apache: Redirect one domain to another

The following .htaccess redirects all traffic to a different domain and preserves the path.

RewriteEngine On
RewriteRule (.*) http://example.com/$1 [R=301,L]

The following redirects non-www to www version, also preserving the path.

RewriteEngine On
RewriteCond %{HTTP_HOST} ^example\.com
RewriteRule (.*) http://www.example.com/$1 [R=301,L]

And hopefully I’ll remember I put this here the next time I’ve forgotten how to do this…

C#: Ordering by a list of ordered predicates

In a project at work we were going to merge a bunch of PDfs and Word documents into a single PDF. The ordering irrelevant except that certain files had to be before all the others. Solved it initially like this:

    var filesInOrder = GetFiles()
        .OrderByDescending(x => x.Filename.StartsWith("ProjectDescription_"))
        .ThenByDescending(x => x.Filename.StartsWith("Budget_"))
        .ThenByDescending(x => x.Filename.StartsWith("CV_"))
        .ToArray();

Found it a bit ugly though, and decided to ask a question about other ways on StackOverflow. Got several interesting answers and inspired by those and some further thinking I tried to make a generic solution myself, which I thought I could also blog here so I definitely know where to find it if I ever need it again…

My solution

public class OrderedPredicateComparer<T> : IComparer<T>
{
    private readonly Func<T, bool>[] ordinals;
    public OrderedPredicateComparer(IEnumerable<Func<T, bool>> predicates)
    {
        ordinals = predicates.ToArray();
    }

    public int Compare(T x, T y)
    {
        return GetOrdinal(x) - GetOrdinal(y);
    }

    private int GetOrdinal(T item)
    {
        for (int i = 0; i < ordinals.Length; i++)
            if (ordinals[i](item))
                return i - ordinals.Length;
        return 0;
    }
}

One issue here might be that the predicates will be called several times per item, which could be bad if working on a huge list. Haven’t really benchmarked it though so could be fine for all I know. For smaller uses it shouldn’t matter much either way. Very curious to know about ways to optimize this though, so do let me know in the comments below if you have any good ideas!

The nice thing about it being an IComparer is that you could push this into both OrderBy and ThenBy, and also use it in for example ordered dictionaries, priority queues, etc, and since it uses a list of fully generic predicates you could order things by pretty much anything with a yes/no answer :)

Usage

var ordering = new Func<string, bool>[]
    {
        x => x.StartsWith("ProjectDescription_"),
        x => x.StartsWith("Budget_"),
        x => x.StartsWith("CV_"),
    };

var files = GetFiles()
    .OrderBy(x => x.Filename, new OrderedPredicatesComparer<string>(ordering))
    .ToArray();

To make the final code even cleaner the ordering could be encapsulated in a sublcass like following, which is what I did in my actual code too:

public class MySpecificOrdering : OrderedPredicatesComparer<string>
{
    private static readonly Func<string, bool>[] order = new Func<string, bool>[]
        {
            x => x.StartsWith("ProjectDescription_"),
            x => x.StartsWith("Budget_"),
            x => x.StartsWith("CV_"),
        };

    public MySpecificOrdering() : base(order) {}
}

var files = GetFiles()
    .OrderBy(x => x.Filename, new MySpecificOrdering())
    .ToArray();

Missing time zones in WAMP MySQL

If you try to run for example SET time_zone = 'Europe/Oslo' on the default MySQL database that comes with WAMP you might get an error saying the time zone doesn’t exist.

Apparently this is because the time_zone tables for some reason are empty.

How to fix

  1. Go to dev.mysql.com/downloads/timezones.html
  2. Download the POSIX standard Time zone description tables, version 2011n zip archive
  3. Extract the files and overwrite the ones in C:\wamp\bin\mysql\mysql5.6.17\data\mysql, or whatever your equivalent path would be
  4. Restart MySQL

Setting the time zone should now work :)

Simple PHP proxy for cross origin HEAD requests

Have some Javascript that runs through all the URLs on a site of mine to prep caching and check for dead links and other problems. Problem is that the site also includes embedded video files hosted by someone else. These fails of course because of cross origin restrictions and since I’m not in control of their servers I needed a workaround.

I wrote this small PHP script to work as a proxy and as far as I can see it works pretty great. Short and easy to follow as well, so that’s always fun :)

So basically the script just pipes through whatever headers it gets to the the target URL an pipes back whatever headers it gets in the response. Seems to work, but let me know of weaknesses and easy improvements if you see any :)

<?php

$request_headers = getallheaders();
unset($request_headers['Cookie']);
unset($request_headers['Host']);

foreach($request_headers as $key => &$value)
    $value = $key.': '.$value;

$url = $_SERVER['QUERY_STRING'];
$limit = 20;

$curl = curl_init();
do
{
    curl_setopt_array($curl, array
    (
        CURLOPT_URL => $url,
        CURLOPT_HTTPHEADER => $request_headers,
       
        CURLOPT_RETURNTRANSFER => TRUE,
        CURLOPT_HEADER => TRUE,
        CURLOPT_NOBODY => TRUE,

        CURLOPT_FOLLOWLOCATION => TRUE,
        CURLOPT_MAXREDIRS => $limit--,
    ));

    ob_start();
    $headers = trim(curl_exec($curl));
    $url = curl_getinfo($curl, CURLINFO_REDIRECT_URL);
    ob_end_clean();
}
while($url and $limit > 0);

curl_close($curl);

$headers = trim(substr($headers, strrpos($headers, "\r\n\r\n")));
header_remove();
foreach(explode("\r\n", $headers) as $h)
    header($h);

Notes

  • The Cookie and Host headers sent from the browser are removed so they don’t mess up the request.
  • CURL wasn’t acting properly where I deployed this. It didn’t follow redirects, and curl_exec output content to the browser even with return transfer set to true. So it has a manual workaround for following the redirects and uses output buffering to make sure nothing goes to the browser before we want to.

ASP.NET MVC Areas in separate projects/assemblies

Had to implement a webshop section for an ASP.NET MVC website project which was to be reused by another one. Solving it was a bit finicky, so documenting it roughly here in case I need to do it again in the future. Not sure I remember all the steps, but hopefully it’ll be enough to reproduce the effect:P

The main problem here is the way razor views are compiled run-time and that is solved by using the Razor Generator VS extension to pre-compile the views and the belonging RazorGenerator.Mvc Nuget package to enable the web application to find them during run-time.

Don’t know if the solution I ended up with is the best, but it worked fairly great. If you have better/cleaner solutions please leave a comment :)

Continue reading ASP.NET MVC Areas in separate projects/assemblies

Use the ASP.NET MVC layout for all Areas

Areas in an ASP.NET MVC web application doesn’t use the layout of your web application by default. The reason (as far as I understand) is that your _ViewStart.cshtml which is usually located in ~/Views/ is only visible by views in that folder and its sub-folders.

So the solution, turns out, was more or less just to move that file up a level.

  1. Move ~/Views/_ViewStart.cshtml to ~/_ViewStart.cshtml.
  2. Cut or copy the following elements from ~/Views/Web.config and merge them into ~/Web.config. I say merge, because configSections for example probably already exists, so put the sectionGroup inside it. Don’t know if the Web.config handles multiple configSections…
      <configSections>
        <sectionGroup name="system.web.webPages.razor" ...>
          ...
        </sectionGroup>
      </configSections>

      <system.web.webPages.razor>
        ...
      </system.web.webPages.razor>

All areas should now use the the same layout as the rest of your application.