Eine Novemberreise: München, Zürich, Köln, Friesland, part deux

Frohes neues Jahr, geschätzte Leser in potentia! Wir geben uns heute auch wieder leutselig und lassen den ganzen “warum-hab-ich-so-lange-nichts-geschrieben-Tanz” einfach mal weg.

Vorwärts! Letztes Mal waren wir in Köln stehengeblieben, wie ja schon so mancher ICE haha. Ne stimmt gar nicht, wir waren noch in Zürich (man sollte vielleicht erstmal seinen eigenen Post wieder lesen…)

Nachdem mich meine Gastgeberin rausgeworfen hatte andere Gäste erwartete, war ich mit dem “Pflichtteil” durch und entschied mich nach etwas Rumeierei für Köln, was ich schon immer mal besuchen wollte. Bonus: Von Zürich gut per Bahn zu erreichen ohne ewiges Umsteigen.

Kleiner Ausflug: Ich habe noch Ewigkeiten recherchiert, ob man irgendwie per Binnenschiff die Strecke oder zumindest einen Teil am Rhein lang fahren kann. Von Zürich nach Basel ist es eine kurze Zugfahrt, und Basel und Köln sind dann beliebte Stationen von Kreuzfahrten – nur leider überhaupt nicht im Winter 😦 Die Kreuzfahrten sind dann auch leider recht teuer, vor allem wenn man nur eine Strecke fahren würde, normalerweise sind die ja so gedacht, daß man an einem Hafen einsteigt und dann da auch wieder abgeliefert wird.

Es gibt eine Reihe von Anbietern für Frachtschiffe, z.B. https://frachtschiffreisen-pfeiffer.de, wo man sich in eine Kabine einmieten kann. Das würde mich ja ungemein reizen, einmal mit einem dieser großen Schüttgutkähne herumzutuckern. Leider sind die nicht so “benutzerfreundlich” (verständlicherweise, das Mitschleppen von romantisch verbrämten Landratten ist da nicht das Hauptgeschäft sondern wohl eher ein wohlmeinendes Hobby) – die meisten scheinen so zu funktionieren, daß man einen gewissen groben Zeitraum und ungefähre Strecke vorher bucht und dann recht kurzfristig zu einem Hafen fahren muß. Muß ich irgendwann mal machen, aber diesmal nicht praktikabel…

Köln also! Erster Eindruck: Der Dom ist ja praktisch direkt in den Hauptbahnhof gebaut bzw. umgekehrt 🙂 Überhaupt, um das mal vorzugreifen, scheint mir die Kölner Innenstadt viel dichter zu sein als andere Städte wie z.B. Berlin – was wohl historisch bedingt ist, eine so alte Stadt zwischen einem nicht verlegbaren Fluß und alter Bausubstanz ist dann schnell “komprimiert” und kann sich nicht wie z.B. Berlin in der Brandenburger Einöde ausbreiten.

Zweiter Eindruck: Der Kölner Dom ist riesig, beeindruckend, protzig, und riesig.

Ich bin ja sehr unreligiös aufgewachsen, und dazu noch im Norden wo die großen Kirchen alle strenge graue evangelische Burgen sind, die eher “Zuflucht vor Sturmflut” ausstrahlen als “Christ sein ist ne Gaudi”. Der Dom ist da der Gegenentwurf – alles was irgendwie kostbar, heilig, oder älter als 1000 Jahre alt ist, wurde hier eingebaut oder gesammelt. Unbedingt einen Besuch wert.

Was sonst noch tun in Köln an zwei zugigen kalten Tagen? Kölsch trinken und gut Essen, natürlich.

Absolutes Highlight: Gaststätte Lommerzheim, wo man auch in der früh ungefragt von strammen Kölner Burschen ein Kölsch hingestellt bekommt, und wo es die dicksten, zartesten Koteletts gibt die ich je vernahm. Definitiv nicht gesund. Und wie schon oben angesprochen: Alles recht dicht und eng bestuhlt, groß gebaute Eigenbrötler wie ich müssen sich auf Ellbogenkontakt und unfreiwillige Unterhaltungen einstellen.

