German calendar with tikz

The spacing between days can be controlled using the day xshift option of \calendar. Note that this spacing is measured between the east anchors of consecutive days.

\calendar[dates=\currentyear-#2-01 to \currentyear-#2-last, day xshift=1.8em]

We can then set the space between east anchors of consecutive day labels to be the same:

\newcommand{\calrow}[1]{\node[anchor=east] (Mon){Mo};
    \node[right=1.8em of Mon.east, anchor=east](Tue){Di};
    ...
}

Edit: If you want the day labels to left-align with the day numbers, one solution is to use a phantom node that has the width of a day number (i.e., 24), and then place the day labels based on their west anchor:

\newcommand{\calrow}[1]{
    % phantom node
    \node[anchor=east, draw=none] (start) {\phantom{24}};
    % left-aligned nodes
    \node[anchor=west] at (start.west) (Mon){Mo};
    \node[right=1.8em of Mon.west, anchor=west](Tue){Di};
    ...
}

calendar

Full code with left-aligned day labels:

\documentclass[tikz,border=5]{standalone}
\renewcommand\familydefault\sfdefault
\usetikzlibrary{positioning,calendar}

\colorlet{darkgreen}{green!50!black}
\colorlet{holiday}{black!50}
\newcommand{\calrow}[1]{
    % phantom node
    \node[anchor=east, draw=none] (start) {\phantom{24}};
    % left-aligned nodes
    \node[anchor=west] at (start.west) (Mon){Mo};
    \node[right=1.8em of Mon.west, anchor=west](Tue){Di}; \node[right=1.8em of Tue.west, anchor=west](Wed){Mi};
    \node[right=1.8em of Wed.west, anchor=west](Thu){Do}; \node[right=1.8em of Thu.west, anchor=west](Fri){Fr};
    \node[right=1.8em of Fri.west, anchor=west](Sat){Sa}; \node[right=1.8em of Sat.west, anchor=west](Sun){So};
    \node[darkgreen, above=of Thu]{\textbf{#1}};
}

\newcommand{\calperiod}[2][\currentyear]{%
    \calendar[dates=\currentyear-#2-01 to \currentyear-#2-last, day xshift=1.8em]
    if (Sunday) [holiday] \holidays;}
\edef\currentyear{\the\year}
\newcommand{\holidays}{% holidays in Italy
    if (equals=01-01) [holiday]%
    if (equals=01-06) [holiday]%
    if (equals=04-04) [holiday]%
    if (equals=04-05) [holiday]%
    if (equals=04-25) [holiday]%
    if (equals=05-01) [holiday]%
    if (equals=05-01) [holiday]%
    if (equals=06-02) [holiday]%
    if (equals=08-15) [holiday]%
    if (equals=11-01) [holiday]%
    if (equals=12-08) [holiday]%
    if (equals=12-25) [holiday]%
    if (equals=12-26) [holiday]%
}
\begin{document}
    \begin{tikzpicture}[every calendar/.style={week list},
    year label/.style={
        fill=white,text=darkgreen,font=\bfseries\Large
    }, current year/.store in=\currentyear,
    current year=2017]
    \matrix[%
    row 1/.style={darkgreen,node distance=.3ex},%
    row 3/.style={darkgreen,node distance=.3ex},
    row 5/.style={darkgreen,node distance=.3ex},
    row 7/.style={darkgreen,node distance=.3ex},
    column sep=1ex,%
    draw=darkgreen,thick,rounded corners=5pt,%
    append after command={ 
        \pgfextra{\edef\matrixname{\tikzlastnode}}
        node [year label/.try, right=1ex of \matrixname.south west] {\currentyear}
        node [year label/.try, right=1ex of \matrixname.north west] {\currentyear}
        node [year label/.try, left=1ex of \matrixname.south east] {\currentyear}
        node [year label/.try, left=1ex of \matrixname.north east] {\currentyear}
    }
    ]{%

        % first row: week day and month
        \calrow{Januar} & \calrow{Februar} & \calrow{M\"arz} \\
        \calperiod{01} & \calperiod{02} & \calperiod{03} \\[1ex]

        % second row: calendar
        \calrow{April} & \calrow{Mai} & \calrow{Juni} \\
        \calperiod{04} & \calperiod{05} & \calperiod{06} \\[1ex]

        % third row: week day and month
        \calrow{Juli} & \calrow{August} & \calrow{September} \\
        \calperiod{07} & \calperiod{08} & \calperiod{09} \\[1ex]

        % forth row: calendar
        \calrow{Oktober} & \calrow{November} & \calrow{Dezember} \\
        \calperiod{10} & \calperiod{11} & \calperiod{12} \\[1ex]\\
    };

    \end{tikzpicture}
\end{document}

I wanted to see if I could make the process a bit smarter and avoid having to manually tinker with too many lengths. I take one weekday ("Mo") as a reference, measure its width, and then use that to set various things in the code. Additionally, there is a parameter \padding which can be adjusted as needed. It can now cope with three-letter weekdays as well (whether or not that is a good idea in the first place shall be left as an exercise to the reader -- it can start looking a bit cramped, though again, \padding).

2-letter weekdays

3-letter weekdays

Some slight manual fiddling was still required by setting every day/.append style={inner xsep=0.2ex}, though now that it's set up, it doesn't seem to require changing anymore (at least not in the few different configurations I've tried out). Maybe somebody can a nice way of automating that too.

\documentclass[tikz,border=5]{standalone}
\usepackage[utf8]{inputenc}
\renewcommand\familydefault\sfdefault
\usetikzlibrary{positioning,calendar}

\colorlet{darkgreen}{green!50!black}

% Adjust formatting here
\newcommand*\refday{Mo}
\newlength\padding
\setlength\padding{0.25ex} % Set as needed

\newcommand{\calrow}[1]{%
    \begin{scope}[every node/.style={
        anchor=east,
        align=right,% or left, depending on preference
        inner sep=0,
        outer sep=\padding,
        minimum width={width("\refday")},
        text width={width("\refday")}
    }
]
        \node[anchor=base east](Mon){Mo};
        \node[base right=0mm of Mon](Tue){Di};
        \node[base right=0mm of Tue](Wed){Mi};
        \node[base right=0mm of Wed](Thu){Do};
        \node[base right=0mm of Thu](Fri){Fr};
        \node[base right=0mm of Fri](Sat){Sa};
        \node[base right=0mm of Sat](Sun){So};
    \end{scope}%
    \node[darkgreen, above=of Thu]{\textbf{#1}};
}

\newcommand{\calperiod}[2][\currentyear]{%
  \calendar[dates=\currentyear-#2-01 to \currentyear-#2-last]
    if (Sunday) [black!50];}
\edef\currentyear{\the\year}

\begin{document}
\begin{tikzpicture}[
    day xshift={width("\refday") + 2 * \padding},% Double the outer sep of the \calrow scope
    every day/.append style={inner xsep=0.2ex},
    every calendar/.style={week list},
    year label/.style={
        fill=white,text=darkgreen,font=\bfseries\Large
    },
    current year/.store in=\currentyear,
    current year=2017]
\matrix[%
row 1/.style={darkgreen,node distance=.3ex},%
row 3/.style={darkgreen,node distance=.3ex},
row 5/.style={darkgreen,node distance=.3ex},
row 7/.style={darkgreen,node distance=.3ex},
column sep=1ex,%
draw=darkgreen,thick,rounded corners=5pt
]{%

% first row: week day and month
\calrow{Januar} & \calrow{Februar} & \calrow{März} \\
\calperiod{01} & \calperiod{02} & \calperiod{03} \\[1ex]

% second row: calendar
\calrow{April} & \calrow{Mai} & \calrow{Juni} \\
\calperiod{04} & \calperiod{05} & \calperiod{06} \\[1ex]

% third row: week day and month
\calrow{Juli} & \calrow{August} & \calrow{September} \\
\calperiod{07} & \calperiod{08} & \calperiod{09} \\[1ex]

% forth row: calendar
\calrow{Oktober} & \calrow{November} & \calrow{Dezember} \\
\calperiod{10} & \calperiod{11} & \calperiod{12} \\[1ex]\\
};

\end{tikzpicture}
\end{document}