2009-07-20

A quote from Tom DeMarco

So, how do you manage a project without controlling it? Well, you manage the people and control the time and money. You say to your team leads, for example,

“I have a finish date in mind, and I’m not even going to share it with you. When I come in one day and tell you the project will end in one week, you have to be ready to package up and deliver what you’ve got as the final product. Your job is to go about the project incrementally, adding pieces to the whole in the order of their relative value, and doing integration and documentation and acceptance testing as you go.”

This might sound like an agile-methods prescription, but I’m too far away today from the actual building of software to recommend at the methods level. Rather, I’m advocating a management approach, one that might well steer the team toward agile methods, at least toward the incremental aspects of the agile school.

Tom DeMarco, via Coding Horror

20:38 [/software] quote_demarco Google Trackback
Tags:

2009-04-01

How to create an empty Git branch

(Source: Empty Branches)

Create a new symbolic reference:

git symbolic-ref HEAD refs/heads/<newbranch>

Empty the index:

git rm --cached -r .

Empty the working copy (watch out!):

rm -r * .gitignore

Commit the empty branch:

git commit --allow-empty -m'initial empty branch'

Because .gitignore is under Git control, this file can have different content depending on the current branch, so if you have e.g. your project’s homepage in a branch of your source repository, the website’s .gitignore can be different than the one from the source branch.

09:08 [/software] git_empty_branch Google Trackback
Tags:

2008-12-06

A quote from Tim Bray

We visited some people at one of the exchanges, and I walked away from that with my mind boggling at their traffic levels, and the number of rows they think it’s reasonable to write into a database in 6½ hours.

Tim Bray

13:21 [/software] timbray_quote Google Trackback
Tags:

2007-11-25

BSOD*: nicht einmal das Fernsehen ist davor sicher!

loly-20071125-214832.jpg
Das aktuelle Bild auf unserem Lokalfernsehen!

* BSOD: Blue Screen of Death

22:18 [/software/windows] loly Google Trackback
Tags:

2007-08-26

Using the Midnight commander mc(1) in a screen(1) session

Just a quick note for those people whose function keys don’t work when they use the GNU Midnight commander inside a screen session: issuing export TERM=xterm before starting @mc@ helps!

Maybe this problem is related to my SSH client PuTTY, but setting TERM fixes it.

22:36 [/software/debian] mc_f_keys_in_screen Google Trackback
Tags:

2007-08-03

3b, 3r und zwei andere Geeks an der Assembly 2007

Ein paar Kollegen unseres geekinfo-Kollektivs sind dieses Jahr also tatsächlich nach Helsinki an die Assembly gefahren!

Laufende Updates gibts auf 3bs Blog, die Bilder sind hier.

19:56 [/software] assembly2007 Google Trackback
Tags:

2007-05-01

GPS-Koordinaten in EXIF-Infos nachführen

Angeregt durch ein Mail von Alexander Klein und einen Artikel in der aktuellsten c’t 10/2007 will ich jetzt doch noch erklären, wie die GPS-Positionen aus meinem ersten Artikel von der Karte in die Bilder gelangen.

In der Karten-Seite befindet sich ein HTML-Formular, das die Eingabe von Breite und Länge erlaubt:

<form method="post" action="exifupd.php">
    <input type="hidden" name="image" value="<?php echo $image ?>" />
    <label for="lat">Latitude:</label>
    <input type="text" id="lat" name="lat" /><br />
    <label for="lon">Longitude:</label>
    <input type="text" id="lon" name="lon" /><br />
    <button type="submit">Update</button>
</form>

Die Werte im Formular werden per JavaScript im onclick() Event der Karte gesetzt:

GEvent.addListener(gMap, 'click', function(obj, pos) {
    document.getElementById('lat').value = pos.lat();
    document.getElementById('lon').value = pos.lng();
});

exifupd.php setzt die Koordinaten via ein Python-Skript ins Bild hinein. Die relevante Zeile des Update-Skripts ist diese:

