 Good afternoon. Ladies and gentlemen, I am going to talk a little bit about how the new routing stuff in Drupal 8 will work and how that is based on shared components with symphony and symphony CMF. First of all, I am not Tobias who was originally supposed to give this talk. I only, I was asked to do it like a week and a half ago and prior to this I didn't actually know that much about this stuff. So I've been trying to read on it like crazy but there might be areas that I cannot answer but luckily the guy who did it is actually here so maybe he can help us. So definitions, what is routing? Generally when dealing with MVC for web frameworks, a thing that's not really very well defined is how do we actually get to our controller's model's views? And that answer is the hidden R in MVC I guess. So whenever HTTP request comes in, then a miracle occurs and somehow the request is transferred to the right controller and everything happens the way we want it to. And basically each framework historically has done this slightly different ways, slightly different but also similar ways. We had something like it in Drupal 7. If you've ever written a Drupal 7 module you're probably familiar with these future arrays where we have all these magic keywords that we Drupal reacts to in interesting ways. And even more interesting if you want to mess with the routes or menu callbacks or whatever we call them provided by other modules you can use this nice hook menu alter to tweak whatever. So for example this example is from the diff module which replaces the standard revisions overview in Drupal Core with one that actually shows the difference between revisions. It can also be used to change the access control on other routes. So if you want to have your own custom access control for node or whatever crazy stuff. The menu system in Drupal 7 is not very well understood by many. It has this big router table and stuff happens magically at cache rebuild and no one tends to worry about it but if you ever get in trouble with this you're going to have a lot of trouble. The system in Drupal 7 has a lot of different responsibilities. I won't read them aloud but it does a lot of stuff. That's not just routing and that leads to interesting problems. So symphony has a very different take on this. It basically has a big file called routing.yaml which defines all the routes for your app and that's very nice but there's a problem. As the symphony documentation says symphony loads all routes for your application from a single routing configuration file. This file can contain includes so you can say yeah by the way I would like to add the panels routes to my module or something like that. And that's fine for symphony but we wouldn't really want our Drupal 8 module to have to contain instructions like go into the core folder and open the routing yaml files and insert these lines here because yeah that's not really a nice friendly experience when that user downloads a new module and this basically means that anyone who has who needs to administer your Drupal site would have need to have access to the file system. It will also mean that we have this huge file that contains information about where we show these local task tabs. So if you need to if you want to hide the local task tab on the signup form so the request password tab is hidden for example you would need to go and edit the routing file. That is not very pretty. So a different solution was needed and as it happens there was there's a similar project or not a similar project but from the symphony side they have been trying to work on building a very nice toolkit of content management related components for symphony and they had a similar problem. Basically what they wanted to be able to was to have some routes being defined by the admin UI so when you go and create a new page you enter a URL and use that as a as a route so to speak so you create page less about and that's stored in the database but that can also be combined with real normal or regular symphony components that loads routes from static files and code. So collaboration happens two of my colleagues and Larry and a few other guys including some people from the EC publish framework got together or I don't know did you get together but at least they figured out to collaborate on on building a better system for this. It says hope. So what did they do? Basically this and I'll try to explain this graph. I'll see if I can liberate the microphone here. Oh well I hope you can hear me. Basically it all starts with the request that comes into Drupal is passed into what is called a chain router and a chain router or the chain router is basically a part of the symphony CMS components and it allows you to have multiple sources of routes for your symphony app or in this case for Drupal. And these routers all the viper RG will be called whenever there's an incoming route. Oh nice very nice thank you. All right yeah much better. And basically what Drupal ships with is a configuration where the single router that's configured out of the box is the so-called dynamic router and that calls into a Drupal component called the route provider. And as the name implies this route provider loads the route collection from the database and before this step whenever you enable the Drupal module in Drupal 8 you are allowed to have a module name dot routing dot yaml file in your module which has the same syntax as the standard symphony routing file but this file will be processed by Drupal and read into the route table in the route database. So whenever this happens whatever routes you define in your module will be taken into consideration. This one loads all possible matches so if you have a long URL so if you have a node slash edit slash diff slash you know whatever it will also load slash node and node slash edit and is that wrong? Okay what's the fit for then? Oh yeah my bad yes it loads all routes where the URL can match and then it goes through the matcher and for your route you can provide additional parameters that needs to be that needs to fit before this route is a match so it could be that this must this route only accepts post requests it could be a special header condition so this route only will only serve JSON data so it could be the accept header and there's a whole a whole bunch of conditions you can provide for your routes and once the matcher is done selecting which route is to be processed it will go into the it will simply modify the request object the request object in symphony has so-called attributes and these attributes are metadata on that different modules have attached to the request so the selected router will simply be another attribute on this request object and then we go into what is called the enhancing phase and enhancers in symphony is a very very powerful tool in many ways so in Drupal 8 for example the authentication of users is a so-called enhancer so whenever a request comes in and the router has been defined the the authentication enhancer runs on the request and looks at the token and figures out is this a valid authentication token and if so it adds stuff to the request object telling you that this this request is authenticated and the user is so and so and the same goes for all sorts of parameters and whatever else you can find on the request object is generally added by these enhancers and once all that is done we have a final request object and this request object is then passed to the controller that the route has defined that it wants to to use and this is pretty much what i just said in text form but basically what it means is that when i go to my dupal sites and requests notes slash 42 slash edit dupal will then go through all this stuff and decide that the notes edit page controller or whatever it's called is the right controller the right route to handle this and will do whatever is necessary to call it the use of this most people will likely never need to mess with this so the common the common use case will simply be to go at this stuff to your module file or to your to the routing file in your module and just be happy that you all this magic works but if you look at the diagram oh where was the diagram here there is the use case for a theoretical other other router so here you can also you can attach a standard symphony router and say i want this router to so provided that you have a standard symphony app that you want to combine with dupal you can simply mount it inside your dupal application and say yeah but all requests that starts with api are now to be handled by this other router or basically all requests will go to each router in the priority order and then you configure the other router you add to only listen to those that start with api for example the other use case so since hook menu is dead hook menu alter is of course also dead and but luckily there's another way to do this and basically this is a so-called enhancer is it not yeah the name the naming for all this is sort of confusing but the main point is that you can add a so-called route subscriber that gets to mess with all routes that are found and so when the router collection is fine the routes collection not router collection the route collection the collection of possible routes for url when that is determined then you're allowed to mess with it and basically what this does is check if the user has selected that he wants to use the admin theme when editing note pages and if so if this is a note operation route so if this is the user the note edit page or a similar page then set the option on the request admin route true and admin route true is then later recognized by dupal as hey let's use the admin theme for this page so this is one thing where we would previously had used hook menu alter and the interesting thing here is that the route object is fully available here so you can not only can you set options on it you can also change options on it so if you want to change whatever so if you want to change one of the routes provided by the views module you don't have to mess with the views modules routing file you can modify it via this process yeah so some of the use case another use case for adding another router to the symphony side of things would be backwards compatibility i know ec publish does this and they do it for the reason that they don't really want to they want to provide backwards compatibility so if you have an old ec publish module using the old ec publish router which i don't know a lot about but the general idea is that you can still use your old ec publish stuff over there and ec publish has then implemented symphony router that calls back through their old routing process and that is then added with a lower priority so first it checks with the symphony the standard nice routing stuff the same as we've pretty much the same as we've seen here first it checks with that do we have anything that matches and if not then it goes back and calls the old the old school routing um hope yeah and you can make your own routers if you have like a high performance use case if you have like a api that receives a thousand requests a second or something it could actually be beneficial for you to say okay i have this ultra optimized router it just has these three methods and i'll just go into plug it in before it calls the dupal router and so there's a lot of flexibility here that's very nice so basically that's the general overview of things i have prepared a few i have you know been digging through this code a lot and i'm not really sure what i would want to know so i would like you well i wonder if you might help me figure out what is there what is what would you like to know if you wanted to mess with this in dupal seven could i get you to step up the mic sorry is that good yes so in dupal seven the menu system is both for routing the incoming requests but also for displaying the menus on the on the page yes does this handle that too or is that some other component it does to some degree or well oh wow this resolution is really small no it does oh wow basically some display logic is in here is this big enough can i make it bigger somehow or something this is not my day where's my whim command one hold on a second give me a proper editor so some of these things are related to presentation so basically the node operation route turns out to help you define what's you know does this this is a node operation so let's display the admin menu and a few other things but as far as the visual visual menu structure the old the the menu module and back well back in dupal seven there was two parts to the menu system there was menu ink which was built into core which was the routing part and there was menu dot module which is the let me create a custom mod menu so i want to have an about link in my menu and i wanted to point to node slash seven that part still exists and i think it's still called menu module as well and that part is basically that hasn't changed all that much i don't know if this is too small but basically this is dupal eight and the menu links table still contains the the visual menu structure with the names of all the pages and stuff and i'm not really sure of the implementation detail but i think that the menu module implements a router that reads from this or okay um but this is this is still separate from the router table which is much smaller i don't know do you want to clarify right um does that answer your question somewhat all right anyone else yes so if i am on drupal eight and i am having like a lot of problems with their routing component and maybe some bugs and i want to just uh like override everything how would i do it like to basically plug the other parts that drupal you know implements and stuff but make basically i don't know make maybe drupal use like phpcr or something like custom very custom um is that possible or how to do it i think it would be theoretically possible there is this file um called call services ink which here is um um chain router basically here these lines says that drupal core uses the symphony chain router i'm actually making less it's readable by selecting it this these lines define declare that the drupal core uses symphonies chain router router uh and it wants to add this router dynamic um which is defined above which is the dynamic router and this this this services yaml is where it's all bound together i'm not really sure if it's easily possible to override this without actually having to edit this file it is uh says larry um but yeah that's that's basically if you if you remove the dynamic router uh from the picture then drupal's routing will no longer be considered but i think in doing so you would basically prevent the function of almost any drupal module you you install and so i i think if you want to do that maybe you don't actually want to use drupal okay enough anyone else over there do you have any code examples of like just a regular module where you want some custom code or entities that you custom make pop up um you know normally in drupal seven you know i i call this menu action and i wanted to run this function how does that work with this new setup so so you're saying you want to make a new url yeah new url and call this certain function in my module to do what i want to do and it's not it's it's using drupal stuff but it's sort of totally custom it doesn't use the same stuff if that makes sense i think actually the examples in in drupal core itself are pretty good uh i used the mode node module before it has a big routing file here and basically what you're doing with these declarations here uh node ad page is somewhat simple so you're saying i want at this url node slash add um i provide a few things here but basically this um you're saying you're declaring your route and saying which which controller do i want to handle this route okay cool um i don't know if there is a simpler version somewhere yeah most of these deal with entity forms but if you this is standard symphony stuff so if you look at the standard symphony routing documentation you can see the like the completely simple brain deads let's call a controller or no magic use case but you will need a controller it's you can't do what we used to do in drupal 7 and have a function that does stuff okay we'll need to make a controller cool thank you um so in drupal 6 i think you had to actually go and visit the modules um listing page in order to pick up new modules that you'd created since the last time you visited the page in drupal 7 i think you had to clear the cache you had to run uh cron or something like that um what's the process for actually activating new routes in drupal 8 i think it's still the same i think you still have to clear the cache uh because the the router the router table i showed before here it ingests all these routes you have to find in your yaml file and that is cached so it doesn't have to read all the modules yaml files and process them for every page request because that would be slow uh so that's pretty much the same anyone else i could also show you i i have played a little bit with xd bug so you can actually see how it works because let's see die on me now um but yeah i think the base the what really helped me understand how all this stuff happens was simply to fire up xd bug see what happens set break points here and i see how it jumps through all these different um different parts of the the layer this is conceptually a bit harder to reason about than what we had in drupal 7 but it is it is much much more flexible uh there's a lot more different points where you can customize stuff without having to override the whole system and sharing code with other projects is of course also a super great idea all right i think yeah oh i think it actually is working now so let's try for a second um almost so i'm going to insert my secret password here and then i'm going to enable xd bug uh yeah somehow stuff never works when you're trying to demo it maybe it went to phpstorm instead never mind um but xd bug yes please and phpstorm is also nice when it works otherwise thank you and um enjoy your con