Kölsch ist auch ein prima Getränk – Schnelleinweisung für alle Unwissenden: Man bekommt ein sehr kleines Gläschen auf einen Bierdeckel gestellt, und auf dem Deckel wird mit einer geübten Drehung des Handgelenks ein Kugelschreiberstrich gezaubert. Daraus ergibt sich dann später die Rechnung, und aus dem Gläschen die gute Laune. Mir schmeckt das ganz hervorragend, und durch die kleinen Gläser ist es immer frisch. Wer genug hat oder Pause machen will, legt den Bierdeckel oben drauf. So ist das Originalprotokoll, soweit ich das verstanden habe – in vielen Läden wird aber auch noch gefragt ob man wirklich noch eins möchte, ich vermute gerade da wo viele sonst überforderte Touristen einkehren.

Wie der Dom ist wohl auch die Hohenzollernbrücke ein Standard für den Besucher. Da sind ein paar Vorhängeschlösser angebracht.

Etwas weniger offensichtlicher Tip von mir: Da ich auf der “falschen Seite” mein Hotel hatte, bin ich immer über die Hohenzollernbrücke in die Stadt gelaufen, via dem auch schicken Rheinboulevard, und über die südlicher gelegene Deutzer Brücke wieder zurück. Unter den Brücken fahren nachts die schon oben erwähnten Schüttgutfrachter durch die Dunkelheit den Rhein hinab. Auf den Brücken kann man die vorbeiziehen sehen, und das Tuckern und die Lichter im Dunkeln tun Ihr Übriges. Wenn es nicht so schneidend kalt gewesen wäre…

2019-11-21 14.54.49
Mehr Essen: “Halve Hahn” im Gaffel am Dom

Man könnte jetzt den Eindruck bekommen, daß ich mich zwei Tage nur durch die lokale Küche gefressen und dann durch die lokalen Kneipen gesoffen hätte. Dieser Eindruck ist natürlich korrekt. Ich war aber zwischendurch nüchtern genug, um noch das Museum für Angewandte Kunst zu besuchen:

Es waren nicht alle Ausstellungen geöffnet, aber was ich gesehen habe hätte ich eher als “Museum des Industriedesign” bezeichnet. Aber obwohl ich mir oft mehr Details an den Tafeln gewünscht hätte, waren viele interessante Stücke zu sehen. Die “Kugel” oben, die aus einer Vielzahl von Schüsseln und Tellern verschiedener Größen besteht, muß ich unbedingt irgendwann mal haben.

Sonstige Notizen:

In der Sonderbar gibt es einen Nagelklotz! Das habe ich seit den Dorffesten meiner Kindheit nicht mehr gesehen 😀

2019-11-20 22.15.15

Im HoteLux konnte ich endlich mal Chicken Kiev probieren. Der Laden ist vielleicht etwas bemüht “sowjetisch”, aber die Küche kann was.

Nach der ganzen Völlerei dann noch ein paar Tage bei meinen Eltern im Friesland verbracht. Dort war es eher sterbenslangweilig ruhig und friedlich:

Die Hooksieler Fußgängerzone und der Alte Hafen – ich hab natürlich ein bißchen geschummelt bei den Bildern, es sind nicht wirklich alle Bewohner am Ende der Touristensaison geschlossen wieder ins Meer getaucht. Aber wenn selbst die einzige Kneipe des Orts bis Weihnachten geschlossen hat…

Und man einen netten Stein findet und sich mit Ihm anfreundet:

2019-11-25 14.39.14
Ich nenne Ihn “Bricky”. Ist eher schweigsam.

…dann ist es Zeit wieder ins dreckige alte Berlin zu fahren. Und dann, Monate später, darüber zu bloggen. Bis ein ander Mal!

Solving “Bundler::GemfileNotFound” or mysteriously missing gem

Here’s a short interlude: I was having the worst time with this error, partly because the error message is pretty misleading, and partly because I’m an idiot. One of these problems could be solved…the other has to be worked around 😉

So, the issue was that we were trying to run one Ruby script from another via the “shell-out” mechanism. There are a couple of ways to do this (Here is a good overview), but we’re using the good old `Backticks` as we are not concerned about security for now (there’s no user input, everything is hardcoded). But when running the “inner” script, we get this error:

/home/mt/.rvm/gems/ruby-2.4.2/gems/bundler-1.17.1/lib/bundler/definition.rb:32:in `build': /home/mt/Development/crowdfunder_scraper/Gemfile not found (Bundler::GemfileNotFound)

when using the “inline” Gemfile syntax, or when using a normal Gemfile:

`require': cannot load such file -- httpx (LoadError)

one of our defined gems would be mysteriously missing. When cd-ing into the “inner” directory and running the script, it works, of course.

This is of course the abridged version. I was spending a whole lot of time fiddling around, trying to pinpoint the problem. A misleading thought was that the issue might stem from rvm and bundler not properly loading in the sub-shell environment, so a lot of cd-ing around within the backticks was tried: cd ruby && ./scrape_crowdfunder

To make a tedious story short, the hint that was finally pointing to the solution was that discovering (after converting both “outer” and “inner” scripts to a normal Gemfile again) that the same issue also occurs when running the inner script from the outer directory (both containing Gemfiles):

crowdfunder_scraper $ ./ruby/scrape_crowdfunder 
./ruby/scrape_crowdfunder:6:in `require': cannot load such file -- httpx (LoadError)

So what seems to happen is that the “inner” script keeps the gems loaded from the “outer” environment. The same thing happens when running via Backticks. Googling “ruby subshell inherits gems?” finally has the solution: Use Bundler.with_clean_env ! Go ahead and read that article, it explains the issue quite well. Basically, bundler sets up a couple of ENV variables when a Gemfile is encountered, and within the same shell and directory, doesn’t change it again. When putting the shell-out backticks within that method’s block, all is well.

So just some additional notes here: Since that article was written, the Bundler method was renamed to Bundler.with_original_env .

And also, I made a small git repository to demonstrate and test the issue for me and anyone else: https://github.com/MGPalmer/bundler_env_error_test

In it, we have the same setup as my problem: An “outer” and an “inner” directory, both having a Gemfile in it. The outer Gemfile actually requires no gems at all, the inner one wants cowsay.

In both dirs we have a script, the outer one simply prints a message and then shells out to the inner script, once within Bundler.with_original_env‘s block, and once without it. The former call works, the latter one reproduces the problem that the inner script can’t find the gems it wants:

bundler_env_error_test $ ./wrangler 

Let's get wranglin'.
 _______________________ 
| Moo moo I'm a cow yo. |
 ----------------------- 
      \   ^__^
       \  (oo)\_______
          (__)\       )\/\
              ||----w |
              ||     ||
Traceback (most recent call last):
	1: from ./cow:5:in `<main>'
./cow:5:in `require': cannot load such file -- cowsay (LoadError)

So there we go. Another one of these stumbling blocks when developing. I learned a little more about how Bundler works, but there was so much wasted time, a pity.

A somewhat amusing coda to this – after changing the test code from the last article to use with_original_env , the issue was solved as described above. But then suddenly, the “inner” Ruby script didn’t pick up the provided CROWDFUNDER_PROJECTS_URL env variable value anymore. For a short time I wasn’t sure I was using Ruby’s accessor to the ENV correctly, but I then realized that with_original_env was doing exactly what it’s saying on the tin – it resets the ENV, wiping out what we added to it within the script 😀

I realized that it’s a much cleaner interface anyway to simply add the url as a command-line parameter, and switched the code to that. So, next time: Finally finishing the tests.

How not to create a stupid Rails extension that screams at you

Hello dear nonexistent readers, it’s story time again! This time, as last time, we’ll talk about how computers make our lives harder when we try to make them do stuff.

TL/DR of actually useful bits of info in this rant:

  • Spammers ruin everything. They suck.
  • Modern browsers make it impossible to just up and play sound at the user. Some kind of interaction is necessary beforehand (there are exceptions for sites that repeatedly use sound, like a video site), usually a button press etc. This actually makes a lot of sense and seems to be implemented pretty neatly.
  • Before fiddling endlessly with stuff and reading messy Stack Overflow answers, it makes super duper sense to take some minutes to read the actual browser docs…

Ok back to ranting

What I wanted to make was really stupid: An extension to the Rails active record framework, which would allow anyone to add a long-missed feature to validations: That when an error occurs, the page would not only display an error message but would also play a sound file really loudly that screams at you for being so stupid to cause errors.

Yeah yeah. One of those ideas that seemed hilarious at 2 am in the morning on the way home from the pub. Although this video, which is the inspiration, still cracks me up…

But I wanted to go at it really professionally. I had everything lined up – a list of requirements, possible bonus features (I18n for sound files? Try to play them in the Rails console as well?), plans for seeing how to create and publish a rubygem in 2019 (I made some gems before but the helpers around that kept changing), etc.

And so I spent quite some time on writing up lists of that. But I should have listened to a nagging feeling – that I should check first on how to actually play sound files in a browser on a page load. Because that sounded a bit like it might be misused and therefore be a bit tricky.

So I finally started on doing that. Some googling led to this SO question … which leads to a sinking feeling in my gut. There’s a whole lot of answers, all quite different, more or less contradicting, and lots of comments saying “doesn’t work in Browser x”…this seems like one of those browser-support-morasses where there’s a lot of history around a feature, everything evolved differently in different browsers, and lots of more or less smart people created workarounds and libraries and left a lot of deprecated info flying around online…i.e. the bad kind of web development. Been there. Not fun.

I also found something a bit more professional: https://developers.google.com/web/updates/2017/09/autoplay-policy-changes but it’s about videos? So I didn’t really read it.

But oh well, let’s actually do something. The first SO answer had something simple looking, so let’s make a test page:

<!doctype html>
<html lang=en>
  <head>
    <meta charset=utf-8>
    <title>Audio test</title>
  </head>
  <body>
    <p>Blah blah</p>
    
      var audio = new Audio("aaa.ogg");
      audio.play();
    
  </body>
</html>

Saving this as a .html file, and opened in a browser, it should directly play that “aaa.ogg” sound file. Easy peasy.

Right, we need a sound snippet, right? Let’s just record a quick soundbite (well, a scream, in keeping with the idea) with the Laptop microphone.

Another aside; On the joys and sorrows of using Ubuntu

I’m one of those freaks in web development that does not use a Mac. Sue me, I never got used to them – I was a Windows kid, then switched to Ubuntu when using Ruby/Rails on Windows was way, way too painful (never say the word “cygwin” to me…)

Ubuntu the good bit: Using the “home” button and typing “record” shows there are no programs installed that would help me, but asks if I want to install “Sound Recorder”. I say yes. Bam, it installs, and opens, and I can record sound. Takes like 20 seconds. Ain’t that something?

Buuut…ok where is my recording? Hello? Mr. Sound Recorder Program?

Not shown: A sensible UI

There is absolutely no way of actually interacting with your recordings – you can only play or delete them. After some educated guessing, it turns out the files end up in ~/Recordings. And they are in .ogg 😦

Ok back to playing .ogg files in the browser

Now we can put the aaa.ogg file in the same folder as the test html file, open it again, and….nothing.

Well except for this helpful error message (in the dev tools console): “Uncaught (in promise) DOMException” . Well fuck you too, Chrome. Googling reveals that this means “Autoplaying is not allowed, fool”.

Firefox has a much better error message: “NotAllowedError: The play method is not allowed by the user agent or the platform in the current context, possibly because the user denied permission.”

So now we get to the end of this little adventure. After actually reading this (which I skimmed over earlier): https://developers.google.com/web/updates/2017/09/autoplay-policy-changes – well, it really makes sense, doesn’t it? If it’d be possible to just start playing sound/video files, all pages would be full of ads and other bits of junk that blared at you. Some more fiddling to actually see this in action:

<!doctype html>
<html lang=en>
  <head>
    <meta charset=utf-8>
    <title>Audio test</title>
  </head>
  <body>
    <p id="hovercraft">Press play on tape</p>
    <button id="tape">Play</button>
    
      var audio = new Audio("aaa.ogg");
      document.getElementById("tape").addEventListener('click', function() {
        audio.play();
      });
      document.getElementById("hovercraft").addEventListener('mouseover', function() {
        audio.play();
      });
    
  </body>
</html>

If you load this in a browser, and move the mouse pointer over the button, nothing happens. But if you click the button, the sound plays – and if you mouse over after that, it also plays. The button press is needed to demonstrate that the user actually wants something from the page, and after that it is allowed to play sounds directly.

Which is all well and good but it kinda makes the original idea moot – because the fun bit is the immediate screaming after you submit a form. No fun if you have to allow it first 😦

The moral of the story

Well, one learning is that browsers are really quite sophisticated – I never thought about the implications of having an Audio API and dealing with malicious websites. I think the approach taken is pretty neat here.

Also, I could have saved a whole lot of time by looking at that doc in the first place. This is something I thought I wasn’t bad at, but I went ahead and made a castle in the sky before checking for the obvious cloud zoning laws and stratospheric building construction permits 😉

Keeping Ruby weird with emojis

Have a look at this: https://medium.com/carwow-product-engineering/emoji-driven-development-in-ruby-2d54264f7b08

Isn’t that just grand? 😀 It’s been quite a while (it might be 15 years or so) since I stumbled upon this little unusual programming language from Japan, which I soon fell in love with. Matchmaker was the weird, quirky, clever code-art that _why the lucky stiff made. Sadly he just up and info-suicided all his online stuff and was gone. This reminds me of his stuff 🙂

Bloody bloody computers (TODO #1 update)

This is the update to TODO #1 – pointing my old monogreen.de domain to this blog (which is the hosted “free” plan from wordpress.com, i.e. no bells and whistles).

A bit of history: I’ve been using hosteurope to host my mailboxes and to register some domain names for years (I get a warm and fuzzy feeling by actually owning my email address and my mails – I’m hoping of course that hosteurope, compared to say, Google, is not interested in scanning my emails and selling my habits…). But I only bought the “email” package from hosteurope, and not anything else like servers or webspace hosting.

Naturally I’d like to point monogreen.de to this blog. As I’ve written last time, you have to have a webspace package booked in order to set that up, so I bought the cheapest plan.

First hurdle: It turns out they make that available quite fast (<15min) after ordering – but you have to log out and back in to see the new package in KIS. Groan.

Next hurdle: As I now had two packages (one email-only, one webspace which also includes a mailbox as well as webspace, php hosting, etc.), I had to “transfer” the domain monogreen.de from the email package. With some trepidation, I did so, as it seemed like the “redirect” setting would only be available on the webspace package, and I assumed I could still have the email addresses themselves point to the actual inbox I’ve been using for years.

Well that worked alright, and could immediately set up the redirect under the webspace package. However…the redirect didn’t work. Knowing things sometimes take a while to start working at hosteurope, I waited a while, but still nothing. Then, being suspicious, I sent myself an email from a different address/provider, and – it bounced o.O . I had managed to break my primary email address.

Photo Credit: Kalle Gustafsson https://flic.kr/p/GweE1X

Half a panicky hour later I had everything back to as it was before (including setting back up the various email aliases to the actual mailbox, which the “move” had severed) – and here’s two tips for anyone in this situation, and for myself in the future:

  • Every package in KIS has its own block of menu entries – and especially the “Domain settings”. Also there is a general one. So in my case there were three places to look for when trying to move the domain back from the webspace package to the email package (the correct one is the “general” area)
  • Many changes in KIS take ~15min to take effect (they say that in the interface, actually, but you usually assume this is only a general “yeah yeah mostly immediately but let’s cover our asses” policy – it’s not with hosteurope. Needless to say that this makes trying out things extremely cumbersome and error-prone…

And fun fact: After all that, the damn redirect still didn’t work…until next morning, after I had given up, and it suddenly worked just perfectly. Groan.

In summary: Mission accomplished but with too much panicky clicking around…

TODO #1 – my own damn domain

TODO for next time (update: here it is) : Make monogreen.de show this blog. I own the domain, I’ve registered it at hosteurope.com a long time ago – but it appears you can’t add any sort of redirect etc. except editing the DNS settings, and it’s probably quite useless to have monogreen.de point to WordPress’s server(s). After getting lost for many a year in KIS, the ever-so-confusing admin interface from hosteurope, I ordered the smallest “Web Pack”, which hopefully then lets me add redirects…you also get classic shared managed hosting – maybe I’ll also play around with that. Should be strange after years of administrating proper servers from scratch…