exec("sudo -u me /home/me/bin/gpstag '{$_POST['lat']}' '{$_POST['lon']}' '{$_SERVER['DOCUMENT_ROOT']}{$_POST['image']}'", $result, $rc);

Der Python-Skript gpstag benötigt seinerseits exiv2, ein Kommandozeilen-Tool zum Bearbeiten von EXIF-Infos.

Diese zwei Zeilen in /etc/sudoers ermöglichen sudo, dass www-data, der User, als der mein Webserver läuft, in meinem Namen das Programm gpstag ausführen darf:

# Apache may update GPS data in images
www-data        ALL = (me) NOPASSWD: /home/me/bin/gpstag

Das Bearbeiten von sudoers erfordert root-Rechte und sollte immer mit dem Befehl visudo geschehen.

Als letztes wird der Update-Skript noch mit einem Eintrag in .htaccess passwortgeschützt:

# Password protection for GPS updates

<Files exifupd.php>
    AuthType Basic
    AuthName "GPS Update"
    AuthUserFile /home/me/lib/htpasswd/php
    Require valid-user
</Files>

Wie man ein Passwort-File bereitstellt, ist unter man htpasswd nachzulesen.

20:27 [/software/php] exif_gps_update Google Trackback
Tags:

2007-02-06

UTF-8? UTF-8!

Warnung: In den nächsten Tagen könnte meine Homepage Probleme mit der Darstellung von Umlauten haben; ich bin dabei, das Filesystem von ISO-8859-1 auf UTF-8 umzustellen. Bei der Shell ist das bereits geschehen; jetzt ist noch ~/public_html dran…

17:02 [/software/blog] utf8_ahead Google Trackback
Tags:

2007-01-03

Scannen übers Netzwerk mit Ubuntu und HPLIP

alias netscan='xsane $(hp-makeuri -s hp2610)'

Das ist alles; hp-makeuri -s generiert eine SANE-URI, die den Netzwerk-Scanner mit Namen hp2610 bezeichnet.

21:54 [/software] ubuntu_hplip_scanning Google Trackback
Tags:

2006-12-22

My first Rhythmbox plugin

Yesterday evening I threw together my first Rhythmbox plugin! Like Luke’s InfoSender for Winamp, it posts the currently playing artist and song title to a webpage. I use it to update my sidebar.

Just put the Python source and config file (see below) into ~/.gnome2/rhythmbox/plugins or /usr/share/rhythmbox/plugins and restart Rhythmbox to enable the plugin. Its name is posttune.

To configure the plugin, change the BASE_URL variable to point to your own page. The artist’s name and song title are appended to BASE_URL, then the plugin makes a GET request to the URL.

[RB Plugin]
Loader=python
Module=posttune
IAge=1
Name=Tune poster
Description=Posts the current artist and song title to a web form
Authors=Beat Bolli <bbolli@ewanet.ch>
Copyright=Copyright 2006 Beat Bolli
Website=http://www.drbeat.li/py/

12:13 [/software/python] rhythmbox_posttune Google Trackback
Tags:

2006-12-13

Fotos, EXIF-Infos, GPS, Google Maps etc…

Nachdem ich vor ca. zwei Wochen Mätthu geholfen hatte, einen Skript zu schreiben, mit dem er in Google Maps zeigen konnte, wo er ein bestimmtes Foto gemacht hat, habe ich diese Woche das selbe in mein Album eingebaut.

JPG-Dateien von Digital-Kameras können Meta-Daten enthalten, wie z.B. Belichtungszeit, Blende, ob der Blitz eingesetzt wurde, etc. Diese Daten werden innerhalb der JPG-Daten im EXIF-Format abgelegt. Seit Version 2.2 des EXIF-Standards ist möglich, in den Meta-Daten eine geografische Position und andere von einem GPS-Empfänger gelieferte Daten zu speichern.

Meine Skripts ermöglichen es nun, die Position auf einer Google Map darzustellen.

Zu Beginn stehen einige JavaScript-Funktionen:

// Convert a decimal degree value to degress, minutes and seconds
function decToDMS(dec) {
    var deg = Math.floor(dec);
    dec = (dec - deg) * 60;
    var min = Math.floor(dec);
    var sec = (dec - min) * 60;
    sec = Math.round(100 * sec) / 100;	// round to 1/100th precision
    return deg + "&#xB0; " + min + "&#x2032; " + sec + "&#x2033;";
}

// Convert latitude and longitude to a HTML string
function LatLngToHtml(lat, lng) {
    lat = decToDMS(Math.abs(lat)) + (lat < 0 ? ' S' : ' N');
    lng = decToDMS(Math.abs(lng)) + (lng < 0 ? ' W' : ' E');
    return lat + ', ' + lng;
}

// Create a marker at the given point with the given label
function GMcreateMarker(point, label) {
    var marker = new GMarker(point);
    GEvent.addListener(marker, "click", function() {
        marker.openInfoWindowHtml(label);
    });
    return marker;
}

// Initialize a map and return it
function GMinit(mapid) {
    var div = document.getElementById(mapid);
    if (!div) {
        alert("Map region not found");
        return null;
    }

    if (!GBrowserIsCompatible()) {
        div.innerHTML = '<p>Sorry, your browser is not compatible with Google Maps.</p>';
        return null;
    }

    var map = new GMap2(div);

    if (parseInt(div.style.height) >= 350) {
        map.addControl(new GOverviewMapControl());
        map.addControl(new GLargeMapControl());
        map.addControl(new GScaleControl());
    }
    else
        map.addControl(new GSmallMapControl());
    map.addControl(new GMapTypeControl());
    // map.enableDoubleClickZoom();
    map.setCenter(new GLatLng(47.2, 7.5), 8);

    // Allow to click anywhere and display the clicked point's coordinates
    GEvent.addListener(map, 'click', function(obj, point) {
        map.lastPoint = point;  // Keep a copy for the main page
        if (point)
            this.openInfoWindowHtml(point, LatLngToHtml(point.lat(), point.lng()));
    });

    // Add a new member function that creates labeled markers
    map.addMarkerOverlay = function(lat, lng, label) {
        var point = new GLatLng(lat, lng);
        this.addOverlay(GMcreateMarker(point, label));
        return point;
    }

    // Register the cleanup function
    window.onunload = GUnload;

    return map;
}

Die Funktion GMinit wird aus dem onload() Event aufgerufen und gibt ein GMap2-Objekt aus dem Google Map API zurück, das um eine Methode addMarkerOverlay() erweitert ist. Diese Methode erleichtert das Anzeigen von Popup-Meldungen.

Weiter gehts mit einigen PHP-Funktionen zum Auslesen der EXIF-Informationen:

// Utility functions dealing with GPS coordinates from EXIF data

define(NO_ALTITUDE, -1024);

// Convert a lat or lon 3-array to decimal degrees
function exif_degrees($a) {
  @eval("$deg = $a[0]; $min = $a[1]; $sec = $a[2];");
  return $deg + $min / 60.0 + $sec / 3600.0;
}

// Extract lat, lon and altitude from an EXIF GPS array
function exif_gps_vars($exif, &$lat, &$lon, &$alt) {
  $lat = exif_degrees($exif['GPS']['GPSLatitude']);
  if ($exif['GPS']['GPSLatitudeRef'] == 'S')
    $lat *= -1;
  $lon = exif_degrees($exif['GPS']['GPSLongitude']);
  if ($exif['GPS']['GPSLongitudeRef'] == 'W')
    $lon *= -1;
  if (isset($exif['GPS']['GPSAltitude']))
    @eval("$alt = {$exif['GPS']['GPSAltitude']};");
  else
    $alt = NO_ALTITUDE;
}

// Convert decimal degrees to deg° min' sec" H
function exif_dec_to_DMS($dec, $hemi_pos, $hemi_neg) {
  $absdec = abs($dec);
  $deg = intval($absdec);
  $absdec = ($absdec - $deg) * 60;
  $min = intval($absdec);
  $sec = ($absdec - $min) * 60;
  return sprintf("%d° %02d′ %05.2f″ %s",
    $deg, $min, $sec, $dec >= 0 ? $hemi_pos : $hemi_neg
  );
}

// Convert an EXIF GPS array to HTML-usable text
function exif_to_html($exif) {
  exif_gps_vars($exif, $lat, $lon, $alt);
  $lat = exif_dec_to_DMS($lat, 'N', 'S');
  $lon = exif_dec_to_DMS($lon, 'E', 'W');
  $alt = intval($alt);
  return "$lat, $lon" . ($alt == NO_ALTITUDE ? '' : " ($alt m)");
}

Diese Funktionen werden in der Karten-Seite zusammengesetzt:

PHP-Code:

$def_image = '/pic/glasses.jpg';
$image = isset($_GET['image']) ? $_GET['image'] : $def_image;

function image_exif_gps($file) {
  if (
    ($exif = @exif_read_data($_SERVER['DOCUMENT_ROOT'] . '/' . $file, 0, true)) !== false &&
    $exif['GPS']
  ) {
    exif_gps_vars($exif, $lat, $lon, $alt);
    // Return a JavaScript dictionary containing all useful GPS info
    return "{isValid: true, lat: $lat, lon: $lon, alt: $alt, file: \"$file\"}";
  }
  else
    return "{isValid: false, file: \"$file\"}";
}

JavaScript-Code:

var gmap;

window.onload = function() {
    if (gmap = GMinit('map')) {
        gmap.addMarkerOverlay(47.0452, 7.2713, 'Home, sweet home!');
        var gps = gmap.gps = <?php echo image_exif_gps($image) ?>;
        if (gps.isValid)
            gmap.setCenter(
                gmap.addMarkerOverlay(gps.lat, gps.lon, LatLngToHtml(gps.lat, gps.lon)),
                14, G_SATELLITE_MAP
            );
    }
}

Das Besondere dabei ist, dass die PHP-Funktion image_exif_gps() dynamisch ein JavaScript-Objekt generiert, das die GPS-Koordinaten enthält.

Den Update-Mechanismus beschreibe ich in einem nächsten Post.

Update: Hier gibts den versprochenen Update der GPS-Position im Bild.

23:33 [/software/php] exif_gps_gmap Google Trackback
Tags:

2006-12-08

Cisco firewalls messing with SMTP STARTTLS?

Ever since our company has implemented a new Cisco firewall, I’m no longer able to send e-mail using TLS. This is what my client sees after connecting:

> 220 **********************************
< EHLO [10.23.0.221]
> 250-my.mail.server
> 250-PIPELINING
> 250-SIZE 10240000
> 250-VRFY
> 250-ETRN
> 250-XXXXXXXA
> 250-ENHANCEDSTATUSCODES
> 250-8BITMIME
> 250 DSN

Strange how the 220 and the 250-STARTTLS lines are mangled… I have verified with tcpdump that what the server sends is correct.

09:35 [/software] cisco_messing_with_starttls Google Trackback
Tags:

2006-06-28

(Nicht nur) schöne Graphen von Web-Seiten

Sala hat ein Java-Applet geschrieben, das Web-Seiten visualisiert. Die DOM-Struktur wird als farbige Grafik angezeigt, wobei die Farben Rückschlüsse auf die verwendeten Elemente (<div> vs. <table>, etc) erlauben. Hier als Beispiel meine Primzahlzerlegung:

[via Hacking for Christ]

23:43 [/software/web] html_vizualization Google Trackback
Tags:

2006-05-11

Niederschlagsradar + Google Earth = ?

In letzter Zeit habe ich mich mit Google Earth beschäftigt; momentan sind gerade zwei Projekte am Laufen, über die ich noch nicht viel sage.

Ein kleiner Mashup ist aber heute so nebenbei noch entstanden: ein Overlay des Niederschlagsradars über die Schweiz:

Die Projektion stimmt leider nicht in allen Ecken hundert prozentig, aber was Google Earth aus diesen paar Zeilen XML macht, ist schon gewaltig!

00:03 [/software] ge_precipradar Google Trackback
Tags:

2006-03-26

Released: plagg 1.4

Download, Changelog.

Grösste Änderung: Link- und body-Ersetzungen sind jetzt eigene XML-Elemente unter einem <outline>-Element. Deshalb können sie auch mehrmals angegeben werden.

23:12 [/software/python] plagg_1_4 Google Trackback
Tags:

2006-02-02

Backup-Tips eines alten Hasen

Tim Bray hat eine gute (und einfache) Beschreibung seiner Backup-Praktiken. Vor allem dieser Abschnitt beeindruckt mich, ist aber wegen der grassierenden Windows- und Office-Abhängigkeit schwer zu verwirklichen. Aber hey, Open Office ist unser Freund!

09:43 [/software] backup_tips Google Trackback
Tags:

2006-01-23

Installier-Wehen

Es ist ja wirklich kaum zu glauben, welche Höhen und Tiefen ich heute beim Installieren zweier Betriebssysteme durchgemacht habe. Zur Veranschaulichung der Tiefen nur dies: Diesen Post schreibe ich direkt auf der Konsole meines Servers. Aber ich beginne besser am Anfang…

Endlich habe ich mich durchgerungen, meine seit fast zehn Monaten brach liegende Samsung-HD in Betrieb zu nehmen. Meine Überlegungen zur Partitionierung ergaben folgendes Ergebnis:

Partition   Inhalt              Grösse
hda1        /boot                 64 MB
hda2        Windows system C:     50 GB
hda5        Linux swap             1 GB
hda6        /                      5 GB
hda7        /home                 15 GB
hda8        Windows data   D:   ~128 GB (Rest)

Beide bootbaren Partitionen (/boot und Windows system) lagen so innerhalb der ersten paar GB. Das sollte mal vom BIOS her keine Probleme geben. Also die beiden alten Scheiben ausgebaut (man will ja einen Plan B haben), die neue Scheibe eingebaut, gebootet: “Error loading operating system”. Soweit noch keine Überraschungen.

Ubuntu 5.04 (Hoary Hedgehog)

Vor einiger Zeit hatte ich mir fünf Ubuntu-CDs bestellt, und jetzt war die Zeit gekommen, eine davon einzusetzen. Ich bootete nochmals mit der Install-CD, und keine 45 Minuten später konnte ich aus Firefox auf meinem HP 2610 über Ethernet Webseiten ausdrucken.

Nun, leider gibt es zum Thema Ubuntu nicht mehr zu schreiben, denn alles funktionierte — ok, nur noch dies: nach einer weiteren halben Stunde hatte ich mich in einem selbst kompilierten Psi bei meinem Jabber-Account angemeldet!

Windows XP Professional SP2

Der geneigte Leser ahnt es bereits, nach diesem Höhenflug musste der Absturz folgen. Ein ungutes Gefühl beschlich mich bereits während des Kopierens der Dateien von der XP-CD auf den Disk, weil einige Dateien nicht gefunden wurden. [Kleiner Einschub: weshalb müssen diese Dateien eigentlich zuerst in ein Installations­verzeichnis, damit sie von dort aus dann nochmals ins eigentliche Windows-Verzeichnis kopiert werden können? Ist es das Ziel, schon von Anbeginn an eine möglichst fragmentierte Platte zu haben? Ende des Einschubs] Das konnte mich aber noch nicht beirren, denn jeder weiss ja, dass Windows Dateien installiert, die es nachher nie wieder braucht, oder weiss jemand, wozu “h323.tsp” gut ist? (An alle MCSEs: das war eine rhetorische Frage.) Der Fairheit halber muss gesagt werden, dass alles gut ging, bis ich mich zum ersten Mal anmelden wollte.

Ah, und hier muss ich noch eine Anmerkung zu XPs hellseherischen Fähigkeiten machen: Ich hatte vier User definiert, je einen für Eva, Dinah, Benjamin und mich. Windows ordnet jedem User ein hübsches kleines Icon zu, das man bei Bedarf ändern kann, aber der Vorschlag war folgender: Ich erhielt eine Bassgitarre, Benjamin ein Flugzeug, Dinah eine Schneeflocke, und Eva ein Motocross-Motorrad. Ok, das letzte Beispiel zeigt, dass der Algorithmus noch nicht ganz ausgereizt ist, aber ich habe trotzdem geschmunzelt!

Ich klicke also auf meine Bassgitarre und freue mich schon auf das Teletubby-Thema, da erscheint die Fehlermeldung “Windows-Produkteaktivierung: Ein Problem hat verhindert, dass die Lizenz für diesen Computer überprüft werden konnte. Fehlercode: 0x80070002”. WTF? Ich hatte (m)eine Lizenz-Nummer eingegeben, und Windows hatte nichts daran auszusetzen gehabt. Könnte Microsoft vielleicht Fehlermeldungen so formulieren, dass man mindestens eine so kleine Ahnung hat, in welcher Richtung man suchen soll? Also schrieb ich mir die Fehlermeldung raus und begann mit Michael nach Lösungen zu suchen. Ein vielversprechender Artikel in einer c’t-Hotline deutete darauf hin, dass die Datenträrger­identifikation im MBR nicht mit derjenigen der System-Partition überein stimmte, man solle doch in Knoppix mit einem Hex-Editor die vier Bytes am Offset 0x1B8 aus dem Backup des alten MBRs in den aktiven MBR kopieren. Nichts leichter als das — nein, halt! Ich wollte XP genau deshalb als zweites OS installieren, damit eben ein später installiertes Linux nicht den Windows-MBR zestört! Ich hatte angenommen, dass Windows rücksichtslos einen bestehenden MBR plattwalzen würde, und deshalb den Zustand des MBR nach der Ubuntu-Installation auf einem USB-Stick gespeichert.

Nun, vielleicht war ja etwas dran an diesen Identifikationen, nur hatte ich keine Vergleichsöglichkeit mit einem Backup. Aber da gab es doch noch diese Disk-Seriennummer, die unten an jedem DIR-Befehl ausgegeben wird; Könnte es sein, dass die beiden etwas mit einander zu tun hatten?

Nach einem kurzen Abstecher in die Formate von MBR- und NTFS-Boot-Sektoren fand ich heraus, dass die ID im MBR ein long long war, also 8 Bytes lang, die Disk-ID hingegen nur vier Bytes.

Fortsetzung folgt!

00:16 [/software/windows] windows_woes Google Trackback
Tags:

2006-01-21

Jabber-Client mit pyxmpp

Die Tatsache, dass Google Talk seit dieser Woche auch mit anderen Jabber-Servern kooperiert, hat mich dazu veranlasst, meinen bisherigen Client GAIM zu ghüderen und einen Jabber-Client zu installieren. Meine Wahl fiel auf Psi. Die Installation verlief problemlos, und meine bisherigen ICQ-Kontakte waren sofort wieder vorhanden.

Das Schöne an Jabber ist in meinen Augen ja, dass das Protokoll im Gegensatz zu AIM, MSN &c offen ist und es dashalb auch offene Bibliotheken dafür gibt. Also begann ich nach einem aptitude install python-pyxmpp, einen minimalen Client zu schreiben. Das war trotz der Library-Doku gar nicht so einfach, weil wirklich nur die API beschrieben ist und keine Konzepte und Zusammenhänge erklärt werden. Ich habs trotzdem geschafft:

#!/usr/bin/python
# -*- encoding: latin-1 -*-

import pyxmpp.all
import pyxmpp.jabber.all

config = dict(
    jid='bbolli@swissjabber.ch/bot',	# My Jabber ID
    pwd='secret*007',			# My password
    srv='swissjabber.ch',		# My Jabber server
    def_dest='bbolli@swissjabber.ch',	# Default destination
)


class msgClient(pyxmpp.jabber.Client):

    def stream_state_changed(self, state, arg):
	print 'stream state:', state, repr(arg)
	if state == 'authorized':
	    self.sendmsg()
	    self.disconnect()

    def sendmsg(self):
	m = pyxmpp.Message(from_jid=self.jid, to_jid=self.dest, body=self.msg)
	#m.set_type('chat')
	self.stream.send(m)


if __name__ == '__main__':
    import sys

    if len(sys.argv) == 1:
	sys.argv.append(config['def_dest'])
    elif sys.argv[1] in ('-h', '-help', '--help'):
	print >>sys.stderr, 'Usage: sabber [to_jid] [message]; uses stdin if no message'
	sys.exit(1)
    if len(sys.argv) == 2:
	sys.argv.append(sys.stdin.read())

    me = pyxmpp.JID(config['jid'])
    cl = msgClient(me, config['pwd'], config['srv'], disco_type='bot')

    cl.dest = pyxmpp.JID(sys.argv[1])
    cl.msg = ' '.join(sys.argv[2:])

    cl.connect()
    try:
	cl.loop()
    except KeyboardInterrupt:
	pass

12:46 [/software/python] python_jabber Google Trackback
Tags:

2006-01-06

Installing the new apt GPG key

apt since version 0.6 supports verifying the Releases.gz file with a GPG key. The key used for checking expires after one year, so a new one needs to be installed each year. The easiest way to accomplish this is:

wget http://ftp-master.debian.org/ziyi_key_2006.asc -O - | apt-key add -

[via Debian Administration]

09:58 [/software/debian] debian_apt_key Google Trackback
Tags:

2005-12-13

SUSE Linux für die Bundesverwaltung!

Die Bundesverwaltung wird auf allen ihrer Server SUSE Linux einsetzen:

More Than 3000 Servers Across Switzerland to Run Novell’s SUSE Linux

WALTHAM, Mass., Dec. 13 /PRNewswire-FirstCall/ — Novell (Nasdaq: NOVL) today announced a breakthrough agreement with the Swiss Federal Government that will see the introduction of Novell’s enterprise Linux* technology across Switzerland’s public sector IT infrastructure. Novell was selected following a formal tender process during which the company conclusively demonstrated it can provide the strongest Linux solution for public sector environments. As a result, more than 3,000 servers operated by the Swiss Federal Government will now run on Novell’s SUSE® Linux platform.

“Linux has been gradually introduced into various government departments in recent years, but this is the first formalized procurement process regarding the introduction of Linux at a federal level,” said Jürg Römer, Delegate for Information Strategy of the Swiss Federal Government. “The agreement we have reached applies to the entire Federal Government and will see the adoption of Novell’s SUSE Linux throughout the Swiss federal administration.”

Tom Francese, president of Novell Europe, Middle East and Africa, said, “The Swiss Federal Government wants greater operational efficiencies and lower costs from its technology infrastructure. This agreement is a great vote of confidence in Novell, Linux and open source, and serves as a strong example for other large organizations, whether public or private, who are looking to open standards and open source to improve their operations.”

[via GrokLaw]

Jürg Römer ist neben seinem Amt als Delegierter für die Informatikstratigie des Bundes auch Vorstandsmitglied des Vereins Linux Solutions e.V..

21:40 [/software] suse_for_bund Google Trackback
Tags: