Allgemein

Fehlermeldung bei Gmail (bei Zugriff auf Mailserver von Plesk): TLS Negotiation failed…

Die genaue Fehlermeldung bei Gmail lautet:

TLS Negotiation failed, the certificate doesn’t match the host., code: 0

Ich habe mir soeben eine neue Email über Gmail eingerichtet. Das hat mich leider einige Nerven gekostet. Das Setup war dabei etwas ausgefallen. Aber weil es so verzwickt war möchte ich hier kurz das Problem und meine Lösung schildern.

Die Ausgangssituation: Domain bei Anbieter A und Umleitung der HTTP-Anfragen auf andere IP-Adresse

  • Domain für Email-Adresse (also example.com für info@example.com) bei Anbieter A
  • Weiterleitung der HTTP-Anfragen auf einen Shop bei Shopify (per DNS)
  • Mailserver auf einem virtuellen Server (von Anbieter B), der mit Plesk konfiguriert wird. Die Adresse lautet hierbei: xxxxxxx.anbieter-b-server.net. Wir nennen ihn im folgenden einfach mal Plesk-Server

Kleine Anmerkung: Der Anbieter A ist in meinem Fall Domain-Offensive (www.do.de) und Anbieter B (der Hoster des Plesk-Servers ist Strato). Hier ein Screenshot der DNS-Einstellungen von Domain-Offensive.

DNS-Einstellungen bei Weiterleitung der HTTP-Anfragen zum Shop und der Anfragen für Email an anderen Server.

Das Ziel: Zugriff von Gmail auf den SMTP-Server (von Anbieter B)

Da der Mailserver von einem anderen Anbieter betrieben wird als das Domain-Hosting-Paket und HTTP-Anfragen wiederum auf einen anderen Server umgeleitet werden, war es für Gmail nicht ganz einfach, auf den SMTP-Server des Plesk-Servers zuzugreifen. Genau das war aber das Ziel.

Letztendlich ist mir dieses auch gelungen – Allerdings erst nach etlichen Versuchen. Denn immer wieder kam bei der Einrichtung in Gmail Fehlermeldungen wie diese:

Fehler bei der Authentifizierung. Bitte überprüfen Sie Ihren Nutzernamen und Ihr Passwort.
Serverfehler “TLS Negotiation failed, the certificate doesn’t match the host., code: 0”

Gmail-Einstellungen für externen SMTP-Sever

Was ist also zu tun, um unter Verwendung einer sicheren Verbindung (SSL) den richtigen SMTP-Server anzusprechen?

Wie kann man bei Gmail per SSL auf den richtigen SMTP-Server zugreifen?

Die Ursache dieses Problems ist, dass das Zertifikat, dass via Plesk für die Emails der Domain konfiguriert sind, nicht für die Domain zertifiziert wurden. Nach unendlich langem Suchen und Ausprobieren, habe ich dann folgende Lösung gefunden:

1. Der SMTP-Server muss der Server des Anbieters sein (nicht die Domain)

Das heißt konkret:
Bei SMTP-Server “xxxxxxx.anbieter-b-server.net” eintragen
… und NICHT: “smtp.example.com”

2. Zertifikat überprüfen

Hierzu ein sehr wichtiger Tipp, der mir letztendlich den Anstoß in die richtige Richtung gegeben hat:
Auf https://de.ssl-tools.net/mailservers kann man jeden Mailserver auf das richtige Zertifikat hin überprüfen. Die bizarre Meldung, die von Gmail kam, und zu der mir im übrigen auch niemand bei Strato oder meinem Domain-Provider helfen konnte, wird also somit entschlüsselt.

Unter Zertifikate sieht man dann, welche Zertifikate verwendet werden. Und hier liegt der Knackpunkt:
Anscheinend wird durch Plesk standardmäßig ein SSL-Zertifikat hinterlegt, was auf den Hostnamen plesk.com ausgestellt wurde. Das ist natürlich Murks. SSL/TSL-Zertifikate sollten schließlich dafür da sein, den Absender zu verifizieren.
Daher muss man jetzt nur noch …

3. Bei Plesk das richtige Zertifikat hinterlegen

Hierfür folgende Kurzanleitung (unten ein Screenshot mit den Einstellungen für Plesk):

  1. Plesk-Login → Tools & Einstellungen → SSL/TLS-Zertifikate
  2. Folgende Einstellungen vornehmen:
    • Lets-Encrypt-Zertifikat auf den Domainname des Servers (xxxxxxx.anbieter-b-server.net) erstellen
    • Zertifikat zum Schutz von E-Mails → das soeben ausgestellte Zertifikat zuweisen
    • Das Lets-Encrypt-Zertifikat als Standard verwenden (es muss dann in der liste fett markiert sein.
Plesk-Einstellungen für Zertifikate, um einen sicheren Zugriff auf den SMTP-Server (für das Verschicken von Emails) zu gewährleisten.

Danach kann man wieder das Zertifikat überprüfen (https://de.ssl-tools.net/mailservers)

Und, wenn alles richtig ist, sollte es bei der Zertifikatsüberprüfung keinen Fehler geben. Auch sollte Gmail nun auf den SMTP-Server zugreifen können.

Von Parallels Desktop 12 auf Mac Apache zugreifen (MAMP)

Wie man von Paralells Desktop (Version 12) auf Mac-Apache zugreift (MAMP):

1. IP auf dem Mac ermitteln:

– Systemeinstellungen > Netzwerk > WLAN > Oben rechts die IP herauslesen („WLAN“ ist mit „…“ verbunden und hat die IP-Adresse 123.456.789.1)

2. IP in Hosts-File in Windows eintragen

– hosts file liegt in:
C:\Windows\System32\drivers\etc

– Unten links nach Notepad suchen
– Öffnen als Administrator
– File > Open hosts
– Folgendes eintragen:
123.456.789.1 local.my-page-1.com
123.456.789.1 local.my-page-2.net

3. Falls 403-Error (forbidden), so ist das ein Hinweis dafür, dass der Web-SErver vom Mac gefunden wurde! Hier muss eventuell nur eine IP in der Applikation (z.B. in Symfony in der app_dev.php) hinterlegt werden. Eine Möglichkeit, dies herauszufinden, ist über XDebug.

4. Debug-Hilfe:

4.1. Virtual hosts deaktiviern
– Virtual Hosts in ‘/Programme/MAMP/conf/apache/extra/httpd-vhosts.conf’ auskommentieren oder löschen (Backup!)
– index.php in Apache Document Root legen
– Dieses sollte dann im IE aufgerufen werden können. Unter der Mac-IP (siehe oben): http://123.456.789.1

4.2 Error-Log suchen und debuggen.
Wenn man die Mac-IP im IE eingibt und Einträge i Virtual-Hosts-File hat, so wird manchmal der erste Eintrag der Virtual hosts geloggt.

Symfony 3 – Log in separate file

In Symfony, it’s pretty easy to log messages in a file. You have to use the Monolog Bundle and then follow the instructions in:

https://symfony.com/doc/current/logging.html

But when you want to log in a separate document, it can be quite a hustle. An easy method which I found out is the following:

Define two new services (in any services.yml ):

In the arguments of the service my_new_logger_handler  you specify the path of the new file in which you want to log.

Then, using Dependency Injection, it’s pretty easy to include that new service and log info messages:

service.yml:

MyService.php:

Mac & MAMP: Neuen Virtual Host anlegen

Zusammenfassung:

Für ein neues Projekt ist es das beste, wenn man einen neuen Virtual-Host anlegt, sodass man eine einfache URL zum ausprobieren hat:
z.B. local.meinprojekt.com

Setup für dieses kurze Tutorial: Mac OS & MAMP

1.) Die hosts-Datei anpassen

  • Folgende Datei öffnen: /private/etc/hosts
    (Ein Finder-Fenster öffnen und dann im Menu auf: Gehe zu > Gehe zu Ordner)
  • Die Datei kann nicht bearbeitet werden, daher erst die Datei auf den Schreibtisch kopieren und dann bearbeiten. Nach dem bearbeiten wieder die ursprüngliche Datei ersetzen.
  • Trage folgende Zeile ein:

2.) Die Apache-hosts-Config anpassen bzw. überprüfen:

  • Datei bearbeiten: /Programme/MAMP/conf/apache/httpd.conf
  • Die folgende Zeile darf nicht auskommentiert sein:

3.) Die vhosts-Datei anpassen:

  • Datei: /Programme/MAMP/conf/apache/extra/httpd-vhosts.conf
  • Eine neuen Eintrag hinzufügen der Form:

4.) MAMP restarten

SQLSTATE[HY000] [2002] No such file or directory (after magento setup:upgrade on Mac OS)

The problem occures, when you trying to upgrade Magento with the terminal (for example on your localhost which is a Mac)

You typed in:

and the result ist:

and/or

The problem is, that php in the Mac-Terminal is running with another php-ini-file than the Apache-Server.

To test that, do the followin:

1.) Find out the path of the php.ini-file that is used by the Mac.
For thattype into the terminal:

2.) Find out the php.ini-file of your localhost Apache-Server
Create a phpinfo-file (phpinfo.php) with the content: <?php phpinfo() ?> . I’m currently using Mamp Pro so for that example the path is:

If the path is NOT the same as the one your Mac is using in the terminal, you now know where the problem is. (Magento is also explaining this issue in this post.)

3.) Create Symlink (symbolic link) from one php.ini-file to the other.
One solution to correct that is, to create a simlink from your Mac-php-ini file to the MAMP Pro – directory, which can be done by the simple command:

 

Docker & Mac OS – Setting up a php development container

It has cost me quite a while to set this up. So I just want to share a simple Tutorial to set up a php development environment with docker on Mac OS.

Goals:

What we want to achieve is, that we have an environment, in which we can develop any php-app and – more important – edit it on the fly with our IDE. For instance, I use PhpStorm, where I have a project folder. And whenever I edit and save something in the folder, I want that theses changes appear in the browser directly.

For me, It was quite a hassle to set this up, so here I want to share my learnings.

Prerequisites:

  • First, you should have understood the basic concepts of docker and you should also have gone through the Getting Started. For example, you have to know:
    • what is an image and a container,
    • what the Dockerfile is good for and
    • what are the basic commants of docker (docker ps, docker-machine, etc.)
  • Secondly, you should have installed boot2docker

Basic setup of development environment:

So you want to set up a php-development-environment in docker? Do the following steps:

  1. Create a directory on your Mac: Your workspace, where you you want to edit your web app. I work with PhpStorm, so I will create a new project, which creates a new folder with the path
  2. Create files and folder:
    • The Dockerfile
    • A Shell script run.sh
    • Create a src-folder. Within that src-folder create two test-files: index.php and phpinfo.php.So finally your directory structure looks like:
  3. Put the following content into your Dockerfile:

    I won’t go into detail, but the code is mainly coming form Github (thanks!). In the following the most important concepts:

    • Name your main image-source (ubuntu):  FROM ubuntu:trusty
    • Starting apache and php:  RUN apt-get update && ...
    • And last but not least, you should add the project source into your working directory in the container. This is done via:  ADD src/ /app
  4. In the run.sh file put the following content:
  5. Put some example content into your php files:
    • index.php
    • phpinfo.php

That’s it. Your development environment is set. Now you just have to do the build and run process and map your src-folder with the app folder in your container. That way changes are seen directly on the fly.

Build and run your php-app with docker:

  1. You have created the folder structure as explained above, so now open your terminal and go to the project folder. Im my case that is:
  2. Make sure that boot2docker is running.

    If boot2docker is already up, then you should see something like. If you don’t know about boot2docker, google and install it.
  3. Do the build-process to create a new docker-image:

    Explanation:

    • docker build  says, that you want to build a new image
    • With  -t you’re stating, that you want to define the image name. After that state any user name and an image name that you like.
    • The Dot in the end is telling docker, that you want to build the image from the directory that your’re currently in. So that’s why you have to be in your project folder
  4. Run the image to get a new docker-container.

    This is the most tricky part, because you have to be aware of the different options:

    • docker run is the opening command, of course
    • -d run in the background
    • -p 80:80 is the port-mapping: Here the 80 port of your browser (on the mac os) is mapped to the port 80 of the container. 80 is the standard apache port, that’s why.
    • -v /Users/tobi/Documents/Docker/my-project-foler/src:/app Similar to the ADD-Statement in the Dockerfile, the v-option tells docker, to mount the project folder (on the Mac) to the app-folder (in the container). This way, when your container is running, changes in your project folder are directly passed to the container.
    • --name mycontainer  gives a name to your created container
    • The last thing is to name the image:  my-user-name/my-image-nameAfter that command, you can test, if your container is running. With using
      docker ps you should see something like:
  5. You’re almost ready to test your php web-app, but first you have to find out the ip-adress of boot2docker:

    If boot2docker is up, you should see the ip, for example:
  6. Now you’re finally ready to test your php-files in the browser. Go to your browser and type in the following url:

    If you see the content of your index-file (“Hello World! Thank god it’s friday!” as stated in the first part) you can be sure, that the build process was successful.
    You can also test your php-version with:
  7. Next, you have to test, if the mapping of your project folder to your container-folder is working correctly (in docker that is called data-volumes, and is explained in detailed here)
    • Edit the index.php file in your project folder. For example put in the following content:
    • Go to your browser, type in the url (or update the page):

      If you see the changes in the browser, you’re all set.

Conclusion

That’s it. By following that guide you should have been able to set up your dev-environment. Hopefully you could follow the guide and it helped you.

Magento – Warning: simplexml_load_string() – parser error

If you see this warning, when opening category of your Magento-Shop …

… Of course you could check the XML-Updates in the file:
app/code/core/Mage/Core/Model/Layout/Update.php

The solution

…might be simple.

The reason can be special characters. For example: The &

For that, just exchange the “&”-Sign in your category (title) by the correct HTML-sign “&”

Magento filter collection – nested AND- and OR-clauses

The other day, if was looking (and searching the web) if there was a method in Magento, with which you can easily filter a collection, in which the AND-clause for an attribute filter is within the OR-clause. In the beginning I thought this problem is quite trivial, but I finally had to realize that there is no easy way to archive that. Seanbreeden posted a solution that worked but I wanted to apply filter generated in a loop, so I had to extend that.

So in this post, I want to summarize the approach and share my learnings:

The problem:

Filter a collection (for instance the product collection) by various attributes in the following way:

Simple as this nested mySql-Query, the solution in Magento is not that easy. In contrast to the query, in which the AND and OR are the other way around.

The solution:

Filter the collection with AND and OR nested the other way around, using addAttributeToFIlter(…) in Magento and then exchange AND and OR again in the where clause using string-operations.

1. Filter the collection

Get the product collection:

Use the following filter:

That will give a mySyl query that would look like that:

…so in the next step, we have to edit the where-clause programmatically.

2. Exchanging the AND and OR-Conditions in the mySQL-query

use the following code, to do that:

Note that the variable $oldWhereCond is not used and it’s just for debugging. Talking about that, you could also add the following in the end, to debug the query and check the where-condition of the query:

2. Optional: Apply other filters

Now you can also apply other filters, for example:

Note that these are added to the query with an AND-Condition, so the would query (simplified) would look like that:

3. Thats’s it

Now you can play around with the loaded products (for example in a foreach-loop):

Summary:

Though I don’t really like the solution (because I think it’s very awkward, that there is no pre-built easier method in Magento), this solution is quite reliable and it works.

If you know an easier way to filter the collection, please let me know in the comments.

Die richtigen Dateirechte für Magento-Installationen (Permissions for Magento)

Wiedermal ist die Antwort auf die Frage nach den richtigen Dateirechten für Magento: “Es kommt drauf an”.

Worauf kommt es an? Auf den Server-Benutzer, also den Benutzer, der die Magento-Installation ausführt, anders ausgedrückt, der Apache-Benutzer (der deswegen auch in Datei der apache2.conf oder httpd.conf definiert ist). Dieser “www-user” muss nämlich in der Lage sein, alle benötigten Dateien auszuführen, bzw. alle sonstigen Dateien zu lesen und in gewissen Verzeichnissen zu schreiben (z.B. im Media-Ordner)

Folgender Artikel gibt ein paar Details: http://magento.stackexchange.com/questions/36543/403-error-while-installing-magento-is-the-install-guide-correct

Folgende Vorgehensweise würde ich empfehlen:

Magento empfiehlt folgende Datei-Berechtigungen:

Übersetzt in Befehle im Terminal (diese einfach in die Shell eingeben)

Sollte das aber nicht funktionieren, was man schnell daran erkennt, dass der Shop nicht erreichbar ist, so ist der www-user höchstwahrscheinlich nicht der “Owner”, d.h. es müssen außer dem Besitzer auch andere Gruppen Berechtigungen für die Magento-Dateien und -Verzeichnisse haben. Also muss man diesen Fall genauer prüfen.

Wenn man es allerdings eilig hat, oder in der Entwicklung ist und später sowieso nochmals die Rechte verändern muss, kann man dies allerdings umgehen, indem man folgende Rechtevergabe wählt:

Shell-Befehle:

Ich hoffe, das hilft euch ein Stück weiter.

 

Magento Downloader: Invalid login credentials

Das Problem:

man möchte sich in Magento unter System –> Magento Connect –> Magento Connect Manager einloggen, gibt den richtigen Benutzernamen und das Passwort ein.

Aber es taucht eine leere weiße Seite auf mit der Meldung “Invalid login credentials” (weiter nichts)

Lösung:

Im Verzeichnis downloader, die Datei connect.cfg löschen oder umbenennen.

Dann sollte der Login wieder funktionieren